/*
 * Another stupid program, this one parsing the headers of an
 * email to figure out authorship and subject
 */
#include "cache.h"
#include "builtin.h"
#include "utf8.h"

static FILE *cmitmsg, *patchfile, *fin, *fout;

static int keep_subject;
static const char *metainfo_charset;
static char line[1000];
static char name[1000];
static char email[1000];

static enum  {
	TE_DONTCARE, TE_QP, TE_BASE64,
} transfer_encoding;
static enum  {
	TYPE_TEXT, TYPE_OTHER,
} message_type;

static char charset[256];
static int patch_lines;
static char **p_hdr_data, **s_hdr_data;

#define MAX_HDR_PARSED 10
#define MAX_BOUNDARIES 5

static char *sanity_check(char *name, char *email)
{
	int len = strlen(name);
	if (len < 3 || len > 60)
		return email;
	if (strchr(name, '@') || strchr(name, '<') || strchr(name, '>'))
		return email;
	return name;
}

static int bogus_from(char *line)
{
	/* John Doe <johndoe> */
	char *bra, *ket, *dst, *cp;

	/* This is fallback, so do not bother if we already have an
	 * e-mail address.
	 */
	if (*email)
		return 0;

	bra = strchr(line, '<');
	if (!bra)
		return 0;
	ket = strchr(bra, '>');
	if (!ket)
		return 0;

	for (dst = email, cp = bra+1; cp < ket; )
		*dst++ = *cp++;
	*dst = 0;
	for (cp = line; isspace(*cp); cp++)
		;
	for (bra--; isspace(*bra); bra--)
		*bra = 0;
	cp = sanity_check(cp, email);
	strcpy(name, cp);
	return 1;
}

static int handle_from(char *in_line)
{
	char line[1000];
	char *at;
	char *dst;

	strcpy(line, in_line);
	at = strchr(line, '@');
	if (!at)
		return bogus_from(line);

	/*
	 * If we already have one email, don't take any confusing lines
	 */
	if (*email && strchr(at+1, '@'))
		return 0;

	/* Pick up the string around '@', possibly delimited with <>
	 * pair; that is the email part.  White them out while copying.
	 */
	while (at > line) {
		char c = at[-1];
		if (isspace(c))
			break;
		if (c == '<') {
			at[-1] = ' ';
			break;
		}
		at--;
	}
	dst = email;
	for (;;) {
		unsigned char c = *at;
		if (!c || c == '>' || isspace(c)) {
			if (c == '>')
				*at = ' ';
			break;
		}
		*at++ = ' ';
		*dst++ = c;
	}
	*dst++ = 0;

	/* The remainder is name.  It could be "John Doe <john.doe@xz>"
	 * or "john.doe@xz (John Doe)", but we have whited out the
	 * email part, so trim from both ends, possibly removing
	 * the () pair at the end.
	 */
	at = line + strlen(line);
	while (at > line) {
		unsigned char c = *--at;
		if (!isspace(c)) {
			at[(c == ')') ? 0 : 1] = 0;
			break;
		}
	}

	at = line;
	for (;;) {
		unsigned char c = *at;
		if (!c || !isspace(c)) {
			if (c == '(')
				at++;
			break;
		}
		at++;
	}
	at = sanity_check(at, email);
	strcpy(name, at);
	return 1;
}

static int handle_header(char *line, char *data, int ofs)
{
	if (!line || !data)
		return 1;

	strcpy(data, line+ofs);

	return 0;
}

/* NOTE NOTE NOTE.  We do not claim we do full MIME.  We just attempt
 * to have enough heuristics to grok MIME encoded patches often found
 * on our mailing lists.  For example, we do not even treat header lines
 * case insensitively.
 */

static int slurp_attr(const char *line, const char *name, char *attr)
{
	const char *ends, *ap = strcasestr(line, name);
	size_t sz;

	if (!ap) {
		*attr = 0;
		return 0;
	}
	ap += strlen(name);
	if (*ap == '"') {
		ap++;
		ends = "\"";
	}
	else
		ends = "; \t";
	sz = strcspn(ap, ends);
	memcpy(attr, ap, sz);
	attr[sz] = 0;
	return 1;
}

struct content_type {
	char *boundary;
	int boundary_len;
};

static struct content_type content[MAX_BOUNDARIES];

