diff options
author | Nikos Mavrogiannopoulos <nmav@gnutls.org> | 2001-12-13 09:51:17 +0000 |
---|---|---|
committer | Nikos Mavrogiannopoulos <nmav@gnutls.org> | 2001-12-13 09:51:17 +0000 |
commit | a3b0cce295f188b9568bdaac216aac0c4070c884 (patch) | |
tree | d625e049ca95f2faf86cabf1e7dd36878740883e | |
parent | d8b4293799146594cad8709684abbc291c439f8f (diff) | |
download | gnutls-a3b0cce295f188b9568bdaac216aac0c4070c884.tar.gz |
More carefull parsing of incoming packets.
-rw-r--r-- | lib/auth_anon.c | 8 | ||||
-rw-r--r-- | lib/auth_dhe_rsa.c | 13 | ||||
-rw-r--r-- | lib/auth_srp.c | 13 | ||||
-rw-r--r-- | lib/auth_x509.c | 16 | ||||
-rw-r--r-- | lib/gnutls_extensions.c | 5 | ||||
-rw-r--r-- | lib/gnutls_handshake.c | 3 |
6 files changed, 50 insertions, 8 deletions
diff --git a/lib/auth_anon.c b/lib/auth_anon.c index 712da0fbff..dda3c275c6 100644 --- a/lib/auth_anon.c +++ b/lib/auth_anon.c @@ -194,18 +194,22 @@ int proc_anon_server_kx( GNUTLS_STATE state, opaque* data, int data_size) { i = 0; + DECR_LEN( data_size, 2); n_p = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_p); data_p = &data[i]; i += n_p; if (i > data_size) { gnutls_assert(); return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_g = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_g); data_g = &data[i]; i += n_g; if (i > data_size) { @@ -213,9 +217,11 @@ int proc_anon_server_kx( GNUTLS_STATE state, opaque* data, int data_size) { return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_Y = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_Y); data_Y = &data[i]; i += n_Y; if (i > data_size) { @@ -267,9 +273,11 @@ int proc_anon_client_kx( GNUTLS_STATE state, opaque* data, int data_size) { bits = cred->dh_bits; } + DECR_LEN( data_size, 2); n_Y = READuint16( &data[0]); _n_Y = n_Y; + DECR_LEN( data_size, n_Y); if (_gnutls_mpi_scan(&state->gnutls_key->client_Y, &data[2], &_n_Y) !=0 || state->gnutls_key->client_Y==NULL) { gnutls_assert(); return GNUTLS_E_MPI_SCAN_FAILED; diff --git a/lib/auth_dhe_rsa.c b/lib/auth_dhe_rsa.c index 5ec132032d..66bc530eac 100644 --- a/lib/auth_dhe_rsa.c +++ b/lib/auth_dhe_rsa.c @@ -260,9 +260,12 @@ static int proc_dhe_rsa_server_kx(GNUTLS_STATE state, opaque * data, } i = 0; + + DECR_LEN( data_size, 2); n_p = READuint16(&data[i]); i += 2; + DECR_LEN( data_size, n_p); data_p = &data[i]; i += n_p; if (i > data_size) { @@ -270,9 +273,11 @@ static int proc_dhe_rsa_server_kx(GNUTLS_STATE state, opaque * data, return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_g = READuint16(&data[i]); i += 2; + DECR_LEN( data_size, n_g); data_g = &data[i]; i += n_g; if (i > data_size) { @@ -280,9 +285,11 @@ static int proc_dhe_rsa_server_kx(GNUTLS_STATE state, opaque * data, return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_Y = READuint16(&data[i]); i += 2; + DECR_LEN( data_size, n_Y); data_Y = &data[i]; i += n_Y; if (i > data_size) { @@ -318,7 +325,10 @@ static int proc_dhe_rsa_server_kx(GNUTLS_STATE state, opaque * data, return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); sigsize = READuint16(&data[vparams.size]); + + DECR_LEN( data_size, sigsize); signature.data = &data[vparams.size + 2]; signature.size = GMIN(data_size - vparams.size - 2, sigsize); @@ -355,10 +365,11 @@ static int proc_dhe_rsa_client_kx(GNUTLS_STATE state, opaque * data, if (bits < MIN_BITS) bits = DEFAULT_BITS; /* default */ - + DECR_LEN( data_size, 2); n_Y = READuint16(&data[0]); _n_Y = n_Y; + DECR_LEN( data_size, n_Y); if (_gnutls_mpi_scan(&state->gnutls_key->client_Y, &data[2], &_n_Y)) { gnutls_assert(); return GNUTLS_E_MPI_SCAN_FAILED; diff --git a/lib/auth_srp.c b/lib/auth_srp.c index 6be3f358a5..a2aa05a60b 100644 --- a/lib/auth_srp.c +++ b/lib/auth_srp.c @@ -323,12 +323,15 @@ int proc_srp_server_hello(GNUTLS_STATE state, const opaque * data, int data_size /* read the algorithm used to generate V */ i = 0; + DECR_LEN( data_size, 1); memcpy( &pwd_algo, data, 1); - i++; + + DECR_LEN( data_size, 2); n_g = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_g); data_g = &data[i]; i += n_g; if (i > data_size) { @@ -336,9 +339,11 @@ int proc_srp_server_hello(GNUTLS_STATE state, const opaque * data, int data_size return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_n = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_n); data_n = &data[i]; i += n_n; if (i > data_size) { @@ -346,9 +351,11 @@ int proc_srp_server_hello(GNUTLS_STATE state, const opaque * data, int data_size return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + DECR_LEN( data_size, 2); n_s = READuint16( &data[i]); i += 2; + DECR_LEN( data_size, n_s); data_s = &data[i]; i += n_s; if (i > data_size) { @@ -390,8 +397,10 @@ int proc_srp_client_kx0(GNUTLS_STATE state, opaque * data, int data_size) { size_t _n_A; + DECR_LEN( data_size, 2); _n_A = READuint16( &data[0]); + DECR_LEN( data_size, _n_A); if (_gnutls_mpi_scan(&A, &data[2], &_n_A) || A == NULL) { gnutls_assert(); return GNUTLS_E_MPI_SCAN_FAILED; @@ -406,8 +415,10 @@ int proc_srp_server_kx2(GNUTLS_STATE state, opaque * data, int data_size) size_t _n_B; int ret; + DECR_LEN( data_size, 2); _n_B = READuint16( &data[0]); + DECR_LEN( data_size, _n_B); if (_gnutls_mpi_scan(&B, &data[2], &_n_B) || B==NULL) { gnutls_assert(); return GNUTLS_E_MPI_SCAN_FAILED; diff --git a/lib/auth_x509.c b/lib/auth_x509.c index 05a225c9a6..cbe1b5f96d 100644 --- a/lib/auth_x509.c +++ b/lib/auth_x509.c @@ -518,11 +518,12 @@ int _gnutls_proc_x509_server_certificate(GNUTLS_STATE state, opaque * data, } i = dsize; + DECR_LEN(dsize, 3); len = READuint24(p); p += 3; - for (; i > 0; len = READuint24(p), p += 3) { - DECR_LEN(dsize, (len + 3)); + for (; i > 0; DECR_LEN(dsize, 3), len = READuint24(p), p += 3) { + DECR_LEN(dsize, len); peer_certificate_list_size++; p += len; i -= len + 3; @@ -532,6 +533,11 @@ int _gnutls_proc_x509_server_certificate(GNUTLS_STATE state, opaque * data, gnutls_assert(); return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; } + + /* Now we start parsing the list (again). + * We don't use DECR_LEN since the list has + * been parsed before. + */ dsize = data_size; i = dsize; peer_certificate_list = @@ -690,6 +696,7 @@ int _gnutls_proc_x509_cert_req(GNUTLS_STATE state, opaque * data, return 0; } + DECR_LEN(dsize, size); if ((ret = _gnutls_find_acceptable_client_cert(state, p, size, &ind)) < 0) { @@ -772,10 +779,7 @@ int _gnutls_proc_x509_client_cert_vrfy(GNUTLS_STATE state, opaque * data, size = READuint16(pdata); pdata += 2; - if (size < data_size - 2) { - gnutls_assert(); - return GNUTLS_E_UNEXPECTED_PACKET_LENGTH; - } + DECR_LEN(dsize, size); sig.data = pdata; sig.size = size; diff --git a/lib/gnutls_extensions.c b/lib/gnutls_extensions.c index 10ab5dc680..52dc1595bc 100644 --- a/lib/gnutls_extensions.c +++ b/lib/gnutls_extensions.c @@ -88,21 +88,26 @@ uint16 size; if (data_size < 2) return 0; + DECR_LEN( data_size, 2); next = READuint16( data); pos+=2; if (data_size < next) return 0; + DECR_LEN( data_size, next); do { next--; if (next < 0) return 0; + DECR_LEN( data_size, 1); memcpy( &type, &data[pos], 1); pos++; next-=2; if (next < 0) return 0; + DECR_LEN( data_size, 2); size = READuint16(&data[pos]); pos+=2; + DECR_LEN( data_size, size); sdata = &data[pos]; pos+=size; next-=size; if (next < 0) return 0; diff --git a/lib/gnutls_handshake.c b/lib/gnutls_handshake.c index 1b3465dfa1..1b745664e8 100644 --- a/lib/gnutls_handshake.c +++ b/lib/gnutls_handshake.c @@ -791,6 +791,9 @@ static int _gnutls_recv_handshake_header(GNUTLS_STATE state, } *recv_type = dataptr[0]; + /* we do not use DECR_LEN because we know + * that the packet has enough data. + */ length32 = READuint24(&dataptr[1]); handshake_header_size = HANDSHAKE_HEADER_SIZE; |