diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/libcharon/plugins/eap_tls/eap_tls.c | 9 | ||||
-rw-r--r-- | src/libcharon/plugins/eap_ttls/eap_ttls.c | 12 | ||||
-rw-r--r-- | src/libtls/tls.c | 33 | ||||
-rw-r--r-- | src/libtls/tls.h | 25 | ||||
-rw-r--r-- | src/libtls/tls_application.h | 1 | ||||
-rw-r--r-- | src/libtls/tls_crypto.c | 44 | ||||
-rw-r--r-- | src/libtls/tls_crypto.h | 4 | ||||
-rw-r--r-- | src/libtls/tls_server.c | 12 | ||||
-rw-r--r-- | src/libtls/tls_server.h | 3 |
9 files changed, 113 insertions, 30 deletions
diff --git a/src/libcharon/plugins/eap_tls/eap_tls.c b/src/libcharon/plugins/eap_tls/eap_tls.c index 8c5680861..fa0babe26 100644 --- a/src/libcharon/plugins/eap_tls/eap_tls.c +++ b/src/libcharon/plugins/eap_tls/eap_tls.c @@ -441,10 +441,13 @@ static eap_tls_t *eap_tls_create(identification_t *server, }, .is_server = is_server, ); - /* MSK PRF ASCII constant label according to EAP-TLS RFC 5216 */ - this->tls = tls_create(is_server, server, peer, TRUE, - "client EAP encryption", NULL); + this->tls = tls_create(is_server, server, peer, TLS_PURPOSE_EAP_TLS, NULL); + if (!this->tls) + { + free(this); + return NULL; + } return &this->public; } diff --git a/src/libcharon/plugins/eap_ttls/eap_ttls.c b/src/libcharon/plugins/eap_ttls/eap_ttls.c index 8ade7caae..80994a37d 100644 --- a/src/libcharon/plugins/eap_ttls/eap_ttls.c +++ b/src/libcharon/plugins/eap_ttls/eap_ttls.c @@ -450,9 +450,15 @@ static eap_ttls_t *eap_ttls_create(identification_t *server, }, .is_server = is_server, ); - /* MSK PRF ASCII constant label according to EAP-TTLS RFC 5281 */ - this->tls = tls_create(is_server, server, peer, FALSE, - "ttls keying material", application); + + this->tls = tls_create(is_server, server, peer, + TLS_PURPOSE_EAP_TTLS, application); + if (!this->tls) + { + application->destroy(application); + free(this); + return NULL; + } return &this->public; } diff --git a/src/libtls/tls.c b/src/libtls/tls.c index e3be79dda..da3b5b4f0 100644 --- a/src/libtls/tls.c +++ b/src/libtls/tls.c @@ -87,6 +87,11 @@ struct private_tls_t { tls_version_t version; /** + * TLS stack purpose, as given to constructor + */ + tls_purpose_t purpose; + + /** * TLS record protection layer */ tls_protection_t *protection; @@ -147,6 +152,12 @@ METHOD(tls_t, set_version, void, this->version = version; } +METHOD(tls_t, get_purpose, tls_purpose_t, + private_tls_t *this) +{ + return this->purpose; +} + METHOD(tls_t, is_complete, bool, private_tls_t *this) { @@ -178,11 +189,20 @@ METHOD(tls_t, destroy, void, * See header */ tls_t *tls_create(bool is_server, identification_t *server, - identification_t *peer, bool request_peer_auth, - char *msk_label, tls_application_t *application) + identification_t *peer, tls_purpose_t purpose, + tls_application_t *application) { private_tls_t *this; + switch (purpose) + { + case TLS_PURPOSE_EAP_TLS: + case TLS_PURPOSE_EAP_TTLS: + break; + default: + return NULL; + } + INIT(this, .public = { .process = _process, @@ -190,6 +210,7 @@ tls_t *tls_create(bool is_server, identification_t *server, .is_server = _is_server, .get_version = _get_version, .set_version = _set_version, + .get_purpose = _get_purpose, .is_complete = _is_complete, .get_eap_msk = _get_eap_msk, .destroy = _destroy, @@ -199,19 +220,19 @@ tls_t *tls_create(bool is_server, identification_t *server, .server = server->clone(server), .peer = peer->clone(peer), .application = application, + .purpose = purpose, ); - this->crypto = tls_crypto_create(&this->public, msk_label); + this->crypto = tls_crypto_create(&this->public); if (is_server) { this->handshake = &tls_server_create(&this->public, this->crypto, - this->server, this->peer, - request_peer_auth)->handshake; + this->server, this->peer)->handshake; } else { this->handshake = &tls_peer_create(&this->public, this->crypto, - this->peer, this->server)->handshake; + this->peer, this->server)->handshake; } this->fragmentation = tls_fragmentation_create(this->handshake, this->application); diff --git a/src/libtls/tls.h b/src/libtls/tls.h index 95ec6011c..6f55075f0 100644 --- a/src/libtls/tls.h +++ b/src/libtls/tls.h @@ -29,6 +29,7 @@ typedef enum tls_version_t tls_version_t; typedef enum tls_content_type_t tls_content_type_t; typedef enum tls_handshake_type_t tls_handshake_type_t; +typedef enum tls_purpose_t tls_purpose_t; typedef struct tls_t tls_t; #include <library.h> @@ -88,6 +89,16 @@ enum tls_handshake_type_t { extern enum_name_t *tls_handshake_type_names; /** + * Purpose the TLS stack is initiated for. + */ +enum tls_purpose_t { + /** authentication in EAP-TLS */ + TLS_PURPOSE_EAP_TLS, + /** outer authentication and protection in EAP-TTLS */ + TLS_PURPOSE_EAP_TTLS, +}; + +/** * A bottom-up driven TLS stack, suitable for EAP implementations. */ struct tls_t { @@ -139,6 +150,13 @@ struct tls_t { void (*set_version)(tls_t *this, tls_version_t version); /** + * Get the purpose of this TLS stack instance. + * + * @return purpose given during construction + */ + tls_purpose_t (*get_purpose)(tls_t *this); + + /** * Check if TLS negotiation completed successfully. * * @return TRUE if TLS negotation and authentication complete @@ -164,13 +182,12 @@ struct tls_t { * @param is_server TRUE to act as server, FALSE for client * @param server server identity * @param peer peer identity - * @param request_peer_auth TRUE to request certificate-based peer authentication - * @param msk_label ASCII string constant used as seed for MSK PRF + * @param purpse purpose this TLS stack instance is used for * @param application higher layer application or NULL if none * @return TLS stack */ tls_t *tls_create(bool is_server, identification_t *server, - identification_t *peer, bool request_peer_auth, - char *msk_label, tls_application_t *application); + identification_t *peer, tls_purpose_t purpose, + tls_application_t *application); #endif /** TLS_H_ @}*/ diff --git a/src/libtls/tls_application.h b/src/libtls/tls_application.h index dacd10ef7..b54a25e22 100644 --- a/src/libtls/tls_application.h +++ b/src/libtls/tls_application.h @@ -23,7 +23,6 @@ typedef struct tls_application_t tls_application_t; -#include "tls.h" #include "tls_reader.h" #include "tls_writer.h" diff --git a/src/libtls/tls_crypto.c b/src/libtls/tls_crypto.c index 90d15cb4d..801a12772 100644 --- a/src/libtls/tls_crypto.c +++ b/src/libtls/tls_crypto.c @@ -440,9 +440,29 @@ static void filter_suite(private_tls_crypto_t *this, } /** + * Purge NULL encryption cipher suites from list + */ +static void filter_null_suites(private_tls_crypto_t *this, + suite_algs_t suites[], int *count) +{ + int i, remaining = 0; + + for (i = 0; i < *count; i++) + { + if (suites[i].encr != ENCR_NULL) + { + suites[remaining] = suites[i]; + remaining++; + } + } + *count = remaining; +} + +/** * Initialize the cipher suite list */ -static void build_cipher_suite_list(private_tls_crypto_t *this) +static void build_cipher_suite_list(private_tls_crypto_t *this, + bool require_encryption) { suite_algs_t suites[countof(suite_algs)]; int count = countof(suite_algs), i; @@ -452,6 +472,10 @@ static void build_cipher_suite_list(private_tls_crypto_t *this) { suites[i] = suite_algs[i]; } + if (require_encryption) + { + filter_null_suites(this, suites, &count); + } /* filter suite list by each algorithm */ filter_suite(this, suites, &count, offsetof(suite_algs_t, encr), lib->crypto->create_crypter_enumerator); @@ -872,7 +896,7 @@ METHOD(tls_crypto_t, destroy, void, /** * See header */ -tls_crypto_t *tls_crypto_create(tls_t *tls, char *msk_label) +tls_crypto_t *tls_crypto_create(tls_t *tls) { private_tls_crypto_t *this; @@ -892,10 +916,20 @@ tls_crypto_t *tls_crypto_create(tls_t *tls, char *msk_label) .destroy = _destroy, }, .tls = tls, - .msk_label = msk_label ); - build_cipher_suite_list(this); - + switch (tls->get_purpose(tls)) + { + case TLS_PURPOSE_EAP_TLS: + /* MSK PRF ASCII constant label according to EAP-TLS RFC 5216 */ + this->msk_label = "client EAP encryption"; + build_cipher_suite_list(this, FALSE); + break; + case TLS_PURPOSE_EAP_TTLS: + /* MSK PRF ASCII constant label according to EAP-TTLS RFC 5281 */ + this->msk_label = "ttls keying material"; + build_cipher_suite_list(this, TRUE); + break; + } return &this->public; } diff --git a/src/libtls/tls_crypto.h b/src/libtls/tls_crypto.h index 09f1a0e8a..5fe90d868 100644 --- a/src/libtls/tls_crypto.h +++ b/src/libtls/tls_crypto.h @@ -359,9 +359,7 @@ struct tls_crypto_t { /** * Create a tls_crypto instance. - * - * @param msk_label ASCII string constant used as seed for MSK PRF */ -tls_crypto_t *tls_crypto_create(tls_t *tls, char *msk_label); +tls_crypto_t *tls_crypto_create(tls_t *tls); #endif /** TLS_CRYPTO_H_ @}*/ diff --git a/src/libtls/tls_server.c b/src/libtls/tls_server.c index 3303365fc..8ff306b24 100644 --- a/src/libtls/tls_server.c +++ b/src/libtls/tls_server.c @@ -629,8 +629,7 @@ METHOD(tls_handshake_t, destroy, void, * See header */ tls_server_t *tls_server_create(tls_t *tls, tls_crypto_t *crypto, - identification_t *server, identification_t *peer, - bool request_peer_auth) + identification_t *server, identification_t *peer) { private_tls_server_t *this; @@ -650,10 +649,17 @@ tls_server_t *tls_server_create(tls_t *tls, tls_crypto_t *crypto, .server = server, .peer = peer, .state = STATE_INIT, - .request_peer_auth = request_peer_auth, .peer_auth = auth_cfg_create(), .server_auth = auth_cfg_create(), ); + switch (tls->get_purpose(tls)) + { + case TLS_PURPOSE_EAP_TLS: + this->request_peer_auth = TRUE; + break; + case TLS_PURPOSE_EAP_TTLS: + break; + } return &this->public; } diff --git a/src/libtls/tls_server.h b/src/libtls/tls_server.h index a15d54f02..6dc26cd3f 100644 --- a/src/libtls/tls_server.h +++ b/src/libtls/tls_server.h @@ -43,7 +43,6 @@ struct tls_server_t { * Create a tls_server instance. */ tls_server_t *tls_server_create(tls_t *tls, tls_crypto_t *crypto, - identification_t *server, identification_t *peer, - bool request_peer_auth); + identification_t *server, identification_t *peer); #endif /** TLS_SERVER_H_ @}*/ |