From 0756125d62450cd6223a55ce356fc28e8a2f52a5 Mon Sep 17 00:00:00 2001 From: Luiz Augusto Von Dentz Date: Tue, 11 May 2010 13:43:06 +0300 Subject: [PATCH] obexd: Fix stream buffering Stream must be buffered in order to deal with -EAGAIN when calling .write on mimetype driver, otherwise the data is lost and async io won't work because there is nothing to be read from the stream while the request is suspended. --- obexd/src/obex-priv.h | 1 + obexd/src/obex.c | 50 +++++++++++++++++-------------------------- 2 files changed, 21 insertions(+), 30 deletions(-) diff --git a/obexd/src/obex-priv.h b/obexd/src/obex-priv.h index 932f27537..11d524f17 100644 --- a/obexd/src/obex-priv.h +++ b/obexd/src/obex-priv.h @@ -48,6 +48,7 @@ struct obex_session { const gchar *path; time_t time; guint8 *buf; + gint32 pending; gint32 offset; gint32 size; gpointer object; diff --git a/obexd/src/obex.c b/obexd/src/obex.c index 14e24ba06..71fef28a4 100644 --- a/obexd/src/obex.c +++ b/obexd/src/obex.c @@ -331,6 +331,9 @@ static gint obex_read_stream(struct obex_session *os, obex_t *obex, if (os->size == OBJECT_SIZE_DELETE) os->size = OBJECT_SIZE_UNKNOWN; + if (os->pending > 0) + goto write; + size = OBEX_ObjectReadStream(obex, obj, &buffer); if (size < 0) { error("Error on OBEX stream"); @@ -342,32 +345,34 @@ static gint obex_read_stream(struct obex_session *os, obex_t *obex, return -EIO; } - if (os->object == NULL && size > 0) { - os->buf = g_realloc(os->buf, os->offset + size); - memcpy(os->buf + os->offset, buffer, size); - os->offset += size; - - debug("Stored %u bytes into temporary buffer", size); - + os->buf = g_realloc(os->buf, os->pending + size); + memcpy(os->buf + os->pending, buffer, size); + os->pending += size; + if (os->object == NULL) { + debug("Stored %u bytes into temporary buffer", os->pending); return 0; } - while (len < size) { +write: + while (os->pending > 0) { gint w; - w = os->driver->write(os->object, buffer + len, size - len); + w = os->driver->write(os->object, os->buf + len, + os->pending); if (w < 0) { if (w == -EINTR) continue; - else + else { + memmove(os->buf, os->buf + len, os->pending); return w; + } } len += w; + os->offset += w; + os->pending -= w; } - os->offset += len; - return 0; } @@ -670,7 +675,6 @@ fail: gint obex_put_stream_start(struct obex_session *os, const gchar *filename) { - gint len; int err; os->object = os->driver->open(filename, O_WRONLY | O_CREAT | O_TRUNC, @@ -689,24 +693,10 @@ gint obex_put_stream_start(struct obex_session *os, const gchar *filename) return 0; } - len = 0; - while (len < os->offset) { - gint w; - - w = os->driver->write(os->object, os->buf + len, - os->offset - len); - if (w < 0) { - error("write(%s): %s (%d)", filename, strerror(-w), -w); - if (w == -EINTR) - continue; - else - return w; - } - - len += w; - } + if (os->pending == 0) + return 0; - return 0; + return obex_read_stream(os, os->obex, NULL); } static gboolean check_put(obex_t *obex, obex_object_t *obj) -- 2.47.3