diff options
author | Martin Willi <martin@revosec.ch> | 2014-03-11 10:57:18 +0100 |
---|---|---|
committer | Martin Willi <martin@revosec.ch> | 2014-03-31 15:56:12 +0200 |
commit | b886dad49865c08c99e97652fe18666289f695d0 (patch) | |
tree | 46cf0da88ae5ce5bd988fb7fddd3f93b017df20f | |
parent | 48d6b57c30f799e1773adbfdd5e1880bab2ab9e4 (diff) | |
download | strongswan-b886dad49865c08c99e97652fe18666289f695d0.tar.bz2 strongswan-b886dad49865c08c99e97652fe18666289f695d0.tar.xz |
tls: Fix AEAD algorithm filtering, avoid filtering all suites if no AEAD found
-rw-r--r-- | src/libtls/tls_crypto.c | 71 |
1 files changed, 52 insertions, 19 deletions
diff --git a/src/libtls/tls_crypto.c b/src/libtls/tls_crypto.c index a4e24543b..c1ed57ae6 100644 --- a/src/libtls/tls_crypto.c +++ b/src/libtls/tls_crypto.c @@ -648,7 +648,7 @@ static suite_algs_t *find_suite(tls_cipher_suite_t suite) /** * Filter a suite list using a transform enumerator */ -static void filter_suite(private_tls_crypto_t *this, bool aead, +static void filter_suite(private_tls_crypto_t *this, suite_algs_t suites[], int *count, int offset, enumerator_t*(*create_enumerator)(crypto_factory_t*)) { @@ -662,23 +662,56 @@ static void filter_suite(private_tls_crypto_t *this, bool aead, for (i = 0; i < *count; i++) { + if (create_enumerator == lib->crypto->create_crypter_enumerator && + encryption_algorithm_is_aead(suites[i].encr)) + { /* filtering crypters, but current suite uses an AEAD, apply */ + suites[remaining] = suites[i]; + remaining++; + continue; + } + if (create_enumerator == lib->crypto->create_aead_enumerator && + !encryption_algorithm_is_aead(suites[i].encr)) + { /* filtering AEADs, but current suite doesn't use one, apply */ + suites[remaining] = suites[i]; + remaining++; + continue; + } enumerator = create_enumerator(lib->crypto); while (enumerator->enumerate(enumerator, current_alg, &plugin_name)) { - if ((suites[i].encr == ENCR_NULL || - aead != encryption_algorithm_is_aead(suites[i].encr) || - !current.encr || current.encr == suites[i].encr) && - (suites[i].mac == AUTH_UNDEFINED || - !current.mac || current.mac == suites[i].mac) && - (!current.prf || current.prf == suites[i].prf) && - (!current.hash || current.hash == suites[i].hash) && - (suites[i].dh == MODP_NONE || - !current.dh || current.dh == suites[i].dh)) + if (current.encr && current.encr != suites[i].encr) { - suites[remaining] = suites[i]; - remaining++; - break; + if (suites[i].encr != ENCR_NULL) + { /* skip, ENCR does not match nor is NULL */ + continue; + } } + if (current.mac && current.mac != suites[i].mac) + { + if (suites[i].mac != AUTH_UNDEFINED) + { /* skip, MAC does not match nor is it undefined */ + continue; + } + } + if (current.prf && current.prf != suites[i].prf) + { /* skip, PRF does not match */ + continue; + } + if (current.hash && current.hash != suites[i].hash) + { /* skip, hash does not match */ + continue; + } + if (current.dh && current.dh != suites[i].dh) + { + if (suites[i].dh != MODP_NONE) + { /* skip DH group, does not match nor NONE */ + continue; + } + } + /* suite supported, apply */ + suites[remaining] = suites[i]; + remaining++; + break; } enumerator->destroy(enumerator); } @@ -969,17 +1002,17 @@ static void build_cipher_suite_list(private_tls_crypto_t *this, } /* filter suite list by each algorithm */ - filter_suite(this, FALSE, suites, &count, offsetof(suite_algs_t, encr), + filter_suite(this, suites, &count, offsetof(suite_algs_t, encr), lib->crypto->create_crypter_enumerator); - filter_suite(this, TRUE, suites, &count, offsetof(suite_algs_t, encr), + filter_suite(this, suites, &count, offsetof(suite_algs_t, encr), lib->crypto->create_aead_enumerator); - filter_suite(this, FALSE, suites, &count, offsetof(suite_algs_t, mac), + filter_suite(this, suites, &count, offsetof(suite_algs_t, mac), lib->crypto->create_signer_enumerator); - filter_suite(this, FALSE, suites, &count, offsetof(suite_algs_t, prf), + filter_suite(this, suites, &count, offsetof(suite_algs_t, prf), lib->crypto->create_prf_enumerator); - filter_suite(this, FALSE, suites, &count, offsetof(suite_algs_t, hash), + filter_suite(this, suites, &count, offsetof(suite_algs_t, hash), lib->crypto->create_hasher_enumerator); - filter_suite(this, FALSE, suites, &count, offsetof(suite_algs_t, dh), + filter_suite(this, suites, &count, offsetof(suite_algs_t, dh), lib->crypto->create_dh_enumerator); /* filter suites with strongswan.conf options */ |