mbedtls: add CURLOPT_TLS13_CIPHERS support

Bring setting ciphers with mbedTLS in line with other SSL backends,
to make the curl interface more consistent across the backends.

Now the tls1.3 ciphers are set with the --tls13-ciphers option, when
not set the default tls1.3 ciphers are used. The tls1.2 (1.1, 1.0)
ciphers are set with the --ciphers option, when not set the default
tls1.2 ciphers are used. The ciphers available for the connection
are now a union of the tls1.3 and tls1.2 ciphers.

This changes the behaviour for mbedTLS when --ciphers is set, but
--tls13-ciphers is not set. Now the ciphers set with --ciphers
are combined with the default tls1.3 ciphers, whereas before solely
the ciphers of --ciphers were used.

Thus before when no tls1.3 ciphers were specified in --ciphers,
tls1.3 was completely disabled. This might not be what the user
expected, especially as this does not happen with OpenSSL.

Closes #14384
This commit is contained in:
Jan Venekamp 2024-08-04 20:06:27 +02:00 committed by Daniel Stenberg
parent d266d19d86
commit 3f7dc8a404
No known key found for this signature in database
GPG Key ID: 5CC908FDB71E12C2
2 changed files with 64 additions and 9 deletions

View File

@ -429,11 +429,13 @@ mbed_cipher_suite_walk_str(const char **str, const char **end)
static CURLcode
mbed_set_selected_ciphers(struct Curl_easy *data,
struct mbed_ssl_backend_data *backend,
const char *ciphers)
const char *ciphers12,
const char *ciphers13)
{
const char *ciphers = ciphers12;
const int *supported;
int *selected;
size_t supported_len, count = 0, i;
size_t supported_len, count = 0, default13_count = 0, i, j;
const char *ptr, *end;
supported = mbedtls_ssl_list_ciphersuites();
@ -444,6 +446,26 @@ mbed_set_selected_ciphers(struct Curl_easy *data,
if(!selected)
return CURLE_OUT_OF_MEMORY;
#ifndef TLS13_SUPPORT
(void) ciphers13, (void) j;
#else
if(!ciphers13) {
/* Add default TLSv1.3 ciphers to selection */
for(j = 0; j < supported_len; j++) {
uint16_t id = (uint16_t) supported[j];
if(strncmp(mbedtls_ssl_get_ciphersuite_name(id), "TLS1-3", 6) != 0)
continue;
selected[count++] = id;
}
default13_count = count;
}
else
ciphers = ciphers13;
add_ciphers:
#endif
for(ptr = ciphers; ptr[0] != '\0' && count < supported_len; ptr = end) {
uint16_t id = mbed_cipher_suite_walk_str(&ptr, &end);
@ -463,14 +485,38 @@ mbed_set_selected_ciphers(struct Curl_easy *data,
/* No duplicates allowed (so selected cannot overflow) */
for(i = 0; i < count && selected[i] != id; i++);
if(i < count) {
infof(data, "mbedTLS: duplicate cipher in list: \"%.*s\"",
(int) (end - ptr), ptr);
if(i >= default13_count)
infof(data, "mbedTLS: duplicate cipher in list: \"%.*s\"",
(int) (end - ptr), ptr);
continue;
}
selected[count++] = id;
}
#ifdef TLS13_SUPPORT
if(ciphers == ciphers13 && ciphers12) {
ciphers = ciphers12;
goto add_ciphers;
}
if(!ciphers12) {
/* Add default TLSv1.2 ciphers to selection */
for(j = 0; j < supported_len; j++) {
uint16_t id = (uint16_t) supported[j];
if(strncmp(mbedtls_ssl_get_ciphersuite_name(id), "TLS1-3", 6) == 0)
continue;
/* No duplicates allowed (so selected cannot overflow) */
for(i = 0; i < count && selected[i] != id; i++);
if(i < count)
continue;
selected[count++] = id;
}
}
#endif
selected[count] = 0;
if(count == 0) {
@ -814,9 +860,17 @@ mbed_connect_step1(struct Curl_cfilter *cf, struct Curl_easy *data)
mbedtls_bio_cf_read,
NULL /* rev_timeout() */);
#ifndef TLS13_SUPPORT
if(conn_config->cipher_list) {
CURLcode result = mbed_set_selected_ciphers(data, backend,
conn_config->cipher_list);
conn_config->cipher_list,
NULL);
#else
if(conn_config->cipher_list || conn_config->cipher_list13) {
CURLcode result = mbed_set_selected_ciphers(data, backend,
conn_config->cipher_list,
conn_config->cipher_list13);
#endif
if(result != CURLE_OK) {
failf(data, "mbedTLS: failed to set cipher suites");
return result;
@ -1669,6 +1723,9 @@ const struct Curl_ssl Curl_ssl_mbedtls = {
SSLSUPP_CERTINFO |
SSLSUPP_PINNEDPUBKEY |
SSLSUPP_SSL_CTX |
#ifdef TLS13_SUPPORT
SSLSUPP_TLS13_CIPHERSUITES |
#endif
SSLSUPP_HTTPS_PROXY,
sizeof(struct mbed_ssl_backend_data),

View File

@ -213,10 +213,8 @@ class TestSSLUse:
pytest.skip('SecureTransport does not support TLSv1.3')
elif env.curl_uses_lib('boringssl'):
pytest.skip('BoringSSL does not support setting TLSv1.3 ciphers')
elif env.curl_uses_lib('mbedtls'):
if not env.curl_lib_version_at_least('mbedtls', '3.6.0'):
pytest.skip('mbedTLS TLSv1.3 support requires at least 3.6.0')
extra_args = ['--ciphers', ':'.join(cipher_names)]
elif env.curl_uses_lib('mbedtls') and not env.curl_lib_version_at_least('mbedtls', '3.6.0'):
pytest.skip('mbedTLS TLSv1.3 support requires at least 3.6.0')
elif env.curl_uses_lib('wolfssl'):
extra_args = ['--ciphers', ':'.join(cipher_names)]
else: