From: Pierre Habouzit Date: Sat, 4 Nov 2006 01:35:36 +0000 (+0100) Subject: simplify block_try function. X-Git-Url: http://git.madism.org/?p=apps%2Fmadmutt.git;a=commitdiff_plain;h=c5ca8b7eaa727392811813926cda758bceef80f1 simplify block_try function. use a lookup for qp encoding Signed-off-by: Pierre Habouzit --- diff --git a/lib-mime/rfc2047.c b/lib-mime/rfc2047.c index c09a97e..5b88b4b 100644 --- a/lib-mime/rfc2047.c +++ b/lib-mime/rfc2047.c @@ -171,6 +171,17 @@ char *mutt_choose_charset(const char *fromcode, const char *charsets, /* Encoding functions */ /****************************************************************************/ +static const char __qp_special[128] = { + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, + 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, + 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +}; + typedef size_t (encoder_t)(char *, const char *, ssize_t, const char *); static size_t @@ -226,7 +237,7 @@ q_encoder(char *s, const char *d, ssize_t dlen, const char *tocode) if (c == ' ') { *s++ = '_'; } else - if (c & 0x80 || c < 0x20 || c == '_' || strchr (MimeSpecials, c)) { + if (c & 0x80 || __qp_special[c]) { *s++ = '='; *s++ = __m_b36chars_upper[c >> 4]; *s++ = __m_b36chars_upper[c & 0xf]; @@ -254,63 +265,63 @@ static size_t try_block (const char *d, ssize_t dlen, encoder_t **encoder, ssize_t *wlen) { char buf1[ENCWORD_LEN_MAX - ENCWORD_LEN_MIN + 1]; - iconv_t cd; - const char *ib; - char *ob, *p; - ssize_t ibl, obl; - int count, len, len_b, len_q; + ssize_t obl = sizeof(buf1) - m_strlen(tocode); + char *ob; if (fromcode) { - cd = mutt_iconv_open (tocode, fromcode, 0); - assert (cd != (iconv_t) (-1)); - ib = d, ibl = dlen, ob = buf1, obl = sizeof (buf1) - m_strlen(tocode); + const char *ib = d; + ssize_t ibl = dlen; + iconv_t cd = mutt_iconv_open(tocode, fromcode, 0); + + assert (cd != (iconv_t)(-1)); + + ob = buf1; + if (my_iconv(cd, &ib, &ibl, &ob, &obl) < 0 || my_iconv(cd, 0, 0, &ob, &obl) < 0) { - assert (errno == E2BIG); - iconv_close (cd); - assert (ib > d); + assert (errno == E2BIG && ib > d); + iconv_close(cd); return (ib - d == dlen) ? dlen : ib - d + 1; } iconv_close (cd); - } - else { - if (dlen > ssizeof(buf1) - m_strlen(tocode)) - return ssizeof(buf1) - m_strlen(tocode) + 1; - memcpy (buf1, d, dlen); + } else { + if (dlen > obl) + return obl + 1; + memcpy(buf1, d, dlen); ob = buf1 + dlen; } - count = 0; - for (p = buf1; p < ob; p++) { - unsigned char c = *p; + { + const char *p; + int count, len, len_b, len_q; - assert (strchr (MimeSpecials, '?')); - if (c >= 0x7f || c < 0x20 || *p == '_' || - (c != ' ' && strchr (MimeSpecials, *p))) - ++count; - } + count = 0; + for (p = buf1; p < ob; p++) { + count += (*p & 0x80 || __qp_special[(int)*p]); + } - len = ENCWORD_LEN_MIN - 2 + m_strlen(tocode); - len_b = len + (((ob - buf1) + 2) / 3) * 4; - len_q = len + (ob - buf1) + 2 * count; + len = ENCWORD_LEN_MIN - 2 + m_strlen(tocode); + len_b = len + (((ob - buf1) + 2) / 3) * 4; + len_q = len + (ob - buf1) + 2 * count; - /* Apparently RFC 1468 says to use B encoding for iso-2022-jp. */ - if (!ascii_strcasecmp (tocode, "ISO-2022-JP")) - len_q = ENCWORD_LEN_MAX + 1; + /* Apparently RFC 1468 says to use B encoding for iso-2022-jp. */ + if (!ascii_strcasecmp(tocode, "ISO-2022-JP")) + len_q = ENCWORD_LEN_MAX + 1; - if (len_b < len_q && len_b <= ENCWORD_LEN_MAX) { - *encoder = b_encoder; - *wlen = len_b; - return 0; - } - else if (len_q <= ENCWORD_LEN_MAX) { - *encoder = q_encoder; - *wlen = len_q; - return 0; + if (len_b < len_q && len_b <= ENCWORD_LEN_MAX) { + *encoder = b_encoder; + *wlen = len_b; + return 0; + } else + if (len_q <= ENCWORD_LEN_MAX) { + *encoder = q_encoder; + *wlen = len_q; + return 0; + } else { + return dlen; + } } - else - return dlen; } /*