X-Git-Url: http://git.madism.org/?p=apps%2Fmadmutt.git;a=blobdiff_plain;f=handler.c;h=f899a642436c467f2e76cb497d724a66c87794cc;hp=a39bc0c9e5cc9f80e1c7edcbb6fde48d34fd17e5;hb=84336b1f31f4acefd0bf8500b8571c33669fd99f;hpb=bbc4fd52516a8afefbd14c77e34f8389d6f0a6ed diff --git a/handler.c b/handler.c index a39bc0c..f899a64 100644 --- a/handler.c +++ b/handler.c @@ -38,7 +38,7 @@ #include "lib/str.h" #include "lib/debug.h" -typedef void handler_f (BODY *, STATE *); +typedef int handler_f (BODY *, STATE *); typedef handler_f *handler_t; int Index_hex[128] = { @@ -664,7 +664,7 @@ static void enriched_set_flags (const char *tag, struct enriched_state *stte) } } -void text_enriched_handler (BODY * a, STATE * s) +int text_enriched_handler (BODY * a, STATE * s) { enum { TEXT, LANGLE, TAG, BOGUS_TAG, NEWLINE, ST_EOF, DONE @@ -777,6 +777,8 @@ void text_enriched_handler (BODY * a, STATE * s) mem_free (&(stte.buffer)); mem_free (&(stte.line)); mem_free (&(stte.param)); + + return (0); } /* @@ -836,10 +838,8 @@ static void print_flowed_line (char *line, STATE * s, int ql) return; } - pos = line + ql + width; - oldpos = line + ql; - if (ql > 0 && ISBLANK (*oldpos)) - ++oldpos; + pos = line + width; + oldpos = line; /* fprintf(stderr,"oldpos = %p line+len = %p\n",oldpos,line+len); */ @@ -893,67 +893,73 @@ static void print_flowed_line (char *line, STATE * s, int ql) state_putc('\n',s); */ } -static void text_plain_flowed_handler (BODY * a, STATE * s) +static int text_plain_flowed_handler (BODY * a, STATE * s) { int bytes = a->length; char buf[LONG_STRING]; - char *curline = strdup (""); + char *curline = str_dup (""); char *t = NULL; unsigned int curline_len = 1; unsigned int quotelevel = 0, newql = 0; - int first_line = 1; + int buf_off, buf_len; while (bytes > 0 && fgets (buf, sizeof (buf), s->fpin)) { - - bytes -= str_len (buf); + buf_len = str_len (buf); + bytes -= buf_len; newql = get_quote_level (buf); - if (bytes == 0 || ((t = strrchr (buf, '\n')) || (t = strrchr (buf, '\r')))) { - if (t) - *t = '\0'; - if (str_len (curline) > 0 && curline[str_len (curline) - 1] == ' ' - && newql == quotelevel - && strcmp (curline + quotelevel, "-- ") != 0) { - if (buf[newql] == ' ') - curline[str_len (curline) - 1] = '\0'; - - curline = realloc (curline, curline_len + str_len (buf)); - if (curline_len == 1) - *curline = '\0'; - curline_len += str_len (buf); - str_ncat (curline, curline_len, buf + newql, - str_len (buf + newql)); - } - else { - if (first_line) { - first_line = 0; - } - else { - print_flowed_line (curline, s, quotelevel); - } - mem_free (&curline); - curline_len = 1; - curline = realloc (curline, curline_len + str_len (buf)); - if (curline_len == 1) - *curline = '\0'; - curline_len += str_len (buf); - str_ncat (curline, curline_len, buf, str_len (buf)); - quotelevel = newql; - } + /* a change of quoting level in a paragraph - shouldn't happen, + * but has to be handled - see RFC 3676, sec. 4.5. + */ + if (newql != quotelevel && curline && *curline) { + print_flowed_line (curline, s, quotelevel); + *curline = '\0'; + curline_len = 1; } + quotelevel = newql; + + /* XXX - If a line is longer than buf (shouldn't happen), it is split. + * This will almost always cause an unintended line break, and + * possibly a change in quoting level. But that's better than not + * displaying it at all. + */ + if ((t = strrchr (buf, '\n')) || (t = strrchr (buf, '\r'))) { + *t = '\0'; + buf_len = t - buf; + } + buf_off = newql; + if (buf[buf_off] == ' ') + buf_off++; + + /* signature separator also flushes the previous paragraph */ + if (strcmp(buf + buf_off, "-- ") == 0 && curline && *curline) { + print_flowed_line (curline, s, quotelevel); + *curline = '\0'; + curline_len = 1; + } + + curline = realloc (curline, curline_len + buf_len - buf_off); + strcpy (curline + curline_len - 1, buf + buf_off); + curline_len += buf_len - buf_off; + + /* if this was a fixed line the paragraph is finished */ + if (buf_len == 0 || buf[buf_len - 1] != ' ' || strcmp(buf + buf_off, "-- ") == 0) { + print_flowed_line (curline, s, quotelevel); + *curline = '\0'; + curline_len = 1; + } + } - if (curline) { - print_flowed_line (curline, s, quotelevel); - mem_free (&curline); - } + mem_free (&curline); + return (0); } #define TXTHTML 1 #define TXTPLAIN 2 #define TXTENRICHED 3 -static void alternative_handler (BODY * a, STATE * s) +static int alternative_handler (BODY * a, STATE * s) { BODY *choice = NULL; BODY *b; @@ -961,6 +967,7 @@ static void alternative_handler (BODY * a, STATE * s) char buf[STRING]; int type = 0; int mustfree = 0; + int rc = 0; if (a->encoding == ENCBASE64 || a->encoding == ENCQUOTEDPRINTABLE || a->encoding == ENCUUENCODED) { @@ -1087,21 +1094,23 @@ static void alternative_handler (BODY * a, STATE * s) else if (s->flags & M_DISPLAY) { /* didn't find anything that we could display! */ state_mark_attach (s); - state_puts (_ - ("[-- Error: Could not display any parts of Multipart/Alternative! --]\n"), - s); + state_puts (_("[-- Error: Could not display any parts of Multipart/Alternative! --]\n"), s); + rc = -1; } if (mustfree) mutt_free_body (&a); + + return (rc); } /* handles message/rfc822 body parts */ -void message_handler (BODY * a, STATE * s) +static int message_handler (BODY * a, STATE * s) { struct stat st; BODY *b; long off_start; + int rc = 0; off_start = ftell (s->fpin); if (a->encoding == ENCBASE64 || a->encoding == ENCQUOTEDPRINTABLE || @@ -1126,12 +1135,14 @@ void message_handler (BODY * a, STATE * s) state_puts (s->prefix, s); state_putc ('\n', s); - mutt_body_handler (b->parts, s); + rc = mutt_body_handler (b->parts, s); } if (a->encoding == ENCBASE64 || a->encoding == ENCQUOTEDPRINTABLE || a->encoding == ENCUUENCODED) mutt_free_body (&b); + + return (rc); } /* returns 1 if decoding the attachment will produce output */ @@ -1171,12 +1182,13 @@ int mutt_can_decode (BODY * a) return (0); } -void multipart_handler (BODY * a, STATE * s) +static int multipart_handler (BODY * a, STATE * s) { BODY *b, *p; char length[5]; struct stat st; int count; + int rc = 0; if (a->encoding == ENCBASE64 || a->encoding == ENCQUOTEDPRINTABLE || a->encoding == ENCUUENCODED) { @@ -1224,19 +1236,21 @@ void multipart_handler (BODY * a, STATE * s) state_printf (s, "%s: \n", p->form_name); } - mutt_body_handler (p, s); + rc = mutt_body_handler (p, s); state_putc ('\n', s); - if ((s->flags & M_REPLYING) - && (option (OPTINCLUDEONLYFIRST)) && (s->flags & M_FIRSTDONE)) + if (rc || ((s->flags & M_REPLYING) + && (option (OPTINCLUDEONLYFIRST)) && (s->flags & M_FIRSTDONE))) break; } if (a->encoding == ENCBASE64 || a->encoding == ENCQUOTEDPRINTABLE || a->encoding == ENCUUENCODED) mutt_free_body (&b); + + return (rc); } -void autoview_handler (BODY * a, STATE * s) +static int autoview_handler (BODY * a, STATE * s) { rfc1524_entry *entry = rfc1524_new_entry (); char buffer[LONG_STRING]; @@ -1249,6 +1263,7 @@ void autoview_handler (BODY * a, STATE * s) FILE *fperr = NULL; int piped = FALSE; pid_t thepid; + int rc = 0; snprintf (type, sizeof (type), "%s/%s", TYPE (a), a->subtype); rfc1524_mailcap_lookup (a, type, entry, M_AUTOVIEW); @@ -1275,7 +1290,7 @@ void autoview_handler (BODY * a, STATE * s) if ((fpin = safe_fopen (tempfile, "w+")) == NULL) { mutt_perror ("fopen"); rfc1524_free_entry (&entry); - return; + return (-1); } mutt_copy_bytes (s->fpin, fpin, a->length); @@ -1299,6 +1314,7 @@ void autoview_handler (BODY * a, STATE * s) state_mark_attach (s); state_printf (s, _("[-- Can't run %s. --]\n"), command); } + rc = -1; goto bail; } @@ -1350,9 +1366,10 @@ void autoview_handler (BODY * a, STATE * s) mutt_clear_error (); } rfc1524_free_entry (&entry); + return (rc); } -static void external_body_handler (BODY * b, STATE * s) +static int external_body_handler (BODY * b, STATE * s) { const char *access_type; const char *expiration; @@ -1362,11 +1379,9 @@ static void external_body_handler (BODY * b, STATE * s) if (!access_type) { if (s->flags & M_DISPLAY) { state_mark_attach (s); - state_puts (_ - ("[-- Error: message/external-body has no access-type parameter --]\n"), - s); + state_puts (_("[-- Error: message/external-body has no access-type parameter --]\n"), s); } - return; + return (-1); } expiration = mutt_get_parameter ("expiration", b->parameter); @@ -1434,6 +1449,7 @@ static void external_body_handler (BODY * b, STATE * s) CH_DECODE, NULL); } } + return (0); } void mutt_decode_attachment (BODY * b, STATE * s) @@ -1478,7 +1494,7 @@ void mutt_decode_attachment (BODY * b, STATE * s) iconv_close (cd); } -void mutt_body_handler (BODY * b, STATE * s) +int mutt_body_handler (BODY * b, STATE * s) { int decode = 0; int plaintext = 0; @@ -1488,6 +1504,7 @@ void mutt_body_handler (BODY * b, STATE * s) long tmpoffset = 0; size_t tmplength = 0; char type[STRING]; + int rc = 0; int oflags = s->flags; @@ -1627,7 +1644,7 @@ void mutt_body_handler (BODY * b, STATE * s) /* process the (decoded) body part */ if (handler) { - handler (b, s); + rc = handler (b, s); if (decode) { b->length = tmplength; @@ -1656,4 +1673,6 @@ void mutt_body_handler (BODY * b, STATE * s) bail: s->flags = oflags | (s->flags & M_FIRSTDONE); + + return (rc); }