aboutsummaryrefslogtreecommitdiffstats
path: root/camel/camel-mime-message.c
diff options
context:
space:
mode:
authorJeffrey Stedfast <fejj@helixcode.com>2000-10-03 07:26:53 +0800
committerJeffrey Stedfast <fejj@src.gnome.org>2000-10-03 07:26:53 +0800
commited3681564ca93350b6c99e393376319a35abefde (patch)
tree911c88e6be6e7473e81c5ae2e435b47b6094777d /camel/camel-mime-message.c
parent419c6ce7e3f3c42ebffe0b20b1529ef4cec93f9a (diff)
downloadgsoc2013-evolution-ed3681564ca93350b6c99e393376319a35abefde.tar.gz
gsoc2013-evolution-ed3681564ca93350b6c99e393376319a35abefde.tar.zst
gsoc2013-evolution-ed3681564ca93350b6c99e393376319a35abefde.zip
New convenience function to determine if there are any 8bit mime parts in
2000-10-02 Jeffrey Stedfast <fejj@helixcode.com> * camel-mime-message.c (camel_mime_message_has_8bit_parts): New convenience function to determine if there are any 8bit mime parts in a mime message. (camel_mime_message_encode_8bit_parts): New convenience function to recursively reencode all 8bit mime parts to either quoted-printable or base64 depending on which would be the best encoding for that part. * providers/smtp/camel-smtp-transport.c (smtp_data): If the mime message contains 8bit parts and the server doesn't support 8bit transfers, reencode those parts before proceding with the send. (smtp_mail): If the mime message contains 8bit parts and the server supports the 8BITMIME extension to SMTP, notify the server that we'll be sending it 8bit mime parts. (_send_to): Find out if the message contains 8bit parts. svn path=/trunk/; revision=5677
Diffstat (limited to 'camel/camel-mime-message.c')
-rw-r--r--camel/camel-mime-message.c171
1 files changed, 170 insertions, 1 deletions
diff --git a/camel/camel-mime-message.c b/camel/camel-mime-message.c
index b6bd93864e..2cb6fed5a7 100644
--- a/camel/camel-mime-message.c
+++ b/camel/camel-mime-message.c
@@ -25,11 +25,14 @@
*/
#include <config.h>
+
#include "camel-mime-message.h"
-#include <stdio.h>
+#include "camel-multipart.h"
#include "gmime-content-field.h"
+#include "camel-stream-mem.h"
#include "string-utils.h"
#include "hash-table-utils.h"
+#include <stdio.h>
#define d(x)
@@ -548,3 +551,169 @@ remove_header(CamelMedium *medium, const char *header_name)
process_header(medium, header_name, NULL);
parent_class->parent_class.remove_header (medium, header_name);
}
+
+static gboolean
+multipart_has_8bit_parts (CamelMultipart *multipart)
+{
+ gboolean has_8bit = FALSE;
+ int i, nparts;
+
+ nparts = camel_multipart_get_number (multipart);
+
+ for (i = 0; i < nparts && !has_8bit; i++) {
+ GMimeContentField *content;
+ CamelMimePart *mime_part;
+
+ mime_part = camel_multipart_get_part (multipart, i);
+ content = camel_mime_part_get_content_type (mime_part);
+
+ if (gmime_content_field_is_type (content, "multipart", "*")) {
+ CamelDataWrapper *wrapper;
+ CamelMultipart *mpart;
+
+ wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part));
+ mpart = CAMEL_MULTIPART (wrapper);
+
+ has_8bit = multipart_has_8bit_parts (mpart);
+ } else {
+ /* see if this part is 8bit */
+ has_8bit = camel_mime_part_get_encoding (mime_part) == CAMEL_MIME_PART_ENCODING_8BIT;
+ }
+ }
+
+ return has_8bit;
+}
+
+gboolean
+camel_mime_message_has_8bit_parts (CamelMimeMessage *mime_message)
+{
+ GMimeContentField *content;
+ gboolean has_8bit = FALSE;
+
+ content = camel_mime_part_get_content_type (CAMEL_MIME_PART (mime_message));
+
+ if (gmime_content_field_is_type (content, "multipart", "*")) {
+ CamelDataWrapper *wrapper;
+ CamelMultipart *multipart;
+
+ wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (CAMEL_MIME_PART (mime_message)));
+ multipart = CAMEL_MULTIPART (wrapper);
+
+ has_8bit = multipart_has_8bit_parts (multipart);
+ } else {
+ /* single-part message so just check this part */
+ has_8bit = camel_mime_part_get_encoding (CAMEL_MIME_PART (mime_message)) == CAMEL_MIME_PART_ENCODING_8BIT;
+ }
+
+ return has_8bit;
+}
+
+static int
+best_encoding (const guchar *text)
+{
+ guchar *ch;
+ int count = 0;
+ int total;
+
+ for (ch = (guchar *) text; *ch; ch++)
+ if (*ch > (guchar) 127)
+ count++;
+
+ total = (int) (ch - text);
+
+ if ((float) count <= total * 0.17)
+ return CAMEL_MIME_PART_ENCODING_QUOTEDPRINTABLE;
+ else
+ return CAMEL_MIME_PART_ENCODING_BASE64;
+}
+
+static void
+multipart_encode_8bit_parts (CamelMultipart *multipart)
+{
+ int i, nparts;
+
+ nparts = camel_multipart_get_number (multipart);
+
+ for (i = 0; i < nparts; i++) {
+ GMimeContentField *content;
+ CamelMimePart *mime_part;
+
+ mime_part = camel_multipart_get_part (multipart, i);
+ content = camel_mime_part_get_content_type (mime_part);
+
+ if (gmime_content_field_is_type (content, "multipart", "*")) {
+ /* ...and the search for Spock continues */
+ CamelDataWrapper *wrapper;
+ CamelMultipart *mpart;
+
+ wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (mime_part));
+ mpart = CAMEL_MULTIPART (wrapper);
+
+ multipart_encode_8bit_parts (mpart);
+ } else {
+ /* re-encode this if necessary */
+ gboolean is_8bit;
+
+ is_8bit = camel_mime_part_get_encoding (mime_part) == CAMEL_MIME_PART_ENCODING_8BIT;
+ if (is_8bit) {
+ CamelStream *stream;
+ GByteArray *array;
+ guchar *content;
+
+ array = g_byte_array_new ();
+ stream = camel_stream_mem_new_with_byte_array (array);
+ camel_data_wrapper_write_to_stream (CAMEL_DATA_WRAPPER (mime_part), stream);
+ g_byte_array_append (array, "", 1);
+
+ content = array->data;
+ g_byte_array_free (array, FALSE);
+
+ camel_mime_part_set_encoding (mime_part, best_encoding (content));
+ g_free (content);
+ camel_object_unref (CAMEL_OBJECT (stream));
+ }
+ }
+ }
+}
+
+void
+camel_mime_message_encode_8bit_parts (CamelMimeMessage *mime_message)
+{
+ GMimeContentField *content;
+
+ content = camel_mime_part_get_content_type (CAMEL_MIME_PART (mime_message));
+
+ if (gmime_content_field_is_type (content, "multipart", "*")) {
+ /* search for Spock */
+ CamelDataWrapper *wrapper;
+ CamelMultipart *multipart;
+
+ wrapper = camel_medium_get_content_object (CAMEL_MEDIUM (CAMEL_MIME_PART (mime_message)));
+ multipart = CAMEL_MULTIPART (wrapper);
+
+ multipart_encode_8bit_parts (multipart);
+ } else {
+ /* re-encode if we need to */
+ gboolean is_8bit;
+
+ is_8bit = camel_mime_part_get_encoding (CAMEL_MIME_PART (mime_message)) == CAMEL_MIME_PART_ENCODING_8BIT;
+ if (is_8bit) {
+ /* FIXME: is there a better way of doing this? */
+ CamelStream *stream;
+ GByteArray *array;
+ guchar *content;
+
+ array = g_byte_array_new ();
+ stream = camel_stream_mem_new_with_byte_array (array);
+ camel_data_wrapper_write_to_stream (CAMEL_DATA_WRAPPER (CAMEL_MIME_PART (mime_message)), stream);
+ g_byte_array_append (array, "", 1);
+
+ content = array->data;
+ g_byte_array_free (array, FALSE);
+
+ camel_mime_part_set_encoding (CAMEL_MIME_PART (mime_message), best_encoding (content));
+ g_free (content);
+ camel_object_unref (CAMEL_OBJECT (stream));
+ }
+ }
+}