From: Nikos Mavrogiannopoulos Date: Wed, 20 Mar 2002 18:13:39 +0000 (+0000) Subject: Optimizations and fixes in compression X-Git-Tag: gnutls_0_3_92~16 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=ea57a587968692cd511a3ab708c39ad78276f40f;p=thirdparty%2Fgnutls.git Optimizations and fixes in compression --- diff --git a/lib/gnutls_algorithms.c b/lib/gnutls_algorithms.c index 669a604cda..c232d73f94 100644 --- a/lib/gnutls_algorithms.c +++ b/lib/gnutls_algorithms.c @@ -144,7 +144,7 @@ typedef struct gnutls_compression_entry gnutls_compression_entry; static const gnutls_compression_entry compression_algorithms[] = { GNUTLS_COMPRESSION_ENTRY(GNUTLS_COMP_NULL, 0), #ifdef HAVE_LIBZ - GNUTLS_COMPRESSION_ENTRY(GNUTLS_COMP_ZLIB, 224), + GNUTLS_COMPRESSION_ENTRY(GNUTLS_COMP_ZLIB, 0xfc), #endif {0} }; diff --git a/lib/gnutls_cipher.c b/lib/gnutls_cipher.c index 49c773b102..777d4e91c0 100644 --- a/lib/gnutls_cipher.c +++ b/lib/gnutls_cipher.c @@ -33,6 +33,23 @@ #include "gnutls_record.h" #include "gnutls_constate.h" +inline static int +is_write_comp_null( GNUTLS_STATE state) { + if (state->security_parameters.write_compression_algorithm == GNUTLS_COMP_NULL) + return 0; + + return 1; +} + +inline static int +is_read_comp_null( GNUTLS_STATE state) { + if (state->security_parameters.read_compression_algorithm == GNUTLS_COMP_NULL) + return 0; + + return 1; +} + + /* returns ciphertext which contains the headers too. This also * calculates the size in the header field. * @@ -45,10 +62,11 @@ int _gnutls_encrypt(GNUTLS_STATE state, const char* headers, int headers_size, gnutls_datum plain = { (char*)data, data_size }; gnutls_datum comp, ciph; int err; + int free_comp = 1; - if (plain.size == 0) { - comp.data = NULL; - comp.size = 0; + if (plain.size == 0 || is_write_comp_null( state)==0) { + comp = plain; + free_comp = 0; } else { err = _gnutls_plaintext2TLSCompressed(state, &comp, plain); if (err < 0) { @@ -63,7 +81,8 @@ int _gnutls_encrypt(GNUTLS_STATE state, const char* headers, int headers_size, return err; } - gnutls_free_datum(&comp); + if (free_comp) + gnutls_free_datum(&comp); /* copy the headers */ memcpy( ciph.data, headers, headers_size); @@ -74,6 +93,7 @@ int _gnutls_encrypt(GNUTLS_STATE state, const char* headers, int headers_size, return ciph.size; } + int _gnutls_decrypt(GNUTLS_STATE state, char *ciphertext, size_t ciphertext_size, uint8 ** data, ContentType type) @@ -96,9 +116,8 @@ int _gnutls_decrypt(GNUTLS_STATE state, char *ciphertext, return ret; } - if (gcomp.size==0) { - gtxt.data = NULL; - gtxt.size = 0; + if (gcomp.size==0 || is_read_comp_null( state)==0) { + gtxt = gcomp; } else { ret = _gnutls_TLSCompressed2plaintext(state, >xt, gcomp); if (ret < 0) { diff --git a/lib/gnutls_compress_int.c b/lib/gnutls_compress_int.c index 5a30c61b89..a57ed9f1dc 100644 --- a/lib/gnutls_compress_int.c +++ b/lib/gnutls_compress_int.c @@ -27,54 +27,69 @@ */ GNUTLS_COMP_HANDLE gnutls_comp_init( CompressionMethod method, int d) { -#ifdef HAVE_LIBZ GNUTLS_COMP_HANDLE ret; int err; + ret = gnutls_malloc( sizeof( struct GNUTLS_COMP_HANDLE_STRUCT)); + if (ret==NULL) { + gnutls_assert(); + return NULL; + } + + ret->algo = method; + ret->handle = NULL; + +#ifdef HAVE_LIBZ if (method==GNUTLS_COMP_ZLIB) { - ret = gnutls_malloc( sizeof(z_stream)); - - if (ret==NULL) { + z_stream* zhandle; + + ret->handle = gnutls_malloc( sizeof( z_stream)); + if (ret->handle==NULL) { gnutls_assert(); return NULL; } - ret->zalloc = (alloc_func)0; - ret->zfree = (free_func)0; - ret->opaque = (voidpf)0; + zhandle = ret->handle; + + zhandle->zalloc = (alloc_func)0; + zhandle->zfree = (free_func)0; + zhandle->opaque = (voidpf)0; if (d) - err = inflateInit(ret); + err = inflateInit(zhandle); else - err = deflateInit(ret, Z_DEFAULT_COMPRESSION); + err = deflateInit(zhandle, Z_DEFAULT_COMPRESSION); if (err!=Z_OK) { gnutls_assert(); gnutls_free( ret); + gnutls_free( ret->handle); return NULL; } - return ret; } #endif - return NULL; + return ret; } void gnutls_comp_deinit(GNUTLS_COMP_HANDLE handle, int d) { -#ifdef HAVE_LIBZ int err; if (handle!=NULL) { - if (d) - err = inflateEnd( handle); - else - err = deflateEnd( handle); - gnutls_free( handle); - if (err!=Z_OK) { - gnutls_assert(); - return; + switch( handle->algo) { +#ifdef HAVE_LIBZ + case GNUTLS_COMP_ZLIB: + if (d) + err = inflateEnd( handle->handle); + else + err = deflateEnd( handle->handle); + break; } - } #endif + gnutls_free( handle->handle); + gnutls_free( handle); + + } + return; } @@ -85,46 +100,47 @@ int gnutls_compress( GNUTLS_COMP_HANDLE handle, char* plain, int plain_size, cha int compressed_size=GNUTLS_E_COMPRESSION_FAILED; #ifdef HAVE_LIBZ uLongf size; +z_stream *zhandle; #endif int err; - if (handle==NULL) { - *compressed = gnutls_malloc(plain_size); - if (*compressed==NULL) { - gnutls_assert(); - return GNUTLS_E_MEMORY_ERROR; - } - memcpy(*compressed, plain, plain_size); - compressed_size = plain_size; - } + /* NULL compression is not handled here + */ + + switch( handle->algo) { #ifdef HAVE_LIBZ - else { - size = (plain_size*2)+10; - *compressed=NULL; + case GNUTLS_COMP_ZLIB: + size = (plain_size*2)+10; + *compressed=NULL; - *compressed = gnutls_malloc(size); - if (*compressed==NULL) { - gnutls_assert(); - return GNUTLS_E_MEMORY_ERROR; - } + *compressed = gnutls_malloc(size); + if (*compressed==NULL) { + gnutls_assert(); + return GNUTLS_E_MEMORY_ERROR; + } + + zhandle = handle->handle; - handle->next_in = (Bytef*) plain; - handle->avail_in = plain_size; - handle->next_out = (Bytef*) *compressed; - handle->avail_out = size; + zhandle->next_in = (Bytef*) plain; + zhandle->avail_in = plain_size; + zhandle->next_out = (Bytef*) *compressed; + zhandle->avail_out = size; - err = deflate( handle, Z_SYNC_FLUSH); + err = deflate( zhandle, Z_SYNC_FLUSH); - if (err!=Z_OK || handle->avail_in != 0) { - gnutls_assert(); - gnutls_free( *compressed); - return GNUTLS_E_COMPRESSION_FAILED; - } + if (err!=Z_OK || zhandle->avail_in != 0) { + gnutls_assert(); + gnutls_free( *compressed); + return GNUTLS_E_COMPRESSION_FAILED; + } - compressed_size = size - handle->avail_out; - - } + compressed_size = size - zhandle->avail_out; + break; #endif + default: + gnutls_assert(); + return GNUTLS_E_INTERNAL_ERROR; + } /* switch */ if (compressed_size > max_comp_size) { gnutls_free(*compressed); @@ -138,67 +154,57 @@ int gnutls_decompress( GNUTLS_COMP_HANDLE handle, char* compressed, int compress int plain_size=GNUTLS_E_DECOMPRESSION_FAILED, err; #ifdef HAVE_LIBZ uLongf size; +z_stream* zhandle; #endif if (compressed_size > max_record_size+1024) { gnutls_assert(); return GNUTLS_E_DECOMPRESSION_FAILED; } + + /* NULL compression is not handled here + */ - if (handle==NULL) { - *plain = gnutls_malloc(compressed_size); - if (*plain==NULL) { - gnutls_assert(); - return GNUTLS_E_MEMORY_ERROR; - } - - memcpy(*plain, compressed, compressed_size); - plain_size = compressed_size; - } + switch(handle->algo) { #ifdef HAVE_LIBZ - else { - *plain = NULL; - size = compressed_size; - plain_size = 0; - - handle->next_in = (Bytef*) compressed; - handle->avail_in = compressed_size; + case GNUTLS_COMP_ZLIB: + *plain = NULL; + size = compressed_size; + plain_size = 0; + + zhandle = handle->handle; + + zhandle->next_in = (Bytef*) compressed; + zhandle->avail_in = compressed_size; - do { - size*=2; - *plain = gnutls_realloc( *plain, size); - if (*plain==NULL) { - gnutls_assert(); - return GNUTLS_E_MEMORY_ERROR; - } - - handle->next_out = (Bytef*) *plain; - handle->avail_out = size; - - err = inflate( handle, Z_SYNC_FLUSH); - - } while( err==Z_BUF_ERROR && handle->avail_out==0 && size < max_record_size); - -#if 0 - *plain = gnutls_malloc(2048); - size =2048; - handle->next_out = (Bytef*) *plain; - handle->avail_out = size; + do { + size*=2; + *plain = gnutls_realloc( *plain, size); + if (*plain==NULL) { + gnutls_assert(); + return GNUTLS_E_MEMORY_ERROR; + } - err = inflate( handle, Z_SYNC_FLUSH); + zhandle->next_out = (Bytef*) *plain; + zhandle->avail_out = size; -#endif - - if (err!=Z_OK || handle->avail_in != 0) { - gnutls_assert(); - gnutls_free( *plain); - return GNUTLS_E_DECOMPRESSION_FAILED; - } - - plain_size = size - handle->avail_out; + err = inflate( zhandle, Z_SYNC_FLUSH); - } + } while( err==Z_BUF_ERROR && zhandle->avail_out==0 && size < max_record_size); + + if (err!=Z_OK || zhandle->avail_in != 0) { + gnutls_assert(); + gnutls_free( *plain); + return GNUTLS_E_DECOMPRESSION_FAILED; + } + + plain_size = size - zhandle->avail_out; + break; #endif + default: + gnutls_assert(); + return GNUTLS_E_INTERNAL_ERROR; + } /* switch */ if (plain_size > max_record_size) { gnutls_assert(); diff --git a/lib/gnutls_compress_int.h b/lib/gnutls_compress_int.h index 7026041dd2..7e5abd4eec 100644 --- a/lib/gnutls_compress_int.h +++ b/lib/gnutls_compress_int.h @@ -23,13 +23,15 @@ #ifdef HAVE_LIBZ # include -# define GNUTLS_COMP_HANDLE z_stream* -# define GNUTLS_COMP_FAILED NULL -#else -# define GNUTLS_COMP_HANDLE void* -# define GNUTLS_COMP_FAILED NULL #endif +#define GNUTLS_COMP_FAILED NULL + +typedef struct GNUTLS_COMP_HANDLE_STRUCT { + void* handle; + CompressionMethod algo; +} *GNUTLS_COMP_HANDLE; + GNUTLS_COMP_HANDLE gnutls_comp_init( CompressionMethod, int d); void gnutls_comp_deinit(GNUTLS_COMP_HANDLE handle, int d); diff --git a/lib/gnutls_constate.c b/lib/gnutls_constate.c index e359ef1c40..a41379b2bb 100644 --- a/lib/gnutls_constate.c +++ b/lib/gnutls_constate.c @@ -315,9 +315,7 @@ int rc; gnutls_comp_init(state->security_parameters. read_compression_algorithm, 1); if (state->connection_state.read_compression_state == - GNUTLS_COMP_FAILED - && state->security_parameters.read_compression_algorithm != - GNUTLS_COMP_NULL) { + GNUTLS_COMP_FAILED) { gnutls_assert(); return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM; } @@ -354,11 +352,9 @@ int rc; state->connection_state.read_compression_state = gnutls_comp_init(state->security_parameters. read_compression_algorithm, 1); - + if (state->connection_state.read_compression_state == - GNUTLS_COMP_FAILED - && state->security_parameters.read_compression_algorithm != - GNUTLS_COMP_NULL) { + GNUTLS_COMP_FAILED) { gnutls_assert(); return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM; } @@ -483,8 +479,7 @@ int rc; state->connection_state.write_compression_state = gnutls_comp_init(state->security_parameters.write_compression_algorithm, 0); - if (state->connection_state.write_compression_state == GNUTLS_COMP_FAILED - && state->security_parameters.write_compression_algorithm != GNUTLS_COMP_NULL) { + if (state->connection_state.write_compression_state == GNUTLS_COMP_FAILED) { gnutls_assert(); return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM; } @@ -522,9 +517,7 @@ int rc; gnutls_comp_init(state->security_parameters.write_compression_algorithm, 0); if (state->connection_state.write_compression_state == - GNUTLS_COMP_FAILED - && state->security_parameters.write_compression_algorithm != - GNUTLS_CIPHER_NULL) { + GNUTLS_COMP_FAILED) { gnutls_assert(); return GNUTLS_E_UNKNOWN_COMPRESSION_ALGORITHM; }