Current list:
+ Trace memory leaks in libgcrypt
+ Audit the code
+* Add support for certificates with DSS parameters
+* OpenPGP certificate support
* Add callbacks to get SRP parameters (instead of a reading password file)
* Minimize footprint.
-* Add support for certificates with DSS parameters
* Add more TLS extensions
* Add support for PKCS8 encrypted private keys
-* OpenPGP certificate support
- Add Kerberos support
(+) Means high priority
*/
int _gnutls_generate_key(GNUTLS_KEY key) {
_gnutls_mpi_print( NULL, &key->key.size, key->KEY);
- key->key.data = secure_malloc( key->key.size);
+ key->key.data = gnutls_secure_malloc( key->key.size);
if ( key->key.data==NULL) {
return GNUTLS_E_MEMORY_ERROR;
}
#ifdef DEBUG
_gnutls_log( "Possible PKCS-1 format attack\n");
#endif
- RANDOMIZE_KEY(state->gnutls_key->key, secure_malloc);
+ RANDOMIZE_KEY(state->gnutls_key->key, gnutls_secure_malloc);
} else {
ret = 0;
if (plaintext.size != TLS_MASTER_SIZE) { /* WOW */
- RANDOMIZE_KEY(state->gnutls_key->key, secure_malloc);
+ RANDOMIZE_KEY(state->gnutls_key->key, gnutls_secure_malloc);
} else {
if (_gnutls_get_adv_version_major( state) != plaintext.data[0]
|| _gnutls_get_adv_version_minor( state) != plaintext.data[1]) {
gnutls_assert();
return GNUTLS_E_INSUFICIENT_CRED;
}
- RANDOMIZE_KEY(state->gnutls_key->key, secure_malloc);
+ RANDOMIZE_KEY(state->gnutls_key->key, gnutls_secure_malloc);
ver = _gnutls_version_max(state);
opaque *key_block;
char keyexp[] = "key expansion";
char random[2*TLS_RANDOM_SIZE];
- int pos;
+ int pos, ret;
int block_size;
if (state->cipher_specs.generated_keys!=0) {
block_size = 2 * hash_size + 2 * key_size + 2 * IV_size;
-
+ key_block = gnutls_secure_malloc( block_size);
+ if (key_block==NULL) {
+ gnutls_assert();
+ return GNUTLS_E_MEMORY_ERROR;
+ }
+
memcpy(random, state->security_parameters.server_random, TLS_RANDOM_SIZE);
memcpy(&random[TLS_RANDOM_SIZE], state->security_parameters.client_random, TLS_RANDOM_SIZE);
if ( state->security_parameters.version == GNUTLS_SSL3) { /* SSL 3 */
- key_block = gnutls_ssl3_generate_random( state->security_parameters.master_secret, TLS_MASTER_SIZE, random, 2*TLS_RANDOM_SIZE,
- block_size);
+ ret = gnutls_ssl3_generate_random( state->security_parameters.master_secret, TLS_MASTER_SIZE, random, 2*TLS_RANDOM_SIZE,
+ block_size, key_block);
} else { /* TLS 1.0 */
- key_block =
+ ret =
gnutls_PRF( state->security_parameters.master_secret, TLS_MASTER_SIZE,
keyexp, strlen(keyexp), random, 2*TLS_RANDOM_SIZE,
- block_size);
+ block_size, key_block);
+ }
+
+ if (ret<0) {
+ gnutls_assert();
+ gnutls_secure_free(key_block);
+ return ret;
}
- if (key_block==NULL) return GNUTLS_E_MEMORY_ERROR;
-
#ifdef HARD_DEBUG
_gnutls_log( "KEY BLOCK[%d]: %s\n",block_size, _gnutls_bin2hex(key_block, block_size));
#endif
pos = 0;
if (hash_size > 0) {
- if (gnutls_sset_datum( &state->cipher_specs.client_write_mac_secret, &key_block[pos], hash_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.client_write_mac_secret, &key_block[pos], hash_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=hash_size;
- if (gnutls_sset_datum( &state->cipher_specs.server_write_mac_secret, &key_block[pos], hash_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.server_write_mac_secret, &key_block[pos], hash_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=hash_size;
}
if (key_size > 0) {
- if (gnutls_sset_datum( &state->cipher_specs.client_write_key, &key_block[pos], key_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.client_write_key, &key_block[pos], key_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=key_size;
- if (gnutls_sset_datum( &state->cipher_specs.server_write_key, &key_block[pos], key_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.server_write_key, &key_block[pos], key_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=key_size;
}
if (IV_size > 0) {
- if (gnutls_sset_datum( &state->cipher_specs.client_write_IV, &key_block[pos], IV_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.client_write_IV, &key_block[pos], IV_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=IV_size;
- if (gnutls_sset_datum( &state->cipher_specs.server_write_IV, &key_block[pos], IV_size) < 0 )
+ if (gnutls_sset_datum( &state->cipher_specs.server_write_IV, &key_block[pos], IV_size) < 0 ) {
+ gnutls_secure_free(key_block);
return GNUTLS_E_MEMORY_ERROR;
+ }
pos+=IV_size;
}
- secure_free(key_block);
+ gnutls_secure_free(key_block);
state->cipher_specs.generated_keys = 1;
}
- _gnutls_set_read_keys(state);
-
+ rc = _gnutls_set_read_keys(state);
+ if (rc < 0)
+ return rc;
+
#ifdef HANDSHAKE_DEBUG
_gnutls_log( "Cipher Suite: %s\n",
_gnutls_cipher_suite_get_name(state->
_gnutls_cpy_write_security_parameters( &state->security_parameters, &state->gnutls_internals.resumed_security_parameters);
}
- _gnutls_set_write_keys(state);
+ rc = _gnutls_set_write_keys(state);
+ if (rc < 0)
+ return rc;
#ifdef HANDSHAKE_DEBUG
_gnutls_log( "Cipher Suite: %s\n",
}
int gnutls_sset_datum( gnutls_datum* dat, const void* data, int data_size) {
- dat->data = secure_malloc(data_size);
+ dat->data = gnutls_secure_malloc(data_size);
if (dat->data==NULL) return GNUTLS_E_MEMORY_ERROR;
dat->size = data_size;
void gnutls_sfree_datum( gnutls_datum* dat) {
if (dat->data!=NULL && dat->size!=0)
- secure_free( dat->data);
+ gnutls_secure_free( dat->data);
dat->data = NULL;
dat->size = 0;
void WRITEdatum32( opaque* dest, gnutls_datum dat);
void WRITEdatum8( opaque* dest, gnutls_datum dat);
-typedef gnutls_datum gnutls_sdatum;
-
int gnutls_set_datum( gnutls_datum* dat, const void* data, int data_size);
/* uses secure_malloc */
int gnutls_sset_datum( gnutls_sdatum* dat, const void* data, int data_size);
GNUTLS_ERROR_ENTRY( GNUTLS_E_UNSUPPORTED_VERSION_PACKET, 1),
GNUTLS_ERROR_ENTRY( GNUTLS_E_UNEXPECTED_PACKET_LENGTH, 1),
GNUTLS_ERROR_ENTRY( GNUTLS_E_INVALID_SESSION, 1),
+ GNUTLS_ERROR_ENTRY( GNUTLS_E_INTERNAL, 1),
GNUTLS_ERROR_ENTRY( GNUTLS_E_UNABLE_SEND_DATA, 1),
GNUTLS_ERROR_ENTRY( GNUTLS_E_FATAL_ALERT_RECEIVED ,1),
GNUTLS_ERROR_ENTRY( GNUTLS_E_RECEIVED_BAD_MESSAGE, 1),
#define GNUTLS_E_ILLEGAL_PARAMETER -55 /* GNUTLS_A_ILLEGAL_PARAMETER */
#define GNUTLS_E_REQUESTED_DATA_NOT_AVAILABLE -56
#define GNUTLS_E_PKCS1_WRONG_PAD -57
+#define GNUTLS_E_INTERNAL -58
#define GNUTLS_E_UNIMPLEMENTED_FEATURE -250
int result;
/* for gcrypt in order to be able to allocate memory */
- gcry_set_allocation_handler(gnutls_malloc, secure_malloc, _gnutls_is_secure_memory, gnutls_realloc, gnutls_free);
+ gcry_set_allocation_handler(gnutls_malloc, gnutls_secure_malloc, _gnutls_is_secure_memory, gnutls_realloc, gnutls_free);
/* set default recv/send functions
*/
/* Calculate The SSL3 Finished message */
#define SSL3_CLIENT_MSG "CLNT"
#define SSL3_SERVER_MSG "SRVR"
-void *_gnutls_ssl3_finished(GNUTLS_STATE state, int type, int skip)
+static int _gnutls_ssl3_finished(GNUTLS_STATE state, int type, int skip, opaque* ret)
{
int siz;
GNUTLS_MAC_HANDLE td;
GNUTLS_MAC_HANDLE td2;
char tmp[MAX_HASH_SIZE];
- char *concat;
char *mesg, *data;
- concat = gnutls_malloc(36);
- if (concat==NULL) {
- gnutls_assert();
- return NULL;
- }
-
td = gnutls_mac_init_ssl3_handshake(GNUTLS_MAC_MD5,
state->security_parameters.
master_secret, 48);
+ if (td==NULL) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+
td2 =
gnutls_mac_init_ssl3_handshake(GNUTLS_MAC_SHA,
state->security_parameters.
master_secret, 48);
+ if (td2==NULL) {
+ gnutls_assert();
+ gnutls_mac_deinit_ssl3_handshake(td, tmp);
+ return GNUTLS_E_HASH_FAILED;
+ }
siz = gnutls_get_handshake_buffer_size(state) - skip;
data = gnutls_malloc(siz);
if (data==NULL) {
gnutls_assert();
- return NULL;
+ gnutls_mac_deinit_ssl3_handshake(td2, tmp);
+ gnutls_mac_deinit_ssl3_handshake(td, tmp);
+ return GNUTLS_E_MEMORY_ERROR;
}
gnutls_read_handshake_buffer(state, data, siz);
gnutls_mac_ssl3(td2, mesg, siz);
gnutls_mac_deinit_ssl3_handshake(td, tmp);
- memcpy(concat, tmp, 16);
+ memcpy(ret, tmp, 16);
gnutls_mac_deinit_ssl3_handshake(td2, tmp);
- memcpy(&concat[16], tmp, 20);
- return concat;
+ memcpy(&ret[16], tmp, 20);
+ return 0;
}
/* Hash the handshake messages as required by TLS 1.0 */
#define SERVER_MSG "server finished"
#define CLIENT_MSG "client finished"
-void *_gnutls_finished(GNUTLS_STATE state, int type, int skip)
+int _gnutls_finished(GNUTLS_STATE state, int type, int skip, void* ret)
{
int siz;
GNUTLS_MAC_HANDLE td;
GNUTLS_MAC_HANDLE td2;
char tmp[MAX_HASH_SIZE];
- char concat[36];
- char *mesg;
- char *data;
+ opaque concat[36];
+ opaque *mesg, *data;
td = gnutls_hash_init(GNUTLS_MAC_MD5);
+ if (td==GNUTLS_HASH_FAILED) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+
td2 = gnutls_hash_init(GNUTLS_MAC_SHA);
+ if (td2==GNUTLS_HASH_FAILED) {
+ gnutls_assert();
+ gnutls_hash_deinit( td2, tmp);
+ return GNUTLS_E_HASH_FAILED;
+ }
siz = gnutls_get_handshake_buffer_size(state) - skip;
- data = gnutls_malloc(siz);
+
+ data = gnutls_malloc( siz);
if (data==NULL) {
gnutls_assert();
- return NULL;
+ gnutls_hash_deinit( td2, tmp);
+ gnutls_hash_deinit( td, tmp);
+ return GNUTLS_E_MEMORY_ERROR;
}
gnutls_read_handshake_buffer(state, data, siz);
} else {
mesg = CLIENT_MSG;
}
- data =
- gnutls_PRF(state->security_parameters.master_secret,
- 48, mesg, strlen(mesg), concat, 36, 12);
- return data;
+ return gnutls_PRF(state->security_parameters.master_secret,
+ 48, mesg, strlen(mesg), concat, 36, 12, ret);
}
/* this function will produce TLS_RANDOM_SIZE bytes of random data
*/
int _gnutls_send_finished( GNUTLS_STATE state, int again)
{
- uint8 *data=NULL;
+ uint8 data[36];
int ret;
int data_size=0;
if (again==0) {
if (state->security_parameters.version == GNUTLS_SSL3) {
- data =
+ ret =
_gnutls_ssl3_finished(state,
state->security_parameters.
- entity, 0);
+ entity, 0, data);
data_size = 36;
} else { /* TLS 1.0 */
- data =
+ ret =
_gnutls_finished(state,
- state->security_parameters.entity, 0);
+ state->security_parameters.entity, 0, data);
data_size = 12;
}
}
+
+ if (ret < 0) {
+ gnutls_assert();
+ return ret;
+ }
+
ret =
_gnutls_send_handshake( state, data, data_size,
GNUTLS_FINISHED);
- gnutls_free(data);
return ret;
}
*/
int _gnutls_recv_finished( GNUTLS_STATE state)
{
- uint8 *data, *vrfy;
+ uint8 data[36], *vrfy;
int data_size;
int ret;
int vrfysize;
gnutls_assert();
return GNUTLS_E_ERROR_IN_FINISHED_PACKET;
}
+
if (state->security_parameters.version == GNUTLS_SSL3) {
/* skip the bytes from the last message */
- data =
+ ret =
_gnutls_ssl3_finished(state,
(state->security_parameters.
entity + 1) % 2,
vrfysize +
- HANDSHAKE_HEADER_SIZE);
+ HANDSHAKE_HEADER_SIZE, data);
} else { /* TLS 1.0 */
- data =
+ ret =
_gnutls_finished(state,
(state->security_parameters.entity +
1) % 2,
- vrfysize + HANDSHAKE_HEADER_SIZE);
+ vrfysize + HANDSHAKE_HEADER_SIZE, data);
+ }
+
+ if (ret < 0) {
+ gnutls_assert();
+ return ret;
}
if (memcmp(vrfy, data, data_size) != 0) {
gnutls_assert();
ret = GNUTLS_E_ERROR_IN_FINISHED_PACKET;
}
- gnutls_free(data);
gnutls_free(vrfy);
return ret;
*/
#include <gnutls_int.h>
-
#include <gnutls_hash_int.h>
+#include <gnutls_errors.h>
/* This file handles all the internal functions that cope with hashes
* and hmacs. Currently it uses the functions provided by
return;
}
-static void ssl3_sha(int i, char *secret, int secret_len, char *random,
+static int ssl3_sha(int i, char *secret, int secret_len, char *random,
int random_len, void* digest)
{
int j;
}
td = gnutls_hash_init(GNUTLS_MAC_SHA);
+ if (td == NULL) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+
gnutls_hash(td, text1, i + 1);
gnutls_hash(td, secret, secret_len);
gnutls_hash(td, random, random_len);
gnutls_hash_deinit(td, digest);
+ return 0;
}
-static void ssl3_md5(int i, char *secret, int secret_len, char *random,
+static int ssl3_md5(int i, char *secret, int secret_len, char *random,
int random_len, void* digest)
{
opaque tmp[MAX_HASH_SIZE];
GNUTLS_MAC_HANDLE td;
-
+ int ret;
+
td = gnutls_hash_init(GNUTLS_MAC_MD5);
+ if (td == NULL) {
+ gnutls_assert();
+ return GNUTLS_E_HASH_FAILED;
+ }
+
gnutls_hash(td, secret, secret_len);
- ssl3_sha(i, secret, secret_len, random, random_len, tmp);
+ ret = ssl3_sha(i, secret, secret_len, random, random_len, tmp);
+ if (ret < 0) {
+ gnutls_assert();
+ gnutls_hash_deinit(td, digest);
+ return ret;
+ }
gnutls_hash(td, tmp, gnutls_hash_get_algo_len(GNUTLS_MAC_SHA));
gnutls_hash_deinit(td, digest);
-
+ return 0;
}
-svoid *gnutls_ssl3_generate_random(void *secret, int secret_len, void *random,
- int random_len, int bytes)
+int gnutls_ssl3_generate_random(void *secret, int secret_len, void *random,
+ int random_len, int bytes, opaque* ret)
{
int size = 0, i = 0;
char digest[MAX_HASH_SIZE];
- char *ret = secure_malloc(bytes);
int block = gnutls_hash_get_algo_len(GNUTLS_MAC_MD5);
+ int result;
while (size < bytes) {
- ssl3_md5(i, secret, secret_len, random, random_len, digest);
-
+ result = ssl3_md5(i, secret, secret_len, random, random_len, digest);
+ if (result < 0) {
+ gnutls_assert();
+ return result;
+ }
+
size += block;
memcpy(&ret[size - block], digest,
i++;
}
- return ret;
+ return 0;
}
int gnutls_hash(GNUTLS_HASH_HANDLE handle, const void* text, int textlen);
void gnutls_hash_deinit(GNUTLS_HASH_HANDLE handle, void* digest);
-svoid *gnutls_ssl3_generate_random(void *secret, int secret_len, void *random, int random_len, int bytes);
+int gnutls_ssl3_generate_random(void *secret, int secret_len, void *random, int random_len, int bytes, opaque* ret);
GNUTLS_MAC_HANDLE gnutls_mac_init_ssl3_handshake(MACAlgorithm algorithm, void *key, int keylen);
void gnutls_mac_deinit_ssl3_handshake(GNUTLS_MAC_HANDLE handle, void* digest);
#define HARD_DEBUG
#define WRITE_DEBUG
#define READ_DEBUG
-#define RECORD_DEBUG
#define HANDSHAKE_DEBUG // Prints some information on handshake
-#define DEBUG
+#define RECORD_DEBUG
*/
+#define DEBUG
+
/* It might be a good idea to replace int with void*
* here.
opaque * data;
int size;
} gnutls_datum;
+typedef gnutls_datum gnutls_sdatum;
typedef struct {
AlertLevel level;
struct GNUTLS_KEY_INT {
/* For DH KX */
- gnutls_datum key;
+ gnutls_sdatum key;
MPI KEY;
MPI client_Y;
MPI client_g;
/* This structure holds parameters got from TLS extension
* mechanism. (some extensions may hold parameters in AUTH_INFO
- * structures instead - see SRP).
+ * structures also - see SRP).
*/
-typedef enum GNUTLS_NAME_IND { GNUTLS_DNSNAME=1 } GNUTLS_NAME_IND;
-
-typedef struct {
- opaque dnsname[MAX_DNSNAME_SIZE];
- GNUTLS_NAME_IND type;
-} name_ind;
typedef struct {
- name_ind name;
opaque srp_username[MAX_SRP_USERNAME];
} TLSExtensions;
/* functions */
int gnutls_send_alert( GNUTLS_STATE state, AlertLevel level, AlertDescription desc);
-svoid *gnutls_PRF( opaque * secret, int secret_size, uint8 * label,
+int gnutls_PRF( opaque * secret, int secret_size, uint8 * label,
int label_size, opaque * seed, int seed_size,
- int total_bytes);
+ int total_bytes, void* ret);
void _gnutls_set_current_version(GNUTLS_STATE state, GNUTLS_Version version);
GNUTLS_Version gnutls_protocol_get_version(GNUTLS_STATE state);
void _gnutls_free_auth_info( GNUTLS_STATE state);
#include "debug.h"
#include "gnutls_gcry.h"
#include <gnutls_record.h>
+#include <gnutls_datum.h>
/* This file contains important thing for the TLS handshake procedure.
*/
return 0;
}
+#define PREMASTER state->gnutls_key->key
static int generate_normal_master( GNUTLS_STATE state) {
-int premaster_size;
-opaque* premaster, *master;
int ret = 0;
char random[2*TLS_RANDOM_SIZE];
memcpy(random, state->security_parameters.client_random, TLS_RANDOM_SIZE);
memcpy(&random[TLS_RANDOM_SIZE], state->security_parameters.server_random, TLS_RANDOM_SIZE);
- /* generate premaster */
- premaster_size = state->gnutls_key->key.size;
- premaster = state->gnutls_key->key.data;
-
#ifdef HARD_DEBUG
- _gnutls_log( "PREMASTER SECRET[%d]: %s\n", premaster_size, _gnutls_bin2hex(premaster, premaster_size));
+ _gnutls_log( "PREMASTER SECRET[%d]: %s\n", PREMASTER.size, _gnutls_bin2hex(PREMASTER.data, PREMASTER.size));
_gnutls_log( "CLIENT RANDOM[%d]: %s\n", 32, _gnutls_bin2hex(state->security_parameters.client_random,32));
_gnutls_log( "SERVER RANDOM[%d]: %s\n", 32, _gnutls_bin2hex(state->security_parameters.server_random,32));
#endif
if ( state->security_parameters.version == GNUTLS_SSL3) {
- master =
- gnutls_ssl3_generate_random( premaster, premaster_size,
- random, 2*TLS_RANDOM_SIZE, TLS_MASTER_SIZE);
+ ret =
+ gnutls_ssl3_generate_random( PREMASTER.data, PREMASTER.size,
+ random, 2*TLS_RANDOM_SIZE, TLS_MASTER_SIZE,
+ state->security_parameters.master_secret);
} else {
- master =
- gnutls_PRF( premaster, premaster_size,
+ ret =
+ gnutls_PRF( PREMASTER.data, PREMASTER.size,
MASTER_SECRET, strlen(MASTER_SECRET),
- random, 2*TLS_RANDOM_SIZE, TLS_MASTER_SIZE);
+ random, 2*TLS_RANDOM_SIZE, TLS_MASTER_SIZE,
+ state->security_parameters.master_secret);
}
- secure_free(premaster);
- state->gnutls_key->key.size = 0;
- state->gnutls_key->key.data = NULL;
+ gnutls_sfree_datum(&PREMASTER);
- if (master==NULL) return GNUTLS_E_MEMORY_ERROR;
+ if (ret<0) return ret;
#ifdef HARD_DEBUG
- _gnutls_log( "MASTER SECRET: %s\n", _gnutls_bin2hex(master, TLS_MASTER_SIZE));
+ _gnutls_log( "MASTER SECRET: %s\n", _gnutls_bin2hex(state->security_parameters.master_secret, TLS_MASTER_SIZE));
#endif
- memcpy(state->security_parameters.master_secret, master, TLS_MASTER_SIZE);
- secure_free(master);
return ret;
}
int _gnutls_is_secure_memory(const svoid * mem)
{
+ if (mem==NULL) return 0;
return *((opaque *) mem - 1);
}
void gnutls_free(void *_ptr)
{
- opaque *ptr = _ptr;
-
if (_ptr == NULL)
return;
- ptr -= EXTRA_SIZE;
+ if ( _gnutls_is_secure_memory( _ptr) != 0) {
+ return gnutls_secure_free( _ptr);
+ } else {
+ opaque *ptr = _ptr;
+
+
+ ptr -= EXTRA_SIZE;
#ifdef MALLOC_DEBUG
- _gnutls_log("Freed: %x with %d bytes\n", _ptr,
+ _gnutls_log("Freed: %x with %d bytes\n", _ptr,
_gnutls_malloc_ptr_size(_ptr));
#endif
- free(ptr);
+ free(ptr);
+ }
}
-svoid *secure_malloc(size_t size)
+svoid *gnutls_secure_malloc(size_t size)
{
opaque *ret;
ret = gnutls_malloc(size);
}
-svoid *secure_calloc(size_t nmemb, size_t size)
+svoid *gnutls_secure_calloc(size_t nmemb, size_t size)
{
svoid *ret;
- ret = secure_malloc(size);
+ ret = gnutls_secure_malloc(size);
if (ret == NULL)
return ret;
return ret;
}
-size_t _secure_ptr_size(svoid * ptr)
+size_t _gnutls_secure_ptr_size(svoid * ptr)
{
return _gnutls_malloc_ptr_size(ptr);
}
-svoid *secure_realloc(svoid * ptr, size_t size)
+svoid *gnutls_secure_realloc(svoid * ptr, size_t size)
{
svoid *ret;
- if (ptr != NULL && size <= _secure_ptr_size(ptr)) {
+ if (ptr != NULL && size <= _gnutls_secure_ptr_size(ptr)) {
/* do not do realloc.
* return the previous pointer.
*/
return ptr;
}
- ret = secure_malloc(size);
+ ret = gnutls_secure_malloc(size);
if (ret == NULL)
return ret;
if (ptr != NULL) {
- memcpy(ret, ptr, GMIN(_secure_ptr_size(ptr), size));
- secure_free(ptr);
+ memcpy(ret, ptr, GMIN(_gnutls_secure_ptr_size(ptr), size));
+ gnutls_secure_free(ptr);
}
return ret;
}
-void secure_free(svoid * ptr)
+void gnutls_secure_free(svoid * ptr)
{
- memset(ptr, 0, _secure_ptr_size(ptr));
+opaque* _ptr = ptr;
+
+ memset(ptr, 0, _gnutls_secure_ptr_size(ptr));
+ *((opaque *) _ptr - 1) = 0; /* not secure mem */
+
gnutls_free(ptr);
}
# include <dmalloc.h>
#endif
-typedef void svoid; /* for functions that allocate using secure_free */
+typedef void svoid; /* for functions that allocate using gnutls_secure_free */
#ifdef USE_DMALLOC
# define gnutls_malloc malloc
# define gnutls_realloc_fast realloc
# define gnutls_free free
# define gnutls_calloc calloc
-# define secure_malloc malloc
-# define secure_realloc realloc
-# define secure_free free
-# define secure_calloc calloc
+# define gnutls_secure_malloc malloc
+# define gnutls_secure_realloc realloc
+# define gnutls_secure_free free
+# define gnutls_secure_calloc calloc
# define gnutls_strdup strdup
int _gnutls_is_secure_memory(const void*);
#else
-svoid* secure_malloc( size_t size);
-svoid* secure_calloc( size_t nmemb, size_t size);
-size_t _secure_ptr_size( svoid* ptr);
-svoid* secure_realloc( svoid* ptr, size_t size);
-void secure_free( svoid* ptr);
+svoid* gnutls_secure_malloc( size_t size);
+svoid* gnutls_secure_calloc( size_t nmemb, size_t size);
+size_t _gnutls_secure_ptr_size( svoid* ptr);
+svoid* gnutls_secure_realloc( svoid* ptr, size_t size);
+void gnutls_secure_free( svoid* ptr);
int _gnutls_is_secure_memory(const svoid* mem);
void* gnutls_malloc( size_t size);
return;
}
-#define MAX_SEED_SIZE 140
+#define MAX_SEED_SIZE 200
/* Produces "total_bytes" bytes using the hash algorithm specified.
* (used in the PRF function)
*/
-static svoid *gnutls_P_hash( MACAlgorithm algorithm, opaque * secret, int secret_size, opaque * seed, int seed_size, int total_bytes)
+static int gnutls_P_hash( MACAlgorithm algorithm, opaque * secret, int secret_size, opaque * seed, int seed_size, int total_bytes, opaque* ret)
{
GNUTLS_MAC_HANDLE td2;
- opaque *ret;
int i = 0, times, how, blocksize, A_size;
opaque final[20], Atmp[MAX_SEED_SIZE];
if (seed_size > MAX_SEED_SIZE || total_bytes<=0) {
gnutls_assert();
- return NULL;
+ return GNUTLS_E_INTERNAL;
}
- ret = secure_calloc(1, total_bytes);
- if (ret==NULL) {
- gnutls_assert();
- return ret;
- }
-
blocksize = gnutls_hmac_get_algo_len(algorithm);
do {
i += blocksize;
memcpy(&ret[i * blocksize], final, how);
}
}
- return ret;
+
+ return 0;
}
/* Function that xor's buffers using the maximum word size supported
return ;
}
+#define MAX_PRF_BYTES 200
+
/* The PRF function expands a given secret
- * needed by the TLS specification
+ * needed by the TLS specification. ret must have a least total_bytes
+ * available.
*/
-svoid *gnutls_PRF( opaque * secret, int secret_size, uint8 * label, int label_size, opaque * seed, int seed_size, int total_bytes)
+int gnutls_PRF( opaque * secret, int secret_size, uint8 * label, int label_size, opaque * seed, int seed_size, int total_bytes, void* ret)
{
int l_s, s_seed_size;
- char *o1, *o2;
char *s1, *s2;
- char *s_seed;
+ opaque s_seed[MAX_SEED_SIZE];
+ opaque o1[MAX_PRF_BYTES], o2[MAX_PRF_BYTES];
+ int result;
+ if (total_bytes > MAX_PRF_BYTES) {
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL;
+ }
/* label+seed = s_seed */
s_seed_size = seed_size + label_size;
- s_seed = gnutls_malloc(s_seed_size);
- if (s_seed==NULL) {
+
+ if (s_seed_size > MAX_SEED_SIZE) {
gnutls_assert();
- return NULL;
+ return GNUTLS_E_INTERNAL;
}
memcpy(s_seed, label, label_size);
l_s++;
}
- o1 = gnutls_P_hash( GNUTLS_MAC_MD5, s1, l_s, s_seed, s_seed_size, total_bytes);
- if (o1==NULL) {
+ result = gnutls_P_hash( GNUTLS_MAC_MD5, s1, l_s, s_seed, s_seed_size, total_bytes, o1);
+ if (result<0) {
gnutls_assert();
- return NULL;
+ return result;
}
- o2 = gnutls_P_hash( GNUTLS_MAC_SHA, s2, l_s, s_seed, s_seed_size, total_bytes);
- if (o2==NULL) {
+ result = gnutls_P_hash( GNUTLS_MAC_SHA, s2, l_s, s_seed, s_seed_size, total_bytes, o2);
+ if (result<0) {
gnutls_assert();
- return NULL;
+ return result;
}
-
- gnutls_free(s_seed);
-
_gnutls_xor(o1, o2, total_bytes);
- secure_free(o2);
+ memcpy( ret, o1, total_bytes);
- return o1;
+ return 0; /* ok */
}