static struct content_type *content_top = content;

static int handle_content_type(char *line)
{
	char boundary[256];

	if (strcasestr(line, "text/") == NULL)
		 message_type = TYPE_OTHER;
	if (slurp_attr(line, "boundary=", boundary + 2)) {
		memcpy(boundary, "--", 2);
		if (content_top++ >= &content[MAX_BOUNDARIES]) {
			fprintf(stderr, "Too many boundaries to handle\n");
			exit(1);
		}
		content_top->boundary_len = strlen(boundary);
		content_top->boundary = xmalloc(content_top->boundary_len+1);
		strcpy(content_top->boundary, boundary);
	}
	if (slurp_attr(line, "charset=", charset)) {
		int i, c;
		for (i = 0; (c = charset[i]) != 0; i++)
			charset[i] = tolower(c);
	}
	return 0;
}

static int handle_content_transfer_encoding(char *line)
{
	if (strcasestr(line, "base64"))
		transfer_encoding = TE_BASE64;
	else if (strcasestr(line, "quoted-printable"))
		transfer_encoding = TE_QP;
	else
		transfer_encoding = TE_DONTCARE;
	return 0;
}

static int is_multipart_boundary(const char *line)
{
	return (!memcmp(line, content_top->boundary, content_top->boundary_len));
}

static int eatspace(char *line)
{
	int len = strlen(line);
	while (len > 0 && isspace(line[len-1]))
		line[--len] = 0;
	return len;
}

static char *cleanup_subject(char *subject)
{
	for (;;) {
		char *p;
		int len, remove;
		switch (*subject) {
		case 'r': case 'R':
			if (!memcmp("e:", subject+1, 2)) {
				subject += 3;
				continue;
			}
			break;
		case ' ': case '\t': case ':':
			subject++;
			continue;

		case '[':
			p = strchr(subject, ']');
			if (!p) {
				subject++;
				continue;
			}
			len = strlen(p);
			remove = p - subject;
			if (remove <= len *2) {
				subject = p+1;
				continue;
			}
			break;
		}
		eatspace(subject);
		return subject;
	}
}

static void cleanup_space(char *buf)
{
	unsigned char c;
	while ((c = *buf) != 0) {
		buf++;
		if (isspace(c)) {
			buf[-1] = ' ';
			c = *buf;
			while (isspace(c)) {
				int len = strlen(buf);
				memmove(buf, buf+1, len);
				c = *buf;
			}
		}
	}
}

static void decode_header(char *it, unsigned itsize);
static const char *header[MAX_HDR_PARSED] = {
	"From","Subject","Date",
};

static int check_header(char *line, unsigned linesize, char **hdr_data, int overwrite)
{
	int i;

	/* search for the interesting parts */
	for (i = 0; header[i]; i++) {
		int len = strlen(header[i]);
		if ((!hdr_data[i] || overwrite) &&
		    !strncasecmp(line, header[i], len) &&
		    line[len] == ':' && isspace(line[len + 1])) {
			/* Unwrap inline B and Q encoding, and optionally
			 * normalize the meta information to utf8.
			 */
			decode_header(line + len + 2, linesize - len - 2);
			hdr_data[i] = xmalloc(1000 * sizeof(char));
			if (! handle_header(line, hdr_data[i], len + 2)) {
				return 1;
			}
		}
	}

	/* Content stuff */
	if (!strncasecmp(line, "Content-Type", 12) &&
		line[12] == ':' && isspace(line[12 + 1])) {
		decode_header(line + 12 + 2, linesize - 12 - 2);
		if (! handle_content_type(line)) {
			return 1;
		}
	}
	if (!strncasecmp(line, "Content-Transfer-Encoding", 25) &&
		line[25] == ':' && isspace(line[25 + 1])) {
		decode_header(line + 25 + 2, linesize - 25 - 2);
		if (! handle_content_transfer_encoding(line)) {
			return 1;
		}
	}

	/* for inbody stuff */
	if (!memcmp(">From", line, 5) && isspace(line[5]))
		return 1;
	if (!memcmp("[PATCH]", line, 7) && isspace(line[7])) {
		for (i = 0; header[i]; i++) {
			if (!memcmp("Subject: ", header[i], 9)) {
				if (! handle_header(line, hdr_data[i], 0)) {
					return 1;
				}
			}
		}
	}

	/* no match */
	return 0;
}

