Partially fixes NB#77528
authorFelipe Erias Morandeira <femorandeira@igalia.com>
Wed, 5 Dec 2007 10:03:30 +0000 (10:03 +0000)
committerFelipe Erias Morandeira <femorandeira@igalia.com>
Wed, 5 Dec 2007 10:03:30 +0000 (10:03 +0000)
Solves a memory problem when obtaining the size of an attachemnt
   * modest-count-stream.[ch] : implementation of TnyStream to get the size of a stream withou wasting extra memory
   * widgets/modest-attachment-view.c : uses the former to get the size of attachments
   * modest-mail-operation.c : removed two redundant lines
   * modest-tny-send-queue.c : check for NULL value before a strdup()

pmo-trunk-r3870

src/Makefile.am
src/modest-count-stream.c [new file with mode: 0644]
src/modest-count-stream.h [new file with mode: 0644]
src/modest-mail-operation.c
src/modest-tny-send-queue.c
src/widgets/modest-attachment-view.c

index bf0da85..a1ef4b9 100644 (file)
@@ -51,6 +51,8 @@ modest_SOURCES=\
        modest-cache-mgr.h \
        modest-conf.c \
        modest-conf.h \
+       modest-count-stream.c \
+       modest-count-stream.h \
        modest-defs.h \
        modest-debug.h \
        modest-dimming-rule.c \
