Jacob Head
Fabian Keil
Didier Barvaux
+ Yotam Medini
+2010-08-25 [colin] 3.7.6cvs31
+
+ * src/procmime.c
+ * AUTHORS
+ * src/gtk/authors.h
+ * src/common/base64.c
+ * src/common/base64.h
+ Fix bug #2245, "base64 decoding fails with line breaks"
+ Patch by Yotam Medini
+
2010-08-25 [colin] 3.7.6cvs30
* src/main.c
( cvs diff -u -r 1.115.2.227 -r 1.115.2.228 src/main.c; ) > 3.7.6cvs28.patchset
( cvs diff -u -r 1.149.2.100 -r 1.149.2.101 src/inc.c; cvs diff -u -r 1.17.2.56 -r 1.17.2.57 src/send_message.c; cvs diff -u -r 1.5.2.26 -r 1.5.2.27 src/statusbar.c; cvs diff -u -r 1.43.2.116 -r 1.43.2.117 src/toolbar.c; ) > 3.7.6cvs29.patchset
( cvs diff -u -r 1.115.2.228 -r 1.115.2.229 src/main.c; ) > 3.7.6cvs30.patchset
+( cvs diff -u -r 1.49.2.132 -r 1.49.2.133 src/procmime.c; cvs diff -u -r 1.100.2.74 -r 1.100.2.75 AUTHORS; cvs diff -u -r 1.1.2.67 -r 1.1.2.68 src/gtk/authors.h; cvs diff -u -r 1.1.4.9 -r 1.1.4.10 src/common/base64.c; cvs diff -u -r 1.1.4.7 -r 1.1.4.8 src/common/base64.h; ) > 3.7.6cvs31.patchset
MICRO_VERSION=6
INTERFACE_AGE=0
BINARY_AGE=0
-EXTRA_VERSION=30
+EXTRA_VERSION=31
EXTRA_RELEASE=
EXTRA_GTK2_VERSION=
}
gint base64_decoder_decode(Base64Decoder *decoder,
- const gchar *in, guchar *out)
+ const gchar *in, guchar *out, gint inlen)
{
+ const gchar *in_end = in + inlen;
gint len, total_len = 0;
+ gboolean in_more = inlen > 0;
+ gboolean got_eq = FALSE;
gint buf_len;
gchar buf[4];
cm_return_val_if_fail(in != NULL, -1);
cm_return_val_if_fail(out != NULL, -1);
+ /* Start with previous saved tail */
buf_len = decoder->buf_len;
memcpy(buf, decoder->buf, sizeof(buf));
- for (;;) {
- while (buf_len < 4) {
+ while (in_more) {
+ while (buf_len < 4 && in_more) {
gchar c = *in;
in++;
- if (c == '\0') break;
- if (c == '\r' || c == '\n') continue;
- if (c != '=' && BASE64VAL(c) == -1)
- return -1;
- buf[buf_len++] = c;
+ got_eq = (c == '=');
+ if (got_eq || BASE64VAL(c) >= 0)
+ buf[buf_len++] = c;
+ in_more = (in < in_end) && !(got_eq && (buf_len == 4));
}
- if (buf_len < 4 || buf[0] == '=' || buf[1] == '=') {
- decoder->buf_len = buf_len;
- memcpy(decoder->buf, buf, sizeof(buf));
- return total_len;
- }
- len = base64_decode(out, buf, 4);
- out += len;
- total_len += len;
- buf_len = 0;
- if (len < 3) {
- decoder->buf_len = 0;
- return total_len;
+ if (buf_len == 4) {
+ len = base64_decode(out, buf, 4);
+ out += len;
+ total_len += len;
+ buf_len = 0;
}
}
+ if (buf_len < 4) {
+ /* Save tail for next iteration call. It wll be ignored if ends here. */
+ decoder->buf_len = buf_len;
+ memcpy(decoder->buf, buf, buf_len);
+ }
+ return total_len;
}
void base64_decoder_free (Base64Decoder *decoder);
gint base64_decoder_decode (Base64Decoder *decoder,
const gchar *in,
- guchar *out);
+ guchar *out,
+ gint inlen);
#endif /* __BASE64_H__ */
"HIRAMATSU Masami",
"Yasuzaki Masayoshi",
"Jason McCarver",
+"Yotam Medini",
"David Mehrmann",
"Christian Mertes",
"Bram Metsch",
FLUSH_LASTLINE();
} else if (encoding == ENC_BASE64) {
gchar outbuf[BUFFSIZE];
- gint len;
+ gint len, inlen, inread;
Base64Decoder *decoder;
gboolean got_error = FALSE;
gboolean uncanonicalize = FALSE;
}
decoder = base64_decoder_new();
- while ((ftell(infp) < readend) && (fgets(buf, sizeof(buf), infp) != NULL)) {
- len = base64_decoder_decode(decoder, buf, outbuf);
+ while ((inlen = MIN(readend - ftell(infp), sizeof(buf))) > 0 && !err) {
+ inread = fread(buf, 1, inlen, infp);
+ len = base64_decoder_decode(decoder, buf, outbuf, inread);
if (uncanonicalize == TRUE && strlen(outbuf) < len && starting) {
uncanonicalize = FALSE;
null_bytes = TRUE;
}
starting = FALSE;
- if (len < 0 && !got_error) {
+ if (((inread != inlen) || len < 0) && !got_error) {
g_warning("Bad BASE64 content.\n");
if (fwrite(_("[Error decoding BASE64]\n"),
sizeof(gchar),