static int is_rfc2822_header(char *line)
{
	/*
	 * The section that defines the loosest possible
	 * field name is "3.6.8 Optional fields".
	 *
	 * optional-field = field-name ":" unstructured CRLF
	 * field-name = 1*ftext
	 * ftext = %d33-57 / %59-126
	 */
	int ch;
	char *cp = line;

	/* Count mbox From headers as headers */
	if (!memcmp(line, "From ", 5) || !memcmp(line, ">From ", 6))
		return 1;

	while ((ch = *cp++)) {
		if (ch == ':')
			return cp != line;
		if ((33 <= ch && ch <= 57) ||
		    (59 <= ch && ch <= 126))
			continue;
		break;
	}
	return 0;
}

/*
 * sz is size of 'line' buffer in bytes.  Must be reasonably
 * long enough to hold one physical real-world e-mail line.
 */
static int read_one_header_line(char *line, int sz, FILE *in)
{
	int len;

	/*
	 * We will read at most (sz-1) bytes and then potentially
	 * re-add NUL after it.  Accessing line[sz] after this is safe
	 * and we can allow len to grow up to and including sz.
	 */
	sz--;

	/* Get the first part of the line. */
	if (!fgets(line, sz, in))
		return 0;

	/*
	 * Is it an empty line or not a valid rfc2822 header?
	 * If so, stop here, and return false ("not a header")
	 */
	len = eatspace(line);
	if (!len || !is_rfc2822_header(line)) {
		/* Re-add the newline */
		line[len] = '\n';
		line[len + 1] = '\0';
		return 0;
	}

	/*
	 * Now we need to eat all the continuation lines..
	 * Yuck, 2822 header "folding"
	 */
	for (;;) {
		int peek, addlen;
		static char continuation[1000];

		peek = fgetc(in); ungetc(peek, in);
		if (peek != ' ' && peek != '\t')
			break;
		if (!fgets(continuation, sizeof(continuation), in))
			break;
		addlen = eatspace(continuation);
		if (len < sz - 1) {
			if (addlen >= sz - len)
				addlen = sz - len - 1;
			memcpy(line + len, continuation, addlen);
			line[len] = '\n';
			len += addlen;
		}
	}
	line[len] = 0;

	return 1;
}

static int decode_q_segment(char *in, char *ot, unsigned otsize, char *ep, int rfc2047)
{
	char *otbegin = ot;
	char *otend = ot + otsize;
	int c;
	while ((c = *in++) != 0 && (in <= ep)) {
		if (ot == otend) {
			*--ot = '\0';
			return -1;
		}
		if (c == '=') {
			int d = *in++;
			if (d == '\n' || !d)
				break; /* drop trailing newline */
			*ot++ = ((hexval(d) << 4) | hexval(*in++));
			continue;
		}
		if (rfc2047 && c == '_') /* rfc2047 4.2 (2) */
			c = 0x20;
		*ot++ = c;
	}
	*ot = 0;
	return (ot - otbegin);
}

static int decode_b_segment(char *in, char *ot, unsigned otsize, char *ep)
{
	/* Decode in..ep, possibly in-place to ot */
	int c, pos = 0, acc = 0;
	char *otbegin = ot;
	char *otend = ot + otsize;

	while ((c = *in++) != 0 && (in <= ep)) {
		if (ot == otend) {
			*--ot = '\0';
			return -1;
		}
		if (c == '+')
			c = 62;
		else if (c == '/')
			c = 63;
		else if ('A' <= c && c <= 'Z')
			c -= 'A';
		else if ('a' <= c && c <= 'z')
			c -= 'a' - 26;
		else if ('0' <= c && c <= '9')
			c -= '0' - 52;
		else if (c == '=') {
			/* padding is almost like (c == 0), except we do
			 * not output NUL resulting only from it;
			 * for now we just trust the data.
			 */
			c = 0;
		}
		else
			continue; /* garbage */
		switch (pos++) {
		case 0:
			acc = (c << 2);
			break;
		case 1:
			*ot++ = (acc | (c >> 4));
			acc = (c & 15) << 4;
			break;
		case 2:
			*ot++ = (acc | (c >> 2));
			acc = (c & 3) << 6;
			break;
		case 3:
			*ot++ = (acc | c);
			acc = pos = 0;
			break;
		}
	}
	*ot = 0;
	return (ot - otbegin);
}

