From e4f5bf6e779c153d9063805be81c547584398f7a Mon Sep 17 00:00:00 2001 From: Lindsay Stewart Date: Mon, 23 Oct 2023 09:28:41 -0700 Subject: [PATCH] Clean up sending supported sig algs (#4254) --- ...ient_signature_algorithms_extension_test.c | 3 +- ...rver_signature_algorithms_extension_test.c | 2 +- tests/unit/s2n_signature_algorithms_test.c | 217 +++++++----------- tests/unit/s2n_tls13_cert_request_test.c | 2 +- .../s2n_client_signature_algorithms.c | 9 +- .../s2n_server_signature_algorithms.c | 9 +- tls/s2n_server_cert_request.c | 2 +- tls/s2n_signature_algorithms.c | 59 ++--- tls/s2n_signature_algorithms.h | 5 +- 9 files changed, 126 insertions(+), 182 deletions(-) diff --git a/tests/unit/s2n_client_signature_algorithms_extension_test.c b/tests/unit/s2n_client_signature_algorithms_extension_test.c index 7461d8aa126..817e66b3188 100644 --- a/tests/unit/s2n_client_signature_algorithms_extension_test.c +++ b/tests/unit/s2n_client_signature_algorithms_extension_test.c @@ -64,8 +64,7 @@ int main(int argc, char **argv) EXPECT_SUCCESS(s2n_client_signature_algorithms_extension.recv(server_conn, &io)); EXPECT_EQUAL(s2n_stuffer_data_available(&io), 0); - EXPECT_EQUAL(server_conn->handshake_params.client_sig_hash_algs.len, - s2n_supported_sig_schemes_count(client_conn)); + EXPECT_TRUE(server_conn->handshake_params.client_sig_hash_algs.len > 0); s2n_stuffer_free(&io); s2n_connection_free(client_conn); diff --git a/tests/unit/s2n_server_signature_algorithms_extension_test.c b/tests/unit/s2n_server_signature_algorithms_extension_test.c index d80c7db0ac7..7ecfd7786ad 100644 --- a/tests/unit/s2n_server_signature_algorithms_extension_test.c +++ b/tests/unit/s2n_server_signature_algorithms_extension_test.c @@ -44,7 +44,7 @@ int main(int argc, char **argv) EXPECT_SUCCESS(s2n_server_signature_algorithms_extension.recv(client_conn, &io)); EXPECT_EQUAL(s2n_stuffer_data_available(&io), 0); - EXPECT_EQUAL(client_conn->handshake_params.server_sig_hash_algs.len, s2n_supported_sig_schemes_count(server_conn)); + EXPECT_TRUE(client_conn->handshake_params.server_sig_hash_algs.len > 0); s2n_stuffer_free(&io); EXPECT_SUCCESS(s2n_connection_free(server_conn)); diff --git a/tests/unit/s2n_signature_algorithms_test.c b/tests/unit/s2n_signature_algorithms_test.c index d31f9fe99c6..a17bc97d76c 100644 --- a/tests/unit/s2n_signature_algorithms_test.c +++ b/tests/unit/s2n_signature_algorithms_test.c @@ -61,149 +61,105 @@ int main(int argc, char **argv) struct s2n_cert_chain_and_key *certs[] = { ecdsa_cert_chain, rsa_cert_chain }; - /* s2n_supported_sig_schemes_count & s2n_supported_sig_scheme_list_size */ + /* s2n_signature_algorithms_supported_list_send */ { - struct s2n_config *config = s2n_config_new(); - - struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT); - s2n_connection_set_config(conn, config); - - const struct s2n_security_policy *security_policy = NULL; - EXPECT_SUCCESS(s2n_connection_get_security_policy(conn, &security_policy)); - EXPECT_NOT_NULL(security_policy); - - struct s2n_security_policy test_security_policy = { - .minimum_protocol_version = security_policy->minimum_protocol_version, - .cipher_preferences = security_policy->cipher_preferences, - .kem_preferences = security_policy->kem_preferences, - .signature_preferences = &test_preferences, - .ecc_preferences = security_policy->ecc_preferences, - }; - - config->security_policy = &test_security_policy; - - /* Test: if all signatures supported, count all signatures */ - { - conn->actual_protocol_version = S2N_TLS13; - EXPECT_EQUAL(s2n_supported_sig_schemes_count(conn), LENGTH); - EXPECT_EQUAL(s2n_supported_sig_scheme_list_size(conn), LENGTH * TLS_SIGNATURE_SCHEME_LEN); - }; - - /* Test: if some signatures are not supported, exclude them from the count */ - { - conn->actual_protocol_version = S2N_TLS10; - /* Do not include s2n_ecdsa_secp384r1_sha384, which has a minimum version of tls13 */ - EXPECT_EQUAL(s2n_supported_sig_schemes_count(conn), LENGTH - 1); - EXPECT_EQUAL(s2n_supported_sig_scheme_list_size(conn), (LENGTH - 1) * TLS_SIGNATURE_SCHEME_LEN); - }; - - s2n_connection_free(conn); - s2n_config_free(config); - }; - - /* s2n_send_supported_sig_scheme_list */ - { - struct s2n_config *config = s2n_config_new(); - - struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT); - s2n_connection_set_config(conn, config); - - const struct s2n_security_policy *security_policy = NULL; - EXPECT_SUCCESS(s2n_connection_get_security_policy(conn, &security_policy)); - EXPECT_NOT_NULL(security_policy); - - struct s2n_security_policy test_security_policy = { - .minimum_protocol_version = security_policy->minimum_protocol_version, - .cipher_preferences = security_policy->cipher_preferences, - .kem_preferences = security_policy->kem_preferences, - .signature_preferences = &test_preferences, - .ecc_preferences = security_policy->ecc_preferences, - }; - - config->security_policy = &test_security_policy; - - struct s2n_stuffer result = { 0 }; - s2n_stuffer_growable_alloc(&result, STUFFER_SIZE); - - uint16_t size, iana_value; + struct s2n_security_policy test_security_policy = *s2n_fetch_default_config()->security_policy; + test_security_policy.signature_preferences = &test_preferences; /* Test: if all signatures supported, send all signatures */ { - s2n_stuffer_wipe(&result); - + DEFER_CLEANUP(struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT), + s2n_connection_ptr_free); + EXPECT_NOT_NULL(conn); + conn->security_policy_override = &test_security_policy; conn->actual_protocol_version = S2N_TLS13; - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); + + uint16_t size = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &size)); - EXPECT_EQUAL(size, s2n_supported_sig_scheme_list_size(conn)); + EXPECT_EQUAL(size, s2n_stuffer_data_available(&result)); - for (int i = 0; i < LENGTH; i++) { + for (size_t i = 0; i < s2n_array_len(test_signature_schemes); i++) { + uint16_t iana_value = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &iana_value)); EXPECT_EQUAL(iana_value, test_signature_schemes[i]->iana_value); } - EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); }; /* Test: do not send unsupported signatures */ { - s2n_stuffer_wipe(&result); - + DEFER_CLEANUP(struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT), + s2n_connection_ptr_free); + EXPECT_NOT_NULL(conn); + conn->security_policy_override = &test_security_policy; conn->actual_protocol_version = S2N_TLS12; - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); + + uint16_t size = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &size)); - EXPECT_EQUAL(size, s2n_supported_sig_scheme_list_size(conn)); + EXPECT_EQUAL(size, s2n_stuffer_data_available(&result)); - for (int i = 0; i < LENGTH; i++) { + for (size_t i = 0; i < s2n_array_len(test_signature_schemes); i++) { if (test_signature_schemes[i] != &s2n_ecdsa_secp384r1_sha384) { + uint16_t iana_value = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &iana_value)); EXPECT_EQUAL(iana_value, test_signature_schemes[i]->iana_value); } } - EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); - } + }; /* Test: written signatures readable */ { - s2n_stuffer_wipe(&result); + DEFER_CLEANUP(struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT), + s2n_connection_ptr_free); + EXPECT_NOT_NULL(conn); + conn->security_policy_override = &test_security_policy; conn->actual_protocol_version = S2N_TLS13; - struct s2n_sig_scheme_list signatures; + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); + struct s2n_sig_scheme_list signatures = { 0 }; EXPECT_SUCCESS(s2n_recv_supported_sig_scheme_list(&result, &signatures)); EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); - EXPECT_EQUAL(signatures.len, LENGTH); - for (int i = 0; i < LENGTH; i++) { + EXPECT_EQUAL(signatures.len, s2n_array_len(test_signature_schemes)); + for (size_t i = 0; i < s2n_array_len(test_signature_schemes); i++) { EXPECT_EQUAL(signatures.iana_list[i], test_signature_schemes[i]->iana_value); } }; /* Test: do not send TLS1.2 signature schemes if QUIC enabled */ { - s2n_stuffer_wipe(&result); - config->quic_enabled = true; - + DEFER_CLEANUP(struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT), + s2n_connection_ptr_free); + EXPECT_NOT_NULL(conn); + conn->security_policy_override = &test_security_policy; conn->actual_protocol_version = S2N_TLS13; - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); + conn->quic_enabled = true; + + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); + uint16_t size = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &size)); - EXPECT_TRUE(size > 0); - EXPECT_EQUAL(size, s2n_supported_sig_scheme_list_size(conn)); + EXPECT_EQUAL(size, s2n_stuffer_data_available(&result)); + uint16_t iana_value = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &iana_value)); EXPECT_EQUAL(iana_value, s2n_ecdsa_secp384r1_sha384.iana_value); EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); - - config->quic_enabled = false; - } - - s2n_connection_free(conn); - s2n_config_free(config); - s2n_stuffer_free(&result); + }; }; /* s2n_get_and_validate_negotiated_signature_scheme */ @@ -689,41 +645,33 @@ int main(int argc, char **argv) }; /* Test: send and receive default signature preferences */ - { - struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT); - - struct s2n_stuffer result = { 0 }; - s2n_stuffer_growable_alloc(&result, STUFFER_SIZE); - - struct s2n_sig_scheme_list signatures; - - for (int i = S2N_TLS10; i < S2N_TLS13; i++) { - s2n_stuffer_wipe(&result); - conn->actual_protocol_version = i; - - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); - EXPECT_SUCCESS(s2n_recv_supported_sig_scheme_list(&result, &signatures)); - EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); - - EXPECT_EQUAL(signatures.len, s2n_supported_sig_schemes_count(conn)); - - /* Verify no duplicates - some preferences contain duplicates, but only - * one should be valid at a time. */ - uint16_t iana, other_iana; - for (int a = 0; a < signatures.len; a++) { - iana = signatures.iana_list[a]; - for (int b = 0; b < signatures.len; b++) { - if (a == b) { - continue; - } - other_iana = signatures.iana_list[b]; - EXPECT_NOT_EQUAL(iana, other_iana); + for (size_t i = S2N_TLS10; i < S2N_TLS13; i++) { + DEFER_CLEANUP(struct s2n_connection *conn = s2n_connection_new(S2N_CLIENT), + s2n_connection_ptr_free); + EXPECT_NOT_NULL(conn); + conn->actual_protocol_version = i; + + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); + + struct s2n_sig_scheme_list signatures = { 0 }; + EXPECT_SUCCESS(s2n_recv_supported_sig_scheme_list(&result, &signatures)); + EXPECT_EQUAL(s2n_stuffer_data_available(&result), 0); + + /* Verify no duplicates - some preferences contain duplicates, but only + * one should be valid at a time. */ + uint16_t iana = 0, other_iana = 0; + for (size_t a = 0; a < signatures.len; a++) { + iana = signatures.iana_list[a]; + for (int b = 0; b < signatures.len; b++) { + if (a == b) { + continue; } + other_iana = signatures.iana_list[b]; + EXPECT_NOT_EQUAL(iana, other_iana); } } - - s2n_connection_free(conn); - s2n_stuffer_free(&result); }; /* Test: libcrypto may not support PSS signatures */ @@ -761,16 +709,15 @@ int main(int argc, char **argv) config->security_policy = &test_security_policy; /* Do not offer PSS signatures schemes if unsupported: - * s2n_send_supported_sig_scheme_list + PSS */ + * s2n_signature_algorithms_supported_list_send + PSS */ { - struct s2n_stuffer result = { 0 }; - s2n_stuffer_growable_alloc(&result, STUFFER_SIZE); + DEFER_CLEANUP(struct s2n_stuffer result = { 0 }, s2n_stuffer_free); + EXPECT_SUCCESS(s2n_stuffer_growable_alloc(&result, 0)); + EXPECT_OK(s2n_signature_algorithms_supported_list_send(conn, &result)); - EXPECT_SUCCESS(s2n_send_supported_sig_scheme_list(conn, &result)); - - uint16_t size; + uint16_t size = 0; EXPECT_SUCCESS(s2n_stuffer_read_uint16(&result, &size)); - EXPECT_EQUAL(size, s2n_supported_sig_scheme_list_size(conn)); + EXPECT_EQUAL(size, s2n_stuffer_data_available(&result)); if (s2n_is_rsa_pss_certs_supported()) { EXPECT_EQUAL(size, 2 * sizeof(uint16_t)); } else if (s2n_is_rsa_pss_signing_supported()) { @@ -778,8 +725,6 @@ int main(int argc, char **argv) } else { EXPECT_EQUAL(size, 0); } - - s2n_stuffer_free(&result); }; /* Do not accept a PSS signature scheme if unsupported: diff --git a/tests/unit/s2n_tls13_cert_request_test.c b/tests/unit/s2n_tls13_cert_request_test.c index 80c6287608f..6d51b8df75c 100644 --- a/tests/unit/s2n_tls13_cert_request_test.c +++ b/tests/unit/s2n_tls13_cert_request_test.c @@ -69,7 +69,7 @@ int main(int argc, char **argv) EXPECT_TRUE(s2n_stuffer_data_available(&client_conn->handshake.io) > 0); EXPECT_SUCCESS(s2n_tls13_cert_req_recv(client_conn)); - EXPECT_EQUAL(client_conn->handshake_params.server_sig_hash_algs.len, s2n_supported_sig_schemes_count(server_conn)); + EXPECT_TRUE(client_conn->handshake_params.server_sig_hash_algs.len > 0); EXPECT_SUCCESS(s2n_connection_free(client_conn)); EXPECT_SUCCESS(s2n_connection_free(server_conn)); diff --git a/tls/extensions/s2n_client_signature_algorithms.c b/tls/extensions/s2n_client_signature_algorithms.c index 876b8a72ad1..c1f06daf2e6 100644 --- a/tls/extensions/s2n_client_signature_algorithms.c +++ b/tls/extensions/s2n_client_signature_algorithms.c @@ -24,12 +24,13 @@ #include "utils/s2n_safety.h" static bool s2n_client_signature_algorithms_should_send(struct s2n_connection *conn); +static int s2n_client_signature_algorithms_send(struct s2n_connection *conn, struct s2n_stuffer *extension); static int s2n_client_signature_algorithms_recv(struct s2n_connection *conn, struct s2n_stuffer *extension); const s2n_extension_type s2n_client_signature_algorithms_extension = { .iana_value = TLS_EXTENSION_SIGNATURE_ALGORITHMS, .is_response = false, - .send = s2n_send_supported_sig_scheme_list, + .send = s2n_client_signature_algorithms_send, .recv = s2n_client_signature_algorithms_recv, .should_send = s2n_client_signature_algorithms_should_send, .if_missing = s2n_extension_noop_if_missing, @@ -40,6 +41,12 @@ static bool s2n_client_signature_algorithms_should_send(struct s2n_connection *c return s2n_connection_get_protocol_version(conn) >= S2N_TLS12; } +static int s2n_client_signature_algorithms_send(struct s2n_connection *conn, struct s2n_stuffer *extension) +{ + POSIX_GUARD_RESULT(s2n_signature_algorithms_supported_list_send(conn, extension)); + return S2N_SUCCESS; +} + static int s2n_client_signature_algorithms_recv(struct s2n_connection *conn, struct s2n_stuffer *extension) { return s2n_recv_supported_sig_scheme_list(extension, &conn->handshake_params.client_sig_hash_algs); diff --git a/tls/extensions/s2n_server_signature_algorithms.c b/tls/extensions/s2n_server_signature_algorithms.c index b8903f2da21..7599a58a984 100644 --- a/tls/extensions/s2n_server_signature_algorithms.c +++ b/tls/extensions/s2n_server_signature_algorithms.c @@ -24,17 +24,24 @@ #include "tls/s2n_tls_parameters.h" #include "utils/s2n_safety.h" +static int s2n_signature_algorithms_send(struct s2n_connection *conn, struct s2n_stuffer *extension); static int s2n_signature_algorithms_recv(struct s2n_connection *conn, struct s2n_stuffer *extension); const s2n_extension_type s2n_server_signature_algorithms_extension = { .iana_value = TLS_EXTENSION_SIGNATURE_ALGORITHMS, .is_response = false, - .send = s2n_send_supported_sig_scheme_list, + .send = s2n_signature_algorithms_send, .recv = s2n_signature_algorithms_recv, .should_send = s2n_extension_always_send, .if_missing = s2n_extension_error_if_missing, }; +static int s2n_signature_algorithms_send(struct s2n_connection *conn, struct s2n_stuffer *extension) +{ + POSIX_GUARD_RESULT(s2n_signature_algorithms_supported_list_send(conn, extension)); + return S2N_SUCCESS; +} + static int s2n_signature_algorithms_recv(struct s2n_connection *conn, struct s2n_stuffer *extension) { return s2n_recv_supported_sig_scheme_list(extension, &conn->handshake_params.server_sig_hash_algs); diff --git a/tls/s2n_server_cert_request.c b/tls/s2n_server_cert_request.c index 65de1e5471f..f838188f2e7 100644 --- a/tls/s2n_server_cert_request.c +++ b/tls/s2n_server_cert_request.c @@ -172,7 +172,7 @@ int s2n_cert_req_send(struct s2n_connection *conn) } if (conn->actual_protocol_version == S2N_TLS12) { - POSIX_GUARD(s2n_send_supported_sig_scheme_list(conn, out)); + POSIX_GUARD_RESULT(s2n_signature_algorithms_supported_list_send(conn, out)); } /* RFC 5246 7.4.4 - If the certificate_authorities list is empty, then the diff --git a/tls/s2n_signature_algorithms.c b/tls/s2n_signature_algorithms.c index 08b8e3650f4..532f504db75 100644 --- a/tls/s2n_signature_algorithms.c +++ b/tls/s2n_signature_algorithms.c @@ -26,27 +26,31 @@ #include "tls/s2n_signature_scheme.h" #include "utils/s2n_safety.h" -static int s2n_signature_scheme_valid_to_offer(struct s2n_connection *conn, const struct s2n_signature_scheme *scheme) +static S2N_RESULT s2n_signature_scheme_validate_for_send(struct s2n_connection *conn, + const struct s2n_signature_scheme *scheme) { - POSIX_ENSURE_REF(conn); + RESULT_ENSURE_REF(conn); - /* We don't know what protocol version we will eventually negotiate, but we know that it won't be any higher. */ - POSIX_ENSURE_GTE(conn->actual_protocol_version, scheme->minimum_protocol_version); + /* If no protocol has been negotiated yet, the actual_protocol_version will + * be equivalent to the client_protocol_version and represent the highest + * version supported. + */ + RESULT_ENSURE_GTE(conn->actual_protocol_version, scheme->minimum_protocol_version); /* QUIC only supports TLS1.3 */ if (s2n_connection_is_quic_enabled(conn) && scheme->maximum_protocol_version) { - POSIX_ENSURE_GTE(scheme->maximum_protocol_version, S2N_TLS13); + RESULT_ENSURE_GTE(scheme->maximum_protocol_version, S2N_TLS13); } if (!s2n_is_rsa_pss_signing_supported()) { - POSIX_ENSURE_NE(scheme->sig_alg, S2N_SIGNATURE_RSA_PSS_RSAE); + RESULT_ENSURE_NE(scheme->sig_alg, S2N_SIGNATURE_RSA_PSS_RSAE); } if (!s2n_is_rsa_pss_certs_supported()) { - POSIX_ENSURE_NE(scheme->sig_alg, S2N_SIGNATURE_RSA_PSS_PSS); + RESULT_ENSURE_NE(scheme->sig_alg, S2N_SIGNATURE_RSA_PSS_PSS); } - return 0; + return S2N_RESULT_OK; } static int s2n_signature_scheme_valid_to_accept(struct s2n_connection *conn, const struct s2n_signature_scheme *scheme) @@ -54,7 +58,7 @@ static int s2n_signature_scheme_valid_to_accept(struct s2n_connection *conn, con POSIX_ENSURE_REF(scheme); POSIX_ENSURE_REF(conn); - POSIX_GUARD(s2n_signature_scheme_valid_to_offer(conn, scheme)); + POSIX_GUARD_RESULT(s2n_signature_scheme_validate_for_send(conn, scheme)); if (scheme->maximum_protocol_version != S2N_UNKNOWN_PROTOCOL_VERSION) { POSIX_ENSURE_LTE(conn->actual_protocol_version, scheme->maximum_protocol_version); @@ -246,42 +250,25 @@ int s2n_choose_sig_scheme_from_peer_preference_list(struct s2n_connection *conn, return S2N_SUCCESS; } -int s2n_send_supported_sig_scheme_list(struct s2n_connection *conn, struct s2n_stuffer *out) +S2N_RESULT s2n_signature_algorithms_supported_list_send(struct s2n_connection *conn, struct s2n_stuffer *out) { const struct s2n_signature_preferences *signature_preferences = NULL; - POSIX_GUARD(s2n_connection_get_signature_preferences(conn, &signature_preferences)); - POSIX_ENSURE_REF(signature_preferences); + RESULT_GUARD_POSIX(s2n_connection_get_signature_preferences(conn, &signature_preferences)); + RESULT_ENSURE_REF(signature_preferences); - POSIX_GUARD(s2n_stuffer_write_uint16(out, s2n_supported_sig_scheme_list_size(conn))); + struct s2n_stuffer_reservation size = { 0 }; + RESULT_GUARD_POSIX(s2n_stuffer_reserve_uint16(out, &size)); for (size_t i = 0; i < signature_preferences->count; i++) { const struct s2n_signature_scheme *const scheme = signature_preferences->signature_schemes[i]; - if (0 == s2n_signature_scheme_valid_to_offer(conn, scheme)) { - POSIX_GUARD(s2n_stuffer_write_uint16(out, scheme->iana_value)); + RESULT_ENSURE_REF(scheme); + if (s2n_result_is_ok(s2n_signature_scheme_validate_for_send(conn, scheme))) { + RESULT_GUARD_POSIX(s2n_stuffer_write_uint16(out, scheme->iana_value)); } } + RESULT_GUARD_POSIX(s2n_stuffer_write_vector_size(&size)); - return 0; -} - -int s2n_supported_sig_scheme_list_size(struct s2n_connection *conn) -{ - return s2n_supported_sig_schemes_count(conn) * TLS_SIGNATURE_SCHEME_LEN; -} - -int s2n_supported_sig_schemes_count(struct s2n_connection *conn) -{ - const struct s2n_signature_preferences *signature_preferences = NULL; - POSIX_GUARD(s2n_connection_get_signature_preferences(conn, &signature_preferences)); - POSIX_ENSURE_REF(signature_preferences); - - uint8_t count = 0; - for (size_t i = 0; i < signature_preferences->count; i++) { - if (0 == s2n_signature_scheme_valid_to_offer(conn, signature_preferences->signature_schemes[i])) { - count++; - } - } - return count; + return S2N_RESULT_OK; } int s2n_recv_supported_sig_scheme_list(struct s2n_stuffer *in, struct s2n_sig_scheme_list *sig_hash_algs) diff --git a/tls/s2n_signature_algorithms.h b/tls/s2n_signature_algorithms.h index 8c118df980a..692096943ad 100644 --- a/tls/s2n_signature_algorithms.h +++ b/tls/s2n_signature_algorithms.h @@ -40,6 +40,5 @@ int s2n_get_and_validate_negotiated_signature_scheme(struct s2n_connection *conn const struct s2n_signature_scheme **chosen_sig_scheme); int s2n_recv_supported_sig_scheme_list(struct s2n_stuffer *in, struct s2n_sig_scheme_list *sig_hash_algs); -int s2n_send_supported_sig_scheme_list(struct s2n_connection *conn, struct s2n_stuffer *out); -int s2n_supported_sig_schemes_count(struct s2n_connection *conn); -int s2n_supported_sig_scheme_list_size(struct s2n_connection *conn); +S2N_RESULT s2n_signature_algorithms_supported_list_send(struct s2n_connection *conn, + struct s2n_stuffer *out);