diff --git a/src/modest-count-stream.c b/src/modest-count-stream.c
new file mode 100644 (file)
index 0000000..f10314e
--- /dev/null
@@ -0,0 +1,210 @@
+/* Copyright (c) 2007, Nokia Corporation
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * * Neither the name of the Nokia Corporation nor the names of its
+ *   contributors may be used to endorse or promote products derived from
+ *   this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
+ * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* modest-count-stream.h */
+
+#include <config.h>
+#include <glib.h>
+#include <glib/gi18n-lib.h>
+
+#include <tny-stream.h>
+#include "modest-count-stream.h"
+
+typedef struct _ModestCountStreamPrivate ModestCountStreamPrivate;
+struct _ModestCountStreamPrivate {
+       gsize count;
+};
+#define MODEST_COUNT_STREAM_GET_PRIVATE(o)      (G_TYPE_INSTANCE_GET_PRIVATE((o), \
+                                                       MODEST_TYPE_COUNT_STREAM, \
+                                                       ModestCountStreamPrivate))
+
+static GObjectClass *parent_class = NULL;
+
+static gssize
+modest_count_stream_read (TnyStream *self, char *buffer, gsize n)
+{
+        return 0;
+}
+
+static gssize
+modest_count_stream_write (TnyStream *self, const char *buffer, gsize n)
+{
+       ModestCountStreamPrivate *priv;
+       priv = MODEST_COUNT_STREAM_GET_PRIVATE(self);
+
+       priv->count += n;
+       return (gssize)n;
+}
+
+static gint
+modest_count_stream_flush (TnyStream *self)
+{
+        return 0;
+}
+
+static gint
+modest_count_stream_close (TnyStream *self)
+{
+        return 0;
+}
+
+static gboolean
+modest_count_stream_is_eos (TnyStream *self)
+{
+        return TRUE;
+}
+
+static gint
+modest_count_stream_reset (TnyStream *self)
+{
+        return 0;
+}
+
+static gssize
+modest_count_stream_write_to_stream (TnyStream *self, TnyStream *output)
+{
+        return 0;
+}
+
+/**
+ * modest_count_stream_get_count
+ * @self: the ModestCountStream
+ * 
+ * returns the number of bytes that have been written through this stream
+ * 
+ * Returns: number of bytes that have passed through this stream
+ */
+gsize
+modest_count_stream_get_count (ModestCountStream *self)
+{
+       ModestCountStreamPrivate *priv;
+       priv = MODEST_COUNT_STREAM_GET_PRIVATE(self);
+
+       return priv->count;
+}
+
+/**
+ * modest_count_stream_reset_count
+ * @self: the ModestCountStream
+ * 
+ * resets the internal counter
+ * 
+ * Returns:
+ */
+void
+modest_count_stream_reset_count (ModestCountStream *self)
+{
+       ModestCountStreamPrivate *priv;
+       priv = MODEST_COUNT_STREAM_GET_PRIVATE(self);
+
+       priv->count = 0;
+}
+
+TnyStream*
+modest_count_stream_new ()
+{
+       return TNY_STREAM (g_object_new (MODEST_TYPE_COUNT_STREAM, NULL)); 
+}
+
+static void
+modest_count_stream_finalize (GObject *object)
+{
+        parent_class->finalize (object);
+}
+static void
+modest_count_stream_instance_init (GTypeInstance *instance, gpointer g_class)
+{
+       ModestCountStreamPrivate *priv;
+       priv = MODEST_COUNT_STREAM_GET_PRIVATE(instance);
+
+       priv->count = 0;
+}
+
+static void
+tny_stream_init (TnyStreamIface *klass)
+{
+        klass->read_func = modest_count_stream_read;
+        klass->write_func = modest_count_stream_write;
+        klass->flush_func = modest_count_stream_flush;
+        klass->close_func = modest_count_stream_close;
+        klass->is_eos_func = modest_count_stream_is_eos;
+        klass->reset_func = modest_count_stream_reset;
+        klass->write_to_stream_func = modest_count_stream_write_to_stream;
+}
+
+static void
+modest_count_stream_class_init (ModestCountStreamClass *klass)
+{
+        GObjectClass *object_class;
+
+        parent_class = g_type_class_peek_parent (klass);
+        object_class = (GObjectClass*) klass;
+        object_class->finalize = modest_count_stream_finalize;
+        
+       g_type_class_add_private (object_class, sizeof(ModestCountStream));
+}
+GType
+modest_count_stream_get_type (void)
+{
+        static GType type = 0;
+        if (G_UNLIKELY(type == 0))
+        {
+                static const GTypeInfo info =
+                {
+                        sizeof (ModestCountStreamClass),
+                        NULL,   /* base_init */
+                        NULL,   /* base_finalize */
+                        (GClassInitFunc) modest_count_stream_class_init,   /* class_init */
+                        NULL,   /* class_finalize */
+                        NULL,   /* class_data */
+                        sizeof (ModestCountStream),
+                        0,      /* n_preallocs */
+                        modest_count_stream_instance_init,    /* instance_init */
+                        NULL
+                };
+
+
+                static const GInterfaceInfo tny_stream_info =
+                {
+                        (GInterfaceInitFunc) tny_stream_init, /* interface_init */
+                        NULL,         /* interface_finalize */
+                        NULL          /* interface_data */
+                };
+
+                type = g_type_register_static (G_TYPE_OBJECT,
+                        "ModestCountStream",
+                        &info, 0);
+
+                /* TODO? : FIX THIS (ADD _TYPE): */
+                g_type_add_interface_static (type, TNY_TYPE_STREAM,
+                        &tny_stream_info);
+
+        }
+        return type;
+}
diff --git a/src/modest-count-stream.h b/src/modest-count-stream.h
new file mode 100644 (file)
index 0000000..6180fc1
--- /dev/null
@@ -0,0 +1,95 @@
+/* Copyright (c) 2007, Nokia Corporation
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ *   notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above copyright
+ *   notice, this list of conditions and the following disclaimer in the
+ *   documentation and/or other materials provided with the distribution.
+ * * Neither the name of the Nokia Corporation nor the names of its
+ *   contributors may be used to endorse or promote products derived from
+ *   this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS
+ * IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
+ * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A
+ * PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER
+ * OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
+ * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
+ * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+
+/* modest-count-streaml.h */
+
+#ifndef __MODEST_COUNT_STREAM_H__
+#define __MODEST_COUNT_STREAM_H__
+
+#include <glib-object.h>
+#include <tny-stream.h>
+
+G_BEGIN_DECLS
+
+/* convenience macros */
+#define MODEST_TYPE_COUNT_STREAM             (modest_count_stream_get_type())
+#define MODEST_COUNT_STREAM(obj)             (G_TYPE_CHECK_INSTANCE_CAST((obj),MODEST_TYPE_COUNT_STREAM,ModestCountStream))
+#define MODEST_COUNT_STREAM_CLASS(klass)     (G_TYPE_CHECK_CLASS_CAST((klass),MODEST_TYPE_COUNT_STREAM,ModestCountStreamClass))
+#define MODEST_IS_COUNT_STREAM(obj)          (G_TYPE_CHECK_INSTANCE_TYPE((obj),MODEST_TYPE_COUNT_STREAM))
+#define MODEST_IS_COUNT_STREAM_CLASS(klass)  (G_TYPE_CHECK_CLASS_TYPE((klass),MODEST_TYPE_COUNT_STREAM))
+#define MODEST_COUNT_STREAM_GET_CLASS(obj)   (G_TYPE_INSTANCE_GET_CLASS((obj),MODEST_TYPE_COUNT_STREAM,ModestCountStreamClass))
+
+typedef struct _ModestCountStream      ModestCountStream;
+typedef struct _ModestCountStreamClass ModestCountStreamClass;
+
+struct _ModestCountStream {
+       GObject parent;
+};
+
+struct _ModestCountStreamClass {
+       GObjectClass parent_class;
+};
+
+GType       modest_count_stream_get_type    (void) G_GNUC_CONST;
+
+
+/**
+ * modest_count_stream_new:
+ * 
+ * creates a new #ModestStream
+ * 
+ * Returns: a new #ModestStream
+ **/
+TnyStream*    modest_count_stream_new         ();
+
+/**
+ * modest_count_stream_get_count
+ * @self: the ModestCountStream
+ * 
+ * returns the number of bytes that have been written through this stream
+ * 
+ * Returns: number of bytes that have passed through this stream
+ */
+gsize          modest_count_stream_get_count (ModestCountStream *self);
+
+/**
+ * modest_count_stream_reset_count
+ * @self: the ModestCountStream
+ * 
+ * resets the internal counter
+ * 
+ * Returns:
+ */
+void           modest_count_stream_reset_count (ModestCountStream *self);
+
+
+G_END_DECLS
+
+#endif /* __MODEST_COUNT_STREAM_H__ */
index a833147..0996030 100644 (file)
@@ -697,9 +697,8 @@ send_mail_error_happened_handler (TnySendQueue *queue, TnyHeader *header, TnyMsg
 {
        SendMsgInfo *info = (SendMsgInfo *) userdata;
        TnyHeader *hdr1, *hdr2;
-       hdr1 = tny_msg_get_header(msg);
-       hdr2 = tny_msg_get_header(info->msg);
        const char *msgid1, *msgid2;
+       
        hdr1 = tny_msg_get_header(msg);
        hdr2 = tny_msg_get_header(info->msg);
        msgid1 = tny_header_get_message_id(hdr1);
index 3bc2861..338201b 100644 (file)
@@ -616,7 +616,7 @@ _on_msg_error_happened (TnySendQueue *self,
                                                  msg_uid);     
        if (item == NULL) {
                info = g_slice_new (SendInfo);
-               info->msg_id = strdup(msg_uid);
+               info->msg_id = (msg_uid != NULL)? strdup(msg_uid) : NULL;
                g_queue_push_tail (priv->queue, info);
        } else
                info = item->data;
index 3628204..a5b6aa4 100644 (file)
@@ -42,6 +42,7 @@
 #include <modest-mail-operation.h>
 #include <modest-mail-operation-queue.h>
 #include <modest-runtime.h>
+#include <modest-count-stream.h>
 
 #define GET_SIZE_BUFFER_SIZE 128
 
@@ -122,25 +123,18 @@ get_mime_part_size_thread (gpointer thr_user_data)
 {
        ModestAttachmentView *view =  (ModestAttachmentView *) thr_user_data;
        ModestAttachmentViewPrivate *priv = MODEST_ATTACHMENT_VIEW_GET_PRIVATE (view);
-       gchar read_buffer[GET_SIZE_BUFFER_SIZE];
        TnyStream *stream;
-       gssize readed_size;
-       gssize total = 0;
+       gsize total = 0;
 
-       stream = tny_camel_mem_stream_new ();
+       stream = modest_count_stream_new();
        tny_mime_part_decode_to_stream (priv->mime_part, stream);
-       tny_stream_reset (stream);
-       if (tny_stream_is_eos (stream)) {
-               tny_stream_close (stream);
-               stream = tny_mime_part_get_stream (priv->mime_part);
+       total = modest_count_stream_get_count(MODEST_COUNT_STREAM (stream));
+       if (total == 0) {
+               modest_count_stream_reset_count(MODEST_COUNT_STREAM (stream));
+               tny_mime_part_write_to_stream (priv->mime_part, stream);
+               total = modest_count_stream_get_count(MODEST_COUNT_STREAM (stream));
        }
-       
-       while (!tny_stream_is_eos (stream)) {
-               readed_size = tny_stream_read (stream, read_buffer, GET_SIZE_BUFFER_SIZE);
-               total += readed_size;
-       }
-
-       priv->size = total;
+       priv->size = (guint64)total;
 
        g_idle_add (idle_get_mime_part_size_cb, g_object_ref (view));