summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorJonathan Bastien-Filiatrault <joe@x2a.org>2009-08-15 16:56:19 -0400
committerNikos Mavrogiannopoulos <nmav@gnutls.org>2010-06-03 19:39:00 +0200
commit954644245d2a3744bf07053f534f3ffd7915e4e7 (patch)
tree08156850a5f1d836aa452c0fe96d90a3e5c90493 /lib
parentb7ad62a4a8e2ff69dfc8cafb5ec3857a4170940c (diff)
downloadgnutls-954644245d2a3744bf07053f534f3ffd7915e4e7.tar.gz
Simplify handshake send buffer logic.
Diffstat (limited to 'lib')
-rw-r--r--lib/gnutls_buffers.c170
-rw-r--r--lib/gnutls_buffers.h7
-rw-r--r--lib/gnutls_handshake.c3
-rw-r--r--lib/gnutls_int.h4
-rw-r--r--lib/gnutls_state.c2
5 files changed, 61 insertions, 125 deletions
diff --git a/lib/gnutls_buffers.c b/lib/gnutls_buffers.c
index fecbf85d49..b1740aa74b 100644
--- a/lib/gnutls_buffers.c
+++ b/lib/gnutls_buffers.c
@@ -733,148 +733,88 @@ _gnutls_io_write_flush (gnutls_session_t session)
/* This function writes the data that are left in the
* Handshake write buffer (ie. because the previous write was
* interrupted.
+ *
+ * FIXME: This is practically the same as _gnutls_io_write_flush.
*/
ssize_t
_gnutls_handshake_io_write_flush (gnutls_session_t session)
{
- ssize_t ret;
- ret = _gnutls_handshake_io_send_int (session, 0, 0, NULL, 0);
- if (ret < 0)
- {
- gnutls_assert ();
- return ret;
- }
+ mbuffer_head_st * const send_buffer = &session->internals.handshake_send_buffer;
+ gnutls_datum_t msg;
+ int ret;
+ ssize_t total = 0;
- _gnutls_write_log ("HANDSHAKE_FLUSH: written[1] %d bytes\n", (int) ret);
+ _gnutls_write_log ("HWRITE FLUSH: %d bytes in buffer.\n",
+ (int)send_buffer->byte_length);
- if (session->internals.handshake_send_buffer.length == 0)
+ for (_gnutls_mbuffer_get_head (send_buffer, &msg);
+ msg.data != NULL && msg.size > 0;
+ _gnutls_mbuffer_get_head (send_buffer, &msg))
{
- ret = session->internals.handshake_send_buffer_prev_size; /* done */
- session->internals.handshake_send_buffer_prev_size = 0;
+ ret = _gnutls_send_int (session, GNUTLS_HANDSHAKE,
+ session->internals.handshake_send_buffer_htype,
+ msg.data, msg.size);
+
+ if (ret >= 0)
+ {
+ dump_bytes (msg.data, msg.size, 1);
+ _gnutls_mbuffer_remove_bytes (send_buffer, ret);
+
+ _gnutls_write_log ("HWRITE: wrote %d bytes, %d bytes left.\n",
+ ret, (int)send_buffer->byte_length);
+
+ total += ret;
+ }
+ else if (ret == GNUTLS_E_INTERRUPTED || ret == GNUTLS_E_AGAIN)
+ {
+ _gnutls_write_log ("HWRITE interrupted: %d bytes left.\n",
+ (int)send_buffer->byte_length);
+ return ret;
+ }
+ else
+ {
+ _gnutls_write_log ("HWRITE error: code %d, %d bytes left.\n",
+ ret, (int)send_buffer->byte_length);
+
+ gnutls_assert ();
+ return ret;
+ }
}
- return ret;
+ return total;
}
/* This is a send function for the gnutls handshake
* protocol. Just makes sure that all data have been sent.
+ *
+ * FIXME: This is practically the same as _gnutls_io_write_buffered.
*/
ssize_t
_gnutls_handshake_io_send_int (gnutls_session_t session,
- content_type_t type,
gnutls_handshake_description_t htype,
const void *iptr, size_t n)
{
- size_t left;
- ssize_t ret = 0;
- const opaque *ptr;
- ssize_t retval = 0;
-
- ptr = iptr;
-
- if (session->internals.handshake_send_buffer.length > 0 && ptr == NULL
- && n == 0)
- {
- gnutls_datum_t bdata;
-
- /* resuming previously interrupted write
- */
- gnutls_assert ();
-
- /* checking is handled above */
- _gnutls_buffer_get_datum (&session->internals.handshake_send_buffer,
- &bdata,
- session->internals.handshake_send_buffer.
- length);
+ mbuffer_head_st * const send_buffer = &session->internals.handshake_send_buffer;
+ mbuffer_st *bufel = _gnutls_mbuffer_alloc(n);
- ptr = bdata.data;
- n = bdata.size;
-
- type = session->internals.handshake_send_buffer_type;
- htype = session->internals.handshake_send_buffer_htype;
-
- }
- else if (session->internals.handshake_send_buffer.length > 0)
- {
- gnutls_assert ();
- return GNUTLS_E_INTERNAL_ERROR;
- }
-#ifdef WRITE_DEBUG
- else
- {
- _gnutls_write_log ("HWRITE: will write %d bytes to %d.\n", n,
- gnutls_transport_get_ptr (session));
-
- dump_bytes(ptr, n, 1);
- }
-#endif
-
- if (n == 0)
- { /* if we have no data to send */
- gnutls_assert ();
- return 0;
- }
- else if (ptr == NULL)
- {
- gnutls_assert ();
- return GNUTLS_E_INTERNAL_ERROR;
- }
-
-
- left = n;
- while (left > 0)
+ if(bufel == NULL)
{
- ret = _gnutls_send_int (session, type, htype, &ptr[n - left], left);
-
- if (ret <= 0)
- {
- if (ret == 0)
- {
- gnutls_assert ();
- ret = GNUTLS_E_INTERNAL_ERROR;
- }
-
- if (left > 0
- && (ret == GNUTLS_E_INTERRUPTED || ret == GNUTLS_E_AGAIN))
- {
- gnutls_assert ();
-
- retval =
- _gnutls_buffer_append (&session->
- internals.handshake_send_buffer,
- &ptr[n - left], left);
- if (retval < 0)
- {
- gnutls_assert ();
- return retval;
- }
-
- session->internals.handshake_send_buffer_prev_size += n - left;
-
- session->internals.handshake_send_buffer_type = type;
- session->internals.handshake_send_buffer_htype = htype;
-
- }
- else
- {
- session->internals.handshake_send_buffer_prev_size = 0;
- session->internals.handshake_send_buffer.length = 0;
- }
-
- gnutls_assert ();
- return ret;
- }
- left -= ret;
+ gnutls_assert ()
+ return GNUTLS_E_MEMORY_ERROR;
}
- retval = n + session->internals.handshake_send_buffer_prev_size;
+ memcpy(bufel->msg.data, iptr, n);
- session->internals.handshake_send_buffer.length = 0;
- session->internals.handshake_send_buffer_prev_size = 0;
+ _gnutls_mbuffer_enqueue (send_buffer, bufel);
+ session->internals.handshake_send_buffer_htype = htype;
- return retval;
+ _gnutls_write_log
+ ("HWRITE: enqueued %d. Total %d bytes.\n",
+ (int)bufel->msg.size,
+ (int)send_buffer->byte_length);
+ return _gnutls_handshake_io_write_flush(session);
}
/* This is a receive function for the gnutls handshake
diff --git a/lib/gnutls_buffers.h b/lib/gnutls_buffers.h
index 2e0b7de767..c1d954e29c 100644
--- a/lib/gnutls_buffers.h
+++ b/lib/gnutls_buffers.h
@@ -48,14 +48,13 @@ int _gnutls_handshake_buffer_get_ptr (gnutls_session_t session,
opaque ** data_ptr, size_t * length);
#define _gnutls_handshake_io_buffer_clear( session) \
- _gnutls_buffer_clear( &session->internals.handshake_send_buffer); \
- _gnutls_buffer_clear( &session->internals.handshake_recv_buffer); \
- session->internals.handshake_send_buffer_prev_size = 0
+ _gnutls_mbuffer_clear( &session->internals.handshake_send_buffer); \
+ _gnutls_buffer_clear( &session->internals.handshake_recv_buffer);
ssize_t _gnutls_handshake_io_recv_int (gnutls_session_t, content_type_t,
gnutls_handshake_description_t, void *,
size_t);
-ssize_t _gnutls_handshake_io_send_int (gnutls_session_t, content_type_t,
+ssize_t _gnutls_handshake_io_send_int (gnutls_session_t,
gnutls_handshake_description_t,
const void *, size_t);
ssize_t _gnutls_io_write_flush (gnutls_session_t session);
diff --git a/lib/gnutls_handshake.c b/lib/gnutls_handshake.c
index c83218579a..21c63574b0 100644
--- a/lib/gnutls_handshake.c
+++ b/lib/gnutls_handshake.c
@@ -1187,8 +1187,7 @@ _gnutls_send_handshake (gnutls_session_t session, void *i_data,
session->internals.last_handshake_out = type;
ret =
- _gnutls_handshake_io_send_int (session, GNUTLS_HANDSHAKE, type,
- data, datasize);
+ _gnutls_handshake_io_send_int (session, type, data, datasize);
gnutls_free (data);
diff --git a/lib/gnutls_int.h b/lib/gnutls_int.h
index d9a8d9245c..a89f13741f 100644
--- a/lib/gnutls_int.h
+++ b/lib/gnutls_int.h
@@ -589,9 +589,7 @@ typedef struct
/* These buffers are used in the handshake
* protocol only. freed using _gnutls_handshake_io_buffer_clear();
*/
- gnutls_buffer handshake_send_buffer;
- size_t handshake_send_buffer_prev_size;
- content_type_t handshake_send_buffer_type;
+ mbuffer_head_st handshake_send_buffer;
gnutls_handshake_description_t handshake_send_buffer_htype;
content_type_t handshake_recv_buffer_type;
gnutls_handshake_description_t handshake_recv_buffer_htype;
diff --git a/lib/gnutls_state.c b/lib/gnutls_state.c
index d9e221fdd2..c99150228b 100644
--- a/lib/gnutls_state.c
+++ b/lib/gnutls_state.c
@@ -301,7 +301,7 @@ gnutls_init (gnutls_session_t * session, gnutls_connection_end_t con_end)
_gnutls_mbuffer_init (&(*session)->internals.record_send_buffer);
_gnutls_buffer_init (&(*session)->internals.record_recv_buffer);
- _gnutls_buffer_init (&(*session)->internals.handshake_send_buffer);
+ _gnutls_mbuffer_init (&(*session)->internals.handshake_send_buffer);
_gnutls_buffer_init (&(*session)->internals.handshake_recv_buffer);
(*session)->key = gnutls_calloc (1, sizeof (struct gnutls_key_st));