X-Git-Url: https://git.octo.it/?a=blobdiff_plain;f=mailinfo.c;h=5b6c2157ede415e019099098f2d0dc522b1e7a27;hb=1a82e79315ed633f6b0b1fc4076054950c5380d3;hp=a2b15e2624702c90bd05d5a457df4c03694020c3;hpb=f30b20282babcd77bcadef70b4e36e24cd1f6d59;p=git.git diff --git a/mailinfo.c b/mailinfo.c index a2b15e26..5b6c2157 100644 --- a/mailinfo.c +++ b/mailinfo.c @@ -72,11 +72,14 @@ static int bogus_from(char *line) return 1; } -static int handle_from(char *line) +static int handle_from(char *in_line) { - char *at = strchr(line, '@'); + char line[1000]; + char *at; char *dst; + strcpy(line, in_line); + at = strchr(line, '@'); if (!at) return bogus_from(line); @@ -237,13 +240,18 @@ static int eatspace(char *line) #define SEEN_FROM 01 #define SEEN_DATE 02 #define SEEN_SUBJECT 04 -#define SEEN_PREFIX 0x08 +#define SEEN_BOGUS_UNIX_FROM 010 +#define SEEN_PREFIX 020 /* First lines of body can have From:, Date:, and Subject: */ static void handle_inbody_header(int *seen, char *line) { - if (*seen & SEEN_PREFIX) - return; + if (!memcmp(">From", line, 5) && isspace(line[5])) { + if (!(*seen & SEEN_BOGUS_UNIX_FROM)) { + *seen |= SEEN_BOGUS_UNIX_FROM; + return; + } + } if (!memcmp("From:", line, 5) && isspace(line[5])) { if (!(*seen & SEEN_FROM) && handle_from(line+6)) { *seen |= SEEN_FROM; @@ -381,19 +389,40 @@ static void check_header_line(char *line) check_header(line, header); } +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; + while ((ch = *cp++)) { + if (ch == ':') + return cp != line; + if ((33 <= ch && ch <= 57) || + (59 <= ch && ch <= 126)) + continue; + break; + } + return 0; +} + static int read_one_header_line(char *line, int sz, FILE *in) { int ofs = 0; while (ofs < sz) { - const char *colon; int peek, len; if (fgets(line + ofs, sz - ofs, in) == NULL) break; len = eatspace(line + ofs); if (len == 0) break; - colon = strchr(line, ':'); - if (!colon || !isspace(colon[1])) { + if (!is_rfc2822_header(line)) { /* Re-add the newline */ line[ofs + len] = '\n'; line[ofs + len + 1] = '\0';