Code

Build: add NO_UINTMAX_T to support ancient systems
[git.git] / builtin-mailinfo.c
index 3e5fe5108533407e0319bbfda19fa63f991e17d2..e890f7a6d1ff7248aed4f03ebbcdfafd7e472dad 100644 (file)
@@ -107,7 +107,7 @@ static void handle_from(const struct strbuf *from)
        el = strcspn(at, " \n\t\r\v\f>");
        strbuf_reset(&email);
        strbuf_add(&email, at, el);
-       strbuf_remove(&f, at - f.buf, el + 1);
+       strbuf_remove(&f, at - f.buf, el + (at[el] ? 1 : 0));
 
        /* The remainder is name.  It could be "John Doe <john.doe@xz>"
         * or "john.doe@xz (John Doe)", but we have removed the
@@ -115,10 +115,10 @@ static void handle_from(const struct strbuf *from)
         * the () pair at the end.
         */
        strbuf_trim(&f);
-       if (f.buf[0] == '(')
-               strbuf_remove(&name, 0, 1);
-       if (f.len && f.buf[f.len - 1] == ')')
+       if (f.buf[0] == '(' && f.len && f.buf[f.len - 1] == ')') {
+               strbuf_remove(&f, 0, 1);
                strbuf_setlen(&f, f.len - 1);
+       }
 
        get_sane_name(&name, &f, &email);
        strbuf_release(&f);
@@ -175,7 +175,7 @@ static void handle_content_type(struct strbuf *line)
                 message_type = TYPE_OTHER;
        if (slurp_attr(line->buf, "boundary=", boundary)) {
                strbuf_insert(boundary, 0, "--", 2);
-               if (content_top++ >= &content[MAX_BOUNDARIES]) {
+               if (++content_top > &content[MAX_BOUNDARIES]) {
                        fprintf(stderr, "Too many boundaries to handle\n");
                        exit(1);
                }
@@ -203,7 +203,8 @@ static void handle_content_transfer_encoding(const struct strbuf *line)
 
 static int is_multipart_boundary(const struct strbuf *line)
 {
-       return !strbuf_cmp(line, *content_top);
+       return (((*content_top)->len <= line->len) &&
+               !memcmp(line->buf, (*content_top)->buf, (*content_top)->len));
 }
 
 static void cleanup_subject(struct strbuf *subject)
@@ -225,10 +226,9 @@ static void cleanup_subject(struct strbuf *subject)
                        continue;
                case '[':
                        if ((pos = strchr(subject->buf, ']'))) {
-                               remove = pos - subject->buf + 1;
-                               /* Don't remove too much. */
-                               if (remove <= (subject->len - remove + 1) * 2) {
-                                       strbuf_remove(subject, 0, remove);
+                               remove = pos - subject->buf;
+                               if (remove <= (subject->len - remove) * 2) {
+                                       strbuf_remove(subject, 0, remove + 1);
                                        continue;
                                }
                        } else
@@ -603,7 +603,7 @@ static void handle_filter(struct strbuf *line);
 static int find_boundary(void)
 {
        while (!strbuf_getline(&line, fin, '\n')) {
-               if (is_multipart_boundary(&line))
+               if (*content_top && is_multipart_boundary(&line))
                        return 1;
        }
        return 0;
@@ -626,7 +626,7 @@ again:
                /* technically won't happen as is_multipart_boundary()
                   will fail first.  But just in case..
                 */
-               if (content_top-- < content) {
+               if (--content_top < content) {
                        fprintf(stderr, "Detected mismatched boundaries, "
                                        "can't recover\n");
                        exit(1);
@@ -650,8 +650,11 @@ again:
                check_header(&line, p_hdr_data, 0);
 
        strbuf_release(&newline);
-       /* eat the blank line after section info */
-       return (strbuf_getline(&line, fin, '\n') == 0);
+       /* replenish line */
+       if (strbuf_getline(&line, fin, '\n'))
+               return 0;
+       strbuf_addch(&line, '\n');
+       return 1;
 }
 
 static inline int patchbreak(const struct strbuf *line)
@@ -758,9 +761,10 @@ static void handle_body(void)
                /* process any boundary lines */
                if (*content_top && is_multipart_boundary(&line)) {
                        /* flush any leftover */
-                       if (line.len)
-                               handle_filter(&line);
-
+                       if (prev.len) {
+                               handle_filter(&prev);
+                               strbuf_reset(&prev);
+                       }
                        if (!handle_boundary())
                                goto handle_body_out;
                }
@@ -907,7 +911,7 @@ static int mailinfo(FILE *in, FILE *out, int ks, const char *encoding,
 }
 
 static const char mailinfo_usage[] =
-       "git-mailinfo [-k] [-u | --encoding=<encoding>] msg patch <mail >info";
+       "git mailinfo [-k] [-u | --encoding=<encoding> | -n] msg patch <mail >info";
 
 int cmd_mailinfo(int argc, const char **argv, const char *prefix)
 {