summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorNikos Mavrogiannopoulos <nmav@gnutls.org>2011-03-19 12:07:51 +0100
committerNikos Mavrogiannopoulos <nmav@gnutls.org>2011-03-19 12:22:50 +0100
commit54ff765c05e88103d39edf79dada728896a3184e (patch)
treec27ac898e59228470021a5418d0bd0ed4a604f9b
parentccdb0059b8a43e8e15b2380e8003e95236cabfa6 (diff)
downloadgnutls-54ff765c05e88103d39edf79dada728896a3184e.tar.gz
Return a special error code if DSA keys with over 1024 are being used with TLS 1.x, x<2.
-rw-r--r--lib/gnutls_alert.c1
-rw-r--r--lib/gnutls_errors.c2
-rw-r--r--lib/gnutls_sig.c17
-rw-r--r--lib/includes/gnutls/gnutls.h.in1
4 files changed, 12 insertions, 9 deletions
diff --git a/lib/gnutls_alert.c b/lib/gnutls_alert.c
index 2f65d19ab0..affdff2c85 100644
--- a/lib/gnutls_alert.c
+++ b/lib/gnutls_alert.c
@@ -209,6 +209,7 @@ gnutls_error_to_alert (int err, int *level)
case GNUTLS_E_NO_COMPRESSION_ALGORITHMS:
case GNUTLS_E_UNSUPPORTED_SIGNATURE_ALGORITHM:
case GNUTLS_E_SAFE_RENEGOTIATION_FAILED:
+ case GNUTLS_E_INCOMPAT_DSA_KEY_WITH_TLS_PROTOCOL:
ret = GNUTLS_A_HANDSHAKE_FAILURE;
_level = GNUTLS_AL_FATAL;
break;
diff --git a/lib/gnutls_errors.c b/lib/gnutls_errors.c
index 1e297c02be..137a590cd9 100644
--- a/lib/gnutls_errors.c
+++ b/lib/gnutls_errors.c
@@ -92,6 +92,8 @@ static const gnutls_error_entry error_algorithms[] = {
GNUTLS_E_ERROR_IN_FINISHED_PACKET, 1),
ERROR_ENTRY (N_("The peer did not send any certificate."),
GNUTLS_E_NO_CERTIFICATE_FOUND, 1),
+ ERROR_ENTRY (N_("The given DSA key is incompatible with the selected TLS protocol."),
+ GNUTLS_E_INCOMPAT_DSA_KEY_WITH_TLS_PROTOCOL, 1),
ERROR_ENTRY (N_("There is already a crypto algorithm with lower priority."),
GNUTLS_E_CRYPTO_ALREADY_REGISTERED, 1),
diff --git a/lib/gnutls_sig.c b/lib/gnutls_sig.c
index 2c195b995d..3e72a68154 100644
--- a/lib/gnutls_sig.c
+++ b/lib/gnutls_sig.c
@@ -65,16 +65,15 @@ int ret;
if (cert->subject_pk_algorithm == GNUTLS_PK_DSA)
{ /* override */
- if (!_gnutls_version_has_selectable_sighash (version))
- *hash_algo = GNUTLS_DIG_SHA1;
- else
- {
- *hash_algo = _gnutls_dsa_q_to_hash (cert->params[1]);
+ *hash_algo = _gnutls_dsa_q_to_hash (cert->params[1]);
- ret = _gnutls_session_sign_algo_requested(session, _gnutls_x509_pk_to_sign (GNUTLS_PK_DSA, *hash_algo));
- if (ret < 0)
- return gnutls_assert_val(ret);
- }
+ /* DSA keys over 1024 bits cannot be used with TLS 1.x, x<2 */
+ if (!_gnutls_version_has_selectable_sighash (version) && *hash_algo != GNUTLS_DIG_SHA1)
+ return gnutls_assert_val(GNUTLS_E_INCOMPAT_DSA_KEY_WITH_TLS_PROTOCOL);
+
+ ret = _gnutls_session_sign_algo_requested(session, _gnutls_x509_pk_to_sign (GNUTLS_PK_DSA, *hash_algo));
+ if (ret < 0)
+ return gnutls_assert_val(ret);
}
else
{
diff --git a/lib/includes/gnutls/gnutls.h.in b/lib/includes/gnutls/gnutls.h.in
index faa33901c1..ee5da9e044 100644
--- a/lib/includes/gnutls/gnutls.h.in
+++ b/lib/includes/gnutls/gnutls.h.in
@@ -1730,6 +1730,7 @@ extern "C"
#define GNUTLS_E_CHANNEL_BINDING_NOT_AVAILABLE -213
#define GNUTLS_E_OPENPGP_PREFERRED_KEY_ERROR -215
+#define GNUTLS_E_INCOMPAT_DSA_KEY_WITH_TLS_PROTOCOL -216
/* PKCS11 related */
#define GNUTLS_E_PKCS11_ERROR -300