diff --git a/gnutls-3.7.3-fips-pkcs12.patch b/gnutls-3.7.3-fips-pkcs12.patch new file mode 100644 index 0000000..45a8194 --- /dev/null +++ b/gnutls-3.7.3-fips-pkcs12.patch @@ -0,0 +1,471 @@ +From 7d8d8feb502ddb20a0d115fa3f63403c849a7168 Mon Sep 17 00:00:00 2001 +From: Daiki Ueno +Date: Thu, 10 Feb 2022 16:43:08 +0100 +Subject: [PATCH 1/2] pkcs12: mark MAC generation and verification as FIPS + non-approved + +Signed-off-by: Daiki Ueno +--- + lib/x509/pkcs12.c | 39 +++++++++++++++++++++++++--- + tests/pkcs12_encode.c | 59 +++++++++++++++++++++++++++++++++++++++++++ + 2 files changed, 94 insertions(+), 4 deletions(-) + +diff --git a/lib/x509/pkcs12.c b/lib/x509/pkcs12.c +index a8f7d8f956..11b9da3ac9 100644 +--- a/lib/x509/pkcs12.c ++++ b/lib/x509/pkcs12.c +@@ -286,13 +286,26 @@ gnutls_pkcs12_export(gnutls_pkcs12_t pkcs12, + gnutls_x509_crt_fmt_t format, void *output_data, + size_t * output_data_size) + { ++ int ret; ++ + if (pkcs12 == NULL) { + gnutls_assert(); + return GNUTLS_E_INVALID_REQUEST; + } + +- return _gnutls_x509_export_int(pkcs12->pkcs12, format, PEM_PKCS12, +- output_data, output_data_size); ++ ret = _gnutls_x509_export_int(pkcs12->pkcs12, format, PEM_PKCS12, ++ output_data, output_data_size); ++ ++ if (ret < 0) { ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_ERROR); ++ } else { ++ /* PKCS#12 export is always non-approved, because the MAC ++ * calculation involves non-approved KDF (PKCS#12 KDF) and ++ * without MAC the protection is insufficient. ++ */ ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_NOT_APPROVED); ++ } ++ return ret; + } + + /** +@@ -317,13 +330,25 @@ int + gnutls_pkcs12_export2(gnutls_pkcs12_t pkcs12, + gnutls_x509_crt_fmt_t format, gnutls_datum_t * out) + { ++ int ret; ++ + if (pkcs12 == NULL) { + gnutls_assert(); + return GNUTLS_E_INVALID_REQUEST; + } + +- return _gnutls_x509_export_int2(pkcs12->pkcs12, format, PEM_PKCS12, +- out); ++ ret = _gnutls_x509_export_int2(pkcs12->pkcs12, format, PEM_PKCS12, ++ out); ++ if (ret < 0) { ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_ERROR); ++ } else { ++ /* PKCS#12 export is always non-approved, because the MAC ++ * calculation involves non-approved KDF (PKCS#12 KDF) and ++ * without MAC the protection is insufficient. ++ */ ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_NOT_APPROVED); ++ } ++ return ret; + } + + static int oid2bag(const char *oid) +@@ -1025,9 +1050,12 @@ int gnutls_pkcs12_generate_mac2(gnutls_pkcs12_t pkcs12, gnutls_mac_algorithm_t m + goto cleanup; + } + ++ /* _gnutls_pkcs12_string_to_key is not a FIPS approved operation */ ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_NOT_APPROVED); + return 0; + + cleanup: ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_ERROR); + _gnutls_free_datum(&tmp); + return result; + } +@@ -1203,8 +1231,11 @@ pkcs12_try_gost: + goto cleanup; + } + ++ /* _gnutls_pkcs12_string_to_key is not a FIPS approved operation */ ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_NOT_APPROVED); + result = 0; + cleanup: ++ _gnutls_switch_fips_state(GNUTLS_FIPS140_OP_ERROR); + _gnutls_free_datum(&tmp); + _gnutls_free_datum(&salt); + return result; +diff --git a/tests/pkcs12_encode.c b/tests/pkcs12_encode.c +index 3b0e84ef13..b8f7d17267 100644 +--- a/tests/pkcs12_encode.c ++++ b/tests/pkcs12_encode.c +@@ -70,6 +70,29 @@ static void tls_log_func(int level, const char *str) + fprintf(stderr, "|<%d>| %s", level, str); + } + ++#define FIPS_PUSH_CONTEXT() do { \ ++ if (gnutls_fips140_mode_enabled()) { \ ++ ret = gnutls_fips140_push_context(fips_context); \ ++ if (ret < 0) { \ ++ fail("gnutls_fips140_push_context failed\n"); \ ++ } \ ++ } \ ++} while (0) ++ ++#define FIPS_POP_CONTEXT(state) do { \ ++ if (gnutls_fips140_mode_enabled()) { \ ++ ret = gnutls_fips140_pop_context(); \ ++ if (ret < 0) { \ ++ fail("gnutls_fips140_context_pop failed\n"); \ ++ } \ ++ fips_state = gnutls_fips140_get_operation_state(fips_context); \ ++ if (fips_state != GNUTLS_FIPS140_OP_ ## state) { \ ++ fail("operation state is not " # state " (%d)\n", \ ++ fips_state); \ ++ } \ ++ } \ ++} while (0) ++ + void doit(void) + { + gnutls_pkcs12_t pkcs12; +@@ -82,6 +105,8 @@ void doit(void) + char outbuf[10240]; + size_t size; + unsigned tests, i; ++ gnutls_fips140_context_t fips_context; ++ gnutls_fips140_operation_state_t fips_state; + + ret = global_init(); + if (ret < 0) { +@@ -93,6 +118,11 @@ void doit(void) + if (debug) + gnutls_global_set_log_level(4711); + ++ ret = gnutls_fips140_context_init(&fips_context); ++ if (ret < 0) { ++ fail("Cannot initialize FIPS context\n"); ++ } ++ + /* Read certs. */ + ret = gnutls_x509_crt_init(&client); + if (ret < 0) { +@@ -196,6 +226,8 @@ void doit(void) + gnutls_pkcs12_bag_deinit(bag); + } + ++ FIPS_PUSH_CONTEXT(); ++ + /* MAC the structure, export and print. */ + ret = gnutls_pkcs12_generate_mac2(pkcs12, GNUTLS_MAC_SHA1, "pass"); + if (ret < 0) { +@@ -203,36 +235,60 @@ void doit(void) + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + ret = gnutls_pkcs12_verify_mac(pkcs12, "pass"); + if (ret < 0) { + fprintf(stderr, "verify_mac: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + ret = gnutls_pkcs12_generate_mac2(pkcs12, GNUTLS_MAC_SHA256, "passwd"); + if (ret < 0) { + fprintf(stderr, "generate_mac2: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + ret = gnutls_pkcs12_verify_mac(pkcs12, "passwd"); + if (ret < 0) { + fprintf(stderr, "verify_mac2: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + ret = gnutls_pkcs12_generate_mac2(pkcs12, GNUTLS_MAC_SHA512, "passwd1"); + if (ret < 0) { + fprintf(stderr, "generate_mac2: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + ret = gnutls_pkcs12_verify_mac(pkcs12, "passwd1"); + if (ret < 0) { + fprintf(stderr, "verify_mac2: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ ++ FIPS_PUSH_CONTEXT(); ++ + size = sizeof(outbuf); + ret = + gnutls_pkcs12_export(pkcs12, GNUTLS_X509_FMT_PEM, outbuf, +@@ -242,10 +298,13 @@ void doit(void) + exit(1); + } + ++ FIPS_POP_CONTEXT(NOT_APPROVED); ++ + if (debug) + fwrite(outbuf, size, 1, stdout); + + /* Cleanup. */ ++ gnutls_fips140_context_deinit(fips_context); + gnutls_pkcs12_deinit(pkcs12); + gnutls_x509_crt_deinit(client); + gnutls_x509_crt_deinit(ca); +-- +2.34.1 + + +From e7f9267342bc2231149a640163c82b63c86f1dfd Mon Sep 17 00:00:00 2001 +From: Daiki Ueno +Date: Thu, 10 Feb 2022 17:35:13 +0100 +Subject: [PATCH 2/2] _gnutls_pkcs_raw_{decrypt,encrypt}_data: use public + crypto API + +These functions previously used the internal crypto +API (_gnutls_cipher_*) which does not have algorithm checks for FIPS. + +This change switches the code to use the public crypto +API (gnutls_cipher_*) to trigger proper state transitions under FIPS +mode. + +Signed-off-by: Daiki Ueno +--- + lib/x509/pkcs7-crypt.c | 36 +++++++++++----------------- + tests/pkcs12_encode.c | 54 +++++++++++++++++++++++++++--------------- + 2 files changed, 49 insertions(+), 41 deletions(-) + +diff --git a/lib/x509/pkcs7-crypt.c b/lib/x509/pkcs7-crypt.c +index 4cce52ecf0..2dc5bc4df0 100644 +--- a/lib/x509/pkcs7-crypt.c ++++ b/lib/x509/pkcs7-crypt.c +@@ -1130,8 +1130,7 @@ _gnutls_pkcs_raw_decrypt_data(schema_id schema, asn1_node pkcs8_asn, + gnutls_datum_t enc = { NULL, 0 }; + uint8_t *key = NULL; + gnutls_datum_t dkey, d_iv; +- cipher_hd_st ch; +- int ch_init = 0; ++ gnutls_cipher_hd_t ch = NULL; + int key_size, ret; + unsigned int pass_len = 0; + const struct pkcs_cipher_schema_st *p; +@@ -1237,8 +1236,7 @@ _gnutls_pkcs_raw_decrypt_data(schema_id schema, asn1_node pkcs8_asn, + d_iv.data = (uint8_t *) enc_params->iv; + d_iv.size = enc_params->iv_size; + +- ret = +- _gnutls_cipher_init(&ch, ce, &dkey, &d_iv, 0); ++ ret = gnutls_cipher_init(&ch, ce->id, &dkey, &d_iv); + + gnutls_free(key); + +@@ -1247,9 +1245,7 @@ _gnutls_pkcs_raw_decrypt_data(schema_id schema, asn1_node pkcs8_asn, + goto error; + } + +- ch_init = 1; +- +- ret = _gnutls_cipher_decrypt(&ch, enc.data, enc.size); ++ ret = gnutls_cipher_decrypt(ch, enc.data, enc.size); + if (ret < 0) { + gnutls_assert(); + ret = GNUTLS_E_DECRYPTION_FAILED; +@@ -1281,7 +1277,7 @@ _gnutls_pkcs_raw_decrypt_data(schema_id schema, asn1_node pkcs8_asn, + decrypted_data->size = enc.size; + } + +- _gnutls_cipher_deinit(&ch); ++ gnutls_cipher_deinit(ch); + + ret = 0; + +@@ -1294,8 +1290,9 @@ _gnutls_pkcs_raw_decrypt_data(schema_id schema, asn1_node pkcs8_asn, + gnutls_free(password); + gnutls_free(enc.data); + gnutls_free(key); +- if (ch_init != 0) +- _gnutls_cipher_deinit(&ch); ++ if (ch) { ++ gnutls_cipher_deinit(ch); ++ } + return ret; + } + +@@ -1725,8 +1722,7 @@ _gnutls_pkcs_raw_encrypt_data(const gnutls_datum_t * plain, + int data_size; + uint8_t *data = NULL; + gnutls_datum_t d_iv; +- cipher_hd_st ch; +- int ch_init = 0; ++ gnutls_cipher_hd_t ch = NULL; + uint8_t pad, pad_size; + const cipher_entry_st *ce; + +@@ -1756,18 +1752,13 @@ _gnutls_pkcs_raw_encrypt_data(const gnutls_datum_t * plain, + + d_iv.data = (uint8_t *) enc_params->iv; + d_iv.size = enc_params->iv_size; +- result = +- _gnutls_cipher_init(&ch, cipher_to_entry(enc_params->cipher), +- key, &d_iv, 1); +- ++ result = gnutls_cipher_init(&ch, enc_params->cipher, key, &d_iv); + if (result < 0) { + gnutls_assert(); + goto error; + } + +- ch_init = 1; +- +- result = _gnutls_cipher_encrypt(&ch, data, data_size); ++ result = gnutls_cipher_encrypt(ch, data, data_size); + if (result < 0) { + gnutls_assert(); + goto error; +@@ -1776,13 +1767,14 @@ _gnutls_pkcs_raw_encrypt_data(const gnutls_datum_t * plain, + encrypted->data = data; + encrypted->size = data_size; + +- _gnutls_cipher_deinit(&ch); ++ gnutls_cipher_deinit(ch); + + return 0; + + error: + gnutls_free(data); +- if (ch_init != 0) +- _gnutls_cipher_deinit(&ch); ++ if (ch) { ++ gnutls_cipher_deinit(ch); ++ } + return result; + } +diff --git a/tests/pkcs12_encode.c b/tests/pkcs12_encode.c +index b8f7d17267..78f6f41b48 100644 +--- a/tests/pkcs12_encode.c ++++ b/tests/pkcs12_encode.c +@@ -104,9 +104,17 @@ void doit(void) + int ret, indx; + char outbuf[10240]; + size_t size; +- unsigned tests, i; ++ unsigned i; + gnutls_fips140_context_t fips_context; + gnutls_fips140_operation_state_t fips_state; ++ size_t n_tests = 0; ++ struct tests { ++ const char *name; ++ gnutls_x509_crt_t crt; ++ const char *friendly_name; ++ unsigned bag_encrypt_flags; ++ int bag_encrypt_expected; ++ } tests[2]; + + ret = global_init(); + if (ret < 0) { +@@ -157,21 +165,34 @@ void doit(void) + exit(1); + } + +- /* Generate and add PKCS#12 cert bags. */ +- if (!gnutls_fips140_mode_enabled()) { +- tests = 2; /* include RC2 */ ++ tests[n_tests].name = "3DES"; ++ tests[n_tests].crt = client; ++ tests[n_tests].friendly_name = "client"; ++ tests[n_tests].bag_encrypt_flags = GNUTLS_PKCS8_USE_PKCS12_3DES; ++ tests[n_tests].bag_encrypt_expected = 0; ++ n_tests++; ++ ++ tests[n_tests].name = "RC2-40"; ++ tests[n_tests].crt = ca; ++ tests[n_tests].friendly_name = "ca"; ++ tests[n_tests].bag_encrypt_flags = GNUTLS_PKCS_USE_PKCS12_RC2_40; ++ if (gnutls_fips140_mode_enabled()) { ++ tests[n_tests].bag_encrypt_expected = ++ GNUTLS_E_UNWANTED_ALGORITHM; + } else { +- tests = 1; ++ tests[n_tests].bag_encrypt_expected = 0; + } ++ n_tests++; + +- for (i = 0; i < tests; i++) { ++ /* Generate and add PKCS#12 cert bags. */ ++ for (i = 0; i < n_tests; i++) { + ret = gnutls_pkcs12_bag_init(&bag); + if (ret < 0) { + fprintf(stderr, "bag_init: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + +- ret = gnutls_pkcs12_bag_set_crt(bag, i == 0 ? client : ca); ++ ret = gnutls_pkcs12_bag_set_crt(bag, tests[i].crt); + if (ret < 0) { + fprintf(stderr, "set_crt: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); +@@ -180,16 +201,14 @@ void doit(void) + indx = ret; + + ret = gnutls_pkcs12_bag_set_friendly_name(bag, indx, +- i == +- 0 ? "client" : +- "ca"); ++ tests[i].friendly_name); + if (ret < 0) { + fprintf(stderr, "set_friendly_name: %s (%d)\n", gnutls_strerror(ret), ret); + exit(1); + } + + size = sizeof(key_id_buf); +- ret = gnutls_x509_crt_get_key_id(i == 0 ? client : ca, 0, ++ ret = gnutls_x509_crt_get_key_id(tests[i].crt, 0, + key_id_buf, &size); + if (ret < 0) { + fprintf(stderr, "get_key_id: %s (%d)\n", gnutls_strerror(ret), ret); +@@ -206,14 +225,11 @@ void doit(void) + } + + ret = gnutls_pkcs12_bag_encrypt(bag, "pass", +- i == +- 0 ? +- GNUTLS_PKCS8_USE_PKCS12_3DES +- : +- GNUTLS_PKCS_USE_PKCS12_RC2_40); +- if (ret < 0) { +- fprintf(stderr, "bag_encrypt: %d: %s", ret, +- i == 0 ? "3DES" : "RC2-40"); ++ tests[i].bag_encrypt_flags); ++ if (ret != tests[i].bag_encrypt_expected) { ++ fprintf(stderr, "bag_encrypt: returned %d, expected %d: %s", ret, ++ tests[i].bag_encrypt_expected, ++ tests[i].name); + exit(1); + } + +-- +2.34.1 + diff --git a/gnutls-3.7.3-fips-rsa-keygen.patch b/gnutls-3.7.3-fips-rsa-keygen.patch new file mode 100644 index 0000000..f99ddc1 --- /dev/null +++ b/gnutls-3.7.3-fips-rsa-keygen.patch @@ -0,0 +1,182 @@ +From 9f5a60c1fe576f82bcd5c7998b2ca2b0d60e8e4f Mon Sep 17 00:00:00 2001 +From: Daiki Ueno +Date: Thu, 27 Jan 2022 18:17:43 +0100 +Subject: [PATCH 1/2] rsa_generate_fips186_4_keypair: accept a few more modulus + sizes + +While _rsa_generate_fips186_4_keypair was modified to accept modulus +sizes other than 2048 and 3076, rsa_generate_fips186_4_keypair, which +calls that function, was not updated to accept such modulus sizes. + +Spotted by Alexander Sosedkin. + +Signed-off-by: Daiki Ueno +--- + lib/nettle/int/rsa-keygen-fips186.c | 67 ++++++++++++++++------------- + 1 file changed, 36 insertions(+), 31 deletions(-) + +diff --git a/lib/nettle/int/rsa-keygen-fips186.c b/lib/nettle/int/rsa-keygen-fips186.c +index 5b221a030a..c6f7e675af 100644 +--- a/lib/nettle/int/rsa-keygen-fips186.c ++++ b/lib/nettle/int/rsa-keygen-fips186.c +@@ -27,6 +27,7 @@ + #include "config.h" + #endif + ++#include + #include + #include + #include +@@ -248,6 +249,33 @@ cleanup: + return ret; + } + ++/* Return the pre-defined seed length for modulus size, or 0 when the ++ * modulus size is unsupported. ++ */ ++static inline unsigned ++seed_length_for_modulus_size(unsigned modulus_size) ++{ ++ switch (modulus_size) { ++ case 2048: /* SP 800-56B rev 2 Appendix D and FIPS 140-2 IG 7.5 */ ++ return 14 * 2; ++ case 3072: /* SP 800-56B rev 2 Appendix D and FIPS 140-2 IG 7.5 */ ++ return 16 * 2; ++ case 4096: /* SP 800-56B rev 2 Appendix D */ ++ return 19 * 2; ++ case 6144: /* SP 800-56B rev 2 Appendix D */ ++ return 22 * 2; ++ case 7680: /* FIPS 140-2 IG 7.5 */ ++ return 24 * 2; ++ case 8192: /* SP 800-56B rev 2 Appendix D */ ++ return 25 * 2; ++ case 15360: /* FIPS 140-2 IG 7.5 */ ++ return 32 * 2; ++ default: ++ return 0; ++ } ++ ++} ++ + /* This generates p,q params using the B.3.2.2 algorithm in FIPS 186-4. + * + * The hash function used is SHA384. +@@ -266,33 +294,15 @@ _rsa_generate_fips186_4_keypair(struct rsa_public_key *pub, + int ret; + struct dss_params_validation_seeds cert; + unsigned l = n_size / 2; ++ unsigned s = seed_length_for_modulus_size(n_size); + +- switch (n_size) { +- case 2048: /* SP 800-56B rev 2 Appendix D and FIPS 140-2 IG 7.5 */ +- FIPS_RULE(seed_length != 14 * 2, 0, "seed length other than 28 bytes\n"); +- break; +- case 3072: /* SP 800-56B rev 2 Appendix D and FIPS 140-2 IG 7.5 */ +- FIPS_RULE(seed_length != 16 * 2, 0, "seed length other than 32 bytes\n"); +- break; +- case 4096: /* SP 800-56B rev 2 Appendix D */ +- FIPS_RULE(seed_length != 19 * 2, 0, "seed length other than 38 bytes\n"); +- break; +- case 6144: /* SP 800-56B rev 2 Appendix D */ +- FIPS_RULE(seed_length != 22 * 2, 0, "seed length other than 44 bytes\n"); +- break; +- case 7680: /* FIPS 140-2 IG 7.5 */ +- FIPS_RULE(seed_length != 24 * 2, 0, "seed length other than 48 bytes\n"); +- break; +- case 8192: /* SP 800-56B rev 2 Appendix D */ +- FIPS_RULE(seed_length != 25 * 2, 0, "seed length other than 50 bytes\n"); +- break; +- case 15360: /* FIPS 140-2 IG 7.5 */ +- FIPS_RULE(seed_length != 32 * 2, 0, "seed length other than 64 bytes\n"); +- break; +- default: ++ if (!s) { + FIPS_RULE(false, 0, "unsupported modulus size\n"); + } + ++ FIPS_RULE(seed_length != s, 0, ++ "seed length other than %u bytes\n", s); ++ + if (!mpz_tstbit(pub->e, 0)) { + _gnutls_debug_log("Unacceptable e (it is even)\n"); + return 0; +@@ -405,10 +415,6 @@ _rsa_generate_fips186_4_keypair(struct rsa_public_key *pub, + return ret; + } + +-/* Not entirely accurate but a good precision +- */ +-#define SEED_LENGTH(bits) (_gnutls_pk_bits_to_subgroup_bits(bits)/8) +- + /* This generates p,q params using the B.3.2.2 algorithm in FIPS 186-4. + * + * The hash function used is SHA384. +@@ -429,11 +435,10 @@ rsa_generate_fips186_4_keypair(struct rsa_public_key *pub, + unsigned seed_length; + int ret; + +- FIPS_RULE(n_size != 2048 && n_size != 3072, 0, "size of prime of other than 2048 or 3072\n"); ++ seed_length = seed_length_for_modulus_size(n_size); ++ FIPS_RULE(!seed_length, 0, "unsupported modulus size\n"); + +- seed_length = SEED_LENGTH(n_size); +- if (seed_length > sizeof(seed)) +- return 0; ++ assert(seed_length <= sizeof(seed)); + + random(random_ctx, seed_length, seed); + +-- +2.34.1 + + +From 46ae6160489151034bca19aa6c40ba0df6b53bcc Mon Sep 17 00:00:00 2001 +From: Daiki Ueno +Date: Tue, 1 Feb 2022 15:19:52 +0100 +Subject: [PATCH 2/2] certtool --generate-privkey: update warnings on RSA key + sizes + +Signed-off-by: Daiki Ueno +--- + src/certtool.c | 18 +++++++++++++++--- + 1 file changed, 15 insertions(+), 3 deletions(-) + +diff --git a/src/certtool.c b/src/certtool.c +index c128500614..71d4aff13e 100644 +--- a/src/certtool.c ++++ b/src/certtool.c +@@ -206,8 +206,12 @@ generate_private_key_int(common_info_st * cinfo) + "Note that DSA keys with size over 1024 may cause incompatibility problems when used with earlier than TLS 1.2 versions.\n\n"); + + if ((HAVE_OPT(SEED) || provable) && GNUTLS_PK_IS_RSA(key_type)) { +- if (bits != 2048 && bits != 3072) { +- fprintf(stderr, "Note that the FIPS 186-4 key generation restricts keys to 2048 and 3072 bits\n"); ++ /* Keep in sync with seed_length_for_modulus_size in ++ * lib/nettle/int/rsa-keygen-fips186.c. */ ++ if (bits != 2048 && bits != 3072 && bits != 4096 && ++ bits != 6144 && bits != 7680 && bits != 8192 && ++ bits != 15360) { ++ fprintf(stderr, "Note that the FIPS 186-4 key generation restricts keys to be of known lengths (2048, 3072, etc)\n"); + } + } + +@@ -225,7 +229,15 @@ generate_private_key_int(common_info_st * cinfo) + kdata[kdata_size++].size = cinfo->seed_size; + + if (GNUTLS_PK_IS_RSA(key_type)) { +- if ((bits == 3072 && cinfo->seed_size != 32) || (bits == 2048 && cinfo->seed_size != 28)) { ++ /* Keep in sync with seed_length_for_modulus_size in ++ * lib/nettle/int/rsa-keygen-fips186.c. */ ++ if ((bits == 2048 && cinfo->seed_size != 28) || ++ (bits == 3072 && cinfo->seed_size != 32) || ++ (bits == 4096 && cinfo->seed_size != 38) || ++ (bits == 6144 && cinfo->seed_size != 44) || ++ (bits == 7680 && cinfo->seed_size != 48) || ++ (bits == 8192 && cinfo->seed_size != 50) || ++ (bits == 15360 && cinfo->seed_size != 64)) { + fprintf(stderr, "The seed size (%d) doesn't match the size of the request security level; use -d 2 for more information.\n", (int)cinfo->seed_size); + } + } else if (key_type == GNUTLS_PK_DSA) { +-- +2.34.1 + diff --git a/gnutls-3.7.3-ktls-stub.patch b/gnutls-3.7.3-ktls-stub.patch new file mode 100644 index 0000000..4d3dace --- /dev/null +++ b/gnutls-3.7.3-ktls-stub.patch @@ -0,0 +1,33 @@ +From a97a93e23483aafc3508adee8e6399a2302e0fbc Mon Sep 17 00:00:00 2001 +From: Daiki Ueno +Date: Tue, 15 Feb 2022 17:38:20 +0100 +Subject: [PATCH] gnutls_transport_is_ktls_enabled: fix return value of stub + +Signed-off-by: Daiki Ueno +--- + lib/system/ktls.c | 7 +++---- + 1 file changed, 3 insertions(+), 4 deletions(-) + +diff --git a/lib/system/ktls.c b/lib/system/ktls.c +index 7e3cb875ed..f156f08ab2 100644 +--- a/lib/system/ktls.c ++++ b/lib/system/ktls.c +@@ -422,12 +422,11 @@ int _gnutls_ktls_recv_int(gnutls_session_t session, content_type_t type, + + #else //ENABLE_KTLS + gnutls_transport_ktls_enable_flags_t +-gnutls_transport_is_ktls_enabled(gnutls_session_t session){ +- return gnutls_assert_val(GNUTLS_E_UNIMPLEMENTED_FEATURE); ++gnutls_transport_is_ktls_enabled(gnutls_session_t session) { ++ return 0; + } + +-void _gnutls_ktls_enable(gnutls_session_t session){ +- return; ++void _gnutls_ktls_enable(gnutls_session_t session) { + } + + int _gnutls_ktls_set_keys(gnutls_session_t session) { +-- +2.34.1 + diff --git a/gnutls.spec b/gnutls.spec index cdf46ad..dd3a738 100644 --- a/gnutls.spec +++ b/gnutls.spec @@ -13,12 +13,15 @@ print(string.sub(hash, 0, 16)) } Version: 3.7.3 -Release: 3%{?dist} +Release: 4%{?dist} Patch1: gnutls-3.6.7-no-now-guile.patch Patch2: gnutls-3.2.7-rpath.patch Patch3: gnutls-3.7.2-enable-intel-cet.patch Patch4: gnutls-3.7.2-no-explicit-init.patch Patch5: gnutls-3.7.3-disable-config-reload.patch +Patch6: gnutls-3.7.3-fips-rsa-keygen.patch +Patch7: gnutls-3.7.3-ktls-stub.patch +Patch8: gnutls-3.7.3-fips-pkcs12.patch %bcond_with bootstrap %bcond_without dane %if 0%{?rhel} @@ -331,6 +334,12 @@ make check %{?_smp_mflags} GNUTLS_SYSTEM_PRIORITY_FILE=/dev/null %endif %changelog +* Wed Feb 16 2022 Daiki Ueno - 3.7.3-4 +- Specify FIPS140-3 module name and version +- fips: allow a few more primes in RSA key generation +- fips: tighten PKCS#12 algorithm checks +- Correct return value of KTLS stub API + * Tue Feb 15 2022 Zoltan Fridrich - 3.7.3-3 - Disable config reload in order to not break allowlisting (#2042532)