summaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
authorNikos Mavrogiannopoulos <nmav@gnutls.org>2002-08-26 08:14:33 +0000
committerNikos Mavrogiannopoulos <nmav@gnutls.org>2002-08-26 08:14:33 +0000
commit32b6675ea3193b6d445bb26957a9bbb66480a25a (patch)
tree2215070afd9f3591384dd4f40c8048c565feb247 /lib
parentbacee492e5dfe72b6ac78074de2ce7d946adaee2 (diff)
downloadgnutls-32b6675ea3193b6d445bb26957a9bbb66480a25a.tar.gz
Added support for RSA_EXPORT_WITH_RC4_EXPORT_MD5 with RSA certificates with modulus less than 512 bits. This change made the code a bit messy.
Diffstat (limited to 'lib')
-rw-r--r--lib/auth_rsa.c62
-rw-r--r--lib/auth_rsa_export.c63
-rw-r--r--lib/gnutls_kx.c24
-rw-r--r--lib/gnutls_rsa_export.h1
-rw-r--r--lib/gnutls_state.c16
-rw-r--r--lib/gnutls_state.h1
6 files changed, 137 insertions, 30 deletions
diff --git a/lib/auth_rsa.c b/lib/auth_rsa.c
index efd3f689fe..e1ceaf6121 100644
--- a/lib/auth_rsa.c
+++ b/lib/auth_rsa.c
@@ -77,25 +77,6 @@ CERTIFICATE_AUTH_INFO info;
gnutls_cert peer_cert;
int i;
- if ( _gnutls_cipher_suite_get_kx_algo(state->security_parameters.current_cipher_suite)
- == GNUTLS_KX_RSA_EXPORT) {
- /* EXPORT case: */
-
- if (state->gnutls_key->rsa[0] == NULL ||
- state->gnutls_key->rsa[1] == NULL) {
- gnutls_assert();
- return GNUTLS_E_INTERNAL_ERROR;
- }
-
- *params_len = 2;
- for (i=0;i<*params_len;i++) {
- params[i] = _gnutls_mpi_copy(state->gnutls_key->rsa[i]);
- }
-
- return 0;
- }
-
-
/* normal non export case */
info = _gnutls_get_auth_info( state);
@@ -132,6 +113,34 @@ int i;
gnutls_assert();
return GNUTLS_E_INTERNAL_ERROR;
}
+
+
+ /* EXPORT case: */
+ if ( _gnutls_cipher_suite_get_kx_algo(state->security_parameters.current_cipher_suite)
+ == GNUTLS_KX_RSA_EXPORT &&
+ _gnutls_mpi_get_nbits(peer_cert.params[0]) > 512) {
+
+ _gnutls_free_cert( peer_cert);
+
+ if (state->gnutls_key->rsa[0] == NULL ||
+ state->gnutls_key->rsa[1] == NULL) {
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL_ERROR;
+ }
+
+ if (*params_len < 2) {
+ gnutls_assert();
+ return GNUTLS_E_INTERNAL_ERROR;
+ }
+ *params_len = 2;
+ for (i=0;i<*params_len;i++) {
+ params[i] = _gnutls_mpi_copy(state->gnutls_key->rsa[i]);
+ }
+
+ return 0;
+ }
+
+ /* end of export case */
if (*params_len < peer_cert.params_size) {
gnutls_assert();
@@ -160,8 +169,15 @@ const GNUTLS_CERTIFICATE_CREDENTIALS cred;
return GNUTLS_E_INSUFICIENT_CRED;
}
+ if ( (index=state->gnutls_internals.selected_cert_index) < 0) {
+ gnutls_assert();
+ return GNUTLS_E_UNKNOWN_ERROR;
+ }
+
if ( _gnutls_cipher_suite_get_kx_algo(state->security_parameters.current_cipher_suite)
- == GNUTLS_KX_RSA_EXPORT) {
+ == GNUTLS_KX_RSA_EXPORT &&
+ _gnutls_mpi_get_nbits(cred->cert_list[index][0].params[0]) > 512) {
+
/* EXPORT case: */
if (cred->rsa_params == NULL) {
gnutls_assert();
@@ -175,12 +191,6 @@ const GNUTLS_CERTIFICATE_CREDENTIALS cred;
}
/* non export cipher suites. */
-
-
- if ( (index=state->gnutls_internals.selected_cert_index) < 0) {
- gnutls_assert();
- return GNUTLS_E_UNKNOWN_ERROR;
- }
*params_size = cred->pkey[index].params_size;
*params = cred->pkey[index].params;
diff --git a/lib/auth_rsa_export.c b/lib/auth_rsa_export.c
index 96a7cc9580..f181dbedb3 100644
--- a/lib/auth_rsa_export.c
+++ b/lib/auth_rsa_export.c
@@ -100,6 +100,13 @@ static int gen_rsa_export_server_kx(GNUTLS_STATE state, opaque ** data)
return ret;
}
+ /* abort sending this message if we have a certificate
+ * of 512 bits or less.
+ */
+ if ( _gnutls_mpi_get_nbits( apr_pkey->params[0]) <= 512) {
+ return GNUTLS_E_INT_RET_0;
+ }
+
rsa_params = _gnutls_get_rsa_params( cred->rsa_params, 512);
if (rsa_params == NULL) {
gnutls_assert();
@@ -173,6 +180,58 @@ static int gen_rsa_export_server_kx(GNUTLS_STATE state, opaque ** data)
return data_size;
}
+/* if the peer's certificate is of 512 bits or less, returns non zero.
+ */
+int _gnutls_peers_cert_less_512( GNUTLS_STATE state)
+{
+gnutls_cert peer_cert;
+int ret;
+CERTIFICATE_AUTH_INFO info = _gnutls_get_auth_info( state);
+
+ if (info == NULL || info->ncerts==0) {
+ gnutls_assert();
+ /* we need this in order to get peer's certificate */
+ return 0;
+ }
+
+ switch( state->security_parameters.cert_type) {
+ case GNUTLS_CRT_X509:
+ if ((ret =
+ _gnutls_x509_cert2gnutls_cert( &peer_cert,
+ info->raw_certificate_list[0], CERT_NO_COPY)) < 0) {
+ gnutls_assert();
+ return 0;
+ }
+ break;
+
+ case GNUTLS_CRT_OPENPGP:
+ if (_E_gnutls_openpgp_cert2gnutls_cert==NULL) {
+ gnutls_assert();
+ return GNUTLS_E_INIT_LIBEXTRA;
+ }
+ if ((ret =
+ _E_gnutls_openpgp_cert2gnutls_cert( &peer_cert,
+ info->raw_certificate_list[0])) < 0) {
+ gnutls_assert();
+ return 0;
+ }
+ break;
+
+ default:
+ gnutls_assert();
+ return 0;
+ }
+
+ if ( _gnutls_mpi_get_nbits( peer_cert.params[0])
+ <= 512) {
+ _gnutls_free_cert( peer_cert);
+ return 1;
+ }
+
+ _gnutls_free_cert( peer_cert);
+
+ return 0;
+}
static int proc_rsa_export_server_kx(GNUTLS_STATE state, opaque * data,
int data_size)
@@ -184,15 +243,17 @@ static int proc_rsa_export_server_kx(GNUTLS_STATE state, opaque * data,
int i, sigsize;
gnutls_datum vparams, signature;
int ret;
- CERTIFICATE_AUTH_INFO info = _gnutls_get_auth_info( state);
+ CERTIFICATE_AUTH_INFO info;
gnutls_cert peer_cert;
+ info = _gnutls_get_auth_info( state);
if (info == NULL || info->ncerts==0) {
gnutls_assert();
/* we need this in order to get peer's certificate */
return GNUTLS_E_UNKNOWN_ERROR;
}
+
i = 0;
DECR_LEN( data_size, 2);
diff --git a/lib/gnutls_kx.c b/lib/gnutls_kx.c
index 5ceac92266..2fa4ec6784 100644
--- a/lib/gnutls_kx.c
+++ b/lib/gnutls_kx.c
@@ -34,6 +34,7 @@
#include <gnutls_state.h>
#include <gnutls_datum.h>
#include <gnutls_alert.h>
+#include <gnutls_rsa_export.h>
/* This file contains important thing for the TLS handshake procedure.
*/
@@ -103,6 +104,11 @@ int _gnutls_send_server_kx_message( GNUTLS_STATE state, int again)
if (again == 0) {
data_size = state->gnutls_internals.auth_struct->gnutls_generate_server_kx( state, &data);
+ if (data_size == GNUTLS_E_INT_RET_0) {
+ gnutls_assert();
+ return 0;
+ }
+
if (data_size < 0) {
gnutls_assert();
return data_size;
@@ -302,24 +308,36 @@ int _gnutls_send_client_certificate_verify( GNUTLS_STATE state, int again)
int _gnutls_recv_server_kx_message( GNUTLS_STATE state)
{
- uint8 *data;
+ uint8 *data = NULL;
int datasize;
int ret = 0;
if (state->gnutls_internals.auth_struct->gnutls_process_server_kx!=NULL) {
+ /* EXCEPTION FOR RSA_EXPORT cipher suite
+ */
+ if ( _gnutls_session_is_export( state) != 0 &&
+ _gnutls_peers_cert_less_512(state) != 0) {
+ gnutls_assert();
+ return 0;
+ }
+
ret =
_gnutls_recv_handshake( state, &data,
&datasize,
GNUTLS_SERVER_KEY_EXCHANGE, MANDATORY_PACKET);
- if (ret < 0)
+ if (ret < 0) {
+ gnutls_assert();
return ret;
+ }
ret = state->gnutls_internals.auth_struct->gnutls_process_server_kx( state, data, datasize);
gnutls_free(data);
- if (ret < 0)
+ if (ret < 0) {
+ gnutls_assert();
return ret;
+ }
}
return ret;
diff --git a/lib/gnutls_rsa_export.h b/lib/gnutls_rsa_export.h
index 7bef5e8275..3c0800dacb 100644
--- a/lib/gnutls_rsa_export.h
+++ b/lib/gnutls_rsa_export.h
@@ -19,4 +19,5 @@
*/
const GNUTLS_MPI* _gnutls_get_rsa_params(GNUTLS_RSA_PARAMS, int bits);
+int _gnutls_peers_cert_less_512( GNUTLS_STATE state);
diff --git a/lib/gnutls_state.c b/lib/gnutls_state.c
index 63cb76fa1e..2bd670bd25 100644
--- a/lib/gnutls_state.c
+++ b/lib/gnutls_state.c
@@ -37,6 +37,7 @@
#include <gnutls_state.h>
#include <auth_cert.h>
#include <auth_anon.h>
+#include <gnutls_algorithms.h>
#define CHECK_AUTH(auth, ret) if (gnutls_auth_get_type(state) != auth) { \
gnutls_assert(); \
@@ -693,6 +694,21 @@ int gnutls_session_is_resumed(GNUTLS_STATE state)
return 0;
}
+/*-
+ * _gnutls_session_is_export - Used to check whether this session is of export grade
+ * @state: is a &GNUTLS_STATE structure.
+ *
+ * This function will return non zero if this session is of export grade.
+ *
+ -*/
+int _gnutls_session_is_export(GNUTLS_STATE state)
+{
+ if ( _gnutls_cipher_suite_get_kx_algo( state->security_parameters.current_cipher_suite)
+ == GNUTLS_KX_RSA_EXPORT) return 1;
+
+ return 0;
+}
+
/**
* gnutls_state_get_ptr - Used to get the user pointer from the state structure
* @state: is a &GNUTLS_STATE structure.
diff --git a/lib/gnutls_state.h b/lib/gnutls_state.h
index 36118ca655..bdb0bf27f8 100644
--- a/lib/gnutls_state.h
+++ b/lib/gnutls_state.h
@@ -30,6 +30,7 @@ void _gnutls_handshake_internal_state_clear( GNUTLS_STATE);
int _gnutls_rsa_export_set_modulus_bits( GNUTLS_STATE state, int bits);
int _gnutls_session_is_resumable( GNUTLS_STATE state);
+int _gnutls_session_is_export( GNUTLS_STATE state);
int _gnutls_openpgp_send_fingerprint( GNUTLS_STATE state);