diff options
author | Nikos Mavrogiannopoulos <nmav@gnutls.org> | 2001-10-20 22:40:32 +0000 |
---|---|---|
committer | Nikos Mavrogiannopoulos <nmav@gnutls.org> | 2001-10-20 22:40:32 +0000 |
commit | 919fa2a0e6dece2d134eb12647e22cd186b70a85 (patch) | |
tree | 7b71fd66a07adb6b5475e8b8119807c97c1f5dc3 /lib | |
parent | 2cce439689c70c22169c5950a3426acd039e4116 (diff) | |
download | gnutls-919fa2a0e6dece2d134eb12647e22cd186b70a85.tar.gz |
Corrected short read bug
Diffstat (limited to 'lib')
-rw-r--r-- | lib/gnutls_buffers.c | 29 | ||||
-rw-r--r-- | lib/gnutls_int.h | 6 |
2 files changed, 28 insertions, 7 deletions
diff --git a/lib/gnutls_buffers.c b/lib/gnutls_buffers.c index 9a4de6f0d8..28ef75e043 100644 --- a/lib/gnutls_buffers.c +++ b/lib/gnutls_buffers.c @@ -156,12 +156,25 @@ static ssize_t _gnutls_Read(int fd, void *iptr, size_t sizeOfPtr, int flag) while (left > 0) { i = _gnutls_recv_func(fd, &ptr[i], left, flag); if (i < 0) { +#ifdef READ_DEBUG + _gnutls_log( "READ: %d returned from %d, errno=%d\n", i, fd, errno); +#endif if (errno == EAGAIN || errno == EINTR) { + if (sizeOfPtr-left > 0) { +#ifdef READ_DEBUG + _gnutls_log( "READ: returning %d bytes from %d\n", sizeOfPtr-left, fd); +#endif + return sizeOfPtr-left; + } if (errno==EAGAIN) return GNUTLS_E_AGAIN; else return GNUTLS_E_INTERRUPTED; } else return GNUTLS_E_UNKNOWN_ERROR; } else { +#ifdef READ_DEBUG + _gnutls_log( "READ: Got %d bytes from %d\n", i, fd); +#endif + if (i == 0) break; /* EOF */ } @@ -243,10 +256,10 @@ ssize_t _gnutls_read_buffered( int fd, GNUTLS_STATE state, opaque **iptr, size_t } /* leave peeked data to the kernel space only if application data - * (NEW: or handshake data) is received and we don't have any peeked + * is received and we don't have any peeked * data in gnutls state. */ - if ( (recv_type != GNUTLS_APPLICATION_DATA && recv_type != GNUTLS_HANDSHAKE) + if ( (recv_type != GNUTLS_APPLICATION_DATA) && state->gnutls_internals.have_peeked_data==0) recvlowat = 0; @@ -258,8 +271,9 @@ ssize_t _gnutls_read_buffered( int fd, GNUTLS_STATE state, opaque **iptr, size_t */ min = GMIN( state->gnutls_internals.recv_buffer_data_size, sizeOfPtr); if ( min > 0) { - if ( min == sizeOfPtr) + if ( min == sizeOfPtr) { return min; + } } /* min is over zero */ @@ -284,6 +298,7 @@ ssize_t _gnutls_read_buffered( int fd, GNUTLS_STATE state, opaque **iptr, size_t } if (ret < 0 || ret2 < 0) { + gnutls_assert(); /* that's because they are initilized to 0 */ return GMIN(ret, ret2); } @@ -299,7 +314,13 @@ ssize_t _gnutls_read_buffered( int fd, GNUTLS_STATE state, opaque **iptr, size_t */ state->gnutls_internals.recv_buffer_data_size += ret; - return ret+min; + ret+=min; + + if ((ret > 0) && (ret < sizeOfPtr)) { + /* Short Read */ + return GNUTLS_E_AGAIN; + } else + return ret; } diff --git a/lib/gnutls_int.h b/lib/gnutls_int.h index b1ca4009b3..36396d2753 100644 --- a/lib/gnutls_int.h +++ b/lib/gnutls_int.h @@ -25,12 +25,12 @@ #include <defines.h> /* -#define READ_DEBUG #define WRITE_DEBUG +#define READ_DEBUG #define BUFFERS_DEBUG #define HARD_DEBUG -#define RECORD_DEBUG -#define HANDSHAKE_DEBUG*/ +#define HANDSHAKE_DEBUG +#define RECORD_DEBUG*/ #define DEBUG |