[libgdata] core: Write upload chunks in an idle handler to avoid stack overflow
- From: Philip Withnall <pwithnall src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [libgdata] core: Write upload chunks in an idle handler to avoid stack overflow
- Date: Wed, 3 Jul 2013 18:47:46 +0000 (UTC)
commit e795f559327b3f208d768a4461ca1829e0f44693
Author: Philip Withnall <philip tecnocode co uk>
Date: Wed Jul 3 19:38:07 2013 +0100
core: Write upload chunks in an idle handler to avoid stack overflow
Otherwise the used stack size would be proportional to the number of
chunks uploaded by GDataUploadStream, and hence stack overflow could
potentially occur.
gdata/gdata-upload-stream.c | 30 ++++++++++++++++++++++++++++--
1 files changed, 28 insertions(+), 2 deletions(-)
---
diff --git a/gdata/gdata-upload-stream.c b/gdata/gdata-upload-stream.c
index 8597e5b..2cbc9b4 100644
--- a/gdata/gdata-upload-stream.c
+++ b/gdata/gdata-upload-stream.c
@@ -1073,10 +1073,32 @@ wrote_headers_cb (SoupMessage *message, GDataUploadStream *self)
write_next_chunk (self, message);
}
+typedef struct {
+ GDataUploadStream *upload_stream;
+ SoupMessage *message;
+} WriteNextChunkData;
+
+static void
+write_next_chunk_data_free (WriteNextChunkData *data)
+{
+ g_object_unref (data->message);
+ g_object_unref (data->upload_stream);
+ g_slice_free (WriteNextChunkData, data);
+}
+
+static gboolean
+write_next_chunk_cb (gpointer user_data)
+{
+ WriteNextChunkData *data = user_data;
+ write_next_chunk (data->upload_stream, data->message);
+ return FALSE;
+}
+
static void
wrote_body_data_cb (SoupMessage *message, SoupBuffer *buffer, GDataUploadStream *self)
{
GDataUploadStreamPrivate *priv = self->priv;
+ WriteNextChunkData *data;
/* Signal the main thread that the chunk has been written */
g_mutex_lock (&(priv->write_mutex));
@@ -1091,8 +1113,12 @@ wrote_body_data_cb (SoupMessage *message, SoupBuffer *buffer, GDataUploadStream
g_cond_signal (&(priv->write_cond));
g_mutex_unlock (&(priv->write_mutex));
- /* Send the next chunk to libsoup */
- write_next_chunk (self, message);
+ /* Send the next chunk to libsoup. Do so in an idle callback to avoid overflowing the stack. */
+ data = g_slice_new (WriteNextChunkData);
+ data->message = g_object_ref (message);
+ data->upload_stream = g_object_ref (self);
+
+ g_idle_add_full (G_PRIORITY_DEFAULT, write_next_chunk_cb, data, (GDestroyNotify)
write_next_chunk_data_free);
}
static gpointer
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]