/*
 * When there is no known charset, guess.
 *
 * Right now we assume that if the target is UTF-8 (the default),
 * and it already looks like UTF-8 (which includes US-ASCII as its
 * subset, of course) then that is what it is and there is nothing
 * to do.
 *
 * Otherwise, we default to assuming it is Latin1 for historical
 * reasons.
 */
static const char *guess_charset(const char *line, const char *target_charset)
{
	if (is_encoding_utf8(target_charset)) {
		if (is_utf8(line))
			return NULL;
	}
	return "latin1";
}

static void convert_to_utf8(char *line, unsigned linesize, const char *charset)
{
	char *out;

	if (!charset || !*charset) {
		charset = guess_charset(line, metainfo_charset);
		if (!charset)
			return;
	}

	if (!strcmp(metainfo_charset, charset))
		return;
	out = reencode_string(line, metainfo_charset, charset);
	if (!out)
		die("cannot convert from %s to %s\n",
		    charset, metainfo_charset);
	strlcpy(line, out, linesize);
	free(out);
}

static int decode_header_bq(char *it, unsigned itsize)
{
	char *in, *out, *ep, *cp, *sp;
	char outbuf[1000];
	int rfc2047 = 0;

	in = it;
	out = outbuf;
	while ((ep = strstr(in, "=?")) != NULL) {
		int sz, encoding;
		char charset_q[256], piecebuf[256];
		rfc2047 = 1;

		if (in != ep) {
			sz = ep - in;
			memcpy(out, in, sz);
			out += sz;
			in += sz;
		}
		/* E.g.
		 * ep : "=?iso-2022-jp?B?GyR...?= foo"
		 * ep : "=?ISO-8859-1?Q?Foo=FCbar?= baz"
		 */
		ep += 2;
		cp = strchr(ep, '?');
		if (!cp)
			return rfc2047; /* no munging */
		for (sp = ep; sp < cp; sp++)
			charset_q[sp - ep] = tolower(*sp);
		charset_q[cp - ep] = 0;
		encoding = cp[1];
		if (!encoding || cp[2] != '?')
			return rfc2047; /* no munging */
		ep = strstr(cp + 3, "?=");
		if (!ep)
			return rfc2047; /* no munging */
		switch (tolower(encoding)) {
		default:
			return rfc2047; /* no munging */
		case 'b':
			sz = decode_b_segment(cp + 3, piecebuf, sizeof(piecebuf), ep);
			break;
		case 'q':
			sz = decode_q_segment(cp + 3, piecebuf, sizeof(piecebuf), ep, 1);
			break;
		}
		if (sz < 0)
			return rfc2047;
		if (metainfo_charset)
			convert_to_utf8(piecebuf, sizeof(piecebuf), charset_q);

		sz = strlen(piecebuf);
		if (outbuf + sizeof(outbuf) <= out + sz)
			return rfc2047; /* no munging */
		strcpy(out, piecebuf);
		out += sz;
		in = ep + 2;
	}
	strcpy(out, in);
	strlcpy(it, outbuf, itsize);
	return rfc2047;
}

static void decode_header(char *it, unsigned itsize)
{

	if (decode_header_bq(it, itsize))
		return;
	/* otherwise "it" is a straight copy of the input.
	 * This can be binary guck but there is no charset specified.
	 */
	if (metainfo_charset)
		convert_to_utf8(it, itsize, "");
}

static int decode_transfer_encoding(char *line, unsigned linesize, int inputlen)
{
	char *ep;

	switch (transfer_encoding) {
	case TE_QP:
		ep = line + inputlen;
		return decode_q_segment(line, line, linesize, ep, 0);
	case TE_BASE64:
		ep = line + inputlen;
		return decode_b_segment(line, line, linesize, ep);
	case TE_DONTCARE:
	default:
		return inputlen;
	}
}

static int handle_filter(char *line, unsigned linesize, int linelen);

static int find_boundary(void)
{
	while(fgets(line, sizeof(line), fin) != NULL) {
		if (is_multipart_boundary(line))
			return 1;
	}
	return 0;
}

static int handle_boundary(void)
{
	char newline[]="\n";
again:
	if (!memcmp(line+content_top->boundary_len, "--", 2)) {
		/* we hit an end boundary */
		/* pop the current boundary off the stack */
		free(content_top->boundary);

		/* technically won't happen as is_multipart_boundary()
		   will fail first.  But just in case..
		 */
		if (content_top-- < content) {
			fprintf(stderr, "Detected mismatched boundaries, "
					"can't recover\n");
			exit(1);
		}
		handle_filter(newline, sizeof(newline), strlen(newline));

		/* skip to the next boundary */
		if (!find_boundary())
			return 0;
		goto again;
	}

	/* set some defaults */
	transfer_encoding = TE_DONTCARE;
	charset[0] = 0;
	message_type = TYPE_TEXT;

	/* slurp in this section's info */
	while (read_one_header_line(line, sizeof(line), fin))
		check_header(line, sizeof(line), p_hdr_data, 0);

	/* eat the blank line after section info */
	return (fgets(line, sizeof(line), fin) != NULL);
}

static inline int patchbreak(const char *line)
{
	/* Beginning of a "diff -" header? */
	if (!memcmp("diff -", line, 6))
		return 1;

	/* CVS "Index: " line? */
	if (!memcmp("Index: ", line, 7))
		return 1;

	/*
	 * "--- <filename>" starts patches without headers
	 * "---<sp>*" is a manual separator
	 */
	if (!memcmp("---", line, 3)) {
		line += 3;
		/* space followed by a filename? */
		if (line[0] == ' ' && !isspace(line[1]))
			return 1;
		/* Just whitespace? */
		for (;;) {
			unsigned char c = *line++;
			if (c == '\n')
				return 1;
			if (!isspace(c))
				break;
		}
		return 0;
	}
	return 0;
}


static int handle_commit_msg(char *line, unsigned linesize)
{
	static int still_looking = 1;
	char *endline = line + linesize;

	if (!cmitmsg)
		return 0;

	if (still_looking) {
		char *cp = line;
		if (isspace(*line)) {
			for (cp = line + 1; *cp; cp++) {
				if (!isspace(*cp))
					break;
			}
			if (!*cp)
				return 0;
		}
		if ((still_looking = check_header(cp, endline - cp, s_hdr_data, 0)) != 0)
			return 0;
	}

	/* normalize the log message to UTF-8. */
	if (metainfo_charset)
		convert_to_utf8(line, endline - line, charset);

	if (patchbreak(line)) {
		fclose(cmitmsg);
		cmitmsg = NULL;
		return 1;
	}

	fputs(line, cmitmsg);
	return 0;
}

static int handle_patch(char *line, int len)
{
	fwrite(line, 1, len, patchfile);
	patch_lines++;
	return 0;
}

static int handle_filter(char *line, unsigned linesize, int linelen)
{
	static int filter = 0;

	/* filter tells us which part we left off on
	 * a non-zero return indicates we hit a filter point
	 */
	switch (filter) {
	case 0:
		if (!handle_commit_msg(line, linesize))
			break;
		filter++;
	case 1:
		if (!handle_patch(line, linelen))
			break;
		filter++;
	default:
		return 1;
	}

	return 0;
}

static void handle_body(void)
{
	int rc = 0;
	static char newline[2000];
	static char *np = newline;
	int len = strlen(line);

	/* Skip up to the first boundary */
	if (content_top->boundary) {
		if (!find_boundary())
			return;
	}

	do {
		/* process any boundary lines */
		if (content_top->boundary && is_multipart_boundary(line)) {
			/* flush any leftover */
			if (np != newline)
				handle_filter(newline, sizeof(newline),
					      np - newline);
			if (!handle_boundary())
				return;
			len = strlen(line);
		}

		/* Unwrap transfer encoding */
		len = decode_transfer_encoding(line, sizeof(line), len);
		if (len < 0) {
			error("Malformed input line");
			return;
		}

		switch (transfer_encoding) {
		case TE_BASE64:
		case TE_QP:
		{
			char *op = line;

			/* binary data most likely doesn't have newlines */
			if (message_type != TYPE_TEXT) {
				rc = handle_filter(line, sizeof(line), len);
				break;
			}

			/*
			 * This is a decoded line that may contain
			 * multiple new lines.  Pass only one chunk
			 * at a time to handle_filter()
			 */
			do {
				while (op < line + len && *op != '\n')
					*np++ = *op++;
				*np = *op;
				if (*np != 0) {
					/* should be sitting on a new line */
					*(++np) = 0;
					op++;
					rc = handle_filter(newline, sizeof(newline), np - newline);
					np = newline;
				}
			} while (op < line + len);
			/*
			 * The partial chunk is saved in newline and will be
			 * appended by the next iteration of read_line_with_nul().
			 */
			break;
		}
		default:
			rc = handle_filter(line, sizeof(line), len);
		}
		if (rc)
			/* nothing left to filter */
			break;
	} while ((len = read_line_with_nul(line, sizeof(line), fin)));

	return;
}

static void output_header_lines(FILE *fout, const char *hdr, char *data)
{
	while (1) {
		char *ep = strchr(data, '\n');
		int len;
		if (!ep)
			len = strlen(data);
		else
			len = ep - data;
		fprintf(fout, "%s: %.*s\n", hdr, len, data);
		if (!ep)
			break;
		data = ep + 1;
	}
}

static void handle_info(void)
{
	char *sub;
	char *hdr;
	int i;

	for (i = 0; header[i]; i++) {

		/* only print inbody headers if we output a patch file */
		if (patch_lines && s_hdr_data[i])
			hdr = s_hdr_data[i];
		else if (p_hdr_data[i])
			hdr = p_hdr_data[i];
		else
			continue;

		if (!memcmp(header[i], "Subject", 7)) {
			if (keep_subject)
				sub = hdr;
			else {
				sub = cleanup_subject(hdr);
				cleanup_space(sub);
			}
			output_header_lines(fout, "Subject", sub);
		} else if (!memcmp(header[i], "From", 4)) {
			handle_from(hdr);
			fprintf(fout, "Author: %s\n", name);
			fprintf(fout, "Email: %s\n", email);
		} else {
			cleanup_space(hdr);
			fprintf(fout, "%s: %s\n", header[i], hdr);
		}
	}
	fprintf(fout, "\n");
}

static int mailinfo(FILE *in, FILE *out, int ks, const char *encoding,
		    const char *msg, const char *patch)
{
	int peek;
	keep_subject = ks;
	metainfo_charset = encoding;
	fin = in;
	fout = out;

	cmitmsg = fopen(msg, "w");
	if (!cmitmsg) {
		perror(msg);
		return -1;
	}
	patchfile = fopen(patch, "w");
	if (!patchfile) {
		perror(patch);
		fclose(cmitmsg);
		return -1;
	}

	p_hdr_data = xcalloc(MAX_HDR_PARSED, sizeof(char *));
	s_hdr_data = xcalloc(MAX_HDR_PARSED, sizeof(char *));

	do {
		peek = fgetc(in);
	} while (isspace(peek));
	ungetc(peek, in);

	/* process the email header */
	while (read_one_header_line(line, sizeof(line), fin))
		check_header(line, sizeof(line), p_hdr_data, 1);

	handle_body();
	handle_info();

	return 0;
}

static const char mailinfo_usage[] =
	"git-mailinfo [-k] [-u | --encoding=<encoding> | -n] msg patch <mail >info";

int cmd_mailinfo(int argc, const char **argv, const char *prefix)
{
	const char *def_charset;

	/* NEEDSWORK: might want to do the optional .git/ directory
	 * discovery
	 */
	git_config(git_default_config, NULL);

	def_charset = (git_commit_encoding ? git_commit_encoding : "utf-8");
	metainfo_charset = def_charset;

	while (1 < argc && argv[1][0] == '-') {
		if (!strcmp(argv[1], "-k"))
			keep_subject = 1;
		else if (!strcmp(argv[1], "-u"))
			metainfo_charset = def_charset;
		else if (!strcmp(argv[1], "-n"))
			metainfo_charset = NULL;
		else if (!prefixcmp(argv[1], "--encoding="))
			metainfo_charset = argv[1] + 11;
		else
			usage(mailinfo_usage);
		argc--; argv++;
	}

	if (argc != 3)
		usage(mailinfo_usage);

	return !!mailinfo(stdin, stdout, keep_subject, metainfo_charset, argv[1], argv[2]);
}
