From 0dc00aa2e320ea00ddb9ca83b4a309c4b04f9711 Mon Sep 17 00:00:00 2001 From: Arne Schwabe Date: Wed, 4 Dec 2024 14:47:56 +0100 Subject: [PATCH] Import OpenSSL 3.4.0 --- apps/asn1parse.c | 5 +- apps/ca.c | 34 +- apps/cmp.c | 378 ++++++- apps/cms.c | 5 +- apps/dgst.c | 2 +- apps/fipsinstall.c | 304 +++++- apps/include/apps.h | 8 +- apps/include/cmp_mock_srv.h | 3 +- apps/include/platform.h | 4 +- apps/info.c | 13 +- apps/lib/apps.c | 85 +- apps/lib/cmp_mock_srv.c | 119 ++- apps/lib/http_server.c | 5 +- apps/lib/tlssrp_depr.c | 6 +- apps/lib/vms_term_sock.c | 12 +- apps/list.c | 74 +- apps/passwd.c | 16 +- apps/pkcs12.c | 96 +- apps/pkeyutl.c | 85 +- apps/rehash.c | 12 +- apps/req.c | 39 +- apps/s_client.c | 5 +- apps/smime.c | 5 +- apps/speed.c | 234 +++-- apps/version.c | 20 +- apps/x509.c | 31 +- crypto/aes/asm/aes-x86_64.S | 2 + crypto/aes/asm/aes-x86_64.pl | 4 +- crypto/aes/asm/aesni-sha1-x86_64.S | 2 + crypto/aes/asm/aesni-sha1-x86_64.pl | 4 +- crypto/aes/asm/aesni-sha256-x86_64.S | 2 + crypto/aes/asm/aesni-sha256-x86_64.pl | 4 +- crypto/aes/asm/aesni-x86_64.S | 2 + crypto/aes/asm/aesni-x86_64.pl | 4 +- crypto/aes/asm/bsaes-x86_64.S | 5 +- crypto/aes/asm/bsaes-x86_64.pl | 7 +- crypto/aes/asm/vpaes-x86_64.S | 3 +- crypto/aes/asm/vpaes-x86_64.pl | 5 +- crypto/arm_arch.h | 1 + crypto/armcap.c | 11 +- crypto/asn1/a_dup.c | 4 +- crypto/asn1/a_i2d_fp.c | 4 +- crypto/asn1/a_object.c | 5 +- crypto/asn1/a_strex.c | 5 +- crypto/asn1/a_time.c | 75 -- crypto/asn1/asn1_item_list.c | 3 +- crypto/asn1/asn1_item_list.h | 3 +- crypto/asn1/asn_mime.c | 4 +- crypto/asn1/f_int.c | 9 +- crypto/asn1/f_string.c | 6 +- crypto/asn1/p5_pbev2.c | 9 +- crypto/asn1/standard_methods.h | 3 +- crypto/async/arch/async_posix.h | 4 +- crypto/bio/bio_addr.c | 17 +- crypto/bio/bss_dgram.c | 2 +- crypto/bio/bss_log.c | 4 +- crypto/bn/asm/mips.pl | 4 +- crypto/bn/asm/rsaz-2k-avx512.S | 4 +- crypto/bn/asm/rsaz-2k-avx512.pl | 6 +- crypto/bn/asm/rsaz-3k-avx512.S | 4 +- crypto/bn/asm/rsaz-3k-avx512.pl | 6 +- crypto/bn/asm/rsaz-4k-avx512.S | 4 +- crypto/bn/asm/rsaz-4k-avx512.pl | 6 +- crypto/bn/asm/rsaz-avx2.S | 2 + crypto/bn/asm/rsaz-avx2.pl | 4 +- crypto/bn/asm/rsaz-x86_64.S | 2 + crypto/bn/asm/rsaz-x86_64.pl | 4 +- crypto/bn/asm/x86_64-mont5.S | 2 + crypto/bn/asm/x86_64-mont5.pl | 4 +- crypto/bn/bn_conv.c | 7 +- crypto/bn/bn_gcd.c | 36 +- crypto/bn/bn_gf2m.c | 30 +- crypto/bn/bn_lib.c | 5 +- crypto/bn/bn_mod.c | 5 +- crypto/bn/bn_mont.c | 44 +- crypto/bn/bn_nist.c | 6 +- crypto/bn/rsaz_exp_x2.c | 8 +- crypto/build.info | 12 +- crypto/buildinf.h | 4 +- ...64-zbb-zvkb.pl => chacha-riscv64-v-zbb.pl} | 270 +++-- crypto/chacha/asm/chacha-x86_64.S | 2 + crypto/chacha/asm/chacha-x86_64.pl | 4 +- crypto/chacha/asm/chachap10-ppc.pl | 10 +- crypto/chacha/build.info | 5 +- crypto/chacha/chacha_riscv.c | 19 +- crypto/cmac/cmac.c | 27 +- crypto/cmp/cmp_asn.c | 487 +++++++++ crypto/cmp/cmp_client.c | 5 +- crypto/cmp/cmp_err.c | 13 +- crypto/cmp/cmp_genm.c | 93 ++ crypto/cmp/cmp_hdr.c | 34 +- crypto/cmp/cmp_local.h | 48 + crypto/cmp/cmp_msg.c | 30 +- crypto/cmp/cmp_server.c | 5 +- crypto/cms/cms_dh.c | 4 +- crypto/cms/cms_env.c | 2 +- crypto/cms/cms_lib.c | 25 +- crypto/cms/cms_rsa.c | 7 +- crypto/cms/cms_sd.c | 2 +- crypto/cms/cms_smime.c | 21 +- crypto/comp_methods.c | 59 ++ crypto/conf/conf_mod.c | 30 +- crypto/context.c | 99 +- crypto/core_namemap.c | 268 ++--- crypto/cpt_err.c | 3 +- crypto/crmf/crmf_asn.c | 9 +- crypto/crmf/crmf_local.h | 34 +- crypto/cversion.c | 71 +- crypto/defaults.c | 200 ++++ crypto/des/set_key.c | 7 +- crypto/dsa/dsa_ameth.c | 16 +- crypto/dsa/dsa_pmeth.c | 24 +- crypto/dso/dso_dl.c | 13 +- crypto/dso/dso_dlfcn.c | 9 +- crypto/ec/asm/ecp_nistz256-x86_64.S | 4 +- crypto/ec/asm/ecp_nistz256-x86_64.pl | 6 +- crypto/ec/curve25519.c | 17 +- crypto/ec/curve448/curve448.c | 7 +- crypto/ec/curve448/eddsa.c | 24 +- crypto/ec/ec_asn1.c | 4 +- crypto/ec/ec_backend.c | 13 +- crypto/ec/ec_curve.c | 38 +- crypto/ec/ec_key.c | 8 +- crypto/ec/ec_lib.c | 6 +- crypto/ec/ec_local.h | 3 +- crypto/ec/ec_oct.c | 6 +- crypto/ec/ec_print.c | 26 +- crypto/ec/ecdsa_ossl.c | 4 + crypto/ec/ecp_nistp256.c | 12 +- crypto/ec/ecp_nistp384.c | 8 +- crypto/ec/ecp_nistz256.c | 130 ++- crypto/engine/eng_list.c | 4 +- crypto/err/openssl.txt | 28 + crypto/evp/bio_b64.c | 128 +-- crypto/evp/bio_ok.c | 10 +- crypto/evp/dh_support.c | 7 +- crypto/evp/digest.c | 74 +- crypto/evp/e_des3.c | 7 +- crypto/evp/encode.c | 4 +- crypto/evp/evp_enc.c | 5 +- crypto/evp/evp_err.c | 148 +-- crypto/evp/evp_lib.c | 336 +++++- crypto/evp/evp_local.h | 11 + crypto/evp/keymgmt_meth.c | 33 + crypto/evp/m_sigver.c | 74 +- crypto/evp/p5_crpt.c | 4 +- crypto/evp/p_lib.c | 3 +- crypto/evp/pmeth_lib.c | 13 + crypto/evp/signature.c | 633 ++++++++--- crypto/ffc/ffc_params.c | 10 +- crypto/ffc/ffc_params_generate.c | 11 +- crypto/hashtable/build.info | 6 + crypto/hashtable/hashtable.c | 760 ++++++++++++++ crypto/hmac/build.info | 21 +- crypto/hmac/hmac.c | 33 +- crypto/hmac/hmac_local.h | 45 +- crypto/hmac/hmac_s390x.c | 329 ++++++ crypto/hpke/hpke.c | 3 +- crypto/http/http_client.c | 19 +- crypto/http/http_lib.c | 20 +- crypto/indicator_core.c | 55 + crypto/info.c | 56 +- crypto/initthread.c | 10 +- crypto/mem.c | 64 +- crypto/mem_sec.c | 8 +- crypto/modes/asm/aes-gcm-avx512.S | 2 +- crypto/modes/asm/aes-gcm-avx512.pl | 4 +- crypto/modes/asm/aesni-gcm-x86_64.S | 2 + crypto/modes/asm/aesni-gcm-x86_64.pl | 4 +- crypto/modes/asm/ghash-x86_64.S | 4 + crypto/modes/asm/ghash-x86_64.pl | 6 +- crypto/modes/gcm128.c | 4 + crypto/o_fopen.c | 10 +- crypto/o_str.c | 86 +- crypto/objects/obj_dat.h | 34 +- crypto/objects/obj_dat.pl | 4 +- crypto/objects/obj_mac.num | 5 +- crypto/objects/objects.txt | 7 +- crypto/ocsp/ocsp_vfy.c | 4 +- crypto/params_idx.c | 553 +++++++++- crypto/pem/pem_pk8.c | 6 +- crypto/pem/pem_pkey.c | 4 +- crypto/perlasm/riscv.pm | 18 + crypto/perlasm/x86_64-xlate.pl | 198 +++- crypto/pkcs12/p12_crt.c | 2 +- crypto/pkcs12/p12_key.c | 4 +- crypto/pkcs12/p12_mutl.c | 307 +++++- crypto/pkcs12/p12_npas.c | 3 +- crypto/pkcs7/pk7_attr.c | 6 +- crypto/pkcs7/pk7_doit.c | 10 +- crypto/pkcs7/pk7_lib.c | 6 +- crypto/pkcs7/pk7_local.h | 3 +- crypto/pkcs7/pk7_smime.c | 42 +- crypto/poly1305/asm/poly1305-x86_64.S | 7 + crypto/poly1305/asm/poly1305-x86_64.pl | 10 +- crypto/poly1305/poly1305.c | 4 +- crypto/provider_core.c | 11 +- crypto/rand/rand_lib.c | 58 +- crypto/riscvcap.c | 47 +- crypto/rsa/rsa_ameth.c | 21 +- crypto/rsa/rsa_backend.c | 6 + crypto/rsa/rsa_gen.c | 60 +- crypto/rsa/rsa_lib.c | 55 + crypto/rsa/rsa_mp.c | 4 +- crypto/rsa/rsa_oaep.c | 26 +- crypto/rsa/rsa_ossl.c | 68 +- crypto/rsa/rsa_pmeth.c | 36 +- crypto/rsa/rsa_pss.c | 33 +- crypto/rsa/rsa_schemes.c | 4 +- crypto/rsa/rsa_sign.c | 18 +- crypto/rsa/rsa_sp800_56b_gen.c | 12 +- crypto/rsa/rsa_x931.c | 35 +- crypto/s390x_arch.h | 17 +- crypto/s390xcpuid.pl | 6 +- crypto/self_test_core.c | 8 +- crypto/sha/asm/keccak1600-x86_64.S | 1 + crypto/sha/asm/keccak1600-x86_64.pl | 3 +- crypto/sha/asm/sha1-mb-x86_64.S | 3 +- crypto/sha/asm/sha1-mb-x86_64.pl | 5 +- crypto/sha/asm/sha1-x86_64.S | 2 + crypto/sha/asm/sha1-x86_64.pl | 4 +- crypto/sha/asm/sha256-mb-x86_64.S | 2 + crypto/sha/asm/sha256-mb-x86_64.pl | 4 +- crypto/sha/asm/sha256-x86_64.S | 2 + crypto/sha/asm/sha512-x86_64.S | 2 + crypto/sha/asm/sha512-x86_64.pl | 6 +- crypto/sha/keccak1600.c | 14 +- crypto/sha/sha256.c | 28 +- crypto/sha/sha3.c | 14 +- crypto/sha/sha512.c | 8 +- crypto/sleep.c | 55 +- crypto/sm2/sm2_crypt.c | 2 +- crypto/sm2/sm2_sign.c | 2 +- crypto/sm4/sm4.c | 7 +- crypto/sparse_array.c | 4 +- crypto/srp/srp_vfy.c | 4 +- crypto/store/store_lib.c | 11 +- crypto/store/store_strings.c | 6 +- crypto/thread/build.info | 2 +- crypto/threads_none.c | 25 + crypto/threads_pthread.c | 150 ++- crypto/threads_win.c | 184 +++- crypto/ui/ui_util.c | 14 +- crypto/x509/build.info | 4 +- crypto/x509/by_store.c | 18 +- crypto/x509/ext_dat.h | 13 +- crypto/x509/pcy_tree.c | 4 +- crypto/x509/standard_exts.h | 15 +- crypto/x509/t_acert.c | 285 +++++ crypto/x509/v3_ac_tgt.c | 239 +++++ crypto/x509/v3_audit_id.c | 20 + crypto/x509/v3_battcons.c | 86 ++ crypto/x509/v3_crld.c | 17 +- crypto/x509/v3_extku.c | 26 +- crypto/x509/v3_genn.c | 31 +- crypto/x509/v3_iobo.c | 32 + crypto/x509/v3_ncons.c | 22 +- crypto/x509/v3_pci.c | 6 +- crypto/x509/v3_san.c | 22 +- crypto/x509/v3_sda.c | 90 ++ crypto/x509/v3_usernotice.c | 94 ++ crypto/x509/v3_utl.c | 80 +- crypto/x509/x509_acert.c | 328 ++++++ crypto/x509/x509_acert.h | 22 + crypto/x509/x509_att.c | 11 +- crypto/x509/x509_d2.c | 7 +- crypto/x509/x509_def.c | 75 +- crypto/x509/x509_err.c | 4 +- crypto/x509/x509_obj.c | 9 +- crypto/x509/x509_req.c | 71 +- crypto/x509/x509_set.c | 9 +- crypto/x509/x509_v3.c | 40 +- crypto/x509/x509aset.c | 177 ++++ crypto/x509/x509rset.c | 6 +- crypto/x509/x_all.c | 60 +- crypto/x509/x_attrib.c | 200 +++- crypto/x509/x_exten.c | 4 +- crypto/x509/x_ietfatt.c | 241 +++++ crypto/x509/x_pubkey.c | 4 +- import_openssl.sh | 1 + include/crypto/asn1.h | 5 +- include/crypto/bn.h | 6 + include/crypto/cmac.h | 22 + include/crypto/context.h | 4 +- include/crypto/cryptoerr.h | 2 +- include/crypto/ecx.h | 7 +- include/crypto/evp.h | 48 +- include/crypto/riscv_arch.def | 64 +- include/crypto/riscv_arch.h | 47 +- include/crypto/rsa.h | 9 + include/crypto/x509.h | 8 +- include/crypto/x509_acert.h | 70 ++ include/internal/common.h | 5 + include/internal/comp.h | 12 +- include/internal/constant_time.h | 18 + include/internal/crmf.h | 51 + include/internal/cryptlib.h | 16 +- include/internal/event_queue.h | 163 --- include/internal/hashtable.h | 335 ++++++ include/internal/list.h | 26 +- include/internal/namemap.h | 4 +- include/internal/packet.h | 4 +- include/internal/param_names.h | 709 +++++++------ include/internal/quic_ackm.h | 4 +- include/internal/refcount.h | 4 +- include/internal/sha3.h | 9 +- include/internal/to_hex.h | 27 + include/openssl/cmp.h | 81 +- include/openssl/cmp.h.in | 57 +- include/openssl/cmperr.h | 6 + include/openssl/comp.h | 50 +- include/openssl/comp.h.in | 76 ++ include/openssl/configuration-32.h | 17 +- include/openssl/configuration-64.h | 17 +- include/openssl/configuration-static-32.h | 17 +- include/openssl/configuration-static-64.h | 17 +- include/openssl/core_dispatch.h | 54 +- include/openssl/core_names.h | 73 +- include/openssl/crmf.h | 33 +- include/openssl/crmf.h.in | 9 +- include/openssl/crypto.h | 21 +- include/openssl/crypto.h.in | 21 +- include/openssl/cryptoerr.h | 3 +- include/openssl/e_os2.h | 3 +- include/openssl/evp.h | 108 +- include/openssl/evperr.h | 5 +- include/openssl/fips_names.h | 51 +- include/openssl/fipskey.h | 7 +- include/openssl/fipskey.h.in | 7 +- include/openssl/http.h | 7 +- include/openssl/indicator.h | 31 + include/openssl/macros.h | 14 +- include/openssl/obj_mac.h | 20 +- include/openssl/objects.h | 3 +- include/openssl/opensslv.h | 12 +- include/openssl/pem.h | 3 +- include/openssl/pkcs12.h | 5 +- include/openssl/pkcs12.h.in | 5 +- include/openssl/proverr.h | 11 +- include/openssl/self_test.h | 2 + include/openssl/ssl.h | 42 +- include/openssl/ssl.h.in | 19 +- include/openssl/sslerr.h | 2 + include/openssl/tls1.h | 8 + include/openssl/ts.h | 19 +- include/openssl/types.h | 8 +- include/openssl/x509.h | 50 +- include/openssl/x509.h.in | 50 +- include/openssl/x509_acert.h | 263 +++++ include/openssl/x509_acert.h.in | 192 ++++ include/openssl/x509err.h | 3 +- include/openssl/x509v3.h | 66 +- include/openssl/x509v3.h.in | 42 +- openssl.cmake | 16 +- openssl.version | 2 +- providers/baseprov.c | 5 +- providers/build.info | 3 +- providers/common/capabilities.c | 4 +- providers/common/digest_to_nid.c | 3 +- providers/common/include/prov/proverr.h | 2 +- providers/common/include/prov/securitycheck.h | 36 +- providers/common/provider_err.c | 175 +-- providers/common/securitycheck.c | 313 +++--- providers/common/securitycheck_default.c | 16 +- providers/common/securitycheck_fips.c | 100 +- providers/defltprov.c | 43 +- providers/fips-sources.checksums | 335 +++--- providers/fips.checksum | 2 +- providers/fips.module.sources | 19 +- providers/fips/build.info | 2 +- providers/fips/fipsindicator.c | 116 ++ providers/fips/fipsprov.c | 305 +++--- providers/fips/include/fips/fipsindicator.h | 151 +++ .../fips/include/fips_indicator_params.inc | 28 + .../fips/include/fips_selftest_params.inc | 3 + .../prov => fips/include}/fipscommon.h | 9 +- providers/fips/self_test.c | 75 +- providers/fips/self_test.h | 7 +- providers/fips/self_test_data.inc | 424 ++++---- providers/fips/self_test_kats.c | 141 +-- .../implementations/asymciphers/rsa_enc.c | 56 +- .../ciphers/cipher_aes_cbc_hmac_sha.c | 8 +- .../implementations/ciphers/cipher_aes_ccm.c | 5 +- .../implementations/ciphers/cipher_aes_gcm.c | 5 +- .../ciphers/cipher_aes_gcm_siv_hw.c | 5 +- .../implementations/ciphers/cipher_aes_ocb.c | 14 +- .../ciphers/cipher_aes_siv_hw.c | 5 +- .../implementations/ciphers/cipher_aes_wrp.c | 5 +- .../implementations/ciphers/cipher_aes_xts.c | 8 +- .../ciphers/cipher_chacha20_poly1305_hw.c | 5 +- .../implementations/ciphers/cipher_cts.c | 5 +- .../implementations/ciphers/cipher_desx_hw.c | 5 +- .../implementations/ciphers/cipher_null.c | 4 +- .../implementations/ciphers/cipher_rc2.c | 34 +- .../implementations/ciphers/cipher_tdes.h | 17 +- .../ciphers/cipher_tdes_common.c | 69 +- .../ciphers/cipher_tdes_wrap.c | 5 +- .../implementations/ciphers/ciphercommon.c | 3 +- .../ciphers/ciphercommon_gcm.c | 11 +- .../implementations/digests/blake2s_prov.c | 6 +- providers/implementations/digests/sha3_prov.c | 131 ++- .../encode_decode/decode_der2key.c | 16 +- .../encode_decode/encode_key2text.c | 5 +- providers/implementations/exchange/dh_exch.c | 61 +- .../implementations/exchange/ecdh_exch.c | 93 +- providers/implementations/exchange/ecx_exch.c | 60 +- .../include/prov/implementations.h | 50 +- .../implementations/include/prov/names.h | 46 +- providers/implementations/kdfs/argon2.c | 6 +- providers/implementations/kdfs/hkdf.c | 241 ++++- providers/implementations/kdfs/hmacdrbg_kdf.c | 10 +- providers/implementations/kdfs/kbkdf.c | 59 +- providers/implementations/kdfs/pbkdf1.c | 2 +- providers/implementations/kdfs/pbkdf2.c | 120 ++- providers/implementations/kdfs/sshkdf.c | 101 +- providers/implementations/kdfs/sskdf.c | 252 ++++- providers/implementations/kdfs/tls1_prf.c | 150 ++- providers/implementations/kdfs/x942kdf.c | 65 +- providers/implementations/kem/rsa_kem.c | 118 ++- providers/implementations/keymgmt/dh_kmgmt.c | 10 +- providers/implementations/keymgmt/dsa_kmgmt.c | 53 +- providers/implementations/keymgmt/ec_kmgmt.c | 49 +- providers/implementations/keymgmt/ecx_kmgmt.c | 59 +- providers/implementations/macs/cmac_prov.c | 78 +- providers/implementations/macs/hmac_prov.c | 84 +- providers/implementations/macs/kmac_prov.c | 140 ++- providers/implementations/rands/build.info | 5 +- providers/implementations/rands/crngt.c | 192 ---- providers/implementations/rands/drbg.c | 57 +- providers/implementations/rands/drbg_ctr.c | 2 + providers/implementations/rands/drbg_hash.c | 16 +- providers/implementations/rands/drbg_hmac.c | 16 +- providers/implementations/rands/drbg_local.h | 9 +- .../implementations/rands/fips_crng_test.c | 428 ++++++++ .../implementations/rands/seed_src_jitter.c | 336 ++++++ .../implementations/rands/seeding/rand_unix.c | 13 +- .../rands/seeding/rand_vxworks.c | 5 +- providers/implementations/rands/test_rng.c | 12 +- providers/implementations/signature/dsa_sig.c | 669 ++++++++++-- .../implementations/signature/ecdsa_sig.c | 728 ++++++++++--- .../implementations/signature/eddsa_sig.c | 653 +++++++++--- providers/implementations/signature/rsa_sig.c | 992 ++++++++++++++---- providers/implementations/signature/sm2_sig.c | 27 +- .../implementations/storemgmt/file_store.c | 4 +- ssl/build.info | 2 +- ssl/d1_lib.c | 6 +- ssl/event_queue.c | 196 ---- ssl/priority_queue.c | 5 +- ssl/quic/quic_cfq.c | 4 +- ssl/quic/quic_engine.c | 4 +- ssl/quic/quic_port.c | 8 +- ssl/quic/quic_rcidm.c | 2 +- ssl/quic/quic_record_util.c | 14 +- ssl/quic/quic_stream_map.c | 2 +- ssl/record/methods/dtls_meth.c | 2 +- ssl/record/methods/recmethod_local.h | 14 +- ssl/record/methods/tls13_meth.c | 192 +++- ssl/record/methods/tls_common.c | 28 +- ssl/record/rec_layer_s3.c | 3 + ssl/record/record.h | 1 + ssl/s3_enc.c | 4 +- ssl/s3_lib.c | 82 +- ssl/ssl_cert.c | 78 +- ssl/ssl_cert_comp.c | 4 +- ssl/ssl_ciph.c | 206 ++-- ssl/ssl_conf.c | 43 +- ssl/ssl_err.c | 4 + ssl/ssl_init.c | 25 +- ssl/ssl_lib.c | 126 ++- ssl/ssl_local.h | 53 +- ssl/ssl_mcnf.c | 17 +- ssl/ssl_sess.c | 12 + ssl/ssl_stat.c | 4 +- ssl/ssl_txt.c | 4 +- ssl/statem/extensions.c | 35 +- ssl/statem/extensions_clnt.c | 48 +- ssl/statem/extensions_srvr.c | 9 +- ssl/statem/statem_clnt.c | 12 +- ssl/statem/statem_dtls.c | 13 +- ssl/statem/statem_srvr.c | 20 +- ssl/t1_lib.c | 149 ++- ssl/t1_trce.c | 67 +- ssl/tls13_enc.c | 188 ++-- 483 files changed, 20567 insertions(+), 5327 deletions(-) rename crypto/chacha/asm/{chacha-riscv64-zbb-zvkb.pl => chacha-riscv64-v-zbb.pl} (71%) mode change 100644 => 100755 create mode 100644 crypto/comp_methods.c create mode 100644 crypto/defaults.c create mode 100644 crypto/hashtable/build.info create mode 100644 crypto/hashtable/hashtable.c create mode 100644 crypto/hmac/hmac_s390x.c create mode 100644 crypto/indicator_core.c create mode 100644 crypto/x509/t_acert.c create mode 100644 crypto/x509/v3_ac_tgt.c create mode 100644 crypto/x509/v3_audit_id.c create mode 100644 crypto/x509/v3_battcons.c create mode 100644 crypto/x509/v3_iobo.c create mode 100644 crypto/x509/v3_sda.c create mode 100644 crypto/x509/v3_usernotice.c create mode 100644 crypto/x509/x509_acert.c create mode 100644 crypto/x509/x509_acert.h create mode 100644 crypto/x509/x509aset.c create mode 100644 crypto/x509/x_ietfatt.c create mode 100644 include/crypto/cmac.h create mode 100644 include/crypto/x509_acert.h create mode 100644 include/internal/crmf.h delete mode 100644 include/internal/event_queue.h create mode 100644 include/internal/hashtable.h create mode 100644 include/internal/to_hex.h create mode 100644 include/openssl/comp.h.in create mode 100644 include/openssl/indicator.h create mode 100644 include/openssl/x509_acert.h create mode 100644 include/openssl/x509_acert.h.in create mode 100644 providers/fips/fipsindicator.c create mode 100644 providers/fips/include/fips/fipsindicator.h create mode 100644 providers/fips/include/fips_indicator_params.inc create mode 100644 providers/fips/include/fips_selftest_params.inc rename providers/{common/include/prov => fips/include}/fipscommon.h (55%) delete mode 100644 providers/implementations/rands/crngt.c create mode 100644 providers/implementations/rands/fips_crng_test.c create mode 100644 providers/implementations/rands/seed_src_jitter.c delete mode 100644 ssl/event_queue.c diff --git a/apps/asn1parse.c b/apps/asn1parse.c index bf62f85947..5f1d955807 100644 --- a/apps/asn1parse.c +++ b/apps/asn1parse.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -216,6 +216,9 @@ int asn1parse_main(int argc, char **argv) i = BIO_read(in, &(buf->data[num]), BUFSIZ); if (i <= 0) break; + /* make sure num doesn't overflow */ + if (i > LONG_MAX - num) + goto end; num += i; } } diff --git a/apps/ca.c b/apps/ca.c index e12a8c2370..a8966399b1 100644 --- a/apps/ca.c +++ b/apps/ca.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -150,7 +150,7 @@ typedef enum OPTION_choice { OPT_IN, OPT_INFORM, OPT_OUT, OPT_DATEOPT, OPT_OUTDIR, OPT_VFYOPT, OPT_SIGOPT, OPT_NOTEXT, OPT_BATCH, OPT_PRESERVEDN, OPT_NOEMAILDN, OPT_GENCRL, OPT_MSIE_HACK, OPT_CRL_LASTUPDATE, OPT_CRL_NEXTUPDATE, - OPT_CRLDAYS, OPT_CRLHOURS, OPT_CRLSEC, + OPT_CRLDAYS, OPT_CRLHOURS, OPT_CRLSEC, OPT_NOT_BEFORE, OPT_NOT_AFTER, OPT_INFILES, OPT_SS_CERT, OPT_SPKAC, OPT_REVOKE, OPT_VALID, OPT_EXTENSIONS, OPT_EXTFILE, OPT_STATUS, OPT_UPDATEDB, OPT_CRLEXTS, OPT_RAND_SERIAL, OPT_QUIET, @@ -199,10 +199,13 @@ const OPTIONS ca_options[] = { "Always create a random serial; do not store it"}, {"multivalue-rdn", OPT_MULTIVALUE_RDN, '-', "Deprecated; multi-valued RDNs support is always on."}, - {"startdate", OPT_STARTDATE, 's', "Cert notBefore, YYMMDDHHMMSSZ"}, + {"startdate", OPT_STARTDATE, 's', + "[CC]YYMMDDHHMMSSZ value for notBefore certificate field"}, + {"not_before", OPT_NOT_BEFORE, 's', "An alias for -startdate"}, {"enddate", OPT_ENDDATE, 's', - "YYMMDDHHMMSSZ cert notAfter (overrides -days)"}, - {"days", OPT_DAYS, 'p', "Number of days to certify the cert for"}, + "[CC]YYMMDDHHMMSSZ value for notAfter certificate field, overrides -days"}, + {"not_after", OPT_NOT_AFTER, 's', "An alias for -enddate"}, + {"days", OPT_DAYS, 'p', "Number of days from today to certify the cert for"}, {"extensions", OPT_EXTENSIONS, 's', "Extension section (override value in config file)"}, {"extfile", OPT_EXTFILE, '<', @@ -359,9 +362,11 @@ int ca_main(int argc, char **argv) /* obsolete */ break; case OPT_STARTDATE: + case OPT_NOT_BEFORE: startdate = opt_arg(); break; case OPT_ENDDATE: + case OPT_NOT_AFTER: enddate = opt_arg(); break; case OPT_DAYS: @@ -874,22 +879,8 @@ int ca_main(int argc, char **argv) if (startdate == NULL) startdate = app_conf_try_string(conf, section, ENV_DEFAULT_STARTDATE); - if (startdate != NULL && !ASN1_TIME_set_string_X509(NULL, startdate)) { - BIO_printf(bio_err, - "start date is invalid, it should be YYMMDDHHMMSSZ or YYYYMMDDHHMMSSZ\n"); - goto end; - } - if (startdate == NULL) - startdate = "today"; - if (enddate == NULL) enddate = app_conf_try_string(conf, section, ENV_DEFAULT_ENDDATE); - if (enddate != NULL && !ASN1_TIME_set_string_X509(NULL, enddate)) { - BIO_printf(bio_err, - "end date is invalid, it should be YYMMDDHHMMSSZ or YYYYMMDDHHMMSSZ\n"); - goto end; - } - if (days == 0) { if (!app_conf_try_number(conf, section, ENV_DEFAULT_DAYS, &days)) days = 0; @@ -898,6 +889,9 @@ int ca_main(int argc, char **argv) BIO_printf(bio_err, "cannot lookup how many days to certify for\n"); goto end; } + if (days != 0 && enddate != NULL) + BIO_printf(bio_err, + "Warning: -enddate or -not_after option overriding -days option\n"); if (rand_ser) { if ((serial = BN_new()) == NULL || !rand_serial(serial, NULL)) { @@ -1671,7 +1665,7 @@ static int do_body(X509 **xret, EVP_PKEY *pkey, X509 *x509, goto end; } - if (!set_cert_times(ret, startdate, enddate, days)) + if (!set_cert_times(ret, startdate, enddate, days, 0)) goto end; if (enddate != NULL) { diff --git a/apps/cmp.c b/apps/cmp.c index 10a477dace..dc2a1c3a6a 100644 --- a/apps/cmp.c +++ b/apps/cmp.c @@ -94,6 +94,11 @@ static char *opt_oldwithold = NULL; static char *opt_newwithnew = NULL; static char *opt_newwithold = NULL; static char *opt_oldwithnew = NULL; +static char *opt_crlcert = NULL; +static char *opt_oldcrl = NULL; +static char *opt_crlout = NULL; +static char *opt_template = NULL; +static char *opt_keyspec = NULL; /* client authentication */ static char *opt_ref = NULL; @@ -143,6 +148,12 @@ static int opt_revreason = CRL_REASON_NONE; /* credentials format */ static char *opt_certform_s = "PEM"; static int opt_certform = FORMAT_PEM; +/* + * DER format is the preferred choice for saving a CRL because it allows for + * more efficient storage, especially when dealing with large CRLs. + */ +static char *opt_crlform_s = "DER"; +static int opt_crlform = FORMAT_ASN1; static char *opt_keyform_s = NULL; static int opt_keyform = FORMAT_UNDEF; static char *opt_otherpass = NULL; @@ -187,6 +198,7 @@ static char *opt_srv_trusted = NULL; static char *opt_srv_untrusted = NULL; static char *opt_ref_cert = NULL; static char *opt_rsp_cert = NULL; +static char *opt_rsp_crl = NULL; static char *opt_rsp_extracerts = NULL; static char *opt_rsp_capubs = NULL; static char *opt_rsp_newwithnew = NULL; @@ -215,6 +227,7 @@ typedef enum OPTION_choice { OPT_CONFIG, OPT_SECTION, OPT_VERBOSITY, OPT_CMD, OPT_INFOTYPE, OPT_PROFILE, OPT_GENINFO, + OPT_TEMPLATE, OPT_KEYSPEC, OPT_NEWKEY, OPT_NEWKEYPASS, OPT_SUBJECT, OPT_DAYS, OPT_REQEXTS, @@ -237,12 +250,13 @@ typedef enum OPTION_choice { OPT_IGNORE_KEYUSAGE, OPT_UNPROTECTED_ERRORS, OPT_NO_CACHE_EXTRACERTS, OPT_SRVCERTOUT, OPT_EXTRACERTSOUT, OPT_CACERTSOUT, OPT_OLDWITHOLD, OPT_NEWWITHNEW, OPT_NEWWITHOLD, OPT_OLDWITHNEW, + OPT_CRLCERT, OPT_OLDCRL, OPT_CRLOUT, OPT_REF, OPT_SECRET, OPT_CERT, OPT_OWN_TRUSTED, OPT_KEY, OPT_KEYPASS, OPT_DIGEST, OPT_MAC, OPT_EXTRACERTS, OPT_UNPROTECTED_REQUESTS, - OPT_CERTFORM, OPT_KEYFORM, + OPT_CERTFORM, OPT_CRLFORM, OPT_KEYFORM, OPT_OTHERPASS, #ifndef OPENSSL_NO_ENGINE OPT_ENGINE, @@ -267,7 +281,7 @@ typedef enum OPTION_choice { OPT_SRV_REF, OPT_SRV_SECRET, OPT_SRV_CERT, OPT_SRV_KEY, OPT_SRV_KEYPASS, OPT_SRV_TRUSTED, OPT_SRV_UNTRUSTED, - OPT_REF_CERT, OPT_RSP_CERT, OPT_RSP_EXTRACERTS, OPT_RSP_CAPUBS, + OPT_REF_CERT, OPT_RSP_CERT, OPT_RSP_CRL, OPT_RSP_EXTRACERTS, OPT_RSP_CAPUBS, OPT_RSP_NEWWITHNEW, OPT_RSP_NEWWITHOLD, OPT_RSP_OLDWITHNEW, OPT_POLL_COUNT, OPT_CHECK_AFTER, OPT_GRANT_IMPLICITCONF, @@ -302,6 +316,10 @@ const OPTIONS cmp_options[] = { "Comma-separated list of OID and value to place in generalInfo PKIHeader"}, {OPT_MORE_STR, 0, 0, "of form :int: or :str:, e.g. \'1.2.3.4:int:56789, id-kp:str:name'"}, + { "template", OPT_TEMPLATE, 's', + "File to save certTemplate received in genp of type certReqTemplate"}, + { "keyspec", OPT_KEYSPEC, 's', + "Optional file to save Key specification received in genp of type certReqTemplate"}, OPT_SECTION("Certificate enrollment"), {"newkey", OPT_NEWKEY, 's', @@ -428,6 +446,12 @@ const OPTIONS cmp_options[] = { "File to save NewWithOld cert received in genp of type rootCaKeyUpdate"}, { "oldwithnew", OPT_OLDWITHNEW, 's', "File to save OldWithNew cert received in genp of type rootCaKeyUpdate"}, + { "crlcert", OPT_CRLCERT, 's', + "certificate to request a CRL for in genm of type crlStatusList"}, + { "oldcrl", OPT_OLDCRL, 's', + "CRL to request update for in genm of type crlStatusList"}, + { "crlout", OPT_CRLOUT, 's', + "File to save new CRL received in genp of type 'crls'"}, OPT_SECTION("Client authentication"), {"ref", OPT_REF, 's', @@ -459,6 +483,8 @@ const OPTIONS cmp_options[] = { OPT_SECTION("Credentials format"), {"certform", OPT_CERTFORM, 's', "Format (PEM or DER) to use when saving a certificate to a file. Default PEM"}, + {"crlform", OPT_CRLFORM, 's', + "Format (PEM or DER) to use when saving a CRL to a file. Default DER"}, {"keyform", OPT_KEYFORM, 's', "Format of the key input (ENGINE, other values ignored)"}, {"otherpass", OPT_OTHERPASS, 's', @@ -544,6 +570,8 @@ const OPTIONS cmp_options[] = { "Certificate to be expected for rr and any oldCertID in kur messages"}, {"rsp_cert", OPT_RSP_CERT, 's', "Certificate to be returned as mock enrollment result"}, + {"rsp_crl", OPT_RSP_CRL, 's', + "CRL to be returned in genp of type crls"}, {"rsp_extracerts", OPT_RSP_EXTRACERTS, 's', "Extra certificates to be included in mock certification responses"}, {"rsp_capubs", OPT_RSP_CAPUBS, 's', @@ -599,6 +627,7 @@ static varref cmp_vars[] = { /* must be in same order as enumerated above! */ {&opt_config}, {&opt_section}, {(char **)&opt_verbosity}, {&opt_cmd_s}, {&opt_infotype_s}, {&opt_profile}, {&opt_geninfo}, + {&opt_template}, {&opt_keyspec}, {&opt_newkey}, {&opt_newkeypass}, {&opt_subject}, {(char **)&opt_days}, {&opt_reqexts}, @@ -623,13 +652,14 @@ static varref cmp_vars[] = { /* must be in same order as enumerated above! */ {(char **)&opt_no_cache_extracerts}, {&opt_srvcertout}, {&opt_extracertsout}, {&opt_cacertsout}, {&opt_oldwithold}, {&opt_newwithnew}, {&opt_newwithold}, {&opt_oldwithnew}, + {&opt_crlcert}, {&opt_oldcrl}, {&opt_crlout}, {&opt_ref}, {&opt_secret}, {&opt_cert}, {&opt_own_trusted}, {&opt_key}, {&opt_keypass}, {&opt_digest}, {&opt_mac}, {&opt_extracerts}, {(char **)&opt_unprotected_requests}, - {&opt_certform_s}, {&opt_keyform_s}, + {&opt_certform_s}, {&opt_crlform_s}, {&opt_keyform_s}, {&opt_otherpass}, #ifndef OPENSSL_NO_ENGINE {&opt_engine}, @@ -652,7 +682,8 @@ static varref cmp_vars[] = { /* must be in same order as enumerated above! */ {&opt_srv_ref}, {&opt_srv_secret}, {&opt_srv_cert}, {&opt_srv_key}, {&opt_srv_keypass}, {&opt_srv_trusted}, {&opt_srv_untrusted}, - {&opt_ref_cert}, {&opt_rsp_cert}, {&opt_rsp_extracerts}, {&opt_rsp_capubs}, + {&opt_ref_cert}, {&opt_rsp_cert}, {&opt_rsp_crl}, + {&opt_rsp_extracerts}, {&opt_rsp_capubs}, {&opt_rsp_newwithnew}, {&opt_rsp_newwithold}, {&opt_rsp_oldwithnew}, {(char **)&opt_poll_count}, {(char **)&opt_check_after}, @@ -1010,6 +1041,19 @@ static int setup_certs(char *files, const char *desc, void *ctx, return ok; } +static int setup_mock_crlout(void *ctx, const char *file, const char *desc) +{ + X509_CRL *crl; + int ok; + + if (file == NULL) + return 1; + if ((crl = load_crl(file, FORMAT_UNDEF, 0, desc)) == NULL) + return 0; + ok = ossl_cmp_mock_srv_set1_crlOut(ctx, crl); + X509_CRL_free(crl); + return ok; +} /* * parse and transform some options, checking their syntax. * Returns 1 on success, 0 on error @@ -1057,6 +1101,11 @@ static int transform_opts(void) CMP_err("unknown option given for certificate storing format"); return 0; } + if (opt_crlform_s != NULL + && !opt_format(opt_crlform_s, OPT_FMT_PEMDER, &opt_crlform)) { + CMP_err("unknown option given for CRL storing format"); + return 0; + } return 1; } @@ -1152,6 +1201,9 @@ static OSSL_CMP_SRV_CTX *setup_srv_ctx(ENGINE *engine) (add_X509_fn_t)ossl_cmp_mock_srv_set1_certOut)) goto err; } + if (!setup_mock_crlout(srv_ctx, opt_rsp_crl, + "CRL to be returned by the mock server")) + goto err; if (!setup_certs(opt_rsp_extracerts, "CMP extra certificates for mock server", srv_ctx, (add_X509_stack_fn_t)ossl_cmp_mock_srv_set1_chainOut)) @@ -1915,20 +1967,20 @@ static int add_certProfile(OSSL_CMP_CTX *ctx, const char *name) if ((sk = sk_ASN1_UTF8STRING_new_reserve(NULL, 1)) == NULL) return 0; - if ((utf8string = ASN1_UTF8STRING_new()) == NULL) - goto err; - if (!ASN1_STRING_set(utf8string, name, (int)strlen(name))) { - ASN1_STRING_free(utf8string); - goto err; - } - /* Due to sk_ASN1_UTF8STRING_new_reserve(NULL, 1), this surely succeeds: */ - (void)sk_ASN1_UTF8STRING_push(sk, utf8string); - if ((itav = OSSL_CMP_ITAV_new0_certProfile(sk)) == NULL) - goto err; - if (OSSL_CMP_CTX_push0_geninfo_ITAV(ctx, itav)) - return 1; - OSSL_CMP_ITAV_free(itav); - return 0; + if ((utf8string = ASN1_UTF8STRING_new()) == NULL) + goto err; + if (!ASN1_STRING_set(utf8string, name, (int)strlen(name))) { + ASN1_STRING_free(utf8string); + goto err; + } + /* Due to sk_ASN1_UTF8STRING_new_reserve(NULL, 1), this surely succeeds: */ + (void)sk_ASN1_UTF8STRING_push(sk, utf8string); + if ((itav = OSSL_CMP_ITAV_new0_certProfile(sk)) == NULL) + goto err; + if (OSSL_CMP_CTX_push0_geninfo_ITAV(ctx, itav)) + return 1; + OSSL_CMP_ITAV_free(itav); + return 0; err: sk_ASN1_UTF8STRING_pop_free(sk, ASN1_UTF8STRING_free); @@ -1973,7 +2025,7 @@ static int handle_opt_geninfo(OSSL_CMP_CTX *ctx) if (*ptr != '\0') { if (*ptr != ',') { CMP_err1("Missing ',' or end of -geninfo arg after int at %.40s", - ptr); + ptr); goto err; } ptr++; @@ -2132,6 +2184,17 @@ static int setup_client_ctx(OSSL_CMP_CTX *ctx, ENGINE *engine) if (opt_oldwithnew != NULL) CMP_warn1("-oldwithnew %s", msg); } + if (opt_cmd != CMP_GENM || opt_infotype != NID_id_it_certReqTemplate) { + const char *msg = "option is ignored unless -cmd 'genm' and -infotype 'certReqTemplate' is given"; + + if (opt_template != NULL) + CMP_warn1("-template %s", msg); + if (opt_keyspec != NULL) + CMP_warn1("-keyspec %s", msg); + } else { + if (opt_template == NULL) + CMP_err("missing -template option for genm with infotype certReqTemplate"); + } if (!setup_verification_ctx(ctx)) goto err; @@ -2248,6 +2311,18 @@ static int write_cert(BIO *bio, X509 *cert) return 0; } +static int write_crl(BIO *bio, X509_CRL *crl) +{ + if (opt_crlform != FORMAT_PEM && opt_crlform != FORMAT_ASN1) { + BIO_printf(bio_err, "error: unsupported type '%s' for writing CRLs\n", + opt_crlform_s); + return 0; + } + + return opt_crlform == FORMAT_PEM ? PEM_write_bio_X509_CRL(bio, crl) + : i2d_X509_CRL_bio(bio, crl); +} + /* * If file != NULL writes out a stack of certs to the given file. * If certs is NULL, the file is emptied. @@ -2295,6 +2370,35 @@ static int save_free_certs(STACK_OF(X509) *certs, return n; } +static int save_crl(X509_CRL *crl, + const char *file, const char *desc) +{ + BIO *bio = NULL; + int res = 0; + + if (file == NULL) + return 1; + if (crl != NULL) + CMP_info2("received %s, saving to file '%s'", desc, file); + + if ((bio = BIO_new(BIO_s_file())) == NULL + || !BIO_write_filename(bio, (char *)file)) { + CMP_err2("could not open file '%s' for writing %s", + file, desc); + goto end; + } + + if (!write_crl(bio, crl)) { + CMP_err2("cannot write %s to file '%s'", desc, file); + goto end; + } + res = 1; + + end: + BIO_free(bio); + return res; +} + static int delete_file(const char *file, const char *desc) { if (file == NULL) @@ -2328,6 +2432,64 @@ static int save_cert_or_delete(X509 *cert, const char *file, const char *desc) } } +static int save_crl_or_delete(X509_CRL *crl, const char *file, const char *desc) +{ + if (file == NULL) + return 1; + return (crl == NULL) ? delete_file(file, desc) : save_crl(crl, file, desc); +} + +static int save_template(const char *file, const OSSL_CRMF_CERTTEMPLATE *tmpl) +{ + BIO *bio = BIO_new_file(file, "wb"); + + if (bio == NULL) { + CMP_err1("error saving certTemplate from genp: cannot open file %s", + file); + return 0; + } + if (!ASN1_i2d_bio_of(OSSL_CRMF_CERTTEMPLATE, i2d_OSSL_CRMF_CERTTEMPLATE, + bio, tmpl)) { + CMP_err1("error saving certTemplate from genp: cannot write file %s", + file); + return 0; + } else { + CMP_info1("stored certTemplate from genp to file '%s'", file); + } + BIO_free(bio); + return 1; +} + +static int save_keyspec(const char *file, const OSSL_CMP_ATAVS *keyspec) +{ + BIO *bio = BIO_new_file(file, "wb"); + + if (bio == NULL) { + CMP_err1("error saving keySpec from genp: cannot open file %s", file); + return 0; + } + + if (!ASN1_i2d_bio_of(OSSL_CMP_ATAVS, i2d_OSSL_CMP_ATAVS, bio, keyspec)) { + CMP_err1("error saving keySpec from genp: cannot write file %s", file); + return 0; + } else { + CMP_info1("stored keySpec from genp to file '%s'", file); + } + BIO_free(bio); + return 1; +} + +static const char *nid_name(int nid) +{ + const char *name = OBJ_nid2ln(nid); + + if (name == NULL) + name = OBJ_nid2sn(nid); + if (name == NULL) + name = ""; + return name; +} + static int print_itavs(const STACK_OF(OSSL_CMP_ITAV) *itavs) { int i, ret = 1; @@ -2727,6 +2889,15 @@ static int get_opts(int argc, char **argv) case OPT_OLDWITHNEW: opt_oldwithnew = opt_str(); break; + case OPT_CRLCERT: + opt_crlcert = opt_str(); + break; + case OPT_OLDCRL: + opt_oldcrl = opt_str(); + break; + case OPT_CRLOUT: + opt_crlout = opt_str(); + break; case OPT_V_CASES: if (!opt_verify(o, vpm)) @@ -2744,6 +2915,12 @@ static int get_opts(int argc, char **argv) case OPT_GENINFO: opt_geninfo = opt_str(); break; + case OPT_TEMPLATE: + opt_template = opt_str(); + break; + case OPT_KEYSPEC: + opt_keyspec = opt_str(); + break; case OPT_NEWKEY: opt_newkey = opt_str(); @@ -2822,6 +2999,9 @@ static int get_opts(int argc, char **argv) case OPT_CERTFORM: opt_certform_s = opt_str(); break; + case OPT_CRLFORM: + opt_crlform_s = opt_str(); + break; case OPT_KEYFORM: opt_keyform_s = opt_str(); break; @@ -2905,6 +3085,9 @@ static int get_opts(int argc, char **argv) case OPT_RSP_CERT: opt_rsp_cert = opt_str(); break; + case OPT_RSP_CRL: + opt_rsp_crl = opt_str(); + break; case OPT_RSP_EXTRACERTS: opt_rsp_extracerts = opt_str(); break; @@ -3047,6 +3230,71 @@ static int cmp_server(OSSL_CMP_CTX *srv_cmp_ctx) } #endif +static void print_keyspec(OSSL_CMP_ATAVS *keySpec) +{ + const char *desc = "specifications contained in keySpec from genp"; + BIO *mem; + int i; + const char *p; + long len; + + if (keySpec == NULL) { + CMP_info1("No %s", desc); + return; + } + + mem = BIO_new(BIO_s_mem()); + if (mem == NULL) { + CMP_err1("Out of memory - cannot dump key %s", desc); + return; + } + BIO_printf(mem, "Key %s:\n", desc); + + for (i = 0; i < sk_OSSL_CMP_ATAV_num(keySpec); i++) { + OSSL_CMP_ATAV *atav = sk_OSSL_CMP_ATAV_value(keySpec, i); + ASN1_OBJECT *type = OSSL_CMP_ATAV_get0_type(atav /* may be NULL */); + int nid = OBJ_obj2nid(type); + + switch (nid) { + case NID_id_regCtrl_algId: + { + X509_ALGOR *alg = OSSL_CMP_ATAV_get0_algId(atav); + const ASN1_OBJECT *oid; + int paramtype; + const void *param; + + X509_ALGOR_get0(&oid, ¶mtype, ¶m, alg); + BIO_printf(mem, "Key algorithm: "); + i2a_ASN1_OBJECT(mem, oid); + if (paramtype == V_ASN1_UNDEF || alg->parameter == NULL) { + BIO_printf(mem, "\n"); + } else { + BIO_printf(mem, " - "); + ASN1_item_print(mem, (ASN1_VALUE *)alg, + 0, ASN1_ITEM_rptr(X509_ALGOR), NULL); + } + } + break; + case NID_id_regCtrl_rsaKeyLen: + BIO_printf(mem, "Key algorithm: RSA %d\n", + OSSL_CMP_ATAV_get_rsaKeyLen(atav)); + break; + default: + BIO_printf(mem, "Invalid key spec: %s\n", nid_name(nid)); + break; + } + } + BIO_printf(mem, "End of key %s", desc); + + len = BIO_get_mem_data(mem, &p); + if (len > INT_MAX) + CMP_err1("Info too large - cannot dump key %s", desc); + else + CMP_info2("%.*s", (int)len, p); + BIO_free(mem); + return; +} + static void print_status(void) { /* print PKIStatusInfo */ @@ -3141,6 +3389,94 @@ static int do_genm(OSSL_CMP_CTX *ctx) end_upd: X509_free(oldwithold); return res; + } else if (opt_infotype == NID_id_it_crlStatusList) { + X509_CRL *oldcrl = NULL, *crl = NULL; + X509 *crlcert = NULL; + int res = 0; + const char *desc = "CRL from genp of type 'crls'"; + + if (opt_oldcrl == NULL && opt_crlcert == NULL) { + CMP_err("Missing -oldcrl and no -crlcert given for -infotype crlStatusList"); + return 0; + } + if (opt_crlout == NULL) { + CMP_err("Missing -crlout for -infotype crlStatusList"); + return 0; + } + + if (opt_crlcert != NULL) { + crlcert = load_cert_pwd(opt_crlcert, opt_otherpass, + "Cert for genm with -infotype crlStatusList"); + if (crlcert == NULL) + goto end_crlupd; + } + + if (opt_oldcrl != NULL) { + oldcrl = load_crl(opt_oldcrl, FORMAT_UNDEF, 0, + "CRL for genm with -infotype crlStatusList"); + if (oldcrl == NULL) + goto end_crlupd; + } + + if (opt_oldcrl != NULL && opt_crlcert != NULL) { + if (X509_NAME_cmp(X509_CRL_get_issuer(oldcrl), + X509_get_issuer_name(crlcert)) + != 0) + CMP_warn("-oldcrl and -crlcert have different issuer"); + } + + if (!OSSL_CMP_get1_crlUpdate(ctx, crlcert, oldcrl, &crl)) + goto end_crlupd; + + if (crl == NULL) + CMP_info("no CRL update available"); + if (!save_crl_or_delete(crl, opt_crlout, desc)) + goto end_crlupd; + + res = 1; + + end_crlupd: + X509_free(crlcert); + X509_CRL_free(oldcrl); + X509_CRL_free(crl); + return res; + + } else if (opt_infotype == NID_id_it_certReqTemplate) { + OSSL_CRMF_CERTTEMPLATE *certTemplate; + OSSL_CMP_ATAVS *keySpec; + int res = 0; + + if (!OSSL_CMP_get1_certReqTemplate(ctx, &certTemplate, &keySpec)) + return 0; + + if (certTemplate == NULL) { + CMP_warn("no certificate request template available"); + if (!delete_file(opt_template, "certTemplate from genp")) + return 0; + if (opt_keyspec != NULL + && !delete_file(opt_keyspec, "keySpec from genp")) + return 0; + return 1; + } + if (!save_template(opt_template, certTemplate)) + goto tmpl_end; + + print_keyspec(keySpec); + if (opt_keyspec != NULL) { + if (keySpec == NULL) { + CMP_warn("no key specifications available"); + if (!delete_file(opt_keyspec, "keySpec from genp")) + goto tmpl_end; + } else if (!save_keyspec(opt_keyspec, keySpec)) { + goto tmpl_end; + } + } + + res = 1; + tmpl_end: + OSSL_CRMF_CERTTEMPLATE_free(certTemplate); + sk_OSSL_CMP_ATAV_pop_free(keySpec, OSSL_CMP_ATAV_free); + return res; } else { OSSL_CMP_ITAV *req; STACK_OF(OSSL_CMP_ITAV) *itavs; @@ -3358,10 +3694,10 @@ int cmp_main(int argc, char **argv) if (opt_reqout_only != NULL) { const char *msg = "option is ignored since -reqout_only option is given"; -#if !defined(OPENSSL_NO_SOCK) && !defined(OPENSSL_NO_HTTP) +# if !defined(OPENSSL_NO_SOCK) && !defined(OPENSSL_NO_HTTP) if (opt_server != NULL) CMP_warn1("-server %s", msg); -#endif +# endif if (opt_use_mock_srv) CMP_warn1("-use_mock_srv %s", msg); if (opt_reqout != NULL) diff --git a/apps/cms.c b/apps/cms.c index ac5f78ecc2..c225f07ac0 100644 --- a/apps/cms.c +++ b/apps/cms.c @@ -175,7 +175,10 @@ const OPTIONS cms_options[] = { OPT_SECTION("Signing"), {"md", OPT_MD, 's', "Digest algorithm to use"}, {"signer", OPT_SIGNER, 's', "Signer certificate input file"}, - {"certfile", OPT_CERTFILE, '<', "Other certificates file"}, + {"certfile", OPT_CERTFILE, '<', + "Extra signer and intermediate CA certificates to include when signing"}, + {OPT_MORE_STR, 0, 0, + "or to use as preferred signer certs and for chain building when verifying"}, {"cades", OPT_CADES, '-', "Include signingCertificate attribute (CAdES-BES)"}, {"nodetach", OPT_NODETACH, '-', "Use opaque signing"}, diff --git a/apps/dgst.c b/apps/dgst.c index 2511a2ffc1..50e4477aef 100644 --- a/apps/dgst.c +++ b/apps/dgst.c @@ -419,7 +419,7 @@ int dgst_main(int argc, char **argv) md_name = EVP_MD_get0_name(md); if (xoflen > 0) { - if (!(EVP_MD_get_flags(md) & EVP_MD_FLAG_XOF)) { + if (!EVP_MD_xof(md)) { BIO_printf(bio_err, "Length can only be specified for XOF\n"); goto end; } diff --git a/apps/fipsinstall.c b/apps/fipsinstall.c index 6d86bb44e2..203f397a48 100644 --- a/apps/fipsinstall.c +++ b/apps/fipsinstall.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -38,8 +38,30 @@ typedef enum OPTION_choice { OPT_NO_LOG, OPT_CORRUPT_DESC, OPT_CORRUPT_TYPE, OPT_QUIET, OPT_CONFIG, OPT_NO_CONDITIONAL_ERRORS, OPT_NO_SECURITY_CHECKS, - OPT_TLS_PRF_EMS_CHECK, + OPT_TLS_PRF_EMS_CHECK, OPT_NO_SHORT_MAC, + OPT_DISALLOW_PKCS15_PADDING, OPT_RSA_PSS_SALTLEN_CHECK, + OPT_DISALLOW_SIGNATURE_X931_PADDING, + OPT_HMAC_KEY_CHECK, OPT_KMAC_KEY_CHECK, OPT_DISALLOW_DRGB_TRUNC_DIGEST, + OPT_SIGNATURE_DIGEST_CHECK, + OPT_HKDF_DIGEST_CHECK, + OPT_TLS13_KDF_DIGEST_CHECK, + OPT_TLS1_PRF_DIGEST_CHECK, + OPT_SSHKDF_DIGEST_CHECK, + OPT_SSKDF_DIGEST_CHECK, + OPT_X963KDF_DIGEST_CHECK, + OPT_DISALLOW_DSA_SIGN, + OPT_DISALLOW_TDES_ENCRYPT, + OPT_HKDF_KEY_CHECK, + OPT_KBKDF_KEY_CHECK, + OPT_TLS13_KDF_KEY_CHECK, + OPT_TLS1_PRF_KEY_CHECK, + OPT_SSHKDF_KEY_CHECK, + OPT_SSKDF_KEY_CHECK, + OPT_X963KDF_KEY_CHECK, + OPT_X942KDF_KEY_CHECK, + OPT_NO_PBKDF2_LOWER_BOUND_CHECK, + OPT_ECDH_COFACTOR_CHECK, OPT_SELF_TEST_ONLOAD, OPT_SELF_TEST_ONINSTALL } OPTION_CHOICE; @@ -48,7 +70,7 @@ const OPTIONS fipsinstall_options[] = { {"help", OPT_HELP, '-', "Display this summary"}, {"pedantic", OPT_PEDANTIC, '-', "Set options for strict FIPS compliance"}, {"verify", OPT_VERIFY, '-', - "Verify a config file instead of generating one"}, + "Verify a config file instead of generating one"}, {"module", OPT_MODULE, '<', "File name of the provider module"}, {"provider_name", OPT_PROV_NAME, 's', "FIPS provider name"}, {"section_name", OPT_SECTION_NAME, 's', @@ -64,8 +86,55 @@ const OPTIONS fipsinstall_options[] = { "Forces self tests to run once on module installation"}, {"ems_check", OPT_TLS_PRF_EMS_CHECK, '-', "Enable the run-time FIPS check for EMS during TLS1_PRF"}, + {"no_short_mac", OPT_NO_SHORT_MAC, '-', "Disallow short MAC output"}, {"no_drbg_truncated_digests", OPT_DISALLOW_DRGB_TRUNC_DIGEST, '-', "Disallow truncated digests with Hash and HMAC DRBGs"}, + {"signature_digest_check", OPT_SIGNATURE_DIGEST_CHECK, '-', + "Enable checking for approved digests for signatures"}, + {"hmac_key_check", OPT_HMAC_KEY_CHECK, '-', "Enable key check for HMAC"}, + {"kmac_key_check", OPT_KMAC_KEY_CHECK, '-', "Enable key check for KMAC"}, + {"hkdf_digest_check", OPT_HKDF_DIGEST_CHECK, '-', + "Enable digest check for HKDF"}, + {"tls13_kdf_digest_check", OPT_TLS13_KDF_DIGEST_CHECK, '-', + "Enable digest check for TLS13-KDF"}, + {"tls1_prf_digest_check", OPT_TLS1_PRF_DIGEST_CHECK, '-', + "Enable digest check for TLS1-PRF"}, + {"sshkdf_digest_check", OPT_SSHKDF_DIGEST_CHECK, '-', + "Enable digest check for SSHKDF"}, + {"sskdf_digest_check", OPT_SSKDF_DIGEST_CHECK, '-', + "Enable digest check for SSKDF"}, + {"x963kdf_digest_check", OPT_X963KDF_DIGEST_CHECK, '-', + "Enable digest check for X963KDF"}, + {"dsa_sign_disabled", OPT_DISALLOW_DSA_SIGN, '-', + "Disallow DSA signing"}, + {"tdes_encrypt_disabled", OPT_DISALLOW_TDES_ENCRYPT, '-', + "Disallow Triple-DES encryption"}, + {"rsa_pkcs15_padding_disabled", OPT_DISALLOW_PKCS15_PADDING, '-', + "Disallow PKCS#1 version 1.5 padding for RSA encryption"}, + {"rsa_pss_saltlen_check", OPT_RSA_PSS_SALTLEN_CHECK, '-', + "Enable salt length check for RSA-PSS signature operations"}, + {"rsa_sign_x931_disabled", OPT_DISALLOW_SIGNATURE_X931_PADDING, '-', + "Disallow X931 Padding for RSA signing"}, + {"hkdf_key_check", OPT_HKDF_KEY_CHECK, '-', + "Enable key check for HKDF"}, + {"kbkdf_key_check", OPT_KBKDF_KEY_CHECK, '-', + "Enable key check for KBKDF"}, + {"tls13_kdf_key_check", OPT_TLS13_KDF_KEY_CHECK, '-', + "Enable key check for TLS13-KDF"}, + {"tls1_prf_key_check", OPT_TLS1_PRF_KEY_CHECK, '-', + "Enable key check for TLS1-PRF"}, + {"sshkdf_key_check", OPT_SSHKDF_KEY_CHECK, '-', + "Enable key check for SSHKDF"}, + {"sskdf_key_check", OPT_SSKDF_KEY_CHECK, '-', + "Enable key check for SSKDF"}, + {"x963kdf_key_check", OPT_X963KDF_KEY_CHECK, '-', + "Enable key check for X963KDF"}, + {"x942kdf_key_check", OPT_X942KDF_KEY_CHECK, '-', + "Enable key check for X942KDF"}, + {"no_pbkdf2_lower_bound_check", OPT_NO_PBKDF2_LOWER_BOUND_CHECK, '-', + "Disable lower bound check for PBKDF2"}, + {"ecdh_cofactor_check", OPT_ECDH_COFACTOR_CHECK, '-', + "Enable Cofactor check for ECDH"}, OPT_SECTION("Input"), {"in", OPT_IN, '<', "Input config file, used when verifying"}, @@ -86,8 +155,33 @@ typedef struct { unsigned int self_test_onload : 1; unsigned int conditional_errors : 1; unsigned int security_checks : 1; + unsigned int hmac_key_check : 1; + unsigned int kmac_key_check : 1; unsigned int tls_prf_ems_check : 1; + unsigned int no_short_mac : 1; unsigned int drgb_no_trunc_dgst : 1; + unsigned int signature_digest_check : 1; + unsigned int hkdf_digest_check : 1; + unsigned int tls13_kdf_digest_check : 1; + unsigned int tls1_prf_digest_check : 1; + unsigned int sshkdf_digest_check : 1; + unsigned int sskdf_digest_check : 1; + unsigned int x963kdf_digest_check : 1; + unsigned int dsa_sign_disabled : 1; + unsigned int tdes_encrypt_disabled : 1; + unsigned int rsa_pkcs15_padding_disabled : 1; + unsigned int rsa_pss_saltlen_check : 1; + unsigned int sign_x931_padding_disabled : 1; + unsigned int hkdf_key_check : 1; + unsigned int kbkdf_key_check : 1; + unsigned int tls13_kdf_key_check : 1; + unsigned int tls1_prf_key_check : 1; + unsigned int sshkdf_key_check : 1; + unsigned int sskdf_key_check : 1; + unsigned int x963kdf_key_check : 1; + unsigned int x942kdf_key_check : 1; + unsigned int pbkdf2_lower_bound_check : 1; + unsigned int ecdh_cofactor_check : 1; } FIPS_OPTS; /* Pedantic FIPS compliance */ @@ -95,8 +189,33 @@ static const FIPS_OPTS pedantic_opts = { 1, /* self_test_onload */ 1, /* conditional_errors */ 1, /* security_checks */ + 1, /* hmac_key_check */ + 1, /* kmac_key_check */ 1, /* tls_prf_ems_check */ + 1, /* no_short_mac */ 1, /* drgb_no_trunc_dgst */ + 1, /* signature_digest_check */ + 1, /* hkdf_digest_check */ + 1, /* tls13_kdf_digest_check */ + 1, /* tls1_prf_digest_check */ + 1, /* sshkdf_digest_check */ + 1, /* sskdf_digest_check */ + 1, /* x963kdf_digest_check */ + 1, /* dsa_sign_disabled */ + 1, /* tdes_encrypt_disabled */ + 1, /* rsa_pkcs15_padding_disabled */ + 1, /* rsa_pss_saltlen_check */ + 1, /* sign_x931_padding_disabled */ + 1, /* hkdf_key_check */ + 1, /* kbkdf_key_check */ + 1, /* tls13_kdf_key_check */ + 1, /* tls1_prf_key_check */ + 1, /* sshkdf_key_check */ + 1, /* sskdf_key_check */ + 1, /* x963kdf_key_check */ + 1, /* x942kdf_key_check */ + 1, /* pbkdf2_lower_bound_check */ + 1, /* ecdh_cofactor_check */ }; /* Default FIPS settings for backward compatibility */ @@ -104,8 +223,33 @@ static FIPS_OPTS fips_opts = { 1, /* self_test_onload */ 1, /* conditional_errors */ 1, /* security_checks */ + 0, /* hmac_key_check */ + 0, /* kmac_key_check */ 0, /* tls_prf_ems_check */ + 0, /* no_short_mac */ 0, /* drgb_no_trunc_dgst */ + 0, /* signature_digest_check */ + 0, /* hkdf_digest_check */ + 0, /* tls13_kdf_digest_check */ + 0, /* tls1_prf_digest_check */ + 0, /* sshkdf_digest_check */ + 0, /* sskdf_digest_check */ + 0, /* x963kdf_digest_check */ + 0, /* dsa_sign_disabled */ + 0, /* tdes_encrypt_disabled */ + 0, /* rsa_pkcs15_padding_disabled */ + 0, /* rsa_pss_saltlen_check */ + 0, /* sign_x931_padding_disabled */ + 0, /* hkdf_key_check */ + 0, /* kbkdf_key_check */ + 0, /* tls13_kdf_key_check */ + 0, /* tls1_prf_key_check */ + 0, /* sshkdf_key_check */ + 0, /* sskdf_key_check */ + 0, /* x963kdf_key_check */ + 0, /* x942kdf_key_check */ + 1, /* pbkdf2_lower_bound_check */ + 0, /* ecdh_cofactor_check */ }; static int check_non_pedantic_fips(int pedantic, const char *name) @@ -223,12 +367,71 @@ static int write_config_fips_section(BIO *out, const char *section, VERSION_VAL) <= 0 || BIO_printf(out, "%s = %s\n", OSSL_PROV_FIPS_PARAM_CONDITIONAL_ERRORS, opts->conditional_errors ? "1" : "0") <= 0 - || BIO_printf(out, "%s = %s\n", OSSL_PROV_FIPS_PARAM_SECURITY_CHECKS, + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_SECURITY_CHECKS, opts->security_checks ? "1" : "0") <= 0 - || BIO_printf(out, "%s = %s\n", OSSL_PROV_FIPS_PARAM_TLS1_PRF_EMS_CHECK, + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_HMAC_KEY_CHECK, + opts->hmac_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_KMAC_KEY_CHECK, + opts->kmac_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_TLS1_PRF_EMS_CHECK, opts->tls_prf_ems_check ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_NO_SHORT_MAC, + opts->no_short_mac ? "1" : "0") <= 0 || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_DRBG_TRUNC_DIGEST, opts->drgb_no_trunc_dgst ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_SIGNATURE_DIGEST_CHECK, + opts->signature_digest_check ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_HKDF_DIGEST_CHECK, + opts->hkdf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_TLS13_KDF_DIGEST_CHECK, + opts->tls13_kdf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_TLS1_PRF_DIGEST_CHECK, + opts->tls1_prf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_SSHKDF_DIGEST_CHECK, + opts->sshkdf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_SSKDF_DIGEST_CHECK, + opts->sskdf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_X963KDF_DIGEST_CHECK, + opts->x963kdf_digest_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_DSA_SIGN_DISABLED, + opts->dsa_sign_disabled ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_TDES_ENCRYPT_DISABLED, + opts->tdes_encrypt_disabled ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_RSA_PKCS15_PAD_DISABLED, + opts->rsa_pkcs15_padding_disabled ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_RSA_PSS_SALTLEN_CHECK, + opts->rsa_pss_saltlen_check ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_RSA_SIGN_X931_PAD_DISABLED, + opts->sign_x931_padding_disabled ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_HKDF_KEY_CHECK, + opts->hkdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_KBKDF_KEY_CHECK, + opts->kbkdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_TLS13_KDF_KEY_CHECK, + opts->tls13_kdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_TLS1_PRF_KEY_CHECK, + opts->tls1_prf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_SSHKDF_KEY_CHECK, + opts->sshkdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_SSKDF_KEY_CHECK, + opts->sskdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_X963KDF_KEY_CHECK, + opts->x963kdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_X942KDF_KEY_CHECK, + opts->x942kdf_key_check ? "1": "0") <= 0 + || BIO_printf(out, "%s = %s\n", + OSSL_PROV_PARAM_PBKDF2_LOWER_BOUND_CHECK, + opts->pbkdf2_lower_bound_check ? "1" : "0") <= 0 + || BIO_printf(out, "%s = %s\n", OSSL_PROV_PARAM_ECDH_COFACTOR_CHECK, + opts->ecdh_cofactor_check ? "1": "0") <= 0 || !print_mac(out, OSSL_PROV_FIPS_PARAM_MODULE_MAC, module_mac, module_mac_len)) goto end; @@ -238,7 +441,7 @@ static int write_config_fips_section(BIO *out, const char *section, install_mac_len) || BIO_printf(out, "%s = %s\n", OSSL_PROV_FIPS_PARAM_INSTALL_STATUS, INSTALL_STATUS_VAL) <= 0) - goto end; + goto end; } ret = 1; end: @@ -255,12 +458,12 @@ static CONF *generate_config_and_load(const char *prov_name, CONF *conf = NULL; mem_bio = BIO_new(BIO_s_mem()); - if (mem_bio == NULL) + if (mem_bio == NULL) return 0; if (!write_config_header(mem_bio, prov_name, section) - || !write_config_fips_section(mem_bio, section, - module_mac, module_mac_len, - opts, NULL, 0)) + || !write_config_fips_section(mem_bio, section, + module_mac, module_mac_len, + opts, NULL, 0)) goto end; conf = app_load_config_bio(mem_bio, NULL); @@ -382,7 +585,7 @@ int fipsinstall_main(int argc, char **argv) switch (o) { case OPT_EOF: case OPT_ERR: -opthelp: + opthelp: BIO_printf(bio_err, "%s: Use -help for summary.\n", prog); goto cleanup; case OPT_HELP: @@ -409,12 +612,89 @@ int fipsinstall_main(int argc, char **argv) goto end; fips_opts.security_checks = 0; break; + case OPT_HMAC_KEY_CHECK: + fips_opts.hmac_key_check = 1; + break; + case OPT_KMAC_KEY_CHECK: + fips_opts.kmac_key_check = 1; + break; case OPT_TLS_PRF_EMS_CHECK: fips_opts.tls_prf_ems_check = 1; break; + case OPT_NO_SHORT_MAC: + fips_opts.no_short_mac = 1; + break; case OPT_DISALLOW_DRGB_TRUNC_DIGEST: fips_opts.drgb_no_trunc_dgst = 1; break; + case OPT_SIGNATURE_DIGEST_CHECK: + fips_opts.signature_digest_check = 1; + break; + case OPT_HKDF_DIGEST_CHECK: + fips_opts.hkdf_digest_check = 1; + break; + case OPT_TLS13_KDF_DIGEST_CHECK: + fips_opts.tls13_kdf_digest_check = 1; + break; + case OPT_TLS1_PRF_DIGEST_CHECK: + fips_opts.tls1_prf_digest_check = 1; + break; + case OPT_SSHKDF_DIGEST_CHECK: + fips_opts.sshkdf_digest_check = 1; + break; + case OPT_SSKDF_DIGEST_CHECK: + fips_opts.sskdf_digest_check = 1; + break; + case OPT_X963KDF_DIGEST_CHECK: + fips_opts.x963kdf_digest_check = 1; + break; + case OPT_DISALLOW_DSA_SIGN: + fips_opts.dsa_sign_disabled = 1; + break; + case OPT_DISALLOW_TDES_ENCRYPT: + fips_opts.tdes_encrypt_disabled = 1; + break; + case OPT_RSA_PSS_SALTLEN_CHECK: + fips_opts.rsa_pss_saltlen_check = 1; + break; + case OPT_DISALLOW_SIGNATURE_X931_PADDING: + fips_opts.sign_x931_padding_disabled = 1; + break; + case OPT_DISALLOW_PKCS15_PADDING: + fips_opts.rsa_pkcs15_padding_disabled = 1; + break; + case OPT_HKDF_KEY_CHECK: + fips_opts.hkdf_key_check = 1; + break; + case OPT_KBKDF_KEY_CHECK: + fips_opts.kbkdf_key_check = 1; + break; + case OPT_TLS13_KDF_KEY_CHECK: + fips_opts.tls13_kdf_key_check = 1; + break; + case OPT_TLS1_PRF_KEY_CHECK: + fips_opts.tls1_prf_key_check = 1; + break; + case OPT_SSHKDF_KEY_CHECK: + fips_opts.sshkdf_key_check = 1; + break; + case OPT_SSKDF_KEY_CHECK: + fips_opts.sskdf_key_check = 1; + break; + case OPT_X963KDF_KEY_CHECK: + fips_opts.x963kdf_key_check = 1; + break; + case OPT_X942KDF_KEY_CHECK: + fips_opts.x942kdf_key_check = 1; + break; + case OPT_NO_PBKDF2_LOWER_BOUND_CHECK: + if (!check_non_pedantic_fips(pedantic, "no_pbkdf2_lower_bound_check")) + goto end; + fips_opts.pbkdf2_lower_bound_check = 0; + break; + case OPT_ECDH_COFACTOR_CHECK: + fips_opts.ecdh_cofactor_check = 1; + break; case OPT_QUIET: quiet = 1; /* FALLTHROUGH */ @@ -478,7 +758,7 @@ int fipsinstall_main(int argc, char **argv) ret = OSSL_PROVIDER_available(NULL, prov_name) ? 0 : 1; if (!quiet) { BIO_printf(bio_err, "FIPS provider is %s\n", - ret == 0 ? "available" : " not available"); + ret == 0 ? "available" : "not available"); } } goto end; diff --git a/apps/include/apps.h b/apps/include/apps.h index a1b2cbbdc3..7c5510976d 100644 --- a/apps/include/apps.h +++ b/apps/include/apps.h @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -82,8 +82,12 @@ int has_stdin_waiting(void); # endif void corrupt_signature(const ASN1_STRING *signature); + +/* Helpers for setting X509v3 certificate fields notBefore and notAfter */ +int check_cert_time_string(const char *time, const char *desc); int set_cert_times(X509 *x, const char *startdate, const char *enddate, - int days); + int days, int strict_compare_times); + int set_crl_lastupdate(X509_CRL *crl, const char *lastupdate); int set_crl_nextupdate(X509_CRL *crl, const char *nextupdate, long days, long hours, long secs); diff --git a/apps/include/cmp_mock_srv.h b/apps/include/cmp_mock_srv.h index fcc1ef7bb4..cddbe8bef5 100644 --- a/apps/include/cmp_mock_srv.h +++ b/apps/include/cmp_mock_srv.h @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Siemens AG 2018-2020 * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -22,6 +22,7 @@ void ossl_cmp_mock_srv_free(OSSL_CMP_SRV_CTX *srv_ctx); int ossl_cmp_mock_srv_set1_refCert(OSSL_CMP_SRV_CTX *srv_ctx, X509 *cert); int ossl_cmp_mock_srv_set1_certOut(OSSL_CMP_SRV_CTX *srv_ctx, X509 *cert); +int ossl_cmp_mock_srv_set1_crlOut(OSSL_CMP_SRV_CTX *srv_ctx, X509_CRL *crl); int ossl_cmp_mock_srv_set1_chainOut(OSSL_CMP_SRV_CTX *srv_ctx, STACK_OF(X509) *chain); int ossl_cmp_mock_srv_set1_caPubsOut(OSSL_CMP_SRV_CTX *srv_ctx, diff --git a/apps/include/platform.h b/apps/include/platform.h index 491559df31..62fc99c5fd 100644 --- a/apps/include/platform.h +++ b/apps/include/platform.h @@ -1,5 +1,5 @@ /* - * Copyright 2019 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,7 +16,7 @@ /* * VMS C only for now, implemented in vms_decc_init.c * If other C compilers forget to terminate argv with NULL, this function - * can be re-used. + * can be reused. */ char **copy_argv(int *argc, char *argv[]); # endif diff --git a/apps/info.c b/apps/info.c index befc62dac1..5a469eed96 100644 --- a/apps/info.c +++ b/apps/info.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -14,7 +14,7 @@ typedef enum OPTION_choice { OPT_COMMON, OPT_CONFIGDIR, OPT_ENGINESDIR, OPT_MODULESDIR, OPT_DSOEXT, OPT_DIRNAMESEP, - OPT_LISTSEP, OPT_SEEDS, OPT_CPUSETTINGS + OPT_LISTSEP, OPT_SEEDS, OPT_CPUSETTINGS, OPT_WINDOWSCONTEXT } OPTION_CHOICE; const OPTIONS info_options[] = { @@ -32,6 +32,7 @@ const OPTIONS info_options[] = { {"listsep", OPT_LISTSEP, '-', "List separator character"}, {"seeds", OPT_SEEDS, '-', "Seed sources"}, {"cpusettings", OPT_CPUSETTINGS, '-', "CPU settings info"}, + {"windowscontext", OPT_WINDOWSCONTEXT, '-', "Windows install context"}, {NULL} }; @@ -40,6 +41,7 @@ int info_main(int argc, char **argv) int ret = 1, dirty = 0, type = 0; char *prog; OPTION_CHOICE o; + const char *typedata; prog = opt_init(argc, argv, info_options); while ((o = opt_next()) != OPT_EOF) { @@ -84,6 +86,10 @@ int info_main(int argc, char **argv) type = OPENSSL_INFO_CPU_SETTINGS; dirty++; break; + case OPT_WINDOWSCONTEXT: + type = OPENSSL_INFO_WINDOWS_CONTEXT; + dirty++; + break; } } if (!opt_check_rest_arg(NULL)) @@ -97,7 +103,8 @@ int info_main(int argc, char **argv) goto opthelp; } - BIO_printf(bio_out, "%s\n", OPENSSL_info(type)); + typedata = OPENSSL_info(type); + BIO_printf(bio_out, "%s\n", typedata == NULL ? "Undefined" : typedata); ret = 0; end: return ret; diff --git a/apps/lib/apps.c b/apps/lib/apps.c index 17a8538069..490ad99ade 100644 --- a/apps/lib/apps.c +++ b/apps/lib/apps.c @@ -1570,9 +1570,9 @@ int save_serial(const char *serialfile, const char *suffix, OPENSSL_strlcpy(buf[0], serialfile, BSIZE); } else { #ifndef OPENSSL_SYS_VMS - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", serialfile, suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", serialfile, suffix); #else - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", serialfile, suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", serialfile, suffix); #endif } out = BIO_new_file(buf[0], "w"); @@ -1614,11 +1614,11 @@ int rotate_serial(const char *serialfile, const char *new_suffix, goto err; } #ifndef OPENSSL_SYS_VMS - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", serialfile, new_suffix); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s.%s", serialfile, old_suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", serialfile, new_suffix); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s.%s", serialfile, old_suffix); #else - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", serialfile, new_suffix); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s-%s", serialfile, old_suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", serialfile, new_suffix); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s-%s", serialfile, old_suffix); #endif if (rename(serialfile, buf[1]) < 0 && errno != ENOENT #ifdef ENOTDIR @@ -1770,13 +1770,13 @@ int save_index(const char *dbfile, const char *suffix, CA_DB *db) goto err; } #ifndef OPENSSL_SYS_VMS - j = BIO_snprintf(buf[2], sizeof(buf[2]), "%s.attr", dbfile); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s.attr.%s", dbfile, suffix); - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", dbfile, suffix); + BIO_snprintf(buf[2], sizeof(buf[2]), "%s.attr", dbfile); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s.attr.%s", dbfile, suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", dbfile, suffix); #else - j = BIO_snprintf(buf[2], sizeof(buf[2]), "%s-attr", dbfile); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s-attr-%s", dbfile, suffix); - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", dbfile, suffix); + BIO_snprintf(buf[2], sizeof(buf[2]), "%s-attr", dbfile); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s-attr-%s", dbfile, suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", dbfile, suffix); #endif out = BIO_new_file(buf[0], "w"); if (out == NULL) { @@ -1820,17 +1820,17 @@ int rotate_index(const char *dbfile, const char *new_suffix, goto err; } #ifndef OPENSSL_SYS_VMS - j = BIO_snprintf(buf[4], sizeof(buf[4]), "%s.attr", dbfile); - j = BIO_snprintf(buf[3], sizeof(buf[3]), "%s.attr.%s", dbfile, old_suffix); - j = BIO_snprintf(buf[2], sizeof(buf[2]), "%s.attr.%s", dbfile, new_suffix); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s.%s", dbfile, old_suffix); - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", dbfile, new_suffix); + BIO_snprintf(buf[4], sizeof(buf[4]), "%s.attr", dbfile); + BIO_snprintf(buf[3], sizeof(buf[3]), "%s.attr.%s", dbfile, old_suffix); + BIO_snprintf(buf[2], sizeof(buf[2]), "%s.attr.%s", dbfile, new_suffix); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s.%s", dbfile, old_suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s.%s", dbfile, new_suffix); #else - j = BIO_snprintf(buf[4], sizeof(buf[4]), "%s-attr", dbfile); - j = BIO_snprintf(buf[3], sizeof(buf[3]), "%s-attr-%s", dbfile, old_suffix); - j = BIO_snprintf(buf[2], sizeof(buf[2]), "%s-attr-%s", dbfile, new_suffix); - j = BIO_snprintf(buf[1], sizeof(buf[1]), "%s-%s", dbfile, old_suffix); - j = BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", dbfile, new_suffix); + BIO_snprintf(buf[4], sizeof(buf[4]), "%s-attr", dbfile); + BIO_snprintf(buf[3], sizeof(buf[3]), "%s-attr-%s", dbfile, old_suffix); + BIO_snprintf(buf[2], sizeof(buf[2]), "%s-attr-%s", dbfile, new_suffix); + BIO_snprintf(buf[1], sizeof(buf[1]), "%s-%s", dbfile, old_suffix); + BIO_snprintf(buf[0], sizeof(buf[0]), "%s-%s", dbfile, new_suffix); #endif if (rename(dbfile, buf[1]) < 0 && errno != ENOENT #ifdef ENOTDIR @@ -3260,23 +3260,54 @@ void corrupt_signature(const ASN1_STRING *signature) s[signature->length - 1] ^= 0x1; } +int check_cert_time_string(const char *time, const char *desc) +{ + if (time == NULL || strcmp(time, "today") == 0 + || ASN1_TIME_set_string_X509(NULL, time)) + return 1; + BIO_printf(bio_err, + "%s is invalid, it should be \"today\" or have format [CC]YYMMDDHHMMSSZ\n", + desc); + return 0; +} + int set_cert_times(X509 *x, const char *startdate, const char *enddate, - int days) + int days, int strict_compare_times) { + if (!check_cert_time_string(startdate, "start date")) + return 0; + if (!check_cert_time_string(enddate, "end date")) + return 0; if (startdate == NULL || strcmp(startdate, "today") == 0) { - if (X509_gmtime_adj(X509_getm_notBefore(x), 0) == NULL) + if (X509_gmtime_adj(X509_getm_notBefore(x), 0) == NULL) { + BIO_printf(bio_err, "Error setting notBefore certificate field\n"); return 0; + } } else { - if (!ASN1_TIME_set_string_X509(X509_getm_notBefore(x), startdate)) + if (!ASN1_TIME_set_string_X509(X509_getm_notBefore(x), startdate)) { + BIO_printf(bio_err, "Error setting notBefore certificate field\n"); return 0; + } + } + if (enddate != NULL && strcmp(enddate, "today") == 0) { + enddate = NULL; + days = 0; } if (enddate == NULL) { - if (X509_time_adj_ex(X509_getm_notAfter(x), days, 0, NULL) - == NULL) + if (X509_time_adj_ex(X509_getm_notAfter(x), days, 0, NULL) == NULL) { + BIO_printf(bio_err, "Error setting notAfter certificate field\n"); return 0; + } } else if (!ASN1_TIME_set_string_X509(X509_getm_notAfter(x), enddate)) { + BIO_printf(bio_err, "Error setting notAfter certificate field\n"); return 0; } + if (ASN1_TIME_compare(X509_get0_notAfter(x), X509_get0_notBefore(x)) < 0) { + BIO_printf(bio_err, "%s: end date before start date\n", + strict_compare_times ? "Error" : "Warning"); + if (strict_compare_times) + return 0; + } return 1; } diff --git a/apps/lib/cmp_mock_srv.c b/apps/lib/cmp_mock_srv.c index 21fe404aa9..5bc166036e 100644 --- a/apps/lib/cmp_mock_srv.c +++ b/apps/lib/cmp_mock_srv.c @@ -16,10 +16,10 @@ #include /* the context for the CMP mock server */ -typedef struct -{ +typedef struct { X509 *refCert; /* cert to expect for oldCertID in kur/rr msg */ X509 *certOut; /* certificate to be returned in cp/ip/kup msg */ + X509_CRL *crlOut; /* CRL to be returned in genp for crls */ STACK_OF(X509) *chainOut; /* chain of certOut to add to extraCerts field */ STACK_OF(X509) *caPubsOut; /* used in caPubs of ip and in caCerts of genp */ X509 *newWithNew; /* to return in newWithNew of rootKeyUpdate */ @@ -87,6 +87,22 @@ static mock_srv_ctx *mock_srv_ctx_new(void) DEFINE_OSSL_SET1_CERT(refCert) DEFINE_OSSL_SET1_CERT(certOut) +int ossl_cmp_mock_srv_set1_crlOut(OSSL_CMP_SRV_CTX *srv_ctx, + X509_CRL *crl) +{ + mock_srv_ctx *ctx = OSSL_CMP_SRV_CTX_get0_custom_ctx(srv_ctx); + + if (ctx == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return 0; + } + if (crl != NULL && !X509_CRL_up_ref(crl)) + return 0; + X509_CRL_free(ctx->crlOut); + ctx->crlOut = crl; + return 1; +} + int ossl_cmp_mock_srv_set1_chainOut(OSSL_CMP_SRV_CTX *srv_ctx, STACK_OF(X509) *chain) { @@ -391,10 +407,50 @@ static OSSL_CMP_PKISI *process_rr(OSSL_CMP_SRV_CTX *srv_ctx, return OSSL_CMP_PKISI_dup(ctx->statusOut); } +/* return -1 for error, 0 for no update available */ +static int check_client_crl(const STACK_OF(OSSL_CMP_CRLSTATUS) *crlStatusList, + const X509_CRL *crl) +{ + OSSL_CMP_CRLSTATUS *crlstatus; + DIST_POINT_NAME *dpn = NULL; + GENERAL_NAMES *issuer = NULL; + ASN1_TIME *thisupd = NULL; + + if (sk_OSSL_CMP_CRLSTATUS_num(crlStatusList) != 1) { + ERR_raise(ERR_LIB_CMP, CMP_R_UNEXPECTED_CRLSTATUSLIST); + return -1; + } + if (crl == NULL) + return 0; + + crlstatus = sk_OSSL_CMP_CRLSTATUS_value(crlStatusList, 0); + if (!OSSL_CMP_CRLSTATUS_get0(crlstatus, &dpn, &issuer, &thisupd)) + return -1; + + if (issuer != NULL) { + GENERAL_NAME *gn = sk_GENERAL_NAME_value(issuer, 0); + + if (gn != NULL && gn->type == GEN_DIRNAME) { + X509_NAME *gen_name = gn->d.dirn; + + if (X509_NAME_cmp(gen_name, X509_CRL_get_issuer(crl)) != 0) { + ERR_raise(ERR_LIB_CMP, CMP_R_UNKNOWN_CRL_ISSUER); + return -1; + } + } else { + ERR_raise(ERR_LIB_CMP, CMP_R_SENDER_GENERALNAME_TYPE_NOT_SUPPORTED); + return -1; /* error according to RFC 9483 section 4.3.4 */ + } + } + + return thisupd == NULL + || ASN1_TIME_compare(thisupd, X509_CRL_get0_lastUpdate(crl)) < 0; +} + static OSSL_CMP_ITAV *process_genm_itav(mock_srv_ctx *ctx, int req_nid, const OSSL_CMP_ITAV *req) { - OSSL_CMP_ITAV *rsp; + OSSL_CMP_ITAV *rsp = NULL; switch (req_nid) { case NID_id_it_caCerts: @@ -418,6 +474,63 @@ static OSSL_CMP_ITAV *process_genm_itav(mock_srv_ctx *ctx, int req_nid, ctx->oldWithNew); } break; + case NID_id_it_crlStatusList: + { + STACK_OF(OSSL_CMP_CRLSTATUS) *crlstatuslist = NULL; + int res = 0; + + if (!OSSL_CMP_ITAV_get0_crlStatusList(req, &crlstatuslist)) + return NULL; + + res = check_client_crl(crlstatuslist, ctx->crlOut); + if (res < 0) + rsp = NULL; + else + rsp = OSSL_CMP_ITAV_new_crls(res == 0 ? NULL : ctx->crlOut); + } + break; + case NID_id_it_certReqTemplate: + { + OSSL_CRMF_CERTTEMPLATE *reqtemp; + OSSL_CMP_ATAVS *keyspec = NULL; + X509_ALGOR *keyalg = NULL; + OSSL_CMP_ATAV *rsakeylen, *eckeyalg; + int ok = 0; + + if ((reqtemp = OSSL_CRMF_CERTTEMPLATE_new()) == NULL) + return NULL; + + if (!OSSL_CRMF_CERTTEMPLATE_fill(reqtemp, NULL, NULL, + X509_get_issuer_name(ctx->refCert), + NULL)) + goto crt_err; + + if ((keyalg = X509_ALGOR_new()) == NULL) + goto crt_err; + + (void)X509_ALGOR_set0(keyalg, OBJ_nid2obj(NID_X9_62_id_ecPublicKey), + V_ASN1_UNDEF, NULL); /* cannot fail */ + + eckeyalg = OSSL_CMP_ATAV_new_algId(keyalg); + rsakeylen = OSSL_CMP_ATAV_new_rsaKeyLen(4096); + ok = OSSL_CMP_ATAV_push1(&keyspec, eckeyalg) + && OSSL_CMP_ATAV_push1(&keyspec, rsakeylen); + OSSL_CMP_ATAV_free(eckeyalg); + OSSL_CMP_ATAV_free(rsakeylen); + X509_ALGOR_free(keyalg); + + if (!ok) + goto crt_err; + + rsp = OSSL_CMP_ITAV_new0_certReqTemplate(reqtemp, keyspec); + return rsp; + + crt_err: + OSSL_CRMF_CERTTEMPLATE_free(reqtemp); + OSSL_CMP_ATAVS_free(keyspec); + return NULL; + } + break; default: rsp = OSSL_CMP_ITAV_dup(req); } diff --git a/apps/lib/http_server.c b/apps/lib/http_server.c index 4bc2012a1e..0db0de2aa7 100644 --- a/apps/lib/http_server.c +++ b/apps/lib/http_server.c @@ -202,8 +202,9 @@ BIO *http_server_init(const char *prog, const char *port, int verb) goto err; acbio = BIO_new(BIO_s_accept()); if (acbio == NULL - || BIO_set_bind_mode(acbio, BIO_BIND_REUSEADDR) < 0 - || BIO_set_accept_name(acbio, name) < 0) { + || BIO_set_accept_ip_family(acbio, BIO_FAMILY_IPANY) <= 0 /* IPv4/6 */ + || BIO_set_bind_mode(acbio, BIO_BIND_REUSEADDR) <= 0 + || BIO_set_accept_name(acbio, name) <= 0) { log_HTTP(prog, LOG_ERR, "error setting up accept BIO"); goto err; } diff --git a/apps/lib/tlssrp_depr.c b/apps/lib/tlssrp_depr.c index f03b013428..413f1f3538 100644 --- a/apps/lib/tlssrp_depr.c +++ b/apps/lib/tlssrp_depr.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2005 Nokia. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -178,7 +178,7 @@ static int ssl_srp_server_param_cb(SSL *s, int *ad, void *arg) goto err; } BIO_printf(bio_err, - "SRP parameters set: username = \"%s\" info=\"%s\" \n", + "SRP parameters set: username = \"%s\" info=\"%s\"\n", p->login, p->user->info); ret = SSL_ERROR_NONE; @@ -199,7 +199,7 @@ int set_up_srp_verifier_file(SSL_CTX *ctx, srpsrvparm *srp_callback_parm, srp_callback_parm->login = NULL; if (srp_callback_parm->vb == NULL) { - BIO_printf(bio_err, "Failed to initialize SRP verifier file \n"); + BIO_printf(bio_err, "Failed to initialize SRP verifier file\n"); return 0; } if ((ret = diff --git a/apps/lib/vms_term_sock.c b/apps/lib/vms_term_sock.c index 86f50c3d9a..5f80eedfcc 100644 --- a/apps/lib/vms_term_sock.c +++ b/apps/lib/vms_term_sock.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2016 VMS Software, Inc. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -353,7 +353,7 @@ static int CreateSocketPair (int SocketFamily, /* ** Get the binary (64-bit) time of the specified timeout value */ - sprintf (AscTimeBuff, "0 0:0:%02d.00", SOCKET_PAIR_TIMEOUT_VALUE); + BIO_snprintf(AscTimeBuff, sizeof(AscTimeBuff), "0 0:0:%02d.00", SOCKET_PAIR_TIMEOUT_VALUE); AscTimeDesc.dsc$w_length = strlen (AscTimeBuff); AscTimeDesc.dsc$a_pointer = AscTimeBuff; status = sys$bintim (&AscTimeDesc, BinTimeBuff); @@ -567,10 +567,10 @@ static void LogMessage (char *msg, ...) /* ** Format the message buffer */ - sprintf (MsgBuff, "%02d-%s-%04d %02d:%02d:%02d [%08X] %s\n", - LocTime->tm_mday, Month[LocTime->tm_mon], - (LocTime->tm_year + 1900), LocTime->tm_hour, LocTime->tm_min, - LocTime->tm_sec, pid, msg); + BIO_snprintf(MsgBuff, sizeof(MsgBuff), "%02d-%s-%04d %02d:%02d:%02d [%08X] %s\n", + LocTime->tm_mday, Month[LocTime->tm_mon], + (LocTime->tm_year + 1900), LocTime->tm_hour, LocTime->tm_min, + LocTime->tm_sec, pid, msg); /* ** Get any variable arguments and add them to the print of the message diff --git a/apps/list.c b/apps/list.c index 433d9a2f00..14a20bd74a 100644 --- a/apps/list.c +++ b/apps/list.c @@ -21,6 +21,7 @@ #include #include #include +#include #include "apps.h" #include "app_params.h" #include "progs.h" @@ -71,7 +72,7 @@ static void legacy_cipher_fn(const EVP_CIPHER *c, { if (select_name != NULL && (c == NULL - || OPENSSL_strcasecmp(select_name, EVP_CIPHER_get0_name(c)) != 0)) + || OPENSSL_strcasecmp(select_name, EVP_CIPHER_get0_name(c)) != 0)) return; if (c != NULL) { BIO_printf(arg, " %s\n", EVP_CIPHER_get0_name(c)); @@ -747,6 +748,53 @@ static void list_signatures(void) BIO_printf(bio_out, " -\n"); } +static int list_provider_tls_sigalgs(const OSSL_PARAM params[], void *data) +{ + const OSSL_PARAM *p; + + /* Get registered IANA name */ + p = OSSL_PARAM_locate_const(params, OSSL_CAPABILITY_TLS_SIGALG_IANA_NAME); + if (p != NULL && p->data_type == OSSL_PARAM_UTF8_STRING) { + if (*((int *)data) > 0) + BIO_printf(bio_out, ":"); + BIO_printf(bio_out, "%s", (char *)(p->data)); + /* mark presence of a provider-based sigalg */ + *((int *)data) = 2; + } + /* As built-in providers don't have this capability, never error */ + return 1; +} + +static int list_tls_sigalg_caps(OSSL_PROVIDER *provider, void *cbdata) +{ + OSSL_PROVIDER_get_capabilities(provider, "TLS-SIGALG", + list_provider_tls_sigalgs, + cbdata); + /* As built-in providers don't have this capability, never error */ + return 1; +} + +static void list_tls_signatures(void) +{ + int tls_sigalg_listed = 0; + char *builtin_sigalgs = SSL_get1_builtin_sigalgs(app_get0_libctx()); + + if (builtin_sigalgs != NULL) { + if (builtin_sigalgs[0] != 0) { + BIO_printf(bio_out, "%s", builtin_sigalgs); + tls_sigalg_listed = 1; + } + OPENSSL_free(builtin_sigalgs); + } + + /* As built-in providers don't have this capability, never error */ + OSSL_PROVIDER_do_all(NULL, list_tls_sigalg_caps, &tls_sigalg_listed); + if (tls_sigalg_listed < 2) + BIO_printf(bio_out, + "\nNo TLS sig algs registered by currently active providers"); + BIO_printf(bio_out, "\n"); +} + DEFINE_STACK_OF(EVP_KEM) static int kem_cmp(const EVP_KEM * const *a, const EVP_KEM * const *b) @@ -1209,6 +1257,7 @@ static int provider_cmp(const OSSL_PROVIDER * const *a, static int collect_providers(OSSL_PROVIDER *provider, void *stack) { STACK_OF(OSSL_PROVIDER) *provider_stack = stack; + /* * If OK - result is the index of inserted data * Error - result is -1 or 0 @@ -1459,11 +1508,12 @@ typedef enum HELPLIST_CHOICE { OPT_PK_ALGORITHMS, OPT_PK_METHOD, OPT_DISABLED, OPT_KDF_ALGORITHMS, OPT_RANDOM_INSTANCES, OPT_RANDOM_GENERATORS, OPT_ENCODERS, OPT_DECODERS, OPT_KEYMANAGERS, OPT_KEYEXCHANGE_ALGORITHMS, - OPT_KEM_ALGORITHMS, OPT_SIGNATURE_ALGORITHMS, OPT_ASYM_CIPHER_ALGORITHMS, - OPT_STORE_LOADERS, OPT_PROVIDER_INFO, - OPT_OBJECTS, OPT_SELECT_NAME, + OPT_KEM_ALGORITHMS, OPT_SIGNATURE_ALGORITHMS, + OPT_TLS_SIGNATURE_ALGORITHMS, OPT_ASYM_CIPHER_ALGORITHMS, + OPT_STORE_LOADERS, OPT_PROVIDER_INFO, OPT_OBJECTS, + OPT_SELECT_NAME, #ifndef OPENSSL_NO_DEPRECATED_3_0 - OPT_ENGINES, + OPT_ENGINES, #endif OPT_PROV_ENUM } HELPLIST_CHOICE; @@ -1495,8 +1545,8 @@ const OPTIONS list_options[] = { {"mac-algorithms", OPT_MAC_ALGORITHMS, '-', "List of message authentication code algorithms"}, #ifndef OPENSSL_NO_DEPRECATED_3_0 - {"cipher-commands", OPT_CIPHER_COMMANDS, '-', - "List of cipher commands (deprecated)"}, + {"cipher-commands", OPT_CIPHER_COMMANDS, '-', + "List of cipher commands (deprecated)"}, #endif {"cipher-algorithms", OPT_CIPHER_ALGORITHMS, '-', "List of symmetric cipher algorithms"}, @@ -1509,6 +1559,8 @@ const OPTIONS list_options[] = { "List of key encapsulation mechanism algorithms" }, {"signature-algorithms", OPT_SIGNATURE_ALGORITHMS, '-', "List of signature algorithms" }, + {"tls-signature-algorithms", OPT_TLS_SIGNATURE_ALGORITHMS, '-', + "List of TLS signature algorithms" }, {"asymcipher-algorithms", OPT_ASYM_CIPHER_ALGORITHMS, '-', "List of asymmetric cipher algorithms" }, {"public-key-algorithms", OPT_PK_ALGORITHMS, '-', @@ -1554,6 +1606,7 @@ int list_main(int argc, char **argv) unsigned int decoder_algorithms:1; unsigned int keymanager_algorithms:1; unsigned int signature_algorithms:1; + unsigned int tls_signature_algorithms:1; unsigned int keyexchange_algorithms:1; unsigned int kem_algorithms:1; unsigned int asym_cipher_algorithms:1; @@ -1627,6 +1680,9 @@ int list_main(int argc, char **argv) case OPT_SIGNATURE_ALGORITHMS: todo.signature_algorithms = 1; break; + case OPT_TLS_SIGNATURE_ALGORITHMS: + todo.tls_signature_algorithms = 1; + break; case OPT_KEYEXCHANGE_ALGORITHMS: todo.keyexchange_algorithms = 1; break; @@ -1686,7 +1742,7 @@ int list_main(int argc, char **argv) BIO_printf(bio_out, "\n"); \ } \ cmd; \ - } while(0) + } while (0) if (todo.commands) MAYBE_ADD_NL(list_type(FT_general, one)); @@ -1744,6 +1800,8 @@ int list_main(int argc, char **argv) MAYBE_ADD_NL(list_keymanagers()); if (todo.signature_algorithms) MAYBE_ADD_NL(list_signatures()); + if (todo.tls_signature_algorithms) + MAYBE_ADD_NL(list_tls_signatures()); if (todo.asym_cipher_algorithms) MAYBE_ADD_NL(list_asymciphers()); if (todo.keyexchange_algorithms) diff --git a/apps/passwd.c b/apps/passwd.c index 379928563c..31c7077ccc 100644 --- a/apps/passwd.c +++ b/apps/passwd.c @@ -1,5 +1,5 @@ /* - * Copyright 2000-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2000-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -589,7 +589,8 @@ static char *shacrypt(const char *passwd, const char *magic, const char *salt) OPENSSL_strlcat(out_buf, ascii_dollar, sizeof(out_buf)); if (rounds_custom) { char tmp_buf[80]; /* "rounds=999999999" */ - sprintf(tmp_buf, "rounds=%u", rounds); + + BIO_snprintf(tmp_buf, sizeof(tmp_buf), "rounds=%u", rounds); #ifdef CHARSET_EBCDIC /* In case we're really on a ASCII based platform and just pretend */ if (tmp_buf[0] != 0x72) /* ASCII 'r' */ @@ -706,15 +707,14 @@ static char *shacrypt(const char *passwd, const char *magic, const char *salt) cp = out_buf + strlen(out_buf); *cp++ = ascii_dollar[0]; -# define b64_from_24bit(B2, B1, B0, N) \ +# define b64_from_24bit(B2, B1, B0, N) \ do { \ unsigned int w = ((B2) << 16) | ((B1) << 8) | (B0); \ int i = (N); \ - while (i-- > 0) \ - { \ - *cp++ = cov_2char[w & 0x3f]; \ - w >>= 6; \ - } \ + while (i-- > 0) { \ + *cp++ = cov_2char[w & 0x3f]; \ + w >>= 6; \ + } \ } while (0) switch (magic[0]) { diff --git a/apps/pkcs12.c b/apps/pkcs12.c index e6fbc574a5..afdb719ccd 100644 --- a/apps/pkcs12.c +++ b/apps/pkcs12.c @@ -70,7 +70,7 @@ typedef enum OPTION_choice { OPT_NAME, OPT_CSP, OPT_CANAME, OPT_IN, OPT_OUT, OPT_PASSIN, OPT_PASSOUT, OPT_PASSWORD, OPT_CAPATH, OPT_CAFILE, OPT_CASTORE, OPT_NOCAPATH, OPT_NOCAFILE, OPT_NOCASTORE, OPT_ENGINE, - OPT_R_ENUM, OPT_PROV_ENUM, OPT_JDKTRUST, + OPT_R_ENUM, OPT_PROV_ENUM, OPT_JDKTRUST, OPT_PBMAC1_PBKDF2, OPT_PBMAC1_PBKDF2_MD, #ifndef OPENSSL_NO_DES OPT_LEGACY_ALG #endif @@ -147,6 +147,8 @@ const OPTIONS pkcs12_options[] = { #endif {"macalg", OPT_MACALG, 's', "Digest algorithm to use in MAC (default SHA256)"}, + {"pbmac1_pbkdf2", OPT_PBMAC1_PBKDF2, '-', "Use PBMAC1 with PBKDF2 instead of MAC"}, + {"pbmac1_pbkdf2_md", OPT_PBMAC1_PBKDF2_MD, 's', "Digest to use for PBMAC1 KDF (default SHA256)"}, {"iter", OPT_ITER, 'p', "Specify the iteration count for encryption and MAC"}, {"noiter", OPT_NOITER, '-', "Don't use encryption iteration"}, {"nomaciter", OPT_NOMACITER, '-', "Don't use MAC iteration)"}, @@ -170,14 +172,14 @@ int pkcs12_main(int argc, char **argv) int use_legacy = 0; #endif /* use library defaults for the iter, maciter, cert, and key PBE */ - int iter = 0, maciter = 0; + int iter = 0, maciter = 0, pbmac1_pbkdf2 = 0; int macsaltlen = PKCS12_SALT_LEN; int cert_pbe = NID_undef; int key_pbe = NID_undef; int ret = 1, macver = 1, add_lmk = 0, private = 0; int noprompt = 0; char *passinarg = NULL, *passoutarg = NULL, *passarg = NULL; - char *passin = NULL, *passout = NULL, *macalg = NULL; + char *passin = NULL, *passout = NULL, *macalg = NULL, *pbmac1_pbkdf2_md = NULL; char *cpass = NULL, *mpass = NULL, *badpass = NULL; const char *CApath = NULL, *CAfile = NULL, *CAstore = NULL, *prog; int noCApath = 0, noCAfile = 0, noCAstore = 0; @@ -283,6 +285,12 @@ int pkcs12_main(int argc, char **argv) case OPT_MACALG: macalg = opt_arg(); break; + case OPT_PBMAC1_PBKDF2: + pbmac1_pbkdf2 = 1; + break; + case OPT_PBMAC1_PBKDF2_MD: + pbmac1_pbkdf2_md = opt_arg(); + break; case OPT_CERTPBE: if (!set_pbe(&cert_pbe, opt_arg())) goto opthelp; @@ -700,10 +708,20 @@ int pkcs12_main(int argc, char **argv) } if (maciter != -1) { - if (!PKCS12_set_mac(p12, mpass, -1, NULL, macsaltlen, maciter, macmd)) { - BIO_printf(bio_err, "Error creating PKCS12 MAC; no PKCS12KDF support?\n"); - BIO_printf(bio_err, "Use -nomac if MAC not required and PKCS12KDF support not available.\n"); - goto export_end; + if (pbmac1_pbkdf2 == 1) { + if (!PKCS12_set_pbmac1_pbkdf2(p12, mpass, -1, NULL, + macsaltlen, maciter, + macmd, pbmac1_pbkdf2_md)) { + BIO_printf(bio_err, "Error creating PBMAC1\n"); + goto export_end; + } + } else { + if (!PKCS12_set_mac(p12, mpass, -1, NULL, macsaltlen, maciter, macmd)) { + BIO_printf(bio_err, "Error creating PKCS12 MAC; no PKCS12KDF support?\n"); + BIO_printf(bio_err, + "Use -nomac or -pbmac1_pbkdf2 if PKCS12KDF support not available\n"); + goto export_end; + } } } assert(private); @@ -774,23 +792,58 @@ int pkcs12_main(int argc, char **argv) X509_ALGOR_get0(&macobj, NULL, NULL, macalgid); BIO_puts(bio_err, "MAC: "); i2a_ASN1_OBJECT(bio_err, macobj); - BIO_printf(bio_err, ", Iteration %ld\n", - tmaciter != NULL ? ASN1_INTEGER_get(tmaciter) : 1L); - BIO_printf(bio_err, "MAC length: %ld, salt length: %ld\n", - tmac != NULL ? ASN1_STRING_length(tmac) : 0L, - tsalt != NULL ? ASN1_STRING_length(tsalt) : 0L); + if (OBJ_obj2nid(macobj) == NID_pbmac1) { + PBKDF2PARAM *pbkdf2_param = PBMAC1_get1_pbkdf2_param(macalgid); + + if (pbkdf2_param == NULL) { + BIO_printf(bio_err, ", Unsupported KDF or params for PBMAC1\n"); + } else { + const ASN1_OBJECT *prfobj; + int prfnid; + + BIO_printf(bio_err, " using PBKDF2, Iteration %ld\n", + ASN1_INTEGER_get(pbkdf2_param->iter)); + BIO_printf(bio_err, "Key length: %ld, Salt length: %d\n", + ASN1_INTEGER_get(pbkdf2_param->keylength), + ASN1_STRING_length(pbkdf2_param->salt->value.octet_string)); + if (pbkdf2_param->prf == NULL) { + prfnid = NID_hmacWithSHA1; + } else { + X509_ALGOR_get0(&prfobj, NULL, NULL, pbkdf2_param->prf); + prfnid = OBJ_obj2nid(prfobj); + } + BIO_printf(bio_err, "PBKDF2 PRF: %s\n", OBJ_nid2sn(prfnid)); + } + PBKDF2PARAM_free(pbkdf2_param); + } else { + BIO_printf(bio_err, ", Iteration %ld\n", + tmaciter != NULL ? ASN1_INTEGER_get(tmaciter) : 1L); + BIO_printf(bio_err, "MAC length: %ld, salt length: %ld\n", + tmac != NULL ? ASN1_STRING_length(tmac) : 0L, + tsalt != NULL ? ASN1_STRING_length(tsalt) : 0L); + } } + if (macver) { - EVP_KDF *pkcs12kdf; + const X509_ALGOR *macalgid; + const ASN1_OBJECT *macobj; - pkcs12kdf = EVP_KDF_fetch(app_get0_libctx(), "PKCS12KDF", - app_get0_propq()); - if (pkcs12kdf == NULL) { - BIO_printf(bio_err, "Error verifying PKCS12 MAC; no PKCS12KDF support.\n"); - BIO_printf(bio_err, "Use -nomacver if MAC verification is not required.\n"); - goto end; + PKCS12_get0_mac(NULL, &macalgid, NULL, NULL, p12); + X509_ALGOR_get0(&macobj, NULL, NULL, macalgid); + + if (OBJ_obj2nid(macobj) != NID_pbmac1) { + EVP_KDF *pkcs12kdf; + + pkcs12kdf = EVP_KDF_fetch(app_get0_libctx(), "PKCS12KDF", + app_get0_propq()); + if (pkcs12kdf == NULL) { + BIO_printf(bio_err, "Error verifying PKCS12 MAC; no PKCS12KDF support.\n"); + BIO_printf(bio_err, "Use -nomacver if MAC verification is not required.\n"); + goto end; + } + EVP_KDF_free(pkcs12kdf); } - EVP_KDF_free(pkcs12kdf); + /* If we enter empty password try no password first */ if (!mpass[0] && PKCS12_verify_mac(p12, NULL, 0)) { /* If mac and crypto pass the same set it to NULL too */ @@ -1257,8 +1310,7 @@ int print_attribs(BIO *out, const STACK_OF(X509_ATTRIBUTE) *attrlst, } if (X509_ATTRIBUTE_count(attr)) { - for (j = 0; j < X509_ATTRIBUTE_count(attr); j++) - { + for (j = 0; j < X509_ATTRIBUTE_count(attr); j++) { av = X509_ATTRIBUTE_get0_type(attr, j); print_attribute(out, av); } diff --git a/apps/pkeyutl.c b/apps/pkeyutl.c index b5390c64c2..b73ef3297b 100644 --- a/apps/pkeyutl.c +++ b/apps/pkeyutl.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -24,7 +24,7 @@ static EVP_PKEY_CTX *init_ctx(const char *kdfalg, int *pkeysize, const char *keyfile, int keyform, int key_type, char *passinarg, int pkey_op, ENGINE *e, const int impl, int rawin, EVP_PKEY **ppkey, - EVP_MD_CTX *mctx, const char *digestname, + EVP_MD_CTX *mctx, const char *digestname, const char *kemop, OSSL_LIB_CTX *libctx, const char *propq); static int setup_peer(EVP_PKEY_CTX *ctx, int peerform, const char *file, @@ -32,7 +32,8 @@ static int setup_peer(EVP_PKEY_CTX *ctx, int peerform, const char *file, static int do_keyop(EVP_PKEY_CTX *ctx, int pkey_op, unsigned char *out, size_t *poutlen, - const unsigned char *in, size_t inlen); + const unsigned char *in, size_t inlen, + unsigned char *secret, size_t *psecretlen); static int do_raw_keyop(int pkey_op, EVP_MD_CTX *mctx, EVP_PKEY *pkey, BIO *in, @@ -47,6 +48,7 @@ typedef enum OPTION_choice { OPT_DERIVE, OPT_SIGFILE, OPT_INKEY, OPT_PEERKEY, OPT_PASSIN, OPT_PEERFORM, OPT_KEYFORM, OPT_PKEYOPT, OPT_PKEYOPT_PASSIN, OPT_KDF, OPT_KDFLEN, OPT_R_ENUM, OPT_PROV_ENUM, + OPT_DECAP, OPT_ENCAP, OPT_SECOUT, OPT_KEMOP, OPT_CONFIG, OPT_RAWIN, OPT_DIGEST } OPTION_CHOICE; @@ -64,6 +66,8 @@ const OPTIONS pkeyutl_options[] = { {"encrypt", OPT_ENCRYPT, '-', "Encrypt input data with public key"}, {"decrypt", OPT_DECRYPT, '-', "Decrypt input data with private key"}, {"derive", OPT_DERIVE, '-', "Derive shared secret"}, + {"decap", OPT_DECAP, '-', "Decapsulate shared secret"}, + {"encap", OPT_ENCAP, '-', "Encapsulate shared secret"}, OPT_CONFIG_OPTION, OPT_SECTION("Input"), @@ -81,12 +85,13 @@ const OPTIONS pkeyutl_options[] = { OPT_SECTION("Output"), {"out", OPT_OUT, '>', "Output file - default stdout"}, + {"secret", OPT_SECOUT, '>', "File to store secret on encapsulation"}, {"asn1parse", OPT_ASN1PARSE, '-', "asn1parse the output data"}, {"hexdump", OPT_HEXDUMP, '-', "Hex dump output"}, {"verifyrecover", OPT_VERIFYRECOVER, '-', "Verify with public key, recover original data"}, - OPT_SECTION("Signing/Derivation"), + OPT_SECTION("Signing/Derivation/Encapsulation"), {"digest", OPT_DIGEST, 's', "Specify the digest algorithm when signing the raw input data"}, {"pkeyopt", OPT_PKEYOPT, 's', "Public key options as opt:value"}, @@ -94,6 +99,7 @@ const OPTIONS pkeyutl_options[] = { "Public key option that is read as a passphrase argument opt:passphrase"}, {"kdf", OPT_KDF, 's', "Use KDF algorithm"}, {"kdflen", OPT_KDFLEN, 'p', "KDF algorithm output length"}, + {"kemop", OPT_KEMOP, 's', "KEM operation specific to the key algorithm"}, OPT_R_OPTIONS, OPT_PROV_OPTIONS, @@ -103,23 +109,23 @@ const OPTIONS pkeyutl_options[] = { int pkeyutl_main(int argc, char **argv) { CONF *conf = NULL; - BIO *in = NULL, *out = NULL; + BIO *in = NULL, *out = NULL, *secout = NULL; ENGINE *e = NULL; EVP_PKEY_CTX *ctx = NULL; EVP_PKEY *pkey = NULL; - char *infile = NULL, *outfile = NULL, *sigfile = NULL, *passinarg = NULL; + char *infile = NULL, *outfile = NULL, *secoutfile = NULL, *sigfile = NULL, *passinarg = NULL; char hexdump = 0, asn1parse = 0, rev = 0, *prog; - unsigned char *buf_in = NULL, *buf_out = NULL, *sig = NULL; + unsigned char *buf_in = NULL, *buf_out = NULL, *sig = NULL, *secret = NULL; OPTION_CHOICE o; int buf_inlen = 0, siglen = -1; int keyform = FORMAT_UNDEF, peerform = FORMAT_UNDEF; int keysize = -1, pkey_op = EVP_PKEY_OP_SIGN, key_type = KEY_PRIVKEY; int engine_impl = 0; int ret = 1, rv = -1; - size_t buf_outlen; + size_t buf_outlen = 0, secretlen = 0; const char *inkey = NULL; const char *peerkey = NULL; - const char *kdfalg = NULL, *digestname = NULL; + const char *kdfalg = NULL, *digestname = NULL, *kemop = NULL; int kdflen = 0; STACK_OF(OPENSSL_STRING) *pkeyopts = NULL; STACK_OF(OPENSSL_STRING) *pkeyopts_passin = NULL; @@ -147,6 +153,9 @@ int pkeyutl_main(int argc, char **argv) case OPT_OUT: outfile = opt_arg(); break; + case OPT_SECOUT: + secoutfile = opt_arg(); + break; case OPT_SIGFILE: sigfile = opt_arg(); break; @@ -216,6 +225,15 @@ int pkeyutl_main(int argc, char **argv) case OPT_DERIVE: pkey_op = EVP_PKEY_OP_DERIVE; break; + case OPT_DECAP: + pkey_op = EVP_PKEY_OP_DECAPSULATE; + break; + case OPT_ENCAP: + pkey_op = EVP_PKEY_OP_ENCAPSULATE; + break; + case OPT_KEMOP: + kemop = opt_arg(); + break; case OPT_KDF: pkey_op = EVP_PKEY_OP_DERIVE; key_type = KEY_NONE; @@ -303,7 +321,7 @@ int pkeyutl_main(int argc, char **argv) } ctx = init_ctx(kdfalg, &keysize, inkey, keyform, key_type, passinarg, pkey_op, e, engine_impl, rawin, &pkey, - mctx, digestname, libctx, app_get0_propq()); + mctx, digestname, kemop, libctx, app_get0_propq()); if (ctx == NULL) { BIO_printf(bio_err, "%s: Error initializing context\n", prog); goto end; @@ -387,7 +405,7 @@ int pkeyutl_main(int argc, char **argv) goto end; } - if (pkey_op != EVP_PKEY_OP_DERIVE) { + if (pkey_op != EVP_PKEY_OP_DERIVE && pkey_op != EVP_PKEY_OP_ENCAPSULATE) { in = bio_open_default(infile, 'r', FORMAT_BINARY); if (infile != NULL) { struct stat st; @@ -402,6 +420,16 @@ int pkeyutl_main(int argc, char **argv) if (out == NULL) goto end; + if (pkey_op == EVP_PKEY_OP_ENCAPSULATE) { + if (secoutfile == NULL) { + BIO_printf(bio_err, "Encapsulation requires '-secret' argument\n"); + goto end; + } + secout = bio_open_default(secoutfile, 'w', FORMAT_BINARY); + if (secout == NULL) + goto end; + } + if (sigfile != NULL) { BIO *sigbio = BIO_new_file(sigfile, "rb"); @@ -473,13 +501,15 @@ int pkeyutl_main(int argc, char **argv) rv = 1; } else { rv = do_keyop(ctx, pkey_op, NULL, (size_t *)&buf_outlen, - buf_in, (size_t)buf_inlen); + buf_in, (size_t)buf_inlen, NULL, (size_t *)&secretlen); } if (rv > 0 && buf_outlen != 0) { buf_out = app_malloc(buf_outlen, "buffer output"); + if (secretlen > 0) + secret = app_malloc(secretlen, "secret output"); rv = do_keyop(ctx, pkey_op, buf_out, (size_t *)&buf_outlen, - buf_in, (size_t)buf_inlen); + buf_in, (size_t)buf_inlen, secret, (size_t *)&secretlen); } } if (rv <= 0) { @@ -500,6 +530,8 @@ int pkeyutl_main(int argc, char **argv) } else { BIO_write(out, buf_out, buf_outlen); } + if (secretlen > 0) + BIO_write(secout, secret, secretlen); end: if (ret != 0) @@ -510,9 +542,11 @@ int pkeyutl_main(int argc, char **argv) release_engine(e); BIO_free(in); BIO_free_all(out); + BIO_free_all(secout); OPENSSL_free(buf_in); OPENSSL_free(buf_out); OPENSSL_free(sig); + OPENSSL_free(secret); sk_OPENSSL_STRING_free(pkeyopts); sk_OPENSSL_STRING_free(pkeyopts_passin); NCONF_free(conf); @@ -524,7 +558,7 @@ static EVP_PKEY_CTX *init_ctx(const char *kdfalg, int *pkeysize, char *passinarg, int pkey_op, ENGINE *e, const int engine_impl, int rawin, EVP_PKEY **ppkey, EVP_MD_CTX *mctx, const char *digestname, - OSSL_LIB_CTX *libctx, const char *propq) + const char *kemop, OSSL_LIB_CTX *libctx, const char *propq) { EVP_PKEY *pkey = NULL; EVP_PKEY_CTX *ctx = NULL; @@ -642,6 +676,18 @@ static EVP_PKEY_CTX *init_ctx(const char *kdfalg, int *pkeysize, case EVP_PKEY_OP_DERIVE: rv = EVP_PKEY_derive_init(ctx); break; + + case EVP_PKEY_OP_ENCAPSULATE: + rv = EVP_PKEY_encapsulate_init(ctx, NULL); + if (rv > 0 && kemop != NULL) + rv = EVP_PKEY_CTX_set_kem_op(ctx, kemop); + break; + + case EVP_PKEY_OP_DECAPSULATE: + rv = EVP_PKEY_decapsulate_init(ctx, NULL); + if (rv > 0 && kemop != NULL) + rv = EVP_PKEY_CTX_set_kem_op(ctx, kemop); + break; } } @@ -679,7 +725,8 @@ static int setup_peer(EVP_PKEY_CTX *ctx, int peerform, const char *file, static int do_keyop(EVP_PKEY_CTX *ctx, int pkey_op, unsigned char *out, size_t *poutlen, - const unsigned char *in, size_t inlen) + const unsigned char *in, size_t inlen, + unsigned char *secret, size_t *pseclen) { int rv = 0; switch (pkey_op) { @@ -703,6 +750,14 @@ static int do_keyop(EVP_PKEY_CTX *ctx, int pkey_op, rv = EVP_PKEY_derive(ctx, out, poutlen); break; + case EVP_PKEY_OP_ENCAPSULATE: + rv = EVP_PKEY_encapsulate(ctx, out, poutlen, secret, pseclen); + break; + + case EVP_PKEY_OP_DECAPSULATE: + rv = EVP_PKEY_decapsulate(ctx, out, poutlen, in, inlen); + break; + } return rv; } diff --git a/apps/rehash.c b/apps/rehash.c index 9862b9fba9..798004b79d 100644 --- a/apps/rehash.c +++ b/apps/rehash.c @@ -140,7 +140,7 @@ static int add_entry(enum Type type, unsigned int hash, const char *filename, } for (ep = bp->first_entry; ep; ep = ep->next) { - if (digest && memcmp(digest, ep->digest, evpmdsize) == 0) { + if (digest && memcmp(digest, ep->digest, (size_t)evpmdsize) == 0) { BIO_printf(bio_err, "%s: warning: skipping duplicate %s in %s\n", opt_getprog(), @@ -183,7 +183,7 @@ static int add_entry(enum Type type, unsigned int hash, const char *filename, if (need_symlink && !ep->need_symlink) { ep->need_symlink = 1; bp->num_needed++; - memcpy(ep->digest, digest, evpmdsize); + memcpy(ep->digest, digest, (size_t)evpmdsize); } return 0; } @@ -553,12 +553,20 @@ int rehash_main(int argc, char **argv) evpmd = EVP_sha1(); evpmdsize = EVP_MD_get_size(evpmd); + if (evpmdsize <= 0 || evpmdsize > EVP_MAX_MD_SIZE) + goto end; + if (*argv != NULL) { while (*argv != NULL) errs += do_dir(*argv++, h); } else if ((env = getenv(X509_get_default_cert_dir_env())) != NULL) { char lsc[2] = { LIST_SEPARATOR_CHAR, '\0' }; m = OPENSSL_strdup(env); + if (m == NULL) { + BIO_puts(bio_err, "out of memory\n"); + errs = 1; + goto end; + } for (e = strtok(m, lsc); e != NULL; e = strtok(NULL, lsc)) errs += do_dir(e, h); OPENSSL_free(m); diff --git a/apps/req.c b/apps/req.c index b54a489722..73dd94a567 100644 --- a/apps/req.c +++ b/apps/req.c @@ -30,6 +30,7 @@ #ifndef OPENSSL_NO_DSA # include #endif +#include "internal/e_os.h" /* For isatty() */ #define BITS "default_bits" #define KEYFILE "default_keyfile" @@ -43,7 +44,7 @@ #define DEFAULT_KEY_LENGTH 2048 #define MIN_KEY_LENGTH 512 -#define DEFAULT_DAYS 30 /* default cert validity period in days */ +#define DEFAULT_DAYS 30 /* default certificate validity period in days */ #define UNSET_DAYS -2 /* -1 may be used for testing expiration checks */ #define EXT_COPY_UNSET -1 @@ -87,7 +88,7 @@ typedef enum OPTION_choice { OPT_VERIFY, OPT_NOENC, OPT_NODES, OPT_NOOUT, OPT_VERBOSE, OPT_UTF8, OPT_NAMEOPT, OPT_REQOPT, OPT_SUBJ, OPT_SUBJECT, OPT_TEXT, OPT_X509, OPT_X509V1, OPT_CA, OPT_CAKEY, - OPT_MULTIVALUE_RDN, OPT_DAYS, OPT_SET_SERIAL, + OPT_MULTIVALUE_RDN, OPT_NOT_BEFORE, OPT_NOT_AFTER, OPT_DAYS, OPT_SET_SERIAL, OPT_COPY_EXTENSIONS, OPT_EXTENSIONS, OPT_REQEXTS, OPT_ADDEXT, OPT_PRECERT, OPT_MD, OPT_SECTION, OPT_QUIET, @@ -127,7 +128,11 @@ const OPTIONS req_options[] = { "Print the subject of the output request or cert"}, {"multivalue-rdn", OPT_MULTIVALUE_RDN, '-', "Deprecated; multi-valued RDNs support is always on."}, - {"days", OPT_DAYS, 'p', "Number of days cert is valid for"}, + {"not_before", OPT_NOT_BEFORE, 's', + "[CC]YYMMDDHHMMSSZ value for notBefore certificate field"}, + {"not_after", OPT_NOT_AFTER, 's', + "[CC]YYMMDDHHMMSSZ value for notAfter certificate field, overrides -days"}, + {"days", OPT_DAYS, 'p', "Number of days certificate is valid for"}, {"set_serial", OPT_SET_SERIAL, 's', "Serial number to use"}, {"copy_extensions", OPT_COPY_EXTENSIONS, 's', "copy extensions from request when using -x509"}, @@ -259,6 +264,7 @@ int req_main(int argc, char **argv) char *template = default_config_file, *keyout = NULL; const char *keyalg = NULL; OPTION_CHOICE o; + char *not_before = NULL, *not_after = NULL; int days = UNSET_DAYS; int ret = 1, gen_x509 = 0, i = 0, newreq = 0, verbose = 0, progress = 1; int informat = FORMAT_UNDEF, outformat = FORMAT_PEM, keyform = FORMAT_UNDEF; @@ -423,9 +429,15 @@ int req_main(int argc, char **argv) case OPT_CAKEY: CAkeyfile = opt_arg(); break; + case OPT_NOT_BEFORE: + not_before = opt_arg(); + break; + case OPT_NOT_AFTER: + not_after = opt_arg(); + break; case OPT_DAYS: days = atoi(opt_arg()); - if (days < -1) { + if (days <= UNSET_DAYS) { BIO_printf(bio_err, "%s: -days parameter arg must be >= -1\n", prog); goto end; @@ -470,7 +482,7 @@ int req_main(int argc, char **argv) } i = duplicated(addexts, p); if (i == 1) - goto opthelp; + goto end; if (i == -1) BIO_printf(bio_err, "Internal error handling -addext %s\n", p); if (i < 0 || BIO_printf(addext_bio, "%s\n", p) < 0) @@ -494,14 +506,18 @@ int req_main(int argc, char **argv) if (!gen_x509) { if (days != UNSET_DAYS) - BIO_printf(bio_err, "Ignoring -days without -x509; not generating a certificate\n"); + BIO_printf(bio_err, "Warning: Ignoring -days without -x509; not generating a certificate\n"); + if (not_before != NULL) + BIO_printf(bio_err, "Warning: Ignoring -not_before without -x509; not generating a certificate\n"); + if (not_after != NULL) + BIO_printf(bio_err, "Warning: Ignoring -not_after without -x509; not generating a certificate\n"); if (ext_copy == EXT_COPY_NONE) - BIO_printf(bio_err, "Ignoring -copy_extensions 'none' when -x509 is not given\n"); + BIO_printf(bio_err, "Warning: Ignoring -copy_extensions 'none' when -x509 is not given\n"); } if (infile == NULL) { if (gen_x509) newreq = 1; - else if (!newreq) + else if (!newreq && isatty(fileno_stdin())) BIO_printf(bio_err, "Warning: Will read cert request from stdin since no -in option is given\n"); } @@ -802,10 +818,11 @@ int req_main(int argc, char **argv) if (!X509_set_issuer_name(new_x509, issuer)) goto end; - if (days == UNSET_DAYS) { + if (days == UNSET_DAYS) days = DEFAULT_DAYS; - } - if (!set_cert_times(new_x509, NULL, NULL, days)) + else if (not_after != NULL) + BIO_printf(bio_err,"Warning: -not_after option overriding -days option\n"); + if (!set_cert_times(new_x509, not_before, not_after, days, 1)) goto end; if (!X509_set_subject_name(new_x509, n_subj)) goto end; diff --git a/apps/s_client.c b/apps/s_client.c index 0dc5123491..5eec42f3cc 100644 --- a/apps/s_client.c +++ b/apps/s_client.c @@ -55,7 +55,7 @@ typedef unsigned int u_int; #endif #undef BUFSIZZ -#define BUFSIZZ 1024*8 +#define BUFSIZZ 1024*16 #define S_CLIENT_IRC_READ_TIMEOUT 8 #define USER_DATA_MODE_NONE 0 @@ -3175,7 +3175,7 @@ int s_client_main(int argc, char **argv) } } #endif - k = SSL_read(con, sbuf, 1024 /* BUFSIZZ */ ); + k = SSL_read(con, sbuf, BUFSIZZ); switch (SSL_get_error(con, k)) { case SSL_ERROR_NONE: @@ -3486,6 +3486,7 @@ static void print_stuff(BIO *bio, SSL *s, int full) c = SSL_get_current_cipher(s); BIO_printf(bio, "%s, Cipher is %s\n", SSL_CIPHER_get_version(c), SSL_CIPHER_get_name(c)); + BIO_printf(bio, "Protocol: %s\n", SSL_get_version(s)); if (peer != NULL) { EVP_PKEY *pktmp; diff --git a/apps/smime.c b/apps/smime.c index c6c300c0b2..d5a4feb489 100644 --- a/apps/smime.c +++ b/apps/smime.c @@ -96,7 +96,10 @@ const OPTIONS smime_options[] = { {"nosigs", OPT_NOSIGS, '-', "Don't verify message signature"}, {"noverify", OPT_NOVERIFY, '-', "Don't verify signers certificate"}, - {"certfile", OPT_CERTFILE, '<', "Other certificates file"}, + {"certfile", OPT_CERTFILE, '<', + "Extra signer and intermediate CA certificates to include when signing"}, + {OPT_MORE_STR, 0, 0, + "or to use as preferred signer certs and for chain building when verifying"}, {"recip", OPT_RECIP, '<', "Recipient certificate file for decryption"}, OPT_SECTION("Email"), diff --git a/apps/speed.c b/apps/speed.c index 468ea56697..be4b8c570f 100644 --- a/apps/speed.c +++ b/apps/speed.c @@ -130,6 +130,8 @@ static int do_multi(int multi, int size_num); #endif static int domlock = 0; +static int testmode = 0; +static int testmoderesult = 0; static const int lengths_list[] = { 16, 64, 256, 1024, 8 * 1024, 16 * 1024 @@ -231,8 +233,9 @@ static int opt_found(const char *name, unsigned int *result, typedef enum OPTION_choice { OPT_COMMON, OPT_ELAPSED, OPT_EVP, OPT_HMAC, OPT_DECRYPT, OPT_ENGINE, OPT_MULTI, - OPT_MR, OPT_MB, OPT_MISALIGN, OPT_ASYNCJOBS, OPT_R_ENUM, OPT_PROV_ENUM, OPT_CONFIG, - OPT_PRIMES, OPT_SECONDS, OPT_BYTES, OPT_AEAD, OPT_CMAC, OPT_MLOCK, OPT_KEM, OPT_SIG + OPT_MR, OPT_MB, OPT_MISALIGN, OPT_ASYNCJOBS, OPT_R_ENUM, OPT_PROV_ENUM, + OPT_CONFIG, OPT_PRIMES, OPT_SECONDS, OPT_BYTES, OPT_AEAD, OPT_CMAC, + OPT_MLOCK, OPT_TESTMODE, OPT_KEM, OPT_SIG } OPTION_CHOICE; const OPTIONS speed_options[] = { @@ -259,6 +262,7 @@ const OPTIONS speed_options[] = { #endif {"primes", OPT_PRIMES, 'p', "Specify number of primes (for RSA only)"}, {"mlock", OPT_MLOCK, '-', "Lock memory for better result determinism"}, + {"testmode", OPT_TESTMODE, '-', "Run the speed command in test mode"}, OPT_CONFIG_OPTION, OPT_SECTION("Selection"), @@ -358,12 +362,14 @@ static const OPT_PAIR doit_choices[] = { static double results[ALGOR_NUM][SIZE_NUM]; +#ifndef OPENSSL_NO_DSA enum { R_DSA_1024, R_DSA_2048, DSA_NUM }; static const OPT_PAIR dsa_choices[DSA_NUM] = { {"dsa1024", R_DSA_1024}, {"dsa2048", R_DSA_2048} }; static double dsa_results[DSA_NUM][2]; /* 2 ops: sign then verify */ +#endif /* OPENSSL_NO_DSA */ enum { R_RSA_512, R_RSA_1024, R_RSA_2048, R_RSA_3072, R_RSA_4096, R_RSA_7680, @@ -505,7 +511,7 @@ static size_t sigs_algs_len = 0; static char *sigs_algname[MAX_SIG_NUM] = { NULL }; static double sigs_results[MAX_SIG_NUM][3]; /* keygen, sign, verify */ -#define COND(unused_cond) (run && count < INT_MAX) +#define COND(unused_cond) (run && count < (testmode ? 1 : INT_MAX)) #define COUNT(d) (count) typedef struct loopargs_st { @@ -523,8 +529,10 @@ typedef struct loopargs_st { EVP_PKEY_CTX *rsa_verify_ctx[RSA_NUM]; EVP_PKEY_CTX *rsa_encrypt_ctx[RSA_NUM]; EVP_PKEY_CTX *rsa_decrypt_ctx[RSA_NUM]; +#ifndef OPENSSL_NO_DSA EVP_PKEY_CTX *dsa_sign_ctx[DSA_NUM]; EVP_PKEY_CTX *dsa_verify_ctx[DSA_NUM]; +#endif EVP_PKEY_CTX *ecdsa_sign_ctx[ECDSA_NUM]; EVP_PKEY_CTX *ecdsa_verify_ctx[ECDSA_NUM]; EVP_PKEY_CTX *ecdh_ctx[EC_NUM]; @@ -573,6 +581,12 @@ static const char *evp_md_name = NULL; static char *evp_mac_ciphername = "aes-128-cbc"; static char *evp_cmac_name = NULL; +static void dofail(void) +{ + ERR_print_errors(bio_err); + testmoderesult = 1; +} + static int have_md(const char *name) { int ret = 0; @@ -613,17 +627,37 @@ static int EVP_Digest_loop(const char *mdname, ossl_unused int algindex, void *a unsigned char digest[EVP_MAX_MD_SIZE]; int count; EVP_MD *md = NULL; + EVP_MD_CTX *ctx = NULL; if (!opt_md_silent(mdname, &md)) return -1; - for (count = 0; COND(c[algindex][testnum]); count++) { - if (!EVP_Digest(buf, (size_t)lengths[testnum], digest, NULL, md, - NULL)) { + if (EVP_MD_xof(md)) { + ctx = EVP_MD_CTX_new(); + if (ctx == NULL) { count = -1; - break; + goto out; + } + + for (count = 0; COND(c[algindex][testnum]); count++) { + if (!EVP_DigestInit_ex2(ctx, md, NULL) + || !EVP_DigestUpdate(ctx, buf, (size_t)lengths[testnum]) + || !EVP_DigestFinalXOF(ctx, digest, sizeof(digest))) { + count = -1; + break; + } + } + } else { + for (count = 0; COND(c[algindex][testnum]); count++) { + if (!EVP_Digest(buf, (size_t)lengths[testnum], digest, NULL, md, + NULL)) { + count = -1; + break; + } } } +out: EVP_MD_free(md); + EVP_MD_CTX_free(ctx); return count; } @@ -964,7 +998,7 @@ static int RSA_sign_loop(void *args) ret = EVP_PKEY_sign(rsa_sign_ctx[testnum], buf2, rsa_num, buf, 36); if (ret <= 0) { BIO_printf(bio_err, "RSA sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -985,7 +1019,7 @@ static int RSA_verify_loop(void *args) ret = EVP_PKEY_verify(rsa_verify_ctx[testnum], buf2, rsa_num, buf, 36); if (ret <= 0) { BIO_printf(bio_err, "RSA verify failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1007,7 +1041,7 @@ static int RSA_encrypt_loop(void *args) ret = EVP_PKEY_encrypt(rsa_encrypt_ctx[testnum], buf2, rsa_num, buf, 36); if (ret <= 0) { BIO_printf(bio_err, "RSA encrypt failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1029,7 +1063,7 @@ static int RSA_decrypt_loop(void *args) ret = EVP_PKEY_decrypt(rsa_decrypt_ctx[testnum], buf, &rsa_num, buf2, tempargs->encsize); if (ret <= 0) { BIO_printf(bio_err, "RSA decrypt failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1056,6 +1090,7 @@ static int FFDH_derive_key_loop(void *args) } #endif /* OPENSSL_NO_DH */ +#ifndef OPENSSL_NO_DSA static int DSA_sign_loop(void *args) { loopargs_t *tempargs = *(loopargs_t **) args; @@ -1070,7 +1105,7 @@ static int DSA_sign_loop(void *args) ret = EVP_PKEY_sign(dsa_sign_ctx[testnum], buf2, dsa_num, buf, 20); if (ret <= 0) { BIO_printf(bio_err, "DSA sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1091,13 +1126,14 @@ static int DSA_verify_loop(void *args) ret = EVP_PKEY_verify(dsa_verify_ctx[testnum], buf2, dsa_num, buf, 20); if (ret <= 0) { BIO_printf(bio_err, "DSA verify failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } } return count; } +#endif /* OPENSSL_NO_DSA */ static int ECDSA_sign_loop(void *args) { @@ -1113,7 +1149,7 @@ static int ECDSA_sign_loop(void *args) ret = EVP_PKEY_sign(ecdsa_sign_ctx[testnum], buf2, ecdsa_num, buf, 20); if (ret <= 0) { BIO_printf(bio_err, "ECDSA sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1135,7 +1171,7 @@ static int ECDSA_verify_loop(void *args) buf, 20); if (ret <= 0) { BIO_printf(bio_err, "ECDSA verify failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1173,14 +1209,14 @@ static int EdDSA_sign_loop(void *args) ret = EVP_DigestSignInit(edctx[testnum], NULL, NULL, NULL, NULL); if (ret == 0) { BIO_printf(bio_err, "EdDSA sign init failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } ret = EVP_DigestSign(edctx[testnum], eddsasig, eddsasigsize, buf, 20); if (ret == 0) { BIO_printf(bio_err, "EdDSA sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1201,14 +1237,14 @@ static int EdDSA_verify_loop(void *args) ret = EVP_DigestVerifyInit(edctx[testnum], NULL, NULL, NULL, NULL); if (ret == 0) { BIO_printf(bio_err, "EdDSA verify init failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } ret = EVP_DigestVerify(edctx[testnum], eddsasig, eddsasigsize, buf, 20); if (ret != 1) { BIO_printf(bio_err, "EdDSA verify failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1235,7 +1271,7 @@ static int SM2_sign_loop(void *args) if (!EVP_DigestSignInit(sm2ctx[testnum], NULL, EVP_sm3(), NULL, sm2_pkey[testnum])) { BIO_printf(bio_err, "SM2 init sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1243,7 +1279,7 @@ static int SM2_sign_loop(void *args) buf, 20); if (ret == 0) { BIO_printf(bio_err, "SM2 sign failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1268,7 +1304,7 @@ static int SM2_verify_loop(void *args) if (!EVP_DigestVerifyInit(sm2ctx[testnum], NULL, EVP_sm3(), NULL, sm2_pkey[testnum])) { BIO_printf(bio_err, "SM2 verify init failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1276,7 +1312,7 @@ static int SM2_verify_loop(void *args) buf, 20); if (ret != 1) { BIO_printf(bio_err, "SM2 verify failure\n"); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1375,7 +1411,7 @@ static int SIG_sign_loop(void *args) if (ret <= 0) { BIO_printf(bio_err, "SIG sign failure at count %d\n", count); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1399,7 +1435,7 @@ static int SIG_verify_loop(void *args) if (ret <= 0) { BIO_printf(bio_err, "SIG verify failure at count %d\n", count); - ERR_print_errors(bio_err); + dofail(); count = -1; break; } @@ -1443,7 +1479,7 @@ static int run_benchmark(int async_jobs, case ASYNC_NO_JOBS: case ASYNC_ERR: BIO_printf(bio_err, "Failure in the job\n"); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1467,7 +1503,7 @@ static int run_benchmark(int async_jobs, (loopargs[i].wait_ctx, NULL, &num_job_fds) || num_job_fds > 1) { BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n"); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1483,7 +1519,7 @@ static int run_benchmark(int async_jobs, "Error: max_fd (%d) must be smaller than FD_SETSIZE (%d). " "Decrease the value of async_jobs\n", max_fd, FD_SETSIZE); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1494,7 +1530,7 @@ static int run_benchmark(int async_jobs, if (select_result == -1) { BIO_printf(bio_err, "Failure in the select\n"); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1511,7 +1547,7 @@ static int run_benchmark(int async_jobs, (loopargs[i].wait_ctx, NULL, &num_job_fds) || num_job_fds > 1) { BIO_printf(bio_err, "Too many fds in ASYNC_WAIT_CTX\n"); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1549,7 +1585,7 @@ static int run_benchmark(int async_jobs, --num_inprogress; loopargs[i].inprogress_job = NULL; BIO_printf(bio_err, "Failure in the job\n"); - ERR_print_errors(bio_err); + dofail(); error = 1; break; } @@ -1575,7 +1611,7 @@ static EVP_PKEY *get_ecdsa(const EC_CURVE *curve) if (ERR_peek_error()) { BIO_printf(bio_err, "WARNING: the error queue contains previous unhandled errors.\n"); - ERR_print_errors(bio_err); + dofail(); } /* @@ -1607,7 +1643,7 @@ static EVP_PKEY *get_ecdsa(const EC_CURVE *curve) if (ERR_peek_error()) { BIO_printf(bio_err, "Unhandled error in the error queue during EC key setup.\n"); - ERR_print_errors(bio_err); + dofail(); return NULL; } @@ -1618,7 +1654,7 @@ static EVP_PKEY *get_ecdsa(const EC_CURVE *curve) curve->nid) <= 0 || EVP_PKEY_paramgen(pctx, ¶ms) <= 0) { BIO_printf(bio_err, "EC params init failure.\n"); - ERR_print_errors(bio_err); + dofail(); EVP_PKEY_CTX_free(pctx); return NULL; } @@ -1632,7 +1668,7 @@ static EVP_PKEY *get_ecdsa(const EC_CURVE *curve) || EVP_PKEY_keygen_init(kctx) <= 0 || EVP_PKEY_keygen(kctx, &key) <= 0) { BIO_printf(bio_err, "EC key generation failure.\n"); - ERR_print_errors(bio_err); + dofail(); key = NULL; } EVP_PKEY_CTX_free(kctx); @@ -1813,8 +1849,10 @@ int speed_main(int argc, char **argv) uint8_t ffdh_doit[FFDH_NUM] = { 0 }; #endif /* OPENSSL_NO_DH */ +#ifndef OPENSSL_NO_DSA static const unsigned int dsa_bits[DSA_NUM] = { 1024, 2048 }; uint8_t dsa_doit[DSA_NUM] = { 0 }; +#endif /* OPENSSL_NO_DSA */ /* * We only test over the following curves as they are representative, To * add tests over more curves, simply add the curve NID and curve name to @@ -1973,14 +2011,17 @@ int speed_main(int argc, char **argv) case OPT_ASYNCJOBS: #ifndef OPENSSL_NO_ASYNC async_jobs = opt_int_arg(); + if (async_jobs > 99999) { + BIO_printf(bio_err, "%s: too many async_jobs\n", prog); + goto opterr; + } if (!ASYNC_is_capable()) { BIO_printf(bio_err, "%s: async_jobs specified but async not supported\n", prog); - goto opterr; - } - if (async_jobs > 99999) { - BIO_printf(bio_err, "%s: too many async_jobs\n", prog); + if (testmode) + /* Return success in the testmode. */ + return 0; goto opterr; } #endif @@ -2050,6 +2091,9 @@ int speed_main(int argc, char **argv) goto end; #endif break; + case OPT_TESTMODE: + testmode = 1; + break; } } @@ -2118,6 +2162,7 @@ int speed_main(int argc, char **argv) sigs_algname[sigs_algs_len++] = OPENSSL_strdup(rsa_choices[i].name); } } +#ifndef OPENSSL_NO_DSA else if (strcmp(sig_name, "DSA") == 0) { if (sigs_algs_len + DSA_NUM >= MAX_SIG_NUM) { BIO_printf(bio_err, @@ -2129,6 +2174,7 @@ int speed_main(int argc, char **argv) sigs_algname[sigs_algs_len++] = OPENSSL_strdup(dsa_choices[i].name); } } +#endif /* OPENSSL_NO_DSA */ /* skipping these algs as tested elsewhere - and b/o setup is a pain */ else if (strcmp(sig_name, "ED25519") && strcmp(sig_name, "ED448") && @@ -2200,6 +2246,7 @@ int speed_main(int argc, char **argv) } } #endif +#ifndef OPENSSL_NO_DSA if (HAS_PREFIX(algo, "dsa")) { if (algo[sizeof("dsa") - 1] == '\0') { memset(dsa_doit, 1, sizeof(dsa_doit)); @@ -2210,6 +2257,7 @@ int speed_main(int argc, char **argv) algo_found = 1; } } +#endif if (strcmp(algo, "aes") == 0) { doit[D_CBC_128_AES] = doit[D_CBC_192_AES] = doit[D_CBC_256_AES] = 1; algo_found = 1; @@ -2435,7 +2483,9 @@ int speed_main(int argc, char **argv) #ifndef OPENSSL_NO_DH memset(ffdh_doit, 1, sizeof(ffdh_doit)); #endif +#ifndef OPENSSL_NO_DSA memset(dsa_doit, 1, sizeof(dsa_doit)); +#endif #ifndef OPENSSL_NO_ECX memset(ecdsa_doit, 1, sizeof(ecdsa_doit)); memset(ecdh_doit, 1, sizeof(ecdh_doit)); @@ -2573,13 +2623,13 @@ int speed_main(int argc, char **argv) if (doit[D_HMAC]) { static const char hmac_key[] = "This is a key..."; int len = strlen(hmac_key); + size_t hmac_name_len = sizeof("hmac()") + strlen(evp_mac_mdname); OSSL_PARAM params[3]; if (evp_mac_mdname == NULL) goto end; - evp_hmac_name = app_malloc(sizeof("hmac()") + strlen(evp_mac_mdname), - "HMAC name"); - sprintf(evp_hmac_name, "hmac(%s)", evp_mac_mdname); + evp_hmac_name = app_malloc(hmac_name_len, "HMAC name"); + BIO_snprintf(evp_hmac_name, hmac_name_len, "hmac(%s)", evp_mac_mdname); names[D_HMAC] = evp_hmac_name; params[0] = @@ -2796,7 +2846,7 @@ int speed_main(int argc, char **argv) if (!EVP_CipherInit_ex(loopargs[k].ctx, evp_cipher, NULL, NULL, iv, decrypt ? 0 : 1)) { BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n"); - ERR_print_errors(bio_err); + dofail(); exit(1); } @@ -2808,7 +2858,7 @@ int speed_main(int argc, char **argv) if (!EVP_CipherInit_ex(loopargs[k].ctx, NULL, NULL, loopargs[k].key, NULL, -1)) { BIO_printf(bio_err, "\nEVP_CipherInit_ex failure\n"); - ERR_print_errors(bio_err); + dofail(); exit(1); } OPENSSL_clear_free(loopargs[k].key, keylen); @@ -2843,6 +2893,7 @@ int speed_main(int argc, char **argv) } if (doit[D_EVP_CMAC]) { + size_t len = sizeof("cmac()") + strlen(evp_mac_ciphername); OSSL_PARAM params[3]; EVP_CIPHER *cipher = NULL; @@ -2855,9 +2906,8 @@ int speed_main(int argc, char **argv) BIO_printf(bio_err, "\nRequested CMAC cipher with unsupported key length.\n"); goto end; } - evp_cmac_name = app_malloc(sizeof("cmac()") - + strlen(evp_mac_ciphername), "CMAC name"); - sprintf(evp_cmac_name, "cmac(%s)", evp_mac_ciphername); + evp_cmac_name = app_malloc(len, "CMAC name"); + BIO_snprintf(evp_cmac_name, len, "cmac(%s)", evp_mac_ciphername); names[D_EVP_CMAC] = evp_cmac_name; params[0] = OSSL_PARAM_construct_utf8_string(OSSL_ALG_PARAM_CIPHER, @@ -2968,7 +3018,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "RSA sign setup failure. No RSA sign will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("private", "rsa sign", @@ -2999,7 +3049,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "RSA verify setup failure. No RSA verify will be done.\n"); - ERR_print_errors(bio_err); + dofail(); rsa_doit[testnum] = 0; } else { pkey_print_message("public", "rsa verify", @@ -3028,7 +3078,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "RSA encrypt setup failure. No RSA encrypt will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("public", "rsa encrypt", @@ -3060,7 +3110,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "RSA decrypt setup failure. No RSA decrypt will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("private", "rsa decrypt", @@ -3084,6 +3134,7 @@ int speed_main(int argc, char **argv) EVP_PKEY_free(rsa_key); } +#ifndef OPENSSL_NO_DSA for (testnum = 0; testnum < DSA_NUM; testnum++) { EVP_PKEY *dsa_key = NULL; int st; @@ -3108,7 +3159,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "DSA sign setup failure. No DSA sign will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("sign", "dsa", @@ -3138,7 +3189,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "DSA verify setup failure. No DSA verify will be done.\n"); - ERR_print_errors(bio_err); + dofail(); dsa_doit[testnum] = 0; } else { pkey_print_message("verify", "dsa", @@ -3159,6 +3210,7 @@ int speed_main(int argc, char **argv) } EVP_PKEY_free(dsa_key); } +#endif /* OPENSSL_NO_DSA */ for (testnum = 0; testnum < ECDSA_NUM; testnum++) { EVP_PKEY *ecdsa_key = NULL; @@ -3184,7 +3236,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "ECDSA sign setup failure. No ECDSA sign will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("sign", "ecdsa", @@ -3214,7 +3266,7 @@ int speed_main(int argc, char **argv) if (!st) { BIO_printf(bio_err, "ECDSA verify setup failure. No ECDSA verify will be done.\n"); - ERR_print_errors(bio_err); + dofail(); ecdsa_doit[testnum] = 0; } else { pkey_print_message("verify", "ecdsa", @@ -3233,6 +3285,7 @@ int speed_main(int argc, char **argv) /* if longer than 10s, don't do any more */ stop_it(ecdsa_doit, testnum); } + EVP_PKEY_free(ecdsa_key); } for (testnum = 0; testnum < EC_NUM; testnum++) { @@ -3259,7 +3312,7 @@ int speed_main(int argc, char **argv) || outlen > MAX_ECDH_SIZE /* avoid buffer overflow */) { ecdh_checks = 0; BIO_printf(bio_err, "ECDH key generation failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; break; } @@ -3279,7 +3332,7 @@ int speed_main(int argc, char **argv) || test_outlen != outlen /* compare output length */) { ecdh_checks = 0; BIO_printf(bio_err, "ECDH computation failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; break; } @@ -3289,7 +3342,7 @@ int speed_main(int argc, char **argv) loopargs[i].secret_b, outlen)) { ecdh_checks = 0; BIO_printf(bio_err, "ECDH computations don't match.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; break; } @@ -3371,7 +3424,7 @@ int speed_main(int argc, char **argv) } if (st == 0) { BIO_printf(bio_err, "EdDSA failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { for (i = 0; i < loopargs_len; i++) { @@ -3386,7 +3439,7 @@ int speed_main(int argc, char **argv) if (st == 0) { BIO_printf(bio_err, "EdDSA sign failure. No EdDSA sign will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("sign", ed_curves[testnum].name, @@ -3414,7 +3467,7 @@ int speed_main(int argc, char **argv) if (st != 1) { BIO_printf(bio_err, "EdDSA verify failure. No EdDSA verify will be done.\n"); - ERR_print_errors(bio_err); + dofail(); eddsa_doit[testnum] = 0; } else { pkey_print_message("verify", ed_curves[testnum].name, @@ -3503,7 +3556,7 @@ int speed_main(int argc, char **argv) } if (st == 0) { BIO_printf(bio_err, "SM2 init failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { for (i = 0; i < loopargs_len; i++) { @@ -3517,7 +3570,7 @@ int speed_main(int argc, char **argv) if (st == 0) { BIO_printf(bio_err, "SM2 sign failure. No SM2 sign will be done.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; } else { pkey_print_message("sign", sm2_curves[testnum].name, @@ -3546,7 +3599,7 @@ int speed_main(int argc, char **argv) if (st != 1) { BIO_printf(bio_err, "SM2 verify failure. No SM2 verify will be done.\n"); - ERR_print_errors(bio_err); + dofail(); sm2_doit[testnum] = 0; } else { pkey_print_message("verify", sm2_curves[testnum].name, @@ -3590,13 +3643,13 @@ int speed_main(int argc, char **argv) if (ERR_peek_error()) { BIO_printf(bio_err, "WARNING: the error queue contains previous unhandled errors.\n"); - ERR_print_errors(bio_err); + dofail(); } pkey_A = EVP_PKEY_new(); if (!pkey_A) { BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3604,7 +3657,7 @@ int speed_main(int argc, char **argv) pkey_B = EVP_PKEY_new(); if (!pkey_B) { BIO_printf(bio_err, "Error while initialising EVP_PKEY (out of memory?).\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3613,7 +3666,7 @@ int speed_main(int argc, char **argv) ffdh_ctx = EVP_PKEY_CTX_new_id(EVP_PKEY_DH, NULL); if (!ffdh_ctx) { BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3621,14 +3674,14 @@ int speed_main(int argc, char **argv) if (EVP_PKEY_keygen_init(ffdh_ctx) <= 0) { BIO_printf(bio_err, "Error while initialising EVP_PKEY_CTX.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; } if (EVP_PKEY_CTX_set_dh_nid(ffdh_ctx, ffdh_params[testnum].nid) <= 0) { BIO_printf(bio_err, "Error setting DH key size for keygen.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3637,7 +3690,7 @@ int speed_main(int argc, char **argv) if (EVP_PKEY_keygen(ffdh_ctx, &pkey_A) <= 0 || EVP_PKEY_keygen(ffdh_ctx, &pkey_B) <= 0) { BIO_printf(bio_err, "FFDH key generation failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3653,28 +3706,28 @@ int speed_main(int argc, char **argv) ffdh_ctx = EVP_PKEY_CTX_new(pkey_A, NULL); if (ffdh_ctx == NULL) { BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; } if (EVP_PKEY_derive_init(ffdh_ctx) <= 0) { BIO_printf(bio_err, "FFDH derivation context init failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; } if (EVP_PKEY_derive_set_peer(ffdh_ctx, pkey_B) <= 0) { BIO_printf(bio_err, "Assigning peer key for derivation failed.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; } if (EVP_PKEY_derive(ffdh_ctx, NULL, &secret_size) <= 0) { BIO_printf(bio_err, "Checking size of shared secret failed.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3689,7 +3742,7 @@ int speed_main(int argc, char **argv) loopargs[i].secret_ff_a, &secret_size) <= 0) { BIO_printf(bio_err, "Shared secret derive failure.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3698,7 +3751,7 @@ int speed_main(int argc, char **argv) test_ctx = EVP_PKEY_CTX_new(pkey_B, NULL); if (!test_ctx) { BIO_printf(bio_err, "Error while allocating EVP_PKEY_CTX.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3718,7 +3771,7 @@ int speed_main(int argc, char **argv) if (CRYPTO_memcmp(loopargs[i].secret_ff_a, loopargs[i].secret_ff_b, secret_size)) { BIO_printf(bio_err, "FFDH computations don't match.\n"); - ERR_print_errors(bio_err); + dofail(); op_count = 1; ffdh_checks = 0; break; @@ -3791,7 +3844,7 @@ int speed_main(int argc, char **argv) if (ERR_peek_error()) { BIO_printf(bio_err, "WARNING: the error queue contains previous unhandled errors.\n"); - ERR_print_errors(bio_err); + dofail(); } if (kem_type == KEM_RSA) { @@ -3897,7 +3950,7 @@ int speed_main(int argc, char **argv) continue; kem_err_break: - ERR_print_errors(bio_err); + dofail(); EVP_PKEY_free(pkey); op_count = 1; kem_checks = 0; @@ -3973,7 +4026,7 @@ int speed_main(int argc, char **argv) if (ERR_peek_error()) { BIO_printf(bio_err, "WARNING: the error queue contains previous unhandled errors.\n"); - ERR_print_errors(bio_err); + dofail(); } /* no string after rsa permitted: */ @@ -4077,7 +4130,7 @@ int speed_main(int argc, char **argv) continue; sig_err_break: - ERR_print_errors(bio_err); + dofail(); EVP_PKEY_free(pkey); op_count = 1; sig_checks = 0; @@ -4192,6 +4245,7 @@ int speed_main(int argc, char **argv) rsa_results[k][2], rsa_results[k][3]); } testnum = 1; +#ifndef OPENSSL_NO_DSA for (k = 0; k < DSA_NUM; k++) { if (!dsa_doit[k]) continue; @@ -4207,6 +4261,7 @@ int speed_main(int argc, char **argv) dsa_bits[k], 1.0 / dsa_results[k][0], 1.0 / dsa_results[k][1], dsa_results[k][0], dsa_results[k][1]); } +#endif /* OPENSSL_NO_DSA */ testnum = 1; for (k = 0; k < OSSL_NELEM(ecdsa_doit); k++) { if (!ecdsa_doit[k]) @@ -4355,6 +4410,8 @@ int speed_main(int argc, char **argv) ret = 0; end: + if (ret == 0 && testmode) + ret = testmoderesult; ERR_print_errors(bio_err); for (i = 0; i < loopargs_len; i++) { OPENSSL_free(loopargs[i].buf_malloc); @@ -4374,10 +4431,12 @@ int speed_main(int argc, char **argv) for (k = 0; k < FFDH_NUM; k++) EVP_PKEY_CTX_free(loopargs[i].ffdh_ctx[k]); #endif +#ifndef OPENSSL_NO_DSA for (k = 0; k < DSA_NUM; k++) { EVP_PKEY_CTX_free(loopargs[i].dsa_sign_ctx[k]); EVP_PKEY_CTX_free(loopargs[i].dsa_verify_ctx[k]); } +#endif for (k = 0; k < ECDSA_NUM; k++) { EVP_PKEY_CTX_free(loopargs[i].ecdsa_sign_ctx[k]); EVP_PKEY_CTX_free(loopargs[i].ecdsa_verify_ctx[k]); @@ -4487,7 +4546,7 @@ static void print_result(int alg, int run_no, int count, double time_used) { if (count == -1) { BIO_printf(bio_err, "%s error!\n", names[alg]); - ERR_print_errors(bio_err); + dofail(); return; } BIO_printf(bio_err, @@ -4626,6 +4685,7 @@ static int do_multi(int multi, int size_num) d = atof(sstrsep(&p, sep)); rsa_results[k][3] += d; } +# ifndef OPENSSL_NO_DSA } else if (CHECK_AND_SKIP_PREFIX(p, "+F3:")) { tk = sstrsep(&p, sep); if (strtoint(tk, 0, OSSL_NELEM(dsa_results), &k)) { @@ -4637,6 +4697,7 @@ static int do_multi(int multi, int size_num) d = atof(sstrsep(&p, sep)); dsa_results[k][1] += d; } +# endif /* OPENSSL_NO_DSA */ } else if (CHECK_AND_SKIP_PREFIX(p, "+F4:")) { tk = sstrsep(&p, sep); if (strtoint(tk, 0, OSSL_NELEM(ecdsa_results), &k)) { @@ -4748,8 +4809,9 @@ static int do_multi(int multi, int size_num) static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single, const openssl_speed_sec_t *seconds) { - static const int mblengths_list[] = - { 8 * 1024, 2 * 8 * 1024, 4 * 8 * 1024, 8 * 8 * 1024, 8 * 16 * 1024 }; + static const int mblengths_list[] = { + 8 * 1024, 2 * 8 * 1024, 4 * 8 * 1024, 8 * 8 * 1024, 8 * 16 * 1024 + }; const int *mblengths = mblengths_list; int j, count, keylen, num = OSSL_NELEM(mblengths_list), ciph_success = 1; const char *alg_name; @@ -4789,7 +4851,7 @@ static void multiblock_speed(const EVP_CIPHER *evp_cipher, int lengths_single, for (j = 0; j < num; j++) { print_message(alg_name, mblengths[j], seconds->sym); Time_F(START); - for (count = 0; run && count < INT_MAX; count++) { + for (count = 0; run && COND(count); count++) { unsigned char aad[EVP_AEAD_TLS1_AAD_LEN]; EVP_CTRL_TLS1_1_MULTIBLOCK_PARAM mb_param; size_t len = mblengths[j]; diff --git a/apps/version.c b/apps/version.c index 7185e9edcd..89fb64b70a 100644 --- a/apps/version.c +++ b/apps/version.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -19,6 +19,9 @@ typedef enum OPTION_choice { OPT_COMMON, OPT_B, OPT_D, OPT_E, OPT_M, OPT_F, OPT_O, OPT_P, OPT_V, OPT_A, OPT_R, OPT_C +#if defined(_WIN32) + ,OPT_W +#endif } OPTION_CHOICE; const OPTIONS version_options[] = { @@ -37,6 +40,9 @@ const OPTIONS version_options[] = { {"r", OPT_R, '-', "Show random seeding options"}, {"v", OPT_V, '-', "Show library version"}, {"c", OPT_C, '-', "Show CPU settings info"}, +#if defined(_WIN32) + {"w", OPT_W, '-', "Show Windows install context"}, +#endif {NULL} }; @@ -45,6 +51,9 @@ int version_main(int argc, char **argv) int ret = 1, dirty = 0, seed = 0; int cflags = 0, version = 0, date = 0, options = 0, platform = 0, dir = 0; int engdir = 0, moddir = 0, cpuinfo = 0; +#if defined(_WIN32) + int windows = 0; +#endif char *prog; OPTION_CHOICE o; @@ -90,6 +99,11 @@ int version_main(int argc, char **argv) case OPT_C: dirty = cpuinfo = 1; break; +#if defined(_WIN32) + case OPT_W: + dirty = windows = 1; + break; +#endif case OPT_A: seed = options = cflags = version = date = platform = dir = engdir = moddir = cpuinfo @@ -131,6 +145,10 @@ int version_main(int argc, char **argv) } if (cpuinfo) printf("%s\n", OpenSSL_version(OPENSSL_CPU_INFO)); +#if defined(_WIN32) + if (windows) + printf("%s\n", OpenSSL_version(OPENSSL_WINCTX)); +#endif ret = 0; end: return ret; diff --git a/apps/x509.c b/apps/x509.c index d96e7819b2..cd5b7bf796 100644 --- a/apps/x509.c +++ b/apps/x509.c @@ -29,8 +29,8 @@ #undef POSTFIX #define POSTFIX ".srl" -#define DEFAULT_DAYS 30 /* default cert validity period in days */ -#define UNSET_DAYS -2 /* -1 is used for testing expiration checks */ +#define DEFAULT_DAYS 30 /* default certificate validity period in days */ +#define UNSET_DAYS -2 /* -1 may be used for testing expiration checks */ #define EXT_COPY_UNSET -1 static int callb(int ok, X509_STORE_CTX *ctx); @@ -54,6 +54,7 @@ typedef enum OPTION_choice { OPT_CLRREJECT, OPT_ALIAS, OPT_CACREATESERIAL, OPT_CLREXT, OPT_OCSPID, OPT_SUBJECT_HASH_OLD, OPT_ISSUER_HASH_OLD, OPT_COPY_EXTENSIONS, OPT_BADSIG, OPT_MD, OPT_ENGINE, OPT_NOCERT, OPT_PRESERVE_DATES, + OPT_NOT_BEFORE, OPT_NOT_AFTER, OPT_R_ENUM, OPT_PROV_ENUM, OPT_EXT } OPTION_CHOICE; @@ -135,6 +136,10 @@ const OPTIONS x509_options[] = { "Serial number to use, overrides -CAserial"}, {"next_serial", OPT_NEXT_SERIAL, '-', "Increment current certificate serial number"}, + {"not_before", OPT_NOT_BEFORE, 's', + "[CC]YYMMDDHHMMSSZ value for notBefore certificate field"}, + {"not_after", OPT_NOT_AFTER, 's', + "[CC]YYMMDDHHMMSSZ value for notAfter certificate field, overrides -days"}, {"days", OPT_DAYS, 'n', "Number of days until newly generated certificate expires - default 30"}, {"preserve_dates", OPT_PRESERVE_DATES, '-', @@ -279,7 +284,7 @@ int x509_main(int argc, char **argv) char *ext_names = NULL; char *extsect = NULL, *extfile = NULL, *passin = NULL, *passinarg = NULL; char *infile = NULL, *outfile = NULL, *privkeyfile = NULL, *CAfile = NULL; - char *prog; + char *prog, *not_before = NULL, *not_after = NULL; int days = UNSET_DAYS; /* not explicitly set */ int x509toreq = 0, modulus = 0, print_pubkey = 0, pprint = 0; int CAformat = FORMAT_UNDEF, CAkeyformat = FORMAT_UNDEF; @@ -376,9 +381,15 @@ int x509_main(int argc, char **argv) if (!vfyopts || !sk_OPENSSL_STRING_push(vfyopts, opt_arg())) goto opthelp; break; + case OPT_NOT_BEFORE: + not_before = opt_arg(); + break; + case OPT_NOT_AFTER: + not_after = opt_arg(); + break; case OPT_DAYS: days = atoi(opt_arg()); - if (days < -1) { + if (days <= UNSET_DAYS) { BIO_printf(bio_err, "%s: -days parameter arg must be >= -1\n", prog); goto err; @@ -610,12 +621,22 @@ int x509_main(int argc, char **argv) if (!opt_check_md(digest)) goto opthelp; + if (preserve_dates && not_before != NULL) { + BIO_printf(bio_err, "Cannot use -preserve_dates with -not_before option\n"); + goto err; + } + if (preserve_dates && not_after != NULL) { + BIO_printf(bio_err, "Cannot use -preserve_dates with -not_after option\n"); + goto err; + } if (preserve_dates && days != UNSET_DAYS) { BIO_printf(bio_err, "Cannot use -preserve_dates with -days option\n"); goto err; } if (days == UNSET_DAYS) days = DEFAULT_DAYS; + else if (not_after != NULL) + BIO_printf(bio_err, "Warning: -not_after option overriding -days option\n"); if (!app_passwd(passinarg, NULL, &passin, NULL)) { BIO_printf(bio_err, "Error getting password\n"); @@ -837,7 +858,7 @@ int x509_main(int argc, char **argv) goto end; if (reqfile || newcert || privkey != NULL || CAfile != NULL) { - if (!preserve_dates && !set_cert_times(x, NULL, NULL, days)) + if (!preserve_dates && !set_cert_times(x, not_before, not_after, days, 1)) goto end; if (fissu != NULL) { if (!X509_set_issuer_name(x, fissu)) diff --git a/crypto/aes/asm/aes-x86_64.S b/crypto/aes/asm/aes-x86_64.S index 1e85beafbe..aeaa4d197b 100644 --- a/crypto/aes/asm/aes-x86_64.S +++ b/crypto/aes/asm/aes-x86_64.S @@ -1870,6 +1870,7 @@ AES_cbc_encrypt: .byte 0xf3,0xc3 .cfi_endproc .size AES_cbc_encrypt,.-AES_cbc_encrypt +.section .rodata .align 64 .LAES_Te: .long 0xa56363c6,0xa56363c6 @@ -2656,6 +2657,7 @@ AES_cbc_encrypt: .long 0x1b1b1b1b, 0x1b1b1b1b, 0, 0 .byte 65,69,83,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/aes/asm/aes-x86_64.pl b/crypto/aes/asm/aes-x86_64.pl index 25f7ded947..8c7b205a05 100755 --- a/crypto/aes/asm/aes-x86_64.pl +++ b/crypto/aes/asm/aes-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2005-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -2221,6 +2221,7 @@ () } $code.=<<___; +.section .rodata align=64 .align 64 .LAES_Te: ___ @@ -2643,6 +2644,7 @@ () .long 0x1b1b1b1b, 0x1b1b1b1b, 0, 0 .asciz "AES for x86_64, CRYPTOGAMS by " .align 64 +.previous ___ # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame, diff --git a/crypto/aes/asm/aesni-sha1-x86_64.S b/crypto/aes/asm/aesni-sha1-x86_64.S index 2078fe2ab3..aeafc094a0 100644 --- a/crypto/aes/asm/aesni-sha1-x86_64.S +++ b/crypto/aes/asm/aesni-sha1-x86_64.S @@ -2718,6 +2718,7 @@ aesni_cbc_sha1_enc_avx: .byte 0xf3,0xc3 .cfi_endproc .size aesni_cbc_sha1_enc_avx,.-aesni_cbc_sha1_enc_avx +.section .rodata .align 64 K_XX_XX: .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 @@ -2729,6 +2730,7 @@ K_XX_XX: .byte 65,69,83,78,73,45,67,66,67,43,83,72,65,49,32,115,116,105,116,99,104,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 +.previous .type aesni_cbc_sha1_enc_shaext,@function .align 32 aesni_cbc_sha1_enc_shaext: diff --git a/crypto/aes/asm/aesni-sha1-x86_64.pl b/crypto/aes/asm/aesni-sha1-x86_64.pl index dbe33a3f1a..4e8fa1d753 100644 --- a/crypto/aes/asm/aesni-sha1-x86_64.pl +++ b/crypto/aes/asm/aesni-sha1-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2011-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -1738,6 +1738,7 @@ () }}} } $code.=<<___; +.section .rodata align=64 .align 64 K_XX_XX: .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 # K_00_19 @@ -1749,6 +1750,7 @@ () .asciz "AESNI-CBC+SHA1 stitch for x86_64, CRYPTOGAMS by " .align 64 +.previous ___ if ($shaext) {{{ ($in0,$out,$len,$key,$ivp,$ctx,$inp)=("%rdi","%rsi","%rdx","%rcx","%r8","%r9","%r10"); diff --git a/crypto/aes/asm/aesni-sha256-x86_64.S b/crypto/aes/asm/aesni-sha256-x86_64.S index c938e50b99..f26bcd4772 100644 --- a/crypto/aes/asm/aesni-sha256-x86_64.S +++ b/crypto/aes/asm/aesni-sha256-x86_64.S @@ -34,6 +34,7 @@ aesni_cbc_sha256_enc: .cfi_endproc .size aesni_cbc_sha256_enc,.-aesni_cbc_sha256_enc +.section .rodata .align 64 .type K256,@object K256: @@ -76,6 +77,7 @@ K256: .long 0,0,0,0, 0,0,0,0 .byte 65,69,83,78,73,45,67,66,67,43,83,72,65,50,53,54,32,115,116,105,116,99,104,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 +.previous .type aesni_cbc_sha256_enc_xop,@function .align 64 aesni_cbc_sha256_enc_xop: diff --git a/crypto/aes/asm/aesni-sha256-x86_64.pl b/crypto/aes/asm/aesni-sha256-x86_64.pl index 5521766a6a..39d29ddbb0 100644 --- a/crypto/aes/asm/aesni-sha256-x86_64.pl +++ b/crypto/aes/asm/aesni-sha256-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -168,6 +168,7 @@ .cfi_endproc .size $func,.-$func +.section .rodata align=64 .align 64 .type $TABLE,\@object $TABLE: @@ -210,6 +211,7 @@ .long 0,0,0,0, 0,0,0,0 .asciz "AESNI-CBC+SHA256 stitch for x86_64, CRYPTOGAMS by " .align 64 +.previous ___ ###################################################################### diff --git a/crypto/aes/asm/aesni-x86_64.S b/crypto/aes/asm/aesni-x86_64.S index 4e35b2b1d3..7970fdf0d4 100644 --- a/crypto/aes/asm/aesni-x86_64.S +++ b/crypto/aes/asm/aesni-x86_64.S @@ -4461,6 +4461,7 @@ __aesni_set_encrypt_key: .cfi_endproc .size aesni_set_encrypt_key,.-aesni_set_encrypt_key .size __aesni_set_encrypt_key,.-__aesni_set_encrypt_key +.section .rodata .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -4483,6 +4484,7 @@ __aesni_set_encrypt_key: .byte 65,69,83,32,102,111,114,32,73,110,116,101,108,32,65,69,83,45,78,73,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/aes/asm/aesni-x86_64.pl b/crypto/aes/asm/aesni-x86_64.pl index 09c8f78890..bff33f2b8d 100644 --- a/crypto/aes/asm/aesni-x86_64.pl +++ b/crypto/aes/asm/aesni-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2009-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2009-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -4743,6 +4743,7 @@ sub aesni_generate8 { } $code.=<<___; +.section .rodata align=64 .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -4765,6 +4766,7 @@ sub aesni_generate8 { .asciz "AES for Intel AES-NI, CRYPTOGAMS by " .align 64 +.previous ___ # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame, diff --git a/crypto/aes/asm/bsaes-x86_64.S b/crypto/aes/asm/bsaes-x86_64.S index ff533b2df3..9705994c04 100644 --- a/crypto/aes/asm/bsaes-x86_64.S +++ b/crypto/aes/asm/bsaes-x86_64.S @@ -1571,6 +1571,7 @@ ossl_bsaes_ctr32_encrypt_blocks: .align 16 ossl_bsaes_xts_encrypt: .cfi_startproc +.byte 243,15,30,250 movq %rsp,%rax .Lxts_enc_prologue: pushq %rbp @@ -2046,6 +2047,7 @@ ossl_bsaes_xts_encrypt: .align 16 ossl_bsaes_xts_decrypt: .cfi_startproc +.byte 243,15,30,250 movq %rsp,%rax .Lxts_dec_prologue: pushq %rbp @@ -2541,6 +2543,7 @@ ossl_bsaes_xts_decrypt: .cfi_endproc .size ossl_bsaes_xts_decrypt,.-ossl_bsaes_xts_decrypt .type _bsaes_const,@object +.section .rodata .align 64 _bsaes_const: .LM0ISR: @@ -2592,9 +2595,9 @@ _bsaes_const: .quad 0x02060a0e03070b0f, 0x0004080c0105090d .L63: .quad 0x6363636363636363, 0x6363636363636363 -.byte 66,105,116,45,115,108,105,99,101,100,32,65,69,83,32,102,111,114,32,120,56,54,95,54,52,47,83,83,83,69,51,44,32,69,109,105,108,105,97,32,75,195,164,115,112,101,114,44,32,80,101,116,101,114,32,83,99,104,119,97,98,101,44,32,65,110,100,121,32,80,111,108,121,97,107,111,118,0 .align 64 .size _bsaes_const,.-_bsaes_const +.byte 66,105,116,45,115,108,105,99,101,100,32,65,69,83,32,102,111,114,32,120,56,54,95,54,52,47,83,83,83,69,51,44,32,69,109,105,108,105,97,32,75,195,164,115,112,101,114,44,32,80,101,116,101,114,32,83,99,104,119,97,98,101,44,32,65,110,100,121,32,80,111,108,121,97,107,111,118,0 .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/aes/asm/bsaes-x86_64.pl b/crypto/aes/asm/bsaes-x86_64.pl index 6498cfe908..7230f76085 100644 --- a/crypto/aes/asm/bsaes-x86_64.pl +++ b/crypto/aes/asm/bsaes-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2011-2021 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -2182,6 +2182,7 @@ sub bitslice_key { .align 16 ossl_bsaes_xts_encrypt: .cfi_startproc + endbranch mov %rsp, %rax .Lxts_enc_prologue: push %rbp @@ -2581,6 +2582,7 @@ sub bitslice_key { .align 16 ossl_bsaes_xts_decrypt: .cfi_startproc + endbranch mov %rsp, %rax .Lxts_dec_prologue: push %rbp @@ -3003,6 +3005,7 @@ sub bitslice_key { } $code.=<<___; .type _bsaes_const,\@object +.section .rodata align=64 .align 64 _bsaes_const: .LM0ISR: # InvShiftRows constants @@ -3054,9 +3057,9 @@ sub bitslice_key { .quad 0x02060a0e03070b0f, 0x0004080c0105090d .L63: .quad 0x6363636363636363, 0x6363636363636363 -.asciz "Bit-sliced AES for x86_64/SSSE3, Emilia Käsper, Peter Schwabe, Andy Polyakov" .align 64 .size _bsaes_const,.-_bsaes_const +.asciz "Bit-sliced AES for x86_64/SSSE3, Emilia Käsper, Peter Schwabe, Andy Polyakov" ___ # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame, diff --git a/crypto/aes/asm/vpaes-x86_64.S b/crypto/aes/asm/vpaes-x86_64.S index 7783c6a659..1c7816840a 100644 --- a/crypto/aes/asm/vpaes-x86_64.S +++ b/crypto/aes/asm/vpaes-x86_64.S @@ -758,6 +758,7 @@ _vpaes_preheat: .type _vpaes_consts,@object +.section .rodata .align 64 _vpaes_consts: .Lk_inv: @@ -853,9 +854,9 @@ _vpaes_consts: .Lk_dsbo: .quad 0x1387EA537EF94000, 0xC7AA6DB9D4943E2D .quad 0x12D7560F93441D00, 0xCA4B8159D8C58E9C -.byte 86,101,99,116,111,114,32,80,101,114,109,117,116,97,116,105,111,110,32,65,69,83,32,102,111,114,32,120,56,54,95,54,52,47,83,83,83,69,51,44,32,77,105,107,101,32,72,97,109,98,117,114,103,32,40,83,116,97,110,102,111,114,100,32,85,110,105,118,101,114,115,105,116,121,41,0 .align 64 .size _vpaes_consts,.-_vpaes_consts +.byte 86,101,99,116,111,114,32,80,101,114,109,117,116,97,116,105,111,110,32,65,69,83,32,102,111,114,32,120,56,54,95,54,52,47,83,83,83,69,51,44,32,77,105,107,101,32,72,97,109,98,117,114,103,32,40,83,116,97,110,102,111,114,100,32,85,110,105,118,101,114,115,105,116,121,41,0 .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/aes/asm/vpaes-x86_64.pl b/crypto/aes/asm/vpaes-x86_64.pl index 845528f41a..f628188415 100644 --- a/crypto/aes/asm/vpaes-x86_64.pl +++ b/crypto/aes/asm/vpaes-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2011-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -1006,6 +1006,7 @@ ## ## ######################################################## .type _vpaes_consts,\@object +.section .rodata align=64 .align 64 _vpaes_consts: .Lk_inv: # inv, inva @@ -1101,9 +1102,9 @@ .Lk_dsbo: # decryption sbox final output .quad 0x1387EA537EF94000, 0xC7AA6DB9D4943E2D .quad 0x12D7560F93441D00, 0xCA4B8159D8C58E9C -.asciz "Vector Permutation AES for x86_64/SSSE3, Mike Hamburg (Stanford University)" .align 64 .size _vpaes_consts,.-_vpaes_consts +.asciz "Vector Permutation AES for x86_64/SSSE3, Mike Hamburg (Stanford University)" ___ if ($win64) { diff --git a/crypto/arm_arch.h b/crypto/arm_arch.h index 7ac978fec0..acd8aee4d5 100644 --- a/crypto/arm_arch.h +++ b/crypto/arm_arch.h @@ -104,6 +104,7 @@ extern unsigned int OPENSSL_armv8_rsa_neonized; # define HISI_CPU_IMP 0x48 # define ARM_CPU_IMP_APPLE 0x61 # define ARM_CPU_IMP_MICROSOFT 0x6D +# define ARM_CPU_IMP_AMPERE 0xC0 # define ARM_CPU_PART_CORTEX_A72 0xD08 # define ARM_CPU_PART_N1 0xD0C diff --git a/crypto/armcap.c b/crypto/armcap.c index 781503eda5..33b9dd4df0 100644 --- a/crypto/armcap.c +++ b/crypto/armcap.c @@ -78,9 +78,10 @@ void OPENSSL_cpuid_setup(void) __attribute__ ((constructor)); # define OSSL_IMPLEMENT_GETAUXVAL # endif # endif -# if defined(__FreeBSD__) +# if defined(__FreeBSD__) || defined(__OpenBSD__) # include -# if __FreeBSD_version >= 1200000 +# if (defined(__FreeBSD__) && __FreeBSD_version >= 1200000) || \ + (defined(__OpenBSD__) && OpenBSD >= 202409) # include # define OSSL_IMPLEMENT_GETAUXVAL @@ -419,11 +420,13 @@ void OPENSSL_cpuid_setup(void) if ((MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V1) || MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_N2) || MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_MICROSOFT, MICROSOFT_CPU_PART_COBALT_100) || - MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V2)) && + MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V2) || + MIDR_IMPLEMENTER(OPENSSL_arm_midr) == ARM_CPU_IMP_AMPERE) && (OPENSSL_armcap_P & ARMV8_SHA3)) OPENSSL_armcap_P |= ARMV8_UNROLL8_EOR3; if ((MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V1) || - MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V2)) && + MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_ARM, ARM_CPU_PART_V2) || + MIDR_IMPLEMENTER(OPENSSL_arm_midr) == ARM_CPU_IMP_AMPERE) && (OPENSSL_armcap_P & ARMV8_SHA3)) OPENSSL_armcap_P |= ARMV8_UNROLL12_EOR3; if ((MIDR_IS_CPU_MODEL(OPENSSL_arm_midr, ARM_CPU_IMP_APPLE, APPLE_CPU_PART_M1_FIRESTORM) || diff --git a/crypto/asn1/a_dup.c b/crypto/asn1/a_dup.c index 23d1d63808..e673023fae 100644 --- a/crypto/asn1/a_dup.c +++ b/crypto/asn1/a_dup.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -75,7 +75,7 @@ void *ASN1_item_dup(const ASN1_ITEM *it, const void *x) } i = ASN1_item_i2d(x, &b, it); - if (b == NULL) { + if (i < 0 || b == NULL) { ERR_raise(ERR_LIB_ASN1, ERR_R_ASN1_LIB); return NULL; } diff --git a/crypto/asn1/a_i2d_fp.c b/crypto/asn1/a_i2d_fp.c index e30f1f2a17..23e0b0f700 100644 --- a/crypto/asn1/a_i2d_fp.c +++ b/crypto/asn1/a_i2d_fp.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -88,7 +88,7 @@ int ASN1_item_i2d_bio(const ASN1_ITEM *it, BIO *out, const void *x) int i, j = 0, n, ret = 1; n = ASN1_item_i2d(x, &b, it); - if (b == NULL) { + if (n < 0 || b == NULL) { ERR_raise(ERR_LIB_ASN1, ERR_R_ASN1_LIB); return 0; } diff --git a/crypto/asn1/a_object.c b/crypto/asn1/a_object.c index 73c69eacd2..6eb9feb16c 100644 --- a/crypto/asn1/a_object.c +++ b/crypto/asn1/a_object.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -198,7 +198,8 @@ int i2a_ASN1_OBJECT(BIO *bp, const ASN1_OBJECT *a) } if (i <= 0) { i = BIO_write(bp, "", 9); - i += BIO_dump(bp, (const char *)a->data, a->length); + if (i > 0) + i += BIO_dump(bp, (const char *)a->data, a->length); return i; } BIO_write(bp, p, i); diff --git a/crypto/asn1/a_strex.c b/crypto/asn1/a_strex.c index f64e3520f8..4b031a73ad 100644 --- a/crypto/asn1/a_strex.c +++ b/crypto/asn1/a_strex.c @@ -235,15 +235,14 @@ static int do_buf(unsigned char *buf, int buflen, static int do_hex_dump(char_io *io_ch, void *arg, unsigned char *buf, int buflen) { - static const char hexdig[] = "0123456789ABCDEF"; unsigned char *p, *q; char hextmp[2]; + if (arg) { p = buf; q = buf + buflen; while (p != q) { - hextmp[0] = hexdig[*p >> 4]; - hextmp[1] = hexdig[*p & 0xf]; + ossl_to_hex(hextmp, *p); if (!io_ch(arg, hextmp, 2)) return -1; p++; diff --git a/crypto/asn1/a_time.c b/crypto/asn1/a_time.c index 96ee63d310..7dfbc5faab 100644 --- a/crypto/asn1/a_time.c +++ b/crypto/asn1/a_time.c @@ -591,78 +591,3 @@ int ASN1_TIME_compare(const ASN1_TIME *a, const ASN1_TIME *b) return -1; return 0; } - -/* - * tweak for Windows - */ -#ifdef WIN32 -# define timezone _timezone -#endif - -#if defined(__FreeBSD__) || defined(__wasi__) -# define USE_TIMEGM -#endif - -time_t ossl_asn1_string_to_time_t(const char *asn1_string) -{ - ASN1_TIME *timestamp_asn1 = NULL; - struct tm *timestamp_tm = NULL; -#if defined(__DJGPP__) - char *tz = NULL; -#elif !defined(USE_TIMEGM) - time_t timestamp_local; -#endif - time_t timestamp_utc; - - timestamp_asn1 = ASN1_TIME_new(); - if (!ASN1_TIME_set_string(timestamp_asn1, asn1_string)) - { - ASN1_TIME_free(timestamp_asn1); - return -1; - } - - timestamp_tm = OPENSSL_malloc(sizeof(*timestamp_tm)); - if (timestamp_tm == NULL) { - ASN1_TIME_free(timestamp_asn1); - return -1; - } - if (!(ASN1_TIME_to_tm(timestamp_asn1, timestamp_tm))) { - OPENSSL_free(timestamp_tm); - ASN1_TIME_free(timestamp_asn1); - return -1; - } - ASN1_TIME_free(timestamp_asn1); - -#if defined(__DJGPP__) - /* - * This is NOT thread-safe. Do not use this method for platforms other - * than djgpp. - */ - tz = getenv("TZ"); - if (tz != NULL) { - tz = OPENSSL_strdup(tz); - if (tz == NULL) { - OPENSSL_free(timestamp_tm); - return -1; - } - } - setenv("TZ", "UTC", 1); - - timestamp_utc = mktime(timestamp_tm); - - if (tz != NULL) { - setenv("TZ", tz, 1); - OPENSSL_free(tz); - } else { - unsetenv("TZ"); - } -#elif defined(USE_TIMEGM) - timestamp_utc = timegm(timestamp_tm); -#else - timestamp_local = mktime(timestamp_tm); - timestamp_utc = timestamp_local - timezone; -#endif - OPENSSL_free(timestamp_tm); - - return timestamp_utc; -} diff --git a/crypto/asn1/asn1_item_list.c b/crypto/asn1/asn1_item_list.c index b5a83ba891..2b57694e33 100644 --- a/crypto/asn1/asn1_item_list.c +++ b/crypto/asn1/asn1_item_list.c @@ -1,5 +1,5 @@ /* - * Copyright 2000-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2000-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -21,6 +21,7 @@ #include #include #include +#include #include "asn1_item_list.h" diff --git a/crypto/asn1/asn1_item_list.h b/crypto/asn1/asn1_item_list.h index 72299a7b6b..3d678ae18f 100644 --- a/crypto/asn1/asn1_item_list.h +++ b/crypto/asn1/asn1_item_list.h @@ -1,5 +1,5 @@ /* - * Copyright 2000-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2000-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -150,6 +150,7 @@ static ASN1_ITEM_EXP *asn1_item_list[] = { ASN1_ITEM_ref(SXNET), ASN1_ITEM_ref(ISSUER_SIGN_TOOL), ASN1_ITEM_ref(USERNOTICE), + ASN1_ITEM_ref(X509_ACERT), ASN1_ITEM_ref(X509_ALGORS), ASN1_ITEM_ref(X509_ALGOR), ASN1_ITEM_ref(X509_ATTRIBUTE), diff --git a/crypto/asn1/asn_mime.c b/crypto/asn1/asn_mime.c index 3a7386f163..44b760534b 100644 --- a/crypto/asn1/asn_mime.c +++ b/crypto/asn1/asn_mime.c @@ -1,5 +1,5 @@ /* - * Copyright 2008-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2008-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -300,6 +300,8 @@ int SMIME_write_ASN1_ex(BIO *bio, ASN1_VALUE *val, BIO *data, int flags, if (ctype_nid == NID_pkcs7_enveloped) { msg_type = "enveloped-data"; + } else if (ctype_nid == NID_id_smime_ct_authEnvelopedData) { + msg_type = "authEnveloped-data"; } else if (ctype_nid == NID_pkcs7_signed) { if (econt_nid == NID_id_smime_ct_receipt) msg_type = "signed-receipt"; diff --git a/crypto/asn1/f_int.c b/crypto/asn1/f_int.c index 20192b577b..5b5dda4ce1 100644 --- a/crypto/asn1/f_int.c +++ b/crypto/asn1/f_int.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,7 +16,6 @@ int i2a_ASN1_INTEGER(BIO *bp, const ASN1_INTEGER *a) { int i, n = 0; - static const char *h = "0123456789ABCDEF"; char buf[2]; if (a == NULL) @@ -39,8 +38,7 @@ int i2a_ASN1_INTEGER(BIO *bp, const ASN1_INTEGER *a) goto err; n += 2; } - buf[0] = h[((unsigned char)a->data[i] >> 4) & 0x0f]; - buf[1] = h[((unsigned char)a->data[i]) & 0x0f]; + ossl_to_hex(buf, a->data[i]); if (BIO_write(bp, buf, 2) != 2) goto err; n += 2; @@ -76,8 +74,7 @@ int a2i_ASN1_INTEGER(BIO *bp, ASN1_INTEGER *bs, char *buf, int size) again = (buf[i - 1] == '\\'); for (j = 0; j < i; j++) { - if (!ossl_isxdigit(buf[j])) - { + if (!ossl_isxdigit(buf[j])) { i = j; break; } diff --git a/crypto/asn1/f_string.c b/crypto/asn1/f_string.c index 1da442a457..7e4e598514 100644 --- a/crypto/asn1/f_string.c +++ b/crypto/asn1/f_string.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,7 +16,6 @@ int i2a_ASN1_STRING(BIO *bp, const ASN1_STRING *a, int type) { int i, n = 0; - static const char *h = "0123456789ABCDEF"; char buf[2]; if (a == NULL) @@ -33,8 +32,7 @@ int i2a_ASN1_STRING(BIO *bp, const ASN1_STRING *a, int type) goto err; n += 2; } - buf[0] = h[((unsigned char)a->data[i] >> 4) & 0x0f]; - buf[1] = h[((unsigned char)a->data[i]) & 0x0f]; + ossl_to_hex(buf, a->data[i]); if (BIO_write(bp, buf, 2) != 2) goto err; n += 2; diff --git a/crypto/asn1/p5_pbev2.c b/crypto/asn1/p5_pbev2.c index 8575d05bf6..b9ad4db4a7 100644 --- a/crypto/asn1/p5_pbev2.c +++ b/crypto/asn1/p5_pbev2.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -35,6 +35,13 @@ ASN1_SEQUENCE(PBKDF2PARAM) = { IMPLEMENT_ASN1_FUNCTIONS(PBKDF2PARAM) +ASN1_SEQUENCE(PBMAC1PARAM) = { + ASN1_SIMPLE(PBMAC1PARAM, keyDerivationFunc, X509_ALGOR), + ASN1_SIMPLE(PBMAC1PARAM, messageAuthScheme, X509_ALGOR) +} ASN1_SEQUENCE_END(PBMAC1PARAM) + +IMPLEMENT_ASN1_FUNCTIONS(PBMAC1PARAM) + /* * Return an algorithm identifier for a PKCS#5 v2.0 PBE algorithm: yes I know * this is horrible! Extended version to allow application supplied PRF NID diff --git a/crypto/asn1/standard_methods.h b/crypto/asn1/standard_methods.h index 6b73d9a771..ebb53e57db 100644 --- a/crypto/asn1/standard_methods.h +++ b/crypto/asn1/standard_methods.h @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -23,7 +23,6 @@ static const EVP_PKEY_ASN1_METHOD *standard_methods[] = { &ossl_dsa_asn1_meths[1], &ossl_dsa_asn1_meths[2], &ossl_dsa_asn1_meths[3], - &ossl_dsa_asn1_meths[4], #endif #ifndef OPENSSL_NO_EC &ossl_eckey_asn1_meth, diff --git a/crypto/async/arch/async_posix.h b/crypto/async/arch/async_posix.h index 603965310d..ceb86e24bf 100644 --- a/crypto/async/arch/async_posix.h +++ b/crypto/async/arch/async_posix.h @@ -1,5 +1,5 @@ /* - * Copyright 2015-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -18,7 +18,7 @@ # include # if _POSIX_VERSION >= 200112L \ - && (_POSIX_VERSION < 200809L || defined(__GLIBC__)) + && (_POSIX_VERSION < 200809L || defined(__GLIBC__) || defined(__FreeBSD__)) # include diff --git a/crypto/bio/bio_addr.c b/crypto/bio/bio_addr.c index 5e0de08970..4b2cef6936 100644 --- a/crypto/bio/bio_addr.c +++ b/crypto/bio/bio_addr.c @@ -774,16 +774,19 @@ int BIO_lookup_ex(const char *host, const char *service, int lookup_type, /* Windows doesn't seem to have in_addr_t */ #if defined(OPENSSL_SYS_WINDOWS) || defined(OPENSSL_SYS_MSDOS) static uint32_t he_fallback_address; - static const char *he_fallback_addresses[] = - { (char *)&he_fallback_address, NULL }; + static const char *he_fallback_addresses[] = { + (char *)&he_fallback_address, NULL + }; #else static in_addr_t he_fallback_address; - static const char *he_fallback_addresses[] = - { (char *)&he_fallback_address, NULL }; + static const char *he_fallback_addresses[] = { + (char *)&he_fallback_address, NULL + }; #endif - static const struct hostent he_fallback = - { NULL, NULL, AF_INET, sizeof(he_fallback_address), - (char **)&he_fallback_addresses }; + static const struct hostent he_fallback = { + NULL, NULL, AF_INET, sizeof(he_fallback_address), + (char **)&he_fallback_addresses + }; #if defined(OPENSSL_SYS_VMS) && defined(__DECC) # pragma pointer_size restore #endif diff --git a/crypto/bio/bss_dgram.c b/crypto/bio/bss_dgram.c index f6d688b353..1ab8c5fd70 100644 --- a/crypto/bio/bss_dgram.c +++ b/crypto/bio/bss_dgram.c @@ -1192,7 +1192,7 @@ static int pack_local(BIO *b, MSGHDR_TYPE *mh, const BIO_ADDR *local) { cmsg->cmsg_type = IP_PKTINFO; info = (struct in_pktinfo *)BIO_CMSG_DATA(cmsg); -# if !defined(OPENSSL_SYS_WINDOWS) && !defined(OPENSSL_SYS_CYGWIN) && !defined(__FreeBSD__) +# if !defined(OPENSSL_SYS_WINDOWS) && !defined(OPENSSL_SYS_CYGWIN) && !defined(__FreeBSD__) && !defined(__QNX__) info->ipi_spec_dst = local->s_in.sin_addr; # endif info->ipi_addr.s_addr = 0; diff --git a/crypto/bio/bss_log.c b/crypto/bio/bss_log.c index c22e603b04..807a42c6dd 100644 --- a/crypto/bio/bss_log.c +++ b/crypto/bio/bss_log.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -281,7 +281,7 @@ static void xsyslog(BIO *bp, int priority, const char *string) break; } - sprintf(pidbuf, "[%lu] ", GetCurrentProcessId()); + BIO_snprintf(pidbuf, sizeof(pidbuf), "[%lu] ", GetCurrentProcessId()); lpszStrings[0] = pidbuf; lpszStrings[1] = string; diff --git a/crypto/bn/asm/mips.pl b/crypto/bn/asm/mips.pl index 91b7aac6e7..44a6f10d4d 100644 --- a/crypto/bn/asm/mips.pl +++ b/crypto/bn/asm/mips.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2010-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2010-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -802,7 +802,7 @@ #if 0 /* - * The bn_div_3_words entry point is re-used for constant-time interface. + * The bn_div_3_words entry point is reused for constant-time interface. * Implementation is retained as historical reference. */ .align 5 diff --git a/crypto/bn/asm/rsaz-2k-avx512.S b/crypto/bn/asm/rsaz-2k-avx512.S index 33df34c360..5b3611aadb 100644 --- a/crypto/bn/asm/rsaz-2k-avx512.S +++ b/crypto/bn/asm/rsaz-2k-avx512.S @@ -411,7 +411,7 @@ ossl_rsaz_amm52x20_x1_ifma256: .byte 0xf3,0xc3 .cfi_endproc .size ossl_rsaz_amm52x20_x1_ifma256, .-ossl_rsaz_amm52x20_x1_ifma256 -.data +.section .rodata .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -887,7 +887,7 @@ ossl_extract_multiplier_2x20_win5: .byte 0xf3,0xc3 .cfi_endproc .size ossl_extract_multiplier_2x20_win5, .-ossl_extract_multiplier_2x20_win5 -.data +.section .rodata .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-2k-avx512.pl b/crypto/bn/asm/rsaz-2k-avx512.pl index 7ee02778df..131e315324 100644 --- a/crypto/bn/asm/rsaz-2k-avx512.pl +++ b/crypto/bn/asm/rsaz-2k-avx512.pl @@ -1,4 +1,4 @@ -# Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2020, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -393,7 +393,7 @@ sub amm52x20_x1_norm { ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -589,7 +589,7 @@ sub amm52x20_x1_norm { .size ossl_extract_multiplier_2x20_win5, .-ossl_extract_multiplier_2x20_win5 ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-3k-avx512.S b/crypto/bn/asm/rsaz-3k-avx512.S index 00a709ceff..022574148e 100644 --- a/crypto/bn/asm/rsaz-3k-avx512.S +++ b/crypto/bn/asm/rsaz-3k-avx512.S @@ -657,7 +657,7 @@ ossl_rsaz_amm52x30_x1_ifma256: .byte 0xf3,0xc3 .cfi_endproc .size ossl_rsaz_amm52x30_x1_ifma256, .-ossl_rsaz_amm52x30_x1_ifma256 -.data +.section .rodata .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -1302,7 +1302,7 @@ ossl_extract_multiplier_2x30_win5: .byte 0xf3,0xc3 .cfi_endproc .size ossl_extract_multiplier_2x30_win5, .-ossl_extract_multiplier_2x30_win5 -.data +.section .rodata .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-3k-avx512.pl b/crypto/bn/asm/rsaz-3k-avx512.pl index 8ed5496479..235268a68a 100644 --- a/crypto/bn/asm/rsaz-3k-avx512.pl +++ b/crypto/bn/asm/rsaz-3k-avx512.pl @@ -1,4 +1,4 @@ -# Copyright 2021-2023 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2021, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -485,7 +485,7 @@ sub amm52x30_x1_norm { ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -730,7 +730,7 @@ sub amm52x30_x1_norm { .size ossl_extract_multiplier_2x30_win5, .-ossl_extract_multiplier_2x30_win5 ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-4k-avx512.S b/crypto/bn/asm/rsaz-4k-avx512.S index 82b9769076..1dcb0db7c5 100644 --- a/crypto/bn/asm/rsaz-4k-avx512.S +++ b/crypto/bn/asm/rsaz-4k-avx512.S @@ -592,7 +592,7 @@ ossl_rsaz_amm52x40_x1_ifma256: .byte 0xf3,0xc3 .cfi_endproc .size ossl_rsaz_amm52x40_x1_ifma256, .-ossl_rsaz_amm52x40_x1_ifma256 -.data +.section .rodata .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -1345,7 +1345,7 @@ ossl_extract_multiplier_2x40_win5: .byte 0xf3,0xc3 .cfi_endproc .size ossl_extract_multiplier_2x40_win5, .-ossl_extract_multiplier_2x40_win5 -.data +.section .rodata .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-4k-avx512.pl b/crypto/bn/asm/rsaz-4k-avx512.pl index 8c59b77f77..e39374362b 100644 --- a/crypto/bn/asm/rsaz-4k-avx512.pl +++ b/crypto/bn/asm/rsaz-4k-avx512.pl @@ -1,4 +1,4 @@ -# Copyright 2021-2023 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2021, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -526,7 +526,7 @@ sub amm52x40_x1_norm { ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lmask52x4: .quad 0xfffffffffffff @@ -786,7 +786,7 @@ () .size ossl_extract_multiplier_2x40_win5, .-ossl_extract_multiplier_2x40_win5 ___ $code.=<<___; -.data +.section .rodata align=32 .align 32 .Lones: .quad 1,1,1,1 diff --git a/crypto/bn/asm/rsaz-avx2.S b/crypto/bn/asm/rsaz-avx2.S index 80d6c81766..f58e783167 100644 --- a/crypto/bn/asm/rsaz-avx2.S +++ b/crypto/bn/asm/rsaz-avx2.S @@ -1730,6 +1730,7 @@ rsaz_avx2_eligible: .byte 0xf3,0xc3 .size rsaz_avx2_eligible,.-rsaz_avx2_eligible +.section .rodata .align 64 .Land_mask: .quad 0x1fffffff,0x1fffffff,0x1fffffff,0x1fffffff @@ -1741,6 +1742,7 @@ rsaz_avx2_eligible: .long 0,0,0,0, 1,1,1,1 .long 2,2,2,2, 3,3,3,3 .long 4,4,4,4, 4,4,4,4 +.previous .align 64 .section ".note.gnu.property", "a" .p2align 3 diff --git a/crypto/bn/asm/rsaz-avx2.pl b/crypto/bn/asm/rsaz-avx2.pl index 3d0e342a6b..59b9c89b5b 100755 --- a/crypto/bn/asm/rsaz-avx2.pl +++ b/crypto/bn/asm/rsaz-avx2.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2012, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -1779,6 +1779,7 @@ ret .size rsaz_avx2_eligible,.-rsaz_avx2_eligible +.section .rodata align=64 .align 64 .Land_mask: .quad 0x1fffffff,0x1fffffff,0x1fffffff,0x1fffffff @@ -1790,6 +1791,7 @@ .long 0,0,0,0, 1,1,1,1 .long 2,2,2,2, 3,3,3,3 .long 4,4,4,4, 4,4,4,4 +.previous .align 64 ___ diff --git a/crypto/bn/asm/rsaz-x86_64.S b/crypto/bn/asm/rsaz-x86_64.S index 0b2513c819..ca03617e92 100644 --- a/crypto/bn/asm/rsaz-x86_64.S +++ b/crypto/bn/asm/rsaz-x86_64.S @@ -2009,10 +2009,12 @@ rsaz_512_gather4: .cfi_endproc .size rsaz_512_gather4,.-rsaz_512_gather4 +.section .rodata .align 64 .Linc: .long 0,0, 1,1 .long 2,2, 2,2 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/bn/asm/rsaz-x86_64.pl b/crypto/bn/asm/rsaz-x86_64.pl index 5c7d526fa3..36bf229477 100755 --- a/crypto/bn/asm/rsaz-x86_64.pl +++ b/crypto/bn/asm/rsaz-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2012, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -2248,10 +2248,12 @@ .cfi_endproc .size rsaz_512_gather4,.-rsaz_512_gather4 +.section .rodata align=64 .align 64 .Linc: .long 0,0, 1,1 .long 2,2, 2,2 +.previous ___ } diff --git a/crypto/bn/asm/x86_64-mont5.S b/crypto/bn/asm/x86_64-mont5.S index 0eb8b6c8b5..1b7e7b9229 100644 --- a/crypto/bn/asm/x86_64-mont5.S +++ b/crypto/bn/asm/x86_64-mont5.S @@ -3596,11 +3596,13 @@ bn_gather5: .LSEH_end_bn_gather5: .cfi_endproc .size bn_gather5,.-bn_gather5 +.section .rodata .align 64 .Linc: .long 0,0, 1,1 .long 2,2, 2,2 .byte 77,111,110,116,103,111,109,101,114,121,32,77,117,108,116,105,112,108,105,99,97,116,105,111,110,32,119,105,116,104,32,115,99,97,116,116,101,114,47,103,97,116,104,101,114,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/bn/asm/x86_64-mont5.pl b/crypto/bn/asm/x86_64-mont5.pl index 1faea0bcf8..07dd40d922 100755 --- a/crypto/bn/asm/x86_64-mont5.pl +++ b/crypto/bn/asm/x86_64-mont5.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2011-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -3577,11 +3577,13 @@ ___ } $code.=<<___; +.section .rodata align=64 .align 64 .Linc: .long 0,0, 1,1 .long 2,2, 2,2 .asciz "Montgomery Multiplication with scatter/gather for x86_64, CRYPTOGAMS by " +.previous ___ # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame, diff --git a/crypto/bn/bn_conv.c b/crypto/bn/bn_conv.c index 849440e71e..57dda04b0d 100644 --- a/crypto/bn/bn_conv.c +++ b/crypto/bn/bn_conv.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -11,8 +11,6 @@ #include "crypto/ctype.h" #include "bn_local.h" -static const char Hex[] = "0123456789ABCDEF"; - /* Must 'OPENSSL_free' the returned data */ char *BN_bn2hex(const BIGNUM *a) { @@ -33,8 +31,7 @@ char *BN_bn2hex(const BIGNUM *a) /* strip leading zeros */ v = (int)((a->d[i] >> j) & 0xff); if (z || v != 0) { - *p++ = Hex[v >> 4]; - *p++ = Hex[v & 0x0f]; + p += ossl_to_hex(p, v); z = 1; } } diff --git a/crypto/bn/bn_gcd.c b/crypto/bn/bn_gcd.c index 2cd8ee35e0..13de70eb0d 100644 --- a/crypto/bn/bn_gcd.c +++ b/crypto/bn/bn_gcd.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -9,6 +9,7 @@ #include "internal/cryptlib.h" #include "bn_local.h" +#include "internal/constant_time.h" /* * bn_mod_inverse_no_branch is a special version of BN_mod_inverse. It does @@ -580,8 +581,8 @@ int BN_are_coprime(BIGNUM *a, const BIGNUM *b, BN_CTX *ctx) int BN_gcd(BIGNUM *r, const BIGNUM *in_a, const BIGNUM *in_b, BN_CTX *ctx) { BIGNUM *g, *temp = NULL; - BN_ULONG mask = 0; - int i, j, top, rlen, glen, m, bit = 1, delta = 1, cond = 0, shifts = 0, ret = 0; + BN_ULONG pow2_numbits, pow2_numbits_temp, pow2_condition_mask, pow2_flag; + int i, j, top, rlen, glen, m, delta = 1, cond = 0, pow2_shifts, ret = 0; /* Note 2: zero input corner cases are not constant-time since they are * handled immediately. An attacker can run an attack under this @@ -611,18 +612,29 @@ int BN_gcd(BIGNUM *r, const BIGNUM *in_a, const BIGNUM *in_b, BN_CTX *ctx) goto err; /* find shared powers of two, i.e. "shifts" >= 1 */ + pow2_flag = 1; + pow2_shifts = 0; + pow2_numbits = 0; for (i = 0; i < r->dmax && i < g->dmax; i++) { - mask = ~(r->d[i] | g->d[i]); - for (j = 0; j < BN_BITS2; j++) { - bit &= mask; - shifts += bit; - mask >>= 1; - } + pow2_numbits_temp = r->d[i] | g->d[i]; + pow2_condition_mask = constant_time_is_zero_bn(pow2_flag); + pow2_flag &= constant_time_is_zero_bn(pow2_numbits_temp); + pow2_shifts += pow2_flag; + pow2_numbits = constant_time_select_bn(pow2_condition_mask, + pow2_numbits, pow2_numbits_temp); + } + pow2_numbits = ~pow2_numbits; + pow2_shifts *= BN_BITS2; + pow2_flag = 1; + for (j = 0; j < BN_BITS2; j++) { + pow2_flag &= pow2_numbits; + pow2_shifts += pow2_flag; + pow2_numbits >>= 1; } /* subtract shared powers of two; shifts >= 1 */ - if (!BN_rshift(r, r, shifts) - || !BN_rshift(g, g, shifts)) + if (!BN_rshift(r, r, pow2_shifts) + || !BN_rshift(g, g, pow2_shifts)) goto err; /* expand to biggest nword, with room for a possible extra word */ @@ -665,7 +677,7 @@ int BN_gcd(BIGNUM *r, const BIGNUM *in_a, const BIGNUM *in_b, BN_CTX *ctx) /* remove possible negative sign */ r->neg = 0; /* add powers of 2 removed, then correct the artificial shift */ - if (!BN_lshift(r, r, shifts) + if (!BN_lshift(r, r, pow2_shifts) || !BN_rshift1(r, r)) goto err; diff --git a/crypto/bn/bn_gf2m.c b/crypto/bn/bn_gf2m.c index 444c5ca7a3..84860fd6a1 100644 --- a/crypto/bn/bn_gf2m.c +++ b/crypto/bn/bn_gf2m.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -15,6 +15,7 @@ #include "bn_local.h" #ifndef OPENSSL_NO_EC2M +# include /* * Maximum number of iterations before BN_GF2m_mod_solve_quad_arr should @@ -1130,16 +1131,26 @@ int BN_GF2m_mod_solve_quad(BIGNUM *r, const BIGNUM *a, const BIGNUM *p, /* * Convert the bit-string representation of a polynomial ( \sum_{i=0}^n a_i * * x^i) into an array of integers corresponding to the bits with non-zero - * coefficient. Array is terminated with -1. Up to max elements of the array - * will be filled. Return value is total number of array elements that would - * be filled if array was large enough. + * coefficient. The array is intended to be suitable for use with + * `BN_GF2m_mod_arr()`, and so the constant term of the polynomial must not be + * zero. This translates to a requirement that the input BIGNUM `a` is odd. + * + * Given sufficient room, the array is terminated with -1. Up to max elements + * of the array will be filled. + * + * The return value is total number of array elements that would be filled if + * array was large enough, including the terminating `-1`. It is `0` when `a` + * is not odd or the constant term is zero contrary to requirement. + * + * The return value is also `0` when the leading exponent exceeds + * `OPENSSL_ECC_MAX_FIELD_BITS`, this guards against CPU exhaustion attacks, */ int BN_GF2m_poly2arr(const BIGNUM *a, int p[], int max) { int i, j, k = 0; BN_ULONG mask; - if (BN_is_zero(a)) + if (!BN_is_odd(a)) return 0; for (i = a->top - 1; i >= 0; i--) { @@ -1157,12 +1168,13 @@ int BN_GF2m_poly2arr(const BIGNUM *a, int p[], int max) } } - if (k < max) { + if (k > 0 && p[0] > OPENSSL_ECC_MAX_FIELD_BITS) + return 0; + + if (k < max) p[k] = -1; - k++; - } - return k; + return k + 1; } /* diff --git a/crypto/bn/bn_lib.c b/crypto/bn/bn_lib.c index 18c9d54f67..bd1d02ba0a 100644 --- a/crypto/bn/bn_lib.c +++ b/crypto/bn/bn_lib.c @@ -82,8 +82,9 @@ int BN_get_params(int which) const BIGNUM *BN_value_one(void) { static const BN_ULONG data_one = 1L; - static const BIGNUM const_one = - { (BN_ULONG *)&data_one, 1, 1, 0, BN_FLG_STATIC_DATA }; + static const BIGNUM const_one = { + (BN_ULONG *)&data_one, 1, 1, 0, BN_FLG_STATIC_DATA + }; return &const_one; } diff --git a/crypto/bn/bn_mod.c b/crypto/bn/bn_mod.c index d7c2f4bd5b..5f08bfa4a5 100644 --- a/crypto/bn/bn_mod.c +++ b/crypto/bn/bn_mod.c @@ -1,5 +1,5 @@ /* - * Copyright 1998-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1998-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -8,6 +8,7 @@ */ #include "internal/cryptlib.h" +#include "internal/nelem.h" #include "bn_local.h" int BN_nnmod(BIGNUM *r, const BIGNUM *m, const BIGNUM *d, BN_CTX *ctx) @@ -61,7 +62,7 @@ int bn_mod_add_fixed_top(BIGNUM *r, const BIGNUM *a, const BIGNUM *b, if (bn_wexpand(r, mtop) == NULL) return 0; - if (mtop > sizeof(storage) / sizeof(storage[0])) { + if (mtop > OSSL_NELEM(storage)) { tp = OPENSSL_malloc(mtop * sizeof(BN_ULONG)); if (tp == NULL) return 0; diff --git a/crypto/bn/bn_mont.c b/crypto/bn/bn_mont.c index 8b4c7900ad..4f08394d7f 100644 --- a/crypto/bn/bn_mont.c +++ b/crypto/bn/bn_mont.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -465,3 +465,45 @@ BN_MONT_CTX *BN_MONT_CTX_set_locked(BN_MONT_CTX **pmont, CRYPTO_RWLOCK *lock, CRYPTO_THREAD_unlock(lock); return ret; } + +int ossl_bn_mont_ctx_set(BN_MONT_CTX *ctx, const BIGNUM *modulus, int ri, const unsigned char *rr, + size_t rrlen, uint32_t nlo, uint32_t nhi) +{ + if (BN_copy(&ctx->N, modulus) == NULL) + return 0; + if (BN_bin2bn(rr, rrlen, &ctx->RR) == NULL) + return 0; + ctx->ri = ri; +#if (BN_BITS2 <= 32) && defined(OPENSSL_BN_ASM_MONT) + ctx->n0[0] = nlo; + ctx->n0[1] = nhi; +#elif BN_BITS2 <= 32 + ctx->n0[0] = nlo; + ctx->n0[1] = 0; +#else + ctx->n0[0] = ((BN_ULONG)nhi << 32)| nlo; + ctx->n0[1] = 0; +#endif + + return 1; +} + +int ossl_bn_mont_ctx_eq(const BN_MONT_CTX *m1, const BN_MONT_CTX *m2) +{ + if (m1->ri != m2->ri) + return 0; + if (BN_cmp(&m1->RR, &m2->RR) != 0) + return 0; + if (m1->flags != m2->flags) + return 0; +#ifdef MONT_WORD + if (m1->n0[0] != m2->n0[0]) + return 0; + if (m1->n0[1] != m2->n0[1]) + return 0; +#else + if (BN_cmp(&m1->Ni, &m2->Ni) != 0) + return 0; +#endif + return 1; +} diff --git a/crypto/bn/bn_nist.c b/crypto/bn/bn_nist.c index bc864346fb..527ecb34d8 100644 --- a/crypto/bn/bn_nist.c +++ b/crypto/bn/bn_nist.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -84,8 +84,8 @@ static const BN_ULONG _nist_p_384_sqr[] = { 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL }; -static const BN_ULONG _nist_p_521[] = - { 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, +static const BN_ULONG _nist_p_521[] = { + 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, 0xFFFFFFFFFFFFFFFFULL, diff --git a/crypto/bn/rsaz_exp_x2.c b/crypto/bn/rsaz_exp_x2.c index 70705486a1..9361400757 100644 --- a/crypto/bn/rsaz_exp_x2.c +++ b/crypto/bn/rsaz_exp_x2.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2020-2021, Intel Corporation. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -576,11 +576,7 @@ static void to_words52(BN_ULONG *out, int out_len, out_len--; } - while (out_len > 0) { - *out = 0; - out_len--; - out++; - } + memset(out, 0, out_len * sizeof(BN_ULONG)); } static ossl_inline void put_digit(uint8_t *out, int out_len, uint64_t digit) diff --git a/crypto/build.info b/crypto/build.info index 2d5b22fcff..2642d30754 100644 --- a/crypto/build.info +++ b/crypto/build.info @@ -1,6 +1,6 @@ # Note that these directories are filtered in Configure. Look for %skipdir # there for further explanations. -SUBDIRS=objects buffer bio stack lhash rand evp asn1 pem x509 conf \ +SUBDIRS=objects buffer bio stack lhash hashtable rand evp asn1 pem x509 conf \ txt_db pkcs7 pkcs12 ui kdf store property \ md2 md4 md5 sha mdc2 hmac ripemd whrlpool poly1305 \ siphash sm3 des aes rc2 rc4 rc5 idea aria bf cast camellia \ @@ -91,7 +91,7 @@ DEFINE[../providers/libdefault.a]=$CPUIDDEF $CORE_COMMON=provider_core.c provider_predefined.c \ core_fetch.c core_algorithm.c core_namemap.c self_test_core.c -SOURCE[../libcrypto]=$CORE_COMMON provider_conf.c +SOURCE[../libcrypto]=$CORE_COMMON provider_conf.c indicator_core.c SOURCE[../providers/libfips.a]=$CORE_COMMON # Central utilities @@ -104,10 +104,10 @@ $UTIL_COMMON=\ SOURCE[../libcrypto]=$UTIL_COMMON \ mem.c mem_sec.c \ - cversion.c info.c cpt_err.c ebcdic.c uid.c o_time.c o_dir.c \ - o_fopen.c getenv.c o_init.c init.c trace.c provider.c provider_child.c \ - punycode.c passphrase.c sleep.c deterministic_nonce.c quic_vlint.c \ - time.c + comp_methods.c cversion.c info.c cpt_err.c ebcdic.c uid.c o_time.c \ + o_dir.c o_fopen.c getenv.c o_init.c init.c trace.c provider.c \ + provider_child.c punycode.c passphrase.c sleep.c deterministic_nonce.c \ + quic_vlint.c time.c defaults.c SOURCE[../providers/libfips.a]=$UTIL_COMMON SOURCE[../libcrypto]=$UPLINKSRC diff --git a/crypto/buildinf.h b/crypto/buildinf.h index 1d746805a6..5b136200f1 100644 --- a/crypto/buildinf.h +++ b/crypto/buildinf.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by util/mkbuildinf.pl * - * Copyright 2014-2017 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2014-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -11,7 +11,7 @@ */ #define PLATFORM "platform: linux-armv4" -#define DATE "built on: Thu Sep 5 16:01:59 2024 UTC" +#define DATE "built on: Wed Dec 4 13:03:23 2024 UTC" /* * Generate compiler_flags as an array of individual characters. This is a diff --git a/crypto/chacha/asm/chacha-riscv64-zbb-zvkb.pl b/crypto/chacha/asm/chacha-riscv64-v-zbb.pl old mode 100644 new mode 100755 similarity index 71% rename from crypto/chacha/asm/chacha-riscv64-zbb-zvkb.pl rename to crypto/chacha/asm/chacha-riscv64-v-zbb.pl index 59db167faf..4aee563ad9 --- a/crypto/chacha/asm/chacha-riscv64-zbb-zvkb.pl +++ b/crypto/chacha/asm/chacha-riscv64-v-zbb.pl @@ -37,9 +37,10 @@ # - RV64I # - RISC-V Vector ('V') with VLEN >= 128 -# - RISC-V Vector Cryptography Bit-manipulation extension ('Zvkb') # - RISC-V Basic Bit-manipulation extension ('Zbb') # - RISC-V Zicclsm(Main memory supports misaligned loads/stores) +# Optional: +# - RISC-V Vector Cryptography Bit-manipulation extension ('Zvkb') use strict; use warnings; @@ -54,15 +55,18 @@ my $output = $#ARGV >= 0 && $ARGV[$#ARGV] =~ m|\.\w+$| ? pop : undef; my $flavour = $#ARGV >= 0 && $ARGV[0] !~ m|\.| ? shift : undef; +my $use_zvkb = $flavour && $flavour =~ /zvkb/i ? 1 : 0; +my $isaext = "_v_zbb" . ( $use_zvkb ? "_zvkb" : "" ); + $output and open STDOUT, ">$output"; my $code = <<___; .text ___ -# void ChaCha20_ctr32_zbb_zvkb(unsigned char *out, const unsigned char *inp, -# size_t len, const unsigned int key[8], -# const unsigned int counter[4]); +# void ChaCha20_ctr32@{[$isaext]}(unsigned char *out, const unsigned char *inp, +# size_t len, const unsigned int key[8], +# const unsigned int counter[4]); ################################################################################ my ( $OUTPUT, $INPUT, $LEN, $KEY, $COUNTER ) = ( "a0", "a1", "a2", "a3", "a4" ); my ( $CONST_DATA0, $CONST_DATA1, $CONST_DATA2, $CONST_DATA3 ) = ( "a5", "a6", @@ -90,6 +94,83 @@ $V22, $V23, $V24, $V25, $V26, $V27, $V28, $V29, $V30, $V31, ) = map( "v$_", ( 0 .. 31 ) ); +sub chacha_sub_round { + my ( + $A0, $B0, $C0, + $A1, $B1, $C1, + $A2, $B2, $C2, + $A3, $B3, $C3, + + $S_A0, $S_B0, $S_C0, + $S_A1, $S_B1, $S_C1, + $S_A2, $S_B2, $S_C2, + $S_A3, $S_B3, $S_C3, + + $ROL_SHIFT, + + $V_T0, $V_T1, $V_T2, $V_T3, + ) = @_; + + # a += b; c ^= a; + my $code = <<___; + @{[vadd_vv $A0, $A0, $B0]} + add $S_A0, $S_A0, $S_B0 + @{[vadd_vv $A1, $A1, $B1]} + add $S_A1, $S_A1, $S_B1 + @{[vadd_vv $A2, $A2, $B2]} + add $S_A2, $S_A2, $S_B2 + @{[vadd_vv $A3, $A3, $B3]} + add $S_A3, $S_A3, $S_B3 + @{[vxor_vv $C0, $C0, $A0]} + xor $S_C0, $S_C0, $S_A0 + @{[vxor_vv $C1, $C1, $A1]} + xor $S_C1, $S_C1, $S_A1 + @{[vxor_vv $C2, $C2, $A2]} + xor $S_C2, $S_C2, $S_A2 + @{[vxor_vv $C3, $C3, $A3]} + xor $S_C3, $S_C3, $S_A3 +___ + + # c <<<= $ROL_SHIFT; + if ($use_zvkb) { + my $ror_part = <<___; + @{[vror_vi $C0, $C0, 32 - $ROL_SHIFT]} + @{[roriw $S_C0, $S_C0, 32 - $ROL_SHIFT]} + @{[vror_vi $C1, $C1, 32 - $ROL_SHIFT]} + @{[roriw $S_C1, $S_C1, 32 - $ROL_SHIFT]} + @{[vror_vi $C2, $C2, 32 - $ROL_SHIFT]} + @{[roriw $S_C2, $S_C2, 32 - $ROL_SHIFT]} + @{[vror_vi $C3, $C3, 32 - $ROL_SHIFT]} + @{[roriw $S_C3, $S_C3, 32 - $ROL_SHIFT]} +___ + + $code .= $ror_part; + } else { + my $ror_part = <<___; + @{[vsll_vi $V_T0, $C0, $ROL_SHIFT]} + @{[vsll_vi $V_T1, $C1, $ROL_SHIFT]} + @{[vsll_vi $V_T2, $C2, $ROL_SHIFT]} + @{[vsll_vi $V_T3, $C3, $ROL_SHIFT]} + @{[vsrl_vi $C0, $C0, 32 - $ROL_SHIFT]} + @{[vsrl_vi $C1, $C1, 32 - $ROL_SHIFT]} + @{[vsrl_vi $C2, $C2, 32 - $ROL_SHIFT]} + @{[vsrl_vi $C3, $C3, 32 - $ROL_SHIFT]} + @{[vor_vv $C0, $C0, $V_T0]} + @{[roriw $S_C0, $S_C0, 32 - $ROL_SHIFT]} + @{[vor_vv $C1, $C1, $V_T1]} + @{[roriw $S_C1, $S_C1, 32 - $ROL_SHIFT]} + @{[vor_vv $C2, $C2, $V_T2]} + @{[roriw $S_C2, $S_C2, 32 - $ROL_SHIFT]} + @{[vor_vv $C3, $C3, $V_T3]} + @{[roriw $S_C3, $S_C3, 32 - $ROL_SHIFT]} +___ + + $code .= $ror_part; + } + + return $code; +} + sub chacha_quad_round_group { my ( $A0, $B0, $C0, $D0, @@ -101,109 +182,59 @@ sub chacha_quad_round_group { $S_A1, $S_B1, $S_C1, $S_D1, $S_A2, $S_B2, $S_C2, $S_D2, $S_A3, $S_B3, $S_C3, $S_D3, + + $V_T0, $V_T1, $V_T2, $V_T3, ) = @_; my $code = <<___; # a += b; d ^= a; d <<<= 16; - @{[vadd_vv $A0, $A0, $B0]} - add $S_A0, $S_A0, $S_B0 - @{[vadd_vv $A1, $A1, $B1]} - add $S_A1, $S_A1, $S_B1 - @{[vadd_vv $A2, $A2, $B2]} - add $S_A2, $S_A2, $S_B2 - @{[vadd_vv $A3, $A3, $B3]} - add $S_A3, $S_A3, $S_B3 - @{[vxor_vv $D0, $D0, $A0]} - xor $S_D0, $S_D0, $S_A0 - @{[vxor_vv $D1, $D1, $A1]} - xor $S_D1, $S_D1, $S_A1 - @{[vxor_vv $D2, $D2, $A2]} - xor $S_D2, $S_D2, $S_A2 - @{[vxor_vv $D3, $D3, $A3]} - xor $S_D3, $S_D3, $S_A3 - @{[vror_vi $D0, $D0, 32 - 16]} - @{[roriw $S_D0, $S_D0, 32 - 16]} - @{[vror_vi $D1, $D1, 32 - 16]} - @{[roriw $S_D1, $S_D1, 32 - 16]} - @{[vror_vi $D2, $D2, 32 - 16]} - @{[roriw $S_D2, $S_D2, 32 - 16]} - @{[vror_vi $D3, $D3, 32 - 16]} - @{[roriw $S_D3, $S_D3, 32 - 16]} + @{[chacha_sub_round + $A0, $B0, $D0, + $A1, $B1, $D1, + $A2, $B2, $D2, + $A3, $B3, $D3, + $S_A0, $S_B0, $S_D0, + $S_A1, $S_B1, $S_D1, + $S_A2, $S_B2, $S_D2, + $S_A3, $S_B3, $S_D3, + 16, + $V_T0, $V_T1, $V_T2, $V_T3]} # c += d; b ^= c; b <<<= 12; - @{[vadd_vv $C0, $C0, $D0]} - add $S_C0, $S_C0, $S_D0 - @{[vadd_vv $C1, $C1, $D1]} - add $S_C1, $S_C1, $S_D1 - @{[vadd_vv $C2, $C2, $D2]} - add $S_C2, $S_C2, $S_D2 - @{[vadd_vv $C3, $C3, $D3]} - add $S_C3, $S_C3, $S_D3 - @{[vxor_vv $B0, $B0, $C0]} - xor $S_B0, $S_B0, $S_C0 - @{[vxor_vv $B1, $B1, $C1]} - xor $S_B1, $S_B1, $S_C1 - @{[vxor_vv $B2, $B2, $C2]} - xor $S_B2, $S_B2, $S_C2 - @{[vxor_vv $B3, $B3, $C3]} - xor $S_B3, $S_B3, $S_C3 - @{[vror_vi $B0, $B0, 32 - 12]} - @{[roriw $S_B0, $S_B0, 32 - 12]} - @{[vror_vi $B1, $B1, 32 - 12]} - @{[roriw $S_B1, $S_B1, 32 - 12]} - @{[vror_vi $B2, $B2, 32 - 12]} - @{[roriw $S_B2, $S_B2, 32 - 12]} - @{[vror_vi $B3, $B3, 32 - 12]} - @{[roriw $S_B3, $S_B3, 32 - 12]} + @{[chacha_sub_round + $C0, $D0, $B0, + $C1, $D1, $B1, + $C2, $D2, $B2, + $C3, $D3, $B3, + $S_C0, $S_D0, $S_B0, + $S_C1, $S_D1, $S_B1, + $S_C2, $S_D2, $S_B2, + $S_C3, $S_D3, $S_B3, + 12, + $V_T0, $V_T1, $V_T2, $V_T3]} # a += b; d ^= a; d <<<= 8; - @{[vadd_vv $A0, $A0, $B0]} - add $S_A0, $S_A0, $S_B0 - @{[vadd_vv $A1, $A1, $B1]} - add $S_A1, $S_A1, $S_B1 - @{[vadd_vv $A2, $A2, $B2]} - add $S_A2, $S_A2, $S_B2 - @{[vadd_vv $A3, $A3, $B3]} - add $S_A3, $S_A3, $S_B3 - @{[vxor_vv $D0, $D0, $A0]} - xor $S_D0, $S_D0, $S_A0 - @{[vxor_vv $D1, $D1, $A1]} - xor $S_D1, $S_D1, $S_A1 - @{[vxor_vv $D2, $D2, $A2]} - xor $S_D2, $S_D2, $S_A2 - @{[vxor_vv $D3, $D3, $A3]} - xor $S_D3, $S_D3, $S_A3 - @{[vror_vi $D0, $D0, 32 - 8]} - @{[roriw $S_D0, $S_D0, 32 - 8]} - @{[vror_vi $D1, $D1, 32 - 8]} - @{[roriw $S_D1, $S_D1, 32 - 8]} - @{[vror_vi $D2, $D2, 32 - 8]} - @{[roriw $S_D2, $S_D2, 32 - 8]} - @{[vror_vi $D3, $D3, 32 - 8]} - @{[roriw $S_D3, $S_D3, 32 - 8]} + @{[chacha_sub_round + $A0, $B0, $D0, + $A1, $B1, $D1, + $A2, $B2, $D2, + $A3, $B3, $D3, + $S_A0, $S_B0, $S_D0, + $S_A1, $S_B1, $S_D1, + $S_A2, $S_B2, $S_D2, + $S_A3, $S_B3, $S_D3, + 8, + $V_T0, $V_T1, $V_T2, $V_T3]} # c += d; b ^= c; b <<<= 7; - @{[vadd_vv $C0, $C0, $D0]} - add $S_C0, $S_C0, $S_D0 - @{[vadd_vv $C1, $C1, $D1]} - add $S_C1, $S_C1, $S_D1 - @{[vadd_vv $C2, $C2, $D2]} - add $S_C2, $S_C2, $S_D2 - @{[vadd_vv $C3, $C3, $D3]} - add $S_C3, $S_C3, $S_D3 - @{[vxor_vv $B0, $B0, $C0]} - xor $S_B0, $S_B0, $S_C0 - @{[vxor_vv $B1, $B1, $C1]} - xor $S_B1, $S_B1, $S_C1 - @{[vxor_vv $B2, $B2, $C2]} - xor $S_B2, $S_B2, $S_C2 - @{[vxor_vv $B3, $B3, $C3]} - xor $S_B3, $S_B3, $S_C3 - @{[vror_vi $B0, $B0, 32 - 7]} - @{[roriw $S_B0, $S_B0, 32 - 7]} - @{[vror_vi $B1, $B1, 32 - 7]} - @{[roriw $S_B1, $S_B1, 32 - 7]} - @{[vror_vi $B2, $B2, 32 - 7]} - @{[roriw $S_B2, $S_B2, 32 - 7]} - @{[vror_vi $B3, $B3, 32 - 7]} - @{[roriw $S_B3, $S_B3, 32 - 7]} + @{[chacha_sub_round + $C0, $D0, $B0, + $C1, $D1, $B1, + $C2, $D2, $B2, + $C3, $D3, $B3, + $S_C0, $S_D0, $S_B0, + $S_C1, $S_D1, $S_B1, + $S_C2, $S_D2, $S_B2, + $S_C3, $S_D3, $S_B3, + 7, + $V_T0, $V_T1, $V_T2, $V_T3]} ___ return $code; @@ -211,9 +242,9 @@ sub chacha_quad_round_group { $code .= <<___; .p2align 3 -.globl ChaCha20_ctr32_zbb_zvkb -.type ChaCha20_ctr32_zbb_zvkb,\@function -ChaCha20_ctr32_zbb_zvkb: +.globl ChaCha20_ctr32@{[$isaext]} +.type ChaCha20_ctr32@{[$isaext]},\@function +ChaCha20_ctr32@{[$isaext]}: addi sp, sp, -96 sd s0, 0(sp) sd s1, 8(sp) @@ -244,7 +275,7 @@ sub chacha_quad_round_group { 1: #### chacha block data - # init chacha const states + # init chacha const states into $V0~$V3 # "expa" little endian li $CONST_DATA0, 0x61707865 @{[vmv_v_x $V0, $CONST_DATA0]} @@ -259,7 +290,7 @@ sub chacha_quad_round_group { lw $KEY0, 0($KEY) @{[vmv_v_x $V3, $CONST_DATA3]} - # init chacha key states + # init chacha key states into $V4~$V11 lw $KEY1, 4($KEY) @{[vmv_v_x $V4, $KEY0]} lw $KEY2, 8($KEY) @@ -276,7 +307,7 @@ sub chacha_quad_round_group { @{[vmv_v_x $V10, $KEY6]} @{[vmv_v_x $V11, $KEY7]} - # init chacha key states + # init chacha key states into $V12~$V13 lw $COUNTER1, 4($COUNTER) @{[vid_v $V12]} lw $NONCE0, 8($COUNTER) @@ -285,17 +316,23 @@ sub chacha_quad_round_group { @{[vmv_v_x $V13, $COUNTER1]} add $COUNTER0, $CURRENT_COUNTER, $VL - # init chacha nonce states + # init chacha nonce states into $V14~$V15 @{[vmv_v_x $V14, $NONCE0]} @{[vmv_v_x $V15, $NONCE1]} li $T0, 64 - # load the top-half of input data + # load the top-half of input data into $V16~$V23 @{[vlsseg_nf_e32_v 8, $V16, $INPUT, $T0]} + # till now in block_loop, we used: + # - $V0~$V15 for chacha states. + # - $V16~$V23 for top-half of input data. + # - $V24~$V31 haven't been used yet. + # 20 round groups li $T0, 10 .Lround_loop: + # we can use $V24~$V31 as temporary registers in round_loop. addi $T0, $T0, -1 @{[chacha_quad_round_group $V0, $V4, $V8, $V12, @@ -305,7 +342,8 @@ sub chacha_quad_round_group { $STATE0, $STATE4, $STATE8, $STATE12, $STATE1, $STATE5, $STATE9, $STATE13, $STATE2, $STATE6, $STATE10, $STATE14, - $STATE3, $STATE7, $STATE11, $STATE15]} + $STATE3, $STATE7, $STATE11, $STATE15, + $V24, $V25, $V26, $V27]} @{[chacha_quad_round_group $V3, $V4, $V9, $V14, $V0, $V5, $V10, $V15, @@ -314,14 +352,17 @@ sub chacha_quad_round_group { $STATE3, $STATE4, $STATE9, $STATE14, $STATE0, $STATE5, $STATE10, $STATE15, $STATE1, $STATE6, $STATE11, $STATE12, - $STATE2, $STATE7, $STATE8, $STATE13]} + $STATE2, $STATE7, $STATE8, $STATE13, + $V24, $V25, $V26, $V27]} bnez $T0, .Lround_loop li $T0, 64 - # load the bottom-half of input data + # load the bottom-half of input data into $V24~$V31 addi $T1, $INPUT, 32 @{[vlsseg_nf_e32_v 8, $V24, $T1, $T0]} + # now, there are no free vector registers until the round_loop exits. + # add chacha top-half initial block states # "expa" little endian li $T0, 0x61707865 @@ -373,7 +414,7 @@ sub chacha_quad_round_group { lw $T2, 24($KEY) @{[vxor_vv $V23, $V23, $V7]} - # save the top-half of output + # save the top-half of output from $V16~$V23 li $T3, 64 @{[vssseg_nf_e32_v 8, $V16, $OUTPUT, $T3]} @@ -419,7 +460,7 @@ sub chacha_quad_round_group { @{[vxor_vv $V31, $V31, $V15]} sw $STATE15, 60(sp) - # save the bottom-half of output + # save the bottom-half of output from $V24~$V31 li $T0, 64 addi $T1, $OUTPUT, 32 @{[vssseg_nf_e32_v 8, $V24, $T1, $T0]} @@ -440,6 +481,7 @@ sub chacha_quad_round_group { mv $T2, sp .Lscalar_data_loop: @{[vsetvli $VL, $T1, "e8", "m8", "ta", "ma"]} + # from this on, vector registers are grouped with lmul = 8 @{[vle8_v $V8, $INPUT]} @{[vle8_v $V16, $T2]} @{[vxor_vv $V8, $V8, $V16]} @@ -468,7 +510,7 @@ sub chacha_quad_round_group { addi sp, sp, 96 ret -.size ChaCha20_ctr32_zbb_zvkb,.-ChaCha20_ctr32_zbb_zvkb +.size ChaCha20_ctr32@{[$isaext]},.-ChaCha20_ctr32@{[$isaext]} ___ print $code; diff --git a/crypto/chacha/asm/chacha-x86_64.S b/crypto/chacha/asm/chacha-x86_64.S index ec5251a82f..bcdb0a922d 100644 --- a/crypto/chacha/asm/chacha-x86_64.S +++ b/crypto/chacha/asm/chacha-x86_64.S @@ -2,6 +2,7 @@ +.section .rodata .align 64 .Lzero: .long 0,0,0,0 @@ -33,6 +34,7 @@ .Lsigma: .byte 101,120,112,97,110,100,32,51,50,45,98,121,116,101,32,107,0 .byte 67,104,97,67,104,97,50,48,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .globl ChaCha20_ctr32 .type ChaCha20_ctr32,@function .align 64 diff --git a/crypto/chacha/asm/chacha-x86_64.pl b/crypto/chacha/asm/chacha-x86_64.pl index cdb900c037..5506e33fa2 100755 --- a/crypto/chacha/asm/chacha-x86_64.pl +++ b/crypto/chacha/asm/chacha-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2016-2021 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -102,6 +102,7 @@ .extern OPENSSL_ia32cap_P +.section .rodata align=64 .align 64 .Lzero: .long 0,0,0,0 @@ -133,6 +134,7 @@ .Lsigma: .asciz "expand 32-byte k" .asciz "ChaCha20 for x86_64, CRYPTOGAMS by " +.previous ___ sub AUTOLOAD() # thunk [simplified] 32-bit style perlasm diff --git a/crypto/chacha/asm/chachap10-ppc.pl b/crypto/chacha/asm/chachap10-ppc.pl index 032cf2585b..a6bff8db38 100755 --- a/crypto/chacha/asm/chachap10-ppc.pl +++ b/crypto/chacha/asm/chachap10-ppc.pl @@ -787,7 +787,7 @@ sub VSX_lane_ROUND_8x { vxxlor $xv6 ,$xb6,$xb6 # save vr23, so we get 8 regs vxxlor $xv7 ,$xb7,$xb7 # save vr23, so we get 8 regs - be?vxxlorc $beperm,$xv26,$xv26 # copy back the the beperm. + be?vxxlorc $beperm,$xv26,$xv26 # copy back the beperm. vxxlorc @K[0],$xv0,$xv0 #27 vxxlorc @K[1],$xv1,$xv1 #24 @@ -1032,10 +1032,10 @@ sub VSX_lane_ROUND_8x { vadduwm $xcn0,$xcn4,@K[2] vadduwm $xdn0,$xdn4,@K[3] - be?vperm $xan0,$xa4,$xa4,$beperm - be?vperm $xbn0,$xb4,$xb4,$beperm - be?vperm $xcn0,$xcn4,$xcn4,$beperm - be?vperm $xdn0,$xdn4,$xdn4,$beperm + be?vperm $xan0,$xan0,$xan0,$beperm + be?vperm $xbn0,$xbn0,$xbn0,$beperm + be?vperm $xcn0,$xcn0,$xcn0,$beperm + be?vperm $xdn0,$xdn0,$xdn0,$beperm ${UCMP}i $len,0x40 blt Ltail_vsx_8x_1 diff --git a/crypto/chacha/build.info b/crypto/chacha/build.info index c1352c9b62..c151e19042 100644 --- a/crypto/chacha/build.info +++ b/crypto/chacha/build.info @@ -22,7 +22,7 @@ IF[{- !$disabled{asm} -}] $CHACHAASM_c64xplus=chacha-c64xplus.s - $CHACHAASM_riscv64=chacha_riscv.c chacha_enc.c chacha-riscv64-zbb-zvkb.s + $CHACHAASM_riscv64=chacha_riscv.c chacha_enc.c chacha-riscv64-v-zbb.s chacha-riscv64-v-zbb-zvkb.s $CHACHADEF_riscv64=INCLUDE_C_CHACHA20 # Now that we have defined all the arch specific variables, use the @@ -53,4 +53,5 @@ GENERATE[chacha-s390x.S]=asm/chacha-s390x.pl GENERATE[chacha-ia64.S]=asm/chacha-ia64.pl GENERATE[chacha-ia64.s]=chacha-ia64.S GENERATE[chacha-loongarch64.S]=asm/chacha-loongarch64.pl -GENERATE[chacha-riscv64-zbb-zvkb.s]=asm/chacha-riscv64-zbb-zvkb.pl +GENERATE[chacha-riscv64-v-zbb.s]=asm/chacha-riscv64-v-zbb.pl +GENERATE[chacha-riscv64-v-zbb-zvkb.s]=asm/chacha-riscv64-v-zbb.pl zvkb diff --git a/crypto/chacha/chacha_riscv.c b/crypto/chacha/chacha_riscv.c index 06e0400ba4..734444bfa8 100644 --- a/crypto/chacha/chacha_riscv.c +++ b/crypto/chacha/chacha_riscv.c @@ -40,16 +40,23 @@ #include "crypto/chacha.h" #include "crypto/riscv_arch.h" -void ChaCha20_ctr32_zbb_zvkb(unsigned char *out, const unsigned char *inp, - size_t len, const unsigned int key[8], - const unsigned int counter[4]); +void ChaCha20_ctr32_v_zbb_zvkb(unsigned char *out, const unsigned char *inp, + size_t len, const unsigned int key[8], + const unsigned int counter[4]); + +void ChaCha20_ctr32_v_zbb(unsigned char *out, const unsigned char *inp, + size_t len, const unsigned int key[8], + const unsigned int counter[4]); void ChaCha20_ctr32(unsigned char *out, const unsigned char *inp, size_t len, const unsigned int key[8], const unsigned int counter[4]) { - if (len > CHACHA_BLK_SIZE && RISCV_HAS_ZVKB() && RISCV_HAS_ZBB() && - riscv_vlen() >= 128) { - ChaCha20_ctr32_zbb_zvkb(out, inp, len, key, counter); + if (len > CHACHA_BLK_SIZE && RISCV_HAS_ZBB() && riscv_vlen() >= 128) { + if (RISCV_HAS_ZVKB()) { + ChaCha20_ctr32_v_zbb_zvkb(out, inp, len, key, counter); + } else { + ChaCha20_ctr32_v_zbb(out, inp, len, key, counter); + } } else { ChaCha20_ctr32_c(out, inp, len, key, counter); } diff --git a/crypto/cmac/cmac.c b/crypto/cmac/cmac.c index 2012774f8d..16f4b904ad 100644 --- a/crypto/cmac/cmac.c +++ b/crypto/cmac/cmac.c @@ -19,6 +19,7 @@ #include "internal/cryptlib.h" #include #include +#include "crypto/cmac.h" #define LOCAL_BUF_SIZE 2048 struct CMAC_CTX_st { @@ -107,8 +108,9 @@ int CMAC_CTX_copy(CMAC_CTX *out, const CMAC_CTX *in) return 1; } -int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, - const EVP_CIPHER *cipher, ENGINE *impl) +int ossl_cmac_init(CMAC_CTX *ctx, const void *key, size_t keylen, + const EVP_CIPHER *cipher, ENGINE *impl, + const OSSL_PARAM param[]) { static const unsigned char zero_iv[EVP_MAX_BLOCK_LENGTH] = { 0 }; int block_len; @@ -118,7 +120,7 @@ int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, /* Not initialised */ if (ctx->nlast_block == -1) return 0; - if (!EVP_EncryptInit_ex(ctx->cctx, NULL, NULL, NULL, zero_iv)) + if (!EVP_EncryptInit_ex2(ctx->cctx, NULL, NULL, zero_iv, param)) return 0; block_len = EVP_CIPHER_CTX_get_block_size(ctx->cctx); if (block_len == 0) @@ -131,8 +133,13 @@ int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, if (cipher != NULL) { /* Ensure we can't use this ctx until we also have a key */ ctx->nlast_block = -1; - if (!EVP_EncryptInit_ex(ctx->cctx, cipher, impl, NULL, NULL)) - return 0; + if (impl != NULL) { + if (!EVP_EncryptInit_ex(ctx->cctx, cipher, impl, NULL, NULL)) + return 0; + } else { + if (!EVP_EncryptInit_ex2(ctx->cctx, cipher, NULL, NULL, param)) + return 0; + } } /* Non-NULL key means initialisation complete */ if (key != NULL) { @@ -144,7 +151,7 @@ int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, return 0; if (EVP_CIPHER_CTX_set_key_length(ctx->cctx, keylen) <= 0) return 0; - if (!EVP_EncryptInit_ex(ctx->cctx, NULL, NULL, key, zero_iv)) + if (!EVP_EncryptInit_ex2(ctx->cctx, NULL, key, zero_iv, param)) return 0; if ((bl = EVP_CIPHER_CTX_get_block_size(ctx->cctx)) < 0) return 0; @@ -154,7 +161,7 @@ int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, make_kn(ctx->k2, ctx->k1, bl); OPENSSL_cleanse(ctx->tbl, bl); /* Reset context again ready for first data block */ - if (!EVP_EncryptInit_ex(ctx->cctx, NULL, NULL, NULL, zero_iv)) + if (!EVP_EncryptInit_ex2(ctx->cctx, NULL, NULL, zero_iv, param)) return 0; /* Zero tbl so resume works */ memset(ctx->tbl, 0, bl); @@ -163,6 +170,12 @@ int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, return 1; } +int CMAC_Init(CMAC_CTX *ctx, const void *key, size_t keylen, + const EVP_CIPHER *cipher, ENGINE *impl) +{ + return ossl_cmac_init(ctx, key, keylen, cipher, impl, NULL); +} + int CMAC_Update(CMAC_CTX *ctx, const void *in, size_t dlen) { const unsigned char *data = in; diff --git a/crypto/cmp/cmp_asn.c b/crypto/cmp/cmp_asn.c index 3285cbf424..4415ede449 100644 --- a/crypto/cmp/cmp_asn.c +++ b/crypto/cmp/cmp_asn.c @@ -12,6 +12,7 @@ #include #include "cmp_local.h" +#include "internal/crmf.h" /* explicit #includes not strictly needed since implied by the above: */ #include @@ -117,9 +118,17 @@ ASN1_ADB(OSSL_CMP_ITAV) = { ADB_ENTRY(NID_id_it_rootCaKeyUpdate, ASN1_OPT(OSSL_CMP_ITAV, infoValue.rootCaKeyUpdate, OSSL_CMP_ROOTCAKEYUPDATE)), + ADB_ENTRY(NID_id_it_certReqTemplate, + ASN1_OPT(OSSL_CMP_ITAV, infoValue.certReqTemplate, + OSSL_CMP_CERTREQTEMPLATE)), ADB_ENTRY(NID_id_it_certProfile, ASN1_SEQUENCE_OF_OPT(OSSL_CMP_ITAV, infoValue.certProfile, ASN1_UTF8STRING)), + ADB_ENTRY(NID_id_it_crlStatusList, + ASN1_SEQUENCE_OF_OPT(OSSL_CMP_ITAV, infoValue.crlStatusList, + OSSL_CMP_CRLSTATUS)), + ADB_ENTRY(NID_id_it_crls, + ASN1_SEQUENCE_OF_OPT(OSSL_CMP_ITAV, infoValue.crls, X509_CRL)) } ASN1_ADB_END(OSSL_CMP_ITAV, 0, infoType, 0, &infotypeandvalue_default_tt, NULL); @@ -138,6 +147,33 @@ ASN1_SEQUENCE(OSSL_CMP_ROOTCAKEYUPDATE) = { } ASN1_SEQUENCE_END(OSSL_CMP_ROOTCAKEYUPDATE) IMPLEMENT_ASN1_FUNCTIONS(OSSL_CMP_ROOTCAKEYUPDATE) +ASN1_ITEM_TEMPLATE(OSSL_CMP_ATAVS) = + ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, + OSSL_CMP_ATAVS, OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +ASN1_ITEM_TEMPLATE_END(OSSL_CMP_ATAVS) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_CMP_ATAVS) + +ASN1_SEQUENCE(OSSL_CMP_CERTREQTEMPLATE) = { + ASN1_SIMPLE(OSSL_CMP_CERTREQTEMPLATE, certTemplate, OSSL_CRMF_CERTTEMPLATE), + ASN1_SEQUENCE_OF_OPT(OSSL_CMP_CERTREQTEMPLATE, keySpec, + OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +} ASN1_SEQUENCE_END(OSSL_CMP_CERTREQTEMPLATE) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_CMP_CERTREQTEMPLATE) + +ASN1_CHOICE(OSSL_CMP_CRLSOURCE) = { + ASN1_EXP(OSSL_CMP_CRLSOURCE, value.dpn, DIST_POINT_NAME, 0), + ASN1_EXP(OSSL_CMP_CRLSOURCE, value.issuer, GENERAL_NAMES, 1), +} ASN1_CHOICE_END(OSSL_CMP_CRLSOURCE) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_CMP_CRLSOURCE) +#define OSSL_CMP_CRLSOURCE_DPN 0 +#define OSSL_CMP_CRLSOURCE_ISSUER 1 + +ASN1_SEQUENCE(OSSL_CMP_CRLSTATUS) = { + ASN1_SIMPLE(OSSL_CMP_CRLSTATUS, source, OSSL_CMP_CRLSOURCE), + ASN1_OPT(OSSL_CMP_CRLSTATUS, thisUpdate, ASN1_TIME) +} ASN1_SEQUENCE_END(OSSL_CMP_CRLSTATUS) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_CMP_CRLSTATUS) + OSSL_CMP_ITAV *OSSL_CMP_ITAV_create(ASN1_OBJECT *type, ASN1_TYPE *value) { OSSL_CMP_ITAV *itav; @@ -339,6 +375,457 @@ int OSSL_CMP_ITAV_get0_rootCaKeyUpdate(const OSSL_CMP_ITAV *itav, return 1; } +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_certReqTemplate(OSSL_CRMF_CERTTEMPLATE *certTemplate, + OSSL_CMP_ATAVS *keySpec) +{ + OSSL_CMP_ITAV *itav; + OSSL_CMP_CERTREQTEMPLATE *tmpl; + + if (certTemplate == NULL && keySpec != NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return NULL; + } + if ((itav = OSSL_CMP_ITAV_new()) == NULL) + return NULL; + itav->infoType = OBJ_nid2obj(NID_id_it_certReqTemplate); + if (certTemplate == NULL) + return itav; + + if ((tmpl = OSSL_CMP_CERTREQTEMPLATE_new()) == NULL) { + OSSL_CMP_ITAV_free(itav); + return NULL; + } + itav->infoValue.certReqTemplate = tmpl; + tmpl->certTemplate = certTemplate; + tmpl->keySpec = keySpec; + return itav; +} + +int OSSL_CMP_ITAV_get1_certReqTemplate(const OSSL_CMP_ITAV *itav, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec) +{ + OSSL_CMP_CERTREQTEMPLATE *tpl; + + if (itav == NULL || certTemplate == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return 0; + } + + *certTemplate = NULL; + if (keySpec != NULL) + *keySpec = NULL; + + if (OBJ_obj2nid(itav->infoType) != NID_id_it_certReqTemplate) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + tpl = itav->infoValue.certReqTemplate; + if (tpl == NULL) /* no requirements available */ + return 1; + + if ((*certTemplate = OSSL_CRMF_CERTTEMPLATE_dup(tpl->certTemplate)) == NULL) + return 0; + if (keySpec != NULL && tpl->keySpec != NULL) { + int i, n = sk_OSSL_CMP_ATAV_num(tpl->keySpec); + + *keySpec = sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new_reserve(NULL, n); + if (*keySpec == NULL) + goto err; + for (i = 0; i < n; i++) { + OSSL_CMP_ATAV *atav = sk_OSSL_CMP_ATAV_value(tpl->keySpec, i); + ASN1_OBJECT *type = OSSL_CMP_ATAV_get0_type(atav /* may be NULL */); + int nid; + const char *name; + + if (type == NULL) { + ERR_raise_data(ERR_LIB_CMP, CMP_R_INVALID_KEYSPEC, + "keySpec with index %d in certReqTemplate does not exist", + i); + goto err; + } + nid = OBJ_obj2nid(type); + + if (nid != NID_id_regCtrl_algId + && nid != NID_id_regCtrl_rsaKeyLen) { + name = OBJ_nid2ln(nid); + if (name == NULL) + name = OBJ_nid2sn(nid); + if (name == NULL) + name = ""; + ERR_raise_data(ERR_LIB_CMP, CMP_R_INVALID_KEYSPEC, + "keySpec with index %d in certReqTemplate has invalid type %s", + i, name); + goto err; + } + OSSL_CMP_ATAV_push1(keySpec, atav); + } + } + return 1; + + err: + OSSL_CRMF_CERTTEMPLATE_free(*certTemplate); + *certTemplate = NULL; + sk_OSSL_CMP_ATAV_pop_free(*keySpec, OSSL_CMP_ATAV_free); + if (keySpec != NULL) + *keySpec = NULL; + return 0; +} + +OSSL_CMP_ATAV *OSSL_CMP_ATAV_create(ASN1_OBJECT *type, ASN1_TYPE *value) +{ + OSSL_CMP_ATAV *atav; + + if ((atav = OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new()) == NULL) + return NULL; + OSSL_CMP_ATAV_set0(atav, type, value); + return atav; +} + +void OSSL_CMP_ATAV_set0(OSSL_CMP_ATAV *atav, ASN1_OBJECT *type, + ASN1_TYPE *value) +{ + atav->type = type; + atav->value.other = value; +} + +ASN1_OBJECT *OSSL_CMP_ATAV_get0_type(const OSSL_CMP_ATAV *atav) +{ + if (atav == NULL) + return NULL; + return atav->type; +} + +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_algId(const X509_ALGOR *alg) +{ + X509_ALGOR *dup; + OSSL_CMP_ATAV *res; + + if (alg == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return NULL; + } + if ((dup = X509_ALGOR_dup(alg)) == NULL) + return NULL; + res = OSSL_CMP_ATAV_create(OBJ_nid2obj(NID_id_regCtrl_algId), + (ASN1_TYPE *)dup); + if (res == NULL) + X509_ALGOR_free(dup); + return res; +} + +X509_ALGOR *OSSL_CMP_ATAV_get0_algId(const OSSL_CMP_ATAV *atav) +{ + if (atav == NULL || OBJ_obj2nid(atav->type) != NID_id_regCtrl_algId) + return NULL; + return atav->value.algId; +} + +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_rsaKeyLen(int len) +{ + ASN1_INTEGER *aint; + OSSL_CMP_ATAV *res = NULL; + + if (len <= 0) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return NULL; + } + if ((aint = ASN1_INTEGER_new()) == NULL) + return NULL; + if (!ASN1_INTEGER_set(aint, len) + || (res = OSSL_CMP_ATAV_create(OBJ_nid2obj(NID_id_regCtrl_rsaKeyLen), + (ASN1_TYPE *)aint)) == NULL) + ASN1_INTEGER_free(aint); + return res; +} + +int OSSL_CMP_ATAV_get_rsaKeyLen(const OSSL_CMP_ATAV *atav) +{ + int64_t val; + + if (atav == NULL || OBJ_obj2nid(atav->type) != NID_id_regCtrl_rsaKeyLen + || !ASN1_INTEGER_get_int64(&val, atav->value.rsaKeyLen)) + return -1; + if (val <= 0 || val > INT_MAX) + return -2; + return (int)val; +} + +ASN1_TYPE *OSSL_CMP_ATAV_get0_value(const OSSL_CMP_ATAV *atav) +{ + if (atav == NULL) + return NULL; + return atav->value.other; +} + +int OSSL_CMP_ATAV_push1(OSSL_CMP_ATAVS **sk_p, const OSSL_CMP_ATAV *atav) +{ + int created = 0; + OSSL_CMP_ATAV *dup; + + if (sk_p == NULL || atav == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + goto err; + } + + if (*sk_p == NULL) { + if ((*sk_p = sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new_null()) == NULL) + goto err; + created = 1; + } + + if ((dup = OSSL_CRMF_ATTRIBUTETYPEANDVALUE_dup((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)atav)) == NULL) + goto err; + if (sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_push(*sk_p, dup)) + return 1; + OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free(dup); + + err: + if (created) { + sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free(*sk_p); + *sk_p = NULL; + } + return 0; +} + +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_crlStatusList(STACK_OF(OSSL_CMP_CRLSTATUS) *crlStatusList) +{ + OSSL_CMP_ITAV *itav; + + if ((itav = OSSL_CMP_ITAV_new()) == NULL) + return NULL; + itav->infoType = OBJ_nid2obj(NID_id_it_crlStatusList); + itav->infoValue.crlStatusList = crlStatusList; + return itav; +} + +int OSSL_CMP_ITAV_get0_crlStatusList(const OSSL_CMP_ITAV *itav, + STACK_OF(OSSL_CMP_CRLSTATUS) **out) +{ + if (itav == NULL || out == NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_NULL_PARAMETER); + return 0; + } + if (OBJ_obj2nid(itav->infoType) != NID_id_it_crlStatusList) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + *out = itav->infoValue.crlStatusList; + return 1; +} + +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_new1(const DIST_POINT_NAME *dpn, + const GENERAL_NAMES *issuer, + const ASN1_TIME *thisUpdate) +{ + OSSL_CMP_CRLSOURCE *crlsource; + OSSL_CMP_CRLSTATUS *crlstatus; + + if (dpn == NULL && issuer == NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_NULL_PARAMETER); + return NULL; + } + if (dpn != NULL && issuer != NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return NULL; + } + + if ((crlstatus = OSSL_CMP_CRLSTATUS_new()) == NULL) + return NULL; + crlsource = crlstatus->source; + + if (dpn != NULL) { + crlsource->type = OSSL_CMP_CRLSOURCE_DPN; + if ((crlsource->value.dpn = DIST_POINT_NAME_dup(dpn)) == NULL) + goto err; + } else { + crlsource->type = OSSL_CMP_CRLSOURCE_ISSUER; + if ((crlsource->value.issuer = + sk_GENERAL_NAME_deep_copy(issuer, GENERAL_NAME_dup, + GENERAL_NAME_free)) == NULL) + goto err; + } + + if (thisUpdate != NULL + && (crlstatus->thisUpdate = ASN1_TIME_dup(thisUpdate)) == NULL) + goto err; + return crlstatus; + + err: + OSSL_CMP_CRLSTATUS_free(crlstatus); + return NULL; +} + +static GENERAL_NAMES *gennames_new(const X509_NAME *nm) +{ + GENERAL_NAMES *names; + GENERAL_NAME *name = NULL; + + if ((names = sk_GENERAL_NAME_new_reserve(NULL, 1)) == NULL) + return NULL; + if (!GENERAL_NAME_set1_X509_NAME(&name, nm)) { + sk_GENERAL_NAME_free(names); + return NULL; + } + (void)sk_GENERAL_NAME_push(names, name); /* cannot fail */ + return names; +} + +static int gennames_allowed(GENERAL_NAMES *names, int only_DN) +{ + if (names == NULL) + return 0; + if (!only_DN) + return 1; + return sk_GENERAL_NAME_num(names) == 1 + && sk_GENERAL_NAME_value(names, 0)->type == GEN_DIRNAME; +} + +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_create(const X509_CRL *crl, + const X509 *cert, int only_DN) +{ + STACK_OF(DIST_POINT) *crldps = NULL; + ISSUING_DIST_POINT *idp = NULL; + DIST_POINT_NAME *dpn = NULL; + AUTHORITY_KEYID *akid = NULL; + GENERAL_NAMES *issuers = NULL; + const GENERAL_NAMES *CRLissuer = NULL; + const ASN1_TIME *last = crl == NULL ? NULL : X509_CRL_get0_lastUpdate(crl); + OSSL_CMP_CRLSTATUS *status = NULL; + int i, NID_akid = NID_authority_key_identifier; + + /* + * Note: + * X509{,_CRL}_get_ext_d2i(..., NID, ..., NULL) return the 1st extension with + * given NID that is available, if any. If there are more, this is an error. + */ + if (cert != NULL) { + crldps = X509_get_ext_d2i(cert, NID_crl_distribution_points, NULL, NULL); + /* if available, take the first suitable element */ + for (i = 0; i < sk_DIST_POINT_num(crldps); i++) { + DIST_POINT *dp = sk_DIST_POINT_value(crldps, i); + + if (dp == NULL) + continue; + if ((dpn = dp->distpoint) != NULL) { + CRLissuer = NULL; + break; + } + if (gennames_allowed(dp->CRLissuer, only_DN) && CRLissuer == NULL) + /* don't break because any dp->distpoint in list is preferred */ + CRLissuer = dp->CRLissuer; + } + } else { + if (crl == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return NULL; + } + idp = X509_CRL_get_ext_d2i(crl, + NID_issuing_distribution_point, NULL, NULL); + if (idp != NULL && idp->distpoint != NULL) + dpn = idp->distpoint; + } + + if (dpn == NULL && CRLissuer == NULL) { + if (cert != NULL) { + akid = X509_get_ext_d2i(cert, NID_akid, NULL, NULL); + if (akid != NULL && gennames_allowed(akid->issuer, only_DN)) + CRLissuer = akid->issuer; + else + CRLissuer = issuers = gennames_new(X509_get_issuer_name(cert)); + } + if (CRLissuer == NULL && crl != NULL) { + akid = X509_CRL_get_ext_d2i(crl, NID_akid, NULL, NULL); + if (akid != NULL && gennames_allowed(akid->issuer, only_DN)) + CRLissuer = akid->issuer; + else + CRLissuer = issuers = gennames_new(X509_CRL_get_issuer(crl)); + } + if (CRLissuer == NULL) + goto end; + } + + status = OSSL_CMP_CRLSTATUS_new1(dpn, CRLissuer, last); + end: + sk_DIST_POINT_pop_free(crldps, DIST_POINT_free); + ISSUING_DIST_POINT_free(idp); + AUTHORITY_KEYID_free(akid); + sk_GENERAL_NAME_pop_free(issuers, GENERAL_NAME_free); + return status; +} + +int OSSL_CMP_CRLSTATUS_get0(const OSSL_CMP_CRLSTATUS *crlstatus, + DIST_POINT_NAME **dpn, GENERAL_NAMES **issuer, + ASN1_TIME **thisUpdate) +{ + OSSL_CMP_CRLSOURCE *crlsource; + + if (crlstatus == NULL || dpn == NULL || issuer == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return 0; + } + if ((crlsource = crlstatus->source) == NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + + if (crlsource->type == OSSL_CMP_CRLSOURCE_DPN) { + *dpn = crlsource->value.dpn; + *issuer = NULL; + } else if (crlsource->type == OSSL_CMP_CRLSOURCE_ISSUER) { + *dpn = NULL; + *issuer = crlsource->value.issuer; + } else { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + if (thisUpdate != NULL) + *thisUpdate = crlstatus->thisUpdate; + return 1; +} + +OSSL_CMP_ITAV *OSSL_CMP_ITAV_new_crls(const X509_CRL *crl) +{ + OSSL_CMP_ITAV *itav; + X509_CRL *crl_copy = NULL; + STACK_OF(X509_CRL) *crls = NULL; + + if ((itav = OSSL_CMP_ITAV_new()) == NULL) + return NULL; + + if (crl != NULL) { + if ((crls = sk_X509_CRL_new_reserve(NULL, 1)) == NULL + || (crl_copy = X509_CRL_dup(crl)) == NULL) + goto err; + (void)sk_X509_CRL_push(crls, crl_copy); /* cannot fail */ + } + + itav->infoType = OBJ_nid2obj(NID_id_it_crls); + itav->infoValue.crls = crls; + return itav; + + err: + sk_X509_CRL_free(crls); + OSSL_CMP_ITAV_free(itav); + return NULL; +} + +int OSSL_CMP_ITAV_get0_crls(const OSSL_CMP_ITAV *itav, STACK_OF(X509_CRL) **out) +{ + if (itav == NULL || out == NULL) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_NULL_PARAMETER); + return 0; + } + if (OBJ_obj2nid(itav->infoType) != NID_id_it_crls) { + ERR_raise(ERR_LIB_CMP, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + *out = itav->infoValue.crls; + return 1; +} + /* get ASN.1 encoded integer, return -2 on error; -1 is valid for certReqId */ int ossl_cmp_asn1_get_int(const ASN1_INTEGER *a) { diff --git a/crypto/cmp/cmp_client.c b/crypto/cmp/cmp_client.c index d588bb358b..e8fe6f30dc 100644 --- a/crypto/cmp/cmp_client.c +++ b/crypto/cmp/cmp_client.c @@ -106,9 +106,12 @@ static int save_statusInfo(OSSL_CMP_CTX *ctx, OSSL_CMP_PKISI *si) ss = si->statusString; /* may be NULL */ for (i = 0; i < sk_ASN1_UTF8STRING_num(ss); i++) { ASN1_UTF8STRING *str = sk_ASN1_UTF8STRING_value(ss, i); + ASN1_UTF8STRING *dup = ASN1_STRING_dup(str); - if (!sk_ASN1_UTF8STRING_push(ctx->statusString, ASN1_STRING_dup(str))) + if (dup == NULL || !sk_ASN1_UTF8STRING_push(ctx->statusString, dup)) { + ASN1_UTF8STRING_free(dup); return 0; + } } return 1; } diff --git a/crypto/cmp/cmp_err.c b/crypto/cmp/cmp_err.c index 56ac3691d7..5cec9438f6 100644 --- a/crypto/cmp/cmp_err.c +++ b/crypto/cmp/cmp_err.c @@ -85,12 +85,18 @@ static const ERR_STRING_DATA CMP_str_reasons[] = { "failure obtaining random"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_FAIL_INFO_OUT_OF_RANGE), "fail info out of range"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_GENERATE_CERTREQTEMPLATE), + "generate certreqtemplate"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_GENERATE_CRLSTATUS), + "error creating crlstatus"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_GETTING_GENP), "getting genp"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_GET_ITAV), "get itav"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_INVALID_ARGS), "invalid args"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_INVALID_GENP), "invalid genp"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_INVALID_KEYSPEC), "invalid keyspec"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_INVALID_OPTION), "invalid option"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_INVALID_ROOTCAKEYUPDATE), - "invalid rootcakeyupdate"}, + "invalid rootcakeyupdate"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_MISSING_CERTID), "missing certid"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_MISSING_KEY_INPUT_FOR_CREATING_PROTECTION), "missing key input for creating protection"}, @@ -146,7 +152,9 @@ static const ERR_STRING_DATA CMP_str_reasons[] = { {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_TRANSFER_ERROR), "transfer error"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNCLEAN_CTX), "unclean ctx"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNEXPECTED_CERTPROFILE), - "unexpected certprofile"}, + "unexpected certprofile"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNEXPECTED_CRLSTATUSLIST), + "unexpected crlstatuslist"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNEXPECTED_PKIBODY), "unexpected pkibody"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNEXPECTED_PKISTATUS), "unexpected pkistatus"}, @@ -156,6 +164,7 @@ static const ERR_STRING_DATA CMP_str_reasons[] = { {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNKNOWN_ALGORITHM_ID), "unknown algorithm id"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNKNOWN_CERT_TYPE), "unknown cert type"}, + {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNKNOWN_CRL_ISSUER), "unknown crl issuer"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNKNOWN_PKISTATUS), "unknown pkistatus"}, {ERR_PACK(ERR_LIB_CMP, 0, CMP_R_UNSUPPORTED_ALGORITHM), "unsupported algorithm"}, diff --git a/crypto/cmp/cmp_genm.c b/crypto/cmp/cmp_genm.c index 5986036f57..6afe3e720e 100644 --- a/crypto/cmp/cmp_genm.c +++ b/crypto/cmp/cmp_genm.c @@ -346,3 +346,96 @@ int OSSL_CMP_get1_rootCaKeyUpdate(OSSL_CMP_CTX *ctx, X509_free(oldWithOld_copy); return res; } + +int OSSL_CMP_get1_crlUpdate(OSSL_CMP_CTX *ctx, const X509 *crlcert, + const X509_CRL *last_crl, + X509_CRL **crl) +{ + OSSL_CMP_CRLSTATUS *status = NULL; + STACK_OF(OSSL_CMP_CRLSTATUS) *list = NULL; + OSSL_CMP_ITAV *req = NULL, *itav = NULL; + STACK_OF(X509_CRL) *crls = NULL; + int res = 0; + + if (crl == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return 0; + } + *crl = NULL; + + if ((status = OSSL_CMP_CRLSTATUS_create(last_crl, crlcert, 1)) == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_GENERATE_CRLSTATUS); + goto end; + } + if ((list = sk_OSSL_CMP_CRLSTATUS_new_reserve(NULL, 1)) == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_GENERATE_CRLSTATUS); + goto end; + } + (void)sk_OSSL_CMP_CRLSTATUS_push(list, status); /* cannot fail */ + + if ((req = OSSL_CMP_ITAV_new0_crlStatusList(list)) == NULL) + goto end; + status = NULL; + list = NULL; + + if ((itav = get_genm_itav(ctx, req, NID_id_it_crls, "crl")) == NULL) + goto end; + + if (!OSSL_CMP_ITAV_get0_crls(itav, &crls)) + goto end; + + if (crls == NULL) { /* no CRL update available */ + res = 1; + goto end; + } + if (sk_X509_CRL_num(crls) != 1) { + ERR_raise_data(ERR_LIB_CMP, CMP_R_INVALID_GENP, + "Unexpected number of CRLs in genp: %d", + sk_X509_CRL_num(crls)); + goto end; + } + + if ((*crl = sk_X509_CRL_value(crls, 0)) == NULL || !X509_CRL_up_ref(*crl)) { + *crl = NULL; + goto end; + } + res = 1; + end: + OSSL_CMP_CRLSTATUS_free(status); + sk_OSSL_CMP_CRLSTATUS_free(list); + OSSL_CMP_ITAV_free(itav); + return res; +} + +int OSSL_CMP_get1_certReqTemplate(OSSL_CMP_CTX *ctx, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec) +{ + OSSL_CMP_ITAV *req, *itav = NULL; + int res = 0; + + if (keySpec != NULL) + *keySpec = NULL; + if (certTemplate == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_NULL_ARGUMENT); + return 0; + } + *certTemplate = NULL; + + if ((req = OSSL_CMP_ITAV_new0_certReqTemplate(NULL, NULL)) == NULL) { + ERR_raise(ERR_LIB_CMP, CMP_R_GENERATE_CERTREQTEMPLATE); + return 0; + } + + if ((itav = get_genm_itav(ctx, req, NID_id_it_certReqTemplate, + "certReqTemplate")) == NULL) + return 0; + + if (!OSSL_CMP_ITAV_get1_certReqTemplate(itav, certTemplate, keySpec)) + goto end; + + res = 1; + end: + OSSL_CMP_ITAV_free(itav); + return res; +} diff --git a/crypto/cmp/cmp_hdr.c b/crypto/cmp/cmp_hdr.c index 4358b38873..d00c9f76bb 100644 --- a/crypto/cmp/cmp_hdr.c +++ b/crypto/cmp/cmp_hdr.c @@ -1,5 +1,5 @@ /* - * Copyright 2007-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -89,34 +89,6 @@ int ossl_cmp_general_name_is_NULL_DN(GENERAL_NAME *name) || (name->type == GEN_DIRNAME && IS_NULL_DN(name->d.directoryName)); } -/* assign to *tgt a copy of src (which may be NULL to indicate an empty DN) */ -static int set1_general_name(GENERAL_NAME **tgt, const X509_NAME *src) -{ - GENERAL_NAME *name; - - if (!ossl_assert(tgt != NULL)) - return 0; - if ((name = GENERAL_NAME_new()) == NULL) - goto err; - name->type = GEN_DIRNAME; - - if (src == NULL) { /* NULL-DN */ - if ((name->d.directoryName = X509_NAME_new()) == NULL) - goto err; - } else if (!X509_NAME_set(&name->d.directoryName, src)) { - goto err; - } - - GENERAL_NAME_free(*tgt); - *tgt = name; - - return 1; - - err: - GENERAL_NAME_free(name); - return 0; -} - /* * Set the sender name in PKIHeader. * when nm is NULL, sender is set to an empty string @@ -126,14 +98,14 @@ int ossl_cmp_hdr_set1_sender(OSSL_CMP_PKIHEADER *hdr, const X509_NAME *nm) { if (!ossl_assert(hdr != NULL)) return 0; - return set1_general_name(&hdr->sender, nm); + return GENERAL_NAME_set1_X509_NAME(&hdr->sender, nm); } int ossl_cmp_hdr_set1_recipient(OSSL_CMP_PKIHEADER *hdr, const X509_NAME *nm) { if (!ossl_assert(hdr != NULL)) return 0; - return set1_general_name(&hdr->recipient, nm); + return GENERAL_NAME_set1_X509_NAME(&hdr->recipient, nm); } int ossl_cmp_hdr_update_messageTime(OSSL_CMP_PKIHEADER *hdr) diff --git a/crypto/cmp/cmp_local.h b/crypto/cmp/cmp_local.h index 89f05d7536..5970803797 100644 --- a/crypto/cmp/cmp_local.h +++ b/crypto/cmp/cmp_local.h @@ -211,6 +211,36 @@ DECLARE_ASN1_FUNCTIONS(OSSL_CMP_CAKEYUPDANNCONTENT) typedef struct ossl_cmp_rootcakeyupdate_st OSSL_CMP_ROOTCAKEYUPDATE; DECLARE_ASN1_FUNCTIONS(OSSL_CMP_ROOTCAKEYUPDATE) +typedef struct ossl_cmp_certreqtemplate_st OSSL_CMP_CERTREQTEMPLATE; +DECLARE_ASN1_FUNCTIONS(OSSL_CMP_CERTREQTEMPLATE) + +/*- + * CRLSource ::= CHOICE { + * dpn [0] DistributionPointName, + * issuer [1] GeneralNames } + */ + +typedef struct ossl_cmp_crlsource_st { + int type; + union { + DIST_POINT_NAME *dpn; + GENERAL_NAMES *issuer; + } value; +} OSSL_CMP_CRLSOURCE; +DECLARE_ASN1_FUNCTIONS(OSSL_CMP_CRLSOURCE) + +/* + * CRLStatus ::= SEQUENCE { + * source CRLSource, + * thisUpdate Time OPTIONAL } + */ + +struct ossl_cmp_crlstatus_st { + OSSL_CMP_CRLSOURCE *source; + ASN1_TIME *thisUpdate; +}; /* OSSL_CMP_CRLSTATUS */ +DECLARE_ASN1_FUNCTIONS(OSSL_CMP_CRLSTATUS) + /*- * declared already here as it will be used in OSSL_CMP_MSG (nested) and * infoType and infoValue @@ -264,6 +294,13 @@ struct ossl_cmp_itav_st { X509 *rootCaCert; /* NID_id_it_rootCaKeyUpdate - Root CA Certificate Update */ OSSL_CMP_ROOTCAKEYUPDATE *rootCaKeyUpdate; + /* NID_id_it_certReqTemplate - Certificate Request Template */ + OSSL_CMP_CERTREQTEMPLATE *certReqTemplate; + /* NID_id_it_crlStatusList - CRL Update Retrieval */ + STACK_OF(OSSL_CMP_CRLSTATUS) *crlStatusList; + /* NID_id_it_crls - Certificate Status Lists */ + STACK_OF(X509_CRL) *crls; + /* this is to be used for so far undeclared objects */ ASN1_TYPE *other; } infoValue; @@ -765,6 +802,17 @@ struct ossl_cmp_rootcakeyupdate_st { } /* OSSL_CMP_ROOTCAKEYUPDATE */; DECLARE_ASN1_FUNCTIONS(OSSL_CMP_ROOTCAKEYUPDATE) +/*- + * CertReqTemplateContent ::= SEQUENCE { + * certTemplate CertTemplate, + * keySpec Controls OPTIONAL + * } + */ +struct ossl_cmp_certreqtemplate_st { + OSSL_CRMF_CERTTEMPLATE *certTemplate; + OSSL_CMP_ATAVS *keySpec; +} /* OSSL_CMP_CERTREQTEMPLATE */; + /* from cmp_asn.c */ int ossl_cmp_asn1_get_int(const ASN1_INTEGER *a); diff --git a/crypto/cmp/cmp_msg.c b/crypto/cmp/cmp_msg.c index 4ba7b81087..9628f0500a 100644 --- a/crypto/cmp/cmp_msg.c +++ b/crypto/cmp/cmp_msg.c @@ -145,34 +145,6 @@ static int add1_extension(X509_EXTENSIONS **pexts, int nid, int crit, void *ex) return res; } -/* Add extension list to the referenced extension stack, which may be NULL */ -static int add_extensions(STACK_OF(X509_EXTENSION) **target, - const STACK_OF(X509_EXTENSION) *exts) -{ - int i; - - if (target == NULL) - return 0; - - for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) { - X509_EXTENSION *ext = sk_X509_EXTENSION_value(exts, i); - ASN1_OBJECT *obj = X509_EXTENSION_get_object(ext); - int idx = X509v3_get_ext_by_OBJ(*target, obj, -1); - - /* Does extension exist in target? */ - if (idx != -1) { - /* Delete all extensions of same type */ - do { - X509_EXTENSION_free(sk_X509_EXTENSION_delete(*target, idx)); - idx = X509v3_get_ext_by_OBJ(*target, obj, -1); - } while (idx != -1); - } - if (!X509v3_add_ext(target, ext, -1)) - return 0; - } - return 1; -} - /* Add a CRL revocation reason code to extension stack, which may be NULL */ static int add_crl_reason_extension(X509_EXTENSIONS **pexts, int reason_code) { @@ -359,7 +331,7 @@ OSSL_CRMF_MSG *OSSL_CMP_CTX_setup_CRM(OSSL_CMP_CTX *ctx, int for_KUR, int rid) && !add1_extension(&exts, NID_subject_alt_name, crit, default_sans)) goto err; if (ctx->reqExtensions != NULL /* augment/override existing ones */ - && !add_extensions(&exts, ctx->reqExtensions)) + && X509v3_add_extensions(&exts, ctx->reqExtensions) == NULL) goto err; if (sk_GENERAL_NAME_num(ctx->subjectAltNames) > 0 && !add1_extension(&exts, NID_subject_alt_name, diff --git a/crypto/cmp/cmp_server.c b/crypto/cmp/cmp_server.c index 53c41bc96e..7919536955 100644 --- a/crypto/cmp/cmp_server.c +++ b/crypto/cmp/cmp_server.c @@ -1,5 +1,5 @@ /* - * Copyright 2007-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -20,8 +20,7 @@ #include /* the context for the generic CMP server */ -struct ossl_cmp_srv_ctx_st -{ +struct ossl_cmp_srv_ctx_st { OSSL_CMP_CTX *ctx; /* CMP client context reused for transactionID etc. */ void *custom_ctx; /* application-specific server context */ int certReqId; /* of ir/cr/kur, OSSL_CMP_CERTREQID_NONE for p10cr */ diff --git a/crypto/cms/cms_dh.c b/crypto/cms/cms_dh.c index c6e8c076da..9cee01793a 100644 --- a/crypto/cms/cms_dh.c +++ b/crypto/cms/cms_dh.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -123,7 +123,7 @@ static int dh_cms_set_shared_info(EVP_PKEY_CTX *pctx, CMS_RecipientInfo *ri) goto err; kekcipher = EVP_CIPHER_fetch(pctx->libctx, name, pctx->propquery); - if (kekcipher == NULL + if (kekcipher == NULL || EVP_CIPHER_get_mode(kekcipher) != EVP_CIPH_WRAP_MODE) goto err; if (!EVP_EncryptInit_ex(kekctx, kekcipher, NULL, NULL, NULL)) diff --git a/crypto/cms/cms_env.c b/crypto/cms/cms_env.c index 2d87738ee4..71059edc9a 100644 --- a/crypto/cms/cms_env.c +++ b/crypto/cms/cms_env.c @@ -1301,7 +1301,7 @@ int ossl_cms_AuthEnvelopedData_final(CMS_ContentInfo *cms, BIO *cmsbio) BIO_get_cipher_ctx(cmsbio, &ctx); - /* + /* * The tag is set only for encryption. There is nothing to do for * decryption. */ diff --git a/crypto/cms/cms_lib.c b/crypto/cms/cms_lib.c index 4ef614162a..1d7cd7e31f 100644 --- a/crypto/cms/cms_lib.c +++ b/crypto/cms/cms_lib.c @@ -622,12 +622,18 @@ STACK_OF(X509) *CMS_get1_certs(CMS_ContentInfo *cms) STACK_OF(X509) *certs = NULL; CMS_CertificateChoices *cch; STACK_OF(CMS_CertificateChoices) **pcerts; - int i; + int i, n; pcerts = cms_get0_certificate_choices(cms); if (pcerts == NULL) return NULL; - for (i = 0; i < sk_CMS_CertificateChoices_num(*pcerts); i++) { + + /* make sure to return NULL only on error */ + n = sk_CMS_CertificateChoices_num(*pcerts); + if ((certs = sk_X509_new_reserve(NULL, n)) == NULL) + return NULL; + + for (i = 0; i < n; i++) { cch = sk_CMS_CertificateChoices_value(*pcerts, i); if (cch->type == 0) { if (!ossl_x509_add_cert_new(&certs, cch->d.certificate, @@ -638,7 +644,6 @@ STACK_OF(X509) *CMS_get1_certs(CMS_ContentInfo *cms) } } return certs; - } STACK_OF(X509_CRL) *CMS_get1_crls(CMS_ContentInfo *cms) @@ -646,18 +651,20 @@ STACK_OF(X509_CRL) *CMS_get1_crls(CMS_ContentInfo *cms) STACK_OF(X509_CRL) *crls = NULL; STACK_OF(CMS_RevocationInfoChoice) **pcrls; CMS_RevocationInfoChoice *rch; - int i; + int i, n; pcrls = cms_get0_revocation_choices(cms); if (pcrls == NULL) return NULL; - for (i = 0; i < sk_CMS_RevocationInfoChoice_num(*pcrls); i++) { + + /* make sure to return NULL only on error */ + n = sk_CMS_RevocationInfoChoice_num(*pcrls); + if ((crls = sk_X509_CRL_new_reserve(NULL, n)) == NULL) + return NULL; + + for (i = 0; i < n; i++) { rch = sk_CMS_RevocationInfoChoice_value(*pcrls, i); if (rch->type == 0) { - if (crls == NULL) { - if ((crls = sk_X509_CRL_new_null()) == NULL) - return NULL; - } if (!sk_X509_CRL_push(crls, rch->d.crl) || !X509_CRL_up_ref(rch->d.crl)) { sk_X509_CRL_pop_free(crls, X509_CRL_free); diff --git a/crypto/cms/cms_rsa.c b/crypto/cms/cms_rsa.c index 31436d4d68..aefa7dd484 100644 --- a/crypto/cms/cms_rsa.c +++ b/crypto/cms/cms_rsa.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -222,7 +222,10 @@ static int rsa_cms_sign(CMS_SignerInfo *si) os = ossl_rsa_ctx_to_pss_string(pkctx); if (os == NULL) return 0; - return X509_ALGOR_set0(alg, OBJ_nid2obj(EVP_PKEY_RSA_PSS), V_ASN1_SEQUENCE, os); + if (X509_ALGOR_set0(alg, OBJ_nid2obj(EVP_PKEY_RSA_PSS), V_ASN1_SEQUENCE, os)) + return 1; + ASN1_STRING_free(os); + return 0; } params[0] = OSSL_PARAM_construct_octet_string( diff --git a/crypto/cms/cms_sd.c b/crypto/cms/cms_sd.c index 8ad94a9ed0..19c82567d1 100644 --- a/crypto/cms/cms_sd.c +++ b/crypto/cms/cms_sd.c @@ -862,7 +862,7 @@ int CMS_SignerInfo_sign(CMS_SignerInfo *si) alen = ASN1_item_i2d((ASN1_VALUE *)si->signedAttrs, &abuf, ASN1_ITEM_rptr(CMS_Attributes_Sign)); - if (!abuf) + if (alen < 0 || abuf == NULL) goto err; if (EVP_DigestSignUpdate(mctx, abuf, alen) <= 0) goto err; diff --git a/crypto/cms/cms_smime.c b/crypto/cms/cms_smime.c index 3a8b13d6ec..6b1ab927f5 100644 --- a/crypto/cms/cms_smime.c +++ b/crypto/cms/cms_smime.c @@ -15,6 +15,7 @@ #include #include "cms_local.h" #include "crypto/asn1.h" +#include "crypto/x509.h" static BIO *cms_get_text_bio(BIO *out, unsigned int flags) { @@ -308,7 +309,7 @@ int CMS_verify(CMS_ContentInfo *cms, STACK_OF(X509) *certs, { CMS_SignerInfo *si; STACK_OF(CMS_SignerInfo) *sinfos; - STACK_OF(X509) *cms_certs = NULL; + STACK_OF(X509) *untrusted = NULL; STACK_OF(X509_CRL) *crls = NULL; STACK_OF(X509) **si_chains = NULL; X509 *signer; @@ -360,13 +361,21 @@ int CMS_verify(CMS_ContentInfo *cms, STACK_OF(X509) *certs, if (si_chains == NULL) goto err; } - cms_certs = CMS_get1_certs(cms); - if (!(flags & CMS_NOCRL)) - crls = CMS_get1_crls(cms); + if ((untrusted = CMS_get1_certs(cms)) == NULL) + goto err; + if (sk_X509_num(certs) > 0 + && !ossl_x509_add_certs_new(&untrusted, certs, + X509_ADD_FLAG_UP_REF | + X509_ADD_FLAG_NO_DUP)) + goto err; + + if ((flags & CMS_NOCRL) == 0 + && (crls = CMS_get1_crls(cms)) == NULL) + goto err; for (i = 0; i < scount; i++) { si = sk_CMS_SignerInfo_value(sinfos, i); - if (!cms_signerinfo_verify_cert(si, store, cms_certs, crls, + if (!cms_signerinfo_verify_cert(si, store, untrusted, crls, si_chains ? &si_chains[i] : NULL, ctx)) goto err; @@ -482,7 +491,7 @@ int CMS_verify(CMS_ContentInfo *cms, STACK_OF(X509) *certs, OSSL_STACK_OF_X509_free(si_chains[i]); OPENSSL_free(si_chains); } - OSSL_STACK_OF_X509_free(cms_certs); + sk_X509_pop_free(untrusted, X509_free); sk_X509_CRL_pop_free(crls, X509_CRL_free); return ret; diff --git a/crypto/comp_methods.c b/crypto/comp_methods.c new file mode 100644 index 0000000000..d4f00c1a54 --- /dev/null +++ b/crypto/comp_methods.c @@ -0,0 +1,59 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include + +#include "internal/cryptlib.h" +#include "internal/comp.h" + +#define SSL_COMP_NULL_IDX 0 +#define SSL_COMP_ZLIB_IDX 1 +#define SSL_COMP_NUM_IDX 2 + +#ifndef OPENSSL_NO_COMP +static int sk_comp_cmp(const SSL_COMP *const *a, const SSL_COMP *const *b) +{ + return ((*a)->id - (*b)->id); +} +#endif + +STACK_OF(SSL_COMP) *ossl_load_builtin_compressions(void) +{ + STACK_OF(SSL_COMP) *comp_methods = NULL; +#ifndef OPENSSL_NO_COMP + SSL_COMP *comp = NULL; + COMP_METHOD *method = COMP_zlib(); + + comp_methods = sk_SSL_COMP_new(sk_comp_cmp); + + if (COMP_get_type(method) != NID_undef && comp_methods != NULL) { + comp = OPENSSL_malloc(sizeof(*comp)); + if (comp != NULL) { + comp->method = method; + comp->id = SSL_COMP_ZLIB_IDX; + comp->name = COMP_get_name(method); + if (!sk_SSL_COMP_push(comp_methods, comp)) + OPENSSL_free(comp); + } + } +#endif + return comp_methods; +} + +static void cmeth_free(SSL_COMP *cm) +{ + OPENSSL_free(cm); +} + +void ossl_free_compression_methods_int(STACK_OF(SSL_COMP) *methods) +{ + sk_SSL_COMP_pop_free(methods, cmeth_free); +} diff --git a/crypto/conf/conf_mod.c b/crypto/conf/conf_mod.c index 6d3683d76f..9d49a5f69d 100644 --- a/crypto/conf/conf_mod.c +++ b/crypto/conf/conf_mod.c @@ -110,7 +110,17 @@ DEFINE_RUN_ONCE_STATIC(do_init_module_list_lock) static int conf_diagnostics(const CONF *cnf) { - return _CONF_get_number(cnf, NULL, "config_diagnostics") != 0; + int status; + long result = 0; + + ERR_set_mark(); + status = NCONF_get_number_e(cnf, NULL, "config_diagnostics", &result); + ERR_pop_to_mark(); + if (status > 0) { + OSSL_LIB_CTX_set_conf_diagnostics(cnf->libctx, result > 0); + return result > 0; + } + return OSSL_LIB_CTX_get_conf_diagnostics(cnf->libctx); } /* Main function: load modules from a CONF structure */ @@ -183,7 +193,7 @@ int CONF_modules_load_file_ex(OSSL_LIB_CTX *libctx, const char *filename, { char *file = NULL; CONF *conf = NULL; - int ret = 0, diagnostics = 0; + int ret = 0, diagnostics = OSSL_LIB_CTX_get_conf_diagnostics(libctx); ERR_set_mark(); @@ -213,7 +223,8 @@ int CONF_modules_load_file_ex(OSSL_LIB_CTX *libctx, const char *filename, } ret = CONF_modules_load(conf, appname, flags); - diagnostics = conf_diagnostics(conf); + /* CONF_modules_load() might change the diagnostics setting, reread it. */ + diagnostics = OSSL_LIB_CTX_get_conf_diagnostics(libctx); err: if (filename == NULL) @@ -368,7 +379,6 @@ static CONF_MODULE *module_add(DSO *dso, const char *name, err: ossl_rcu_write_unlock(module_list_lock); - sk_CONF_MODULE_free(new_modules); if (tmod != NULL) { OPENSSL_free(tmod->name); OPENSSL_free(tmod); @@ -682,6 +692,18 @@ char *CONF_get1_default_config_file(void) return OPENSSL_strdup(file); t = X509_get_default_cert_area(); + /* + * On windows systems with -DOSSL_WINCTX set, if the needed registry + * keys are not yet set, openssl applets will return, due to an inability + * to locate various directories, like the default cert area. In that + * event, clone an empty string here, so that commands like openssl version + * continue to operate properly without needing to set OPENSSL_CONF. + * Applets like cms will fail gracefully later when they try to parse an + * empty config file + */ + if (t == NULL) + return OPENSSL_strdup(""); + #ifndef OPENSSL_SYS_VMS sep = "/"; #endif diff --git a/crypto/context.c b/crypto/context.c index e6edaac51f..96216abcda 100644 --- a/crypto/context.c +++ b/crypto/context.c @@ -11,6 +11,7 @@ #include #include "internal/thread_once.h" #include "internal/property.h" +#include "internal/cryptlib.h" #include "internal/core.h" #include "internal/bio.h" #include "internal/provider.h" @@ -18,7 +19,7 @@ #include "crypto/context.h" struct ossl_lib_ctx_st { - CRYPTO_RWLOCK *lock, *rand_crngt_lock; + CRYPTO_RWLOCK *lock; OSSL_EX_DATA_GLOBAL global; void *property_string_data; @@ -39,17 +40,19 @@ struct ossl_lib_ctx_st { OSSL_METHOD_STORE *encoder_store; OSSL_METHOD_STORE *store_loader_store; void *self_test_cb; + void *indicator_cb; #endif #if defined(OPENSSL_THREADS) void *threads; #endif - void *rand_crngt; #ifdef FIPS_MODULE void *thread_event_handler; void *fips_prov; #endif + STACK_OF(SSL_COMP) *comp_methods; - unsigned int ischild:1; + int ischild; + int conf_diagnostics; }; int ossl_lib_ctx_write_lock(OSSL_LIB_CTX *ctx) @@ -89,10 +92,6 @@ static int context_init(OSSL_LIB_CTX *ctx) if (ctx->lock == NULL) goto err; - ctx->rand_crngt_lock = CRYPTO_THREAD_lock_new(); - if (ctx->rand_crngt_lock == NULL) - goto err; - /* Initialize ex_data. */ if (!ossl_do_ex_data_init(ctx)) goto err; @@ -174,6 +173,9 @@ static int context_init(OSSL_LIB_CTX *ctx) ctx->self_test_cb = ossl_self_test_set_callback_new(ctx); if (ctx->self_test_cb == NULL) goto err; + ctx->indicator_cb = ossl_indicator_set_callback_new(ctx); + if (ctx->indicator_cb == NULL) + goto err; #endif #ifdef FIPS_MODULE @@ -203,6 +205,10 @@ static int context_init(OSSL_LIB_CTX *ctx) if (!ossl_property_parse_init(ctx)) goto err; +#ifndef FIPS_MODULE + ctx->comp_methods = ossl_load_builtin_compressions(); +#endif + return 1; err: @@ -211,7 +217,6 @@ static int context_init(OSSL_LIB_CTX *ctx) if (exdata_done) ossl_crypto_cleanup_all_ex_data_int(ctx); - CRYPTO_THREAD_lock_free(ctx->rand_crngt_lock); CRYPTO_THREAD_lock_free(ctx->lock); CRYPTO_THREAD_cleanup_local(&ctx->rcu_local_key); memset(ctx, '\0', sizeof(*ctx)); @@ -306,17 +311,17 @@ static void context_deinit_objs(OSSL_LIB_CTX *ctx) } #ifndef FIPS_MODULE + if (ctx->indicator_cb != NULL) { + ossl_indicator_set_callback_free(ctx->indicator_cb); + ctx->indicator_cb = NULL; + } + if (ctx->self_test_cb != NULL) { ossl_self_test_set_callback_free(ctx->self_test_cb); ctx->self_test_cb = NULL; } #endif - if (ctx->rand_crngt != NULL) { - ossl_rand_crng_ctx_free(ctx->rand_crngt); - ctx->rand_crngt = NULL; - } - #ifdef FIPS_MODULE if (ctx->thread_event_handler != NULL) { ossl_thread_event_ctx_free(ctx->thread_event_handler); @@ -343,6 +348,14 @@ static void context_deinit_objs(OSSL_LIB_CTX *ctx) ctx->child_provider = NULL; } #endif + +#ifndef FIPS_MODULE + if (ctx->comp_methods != NULL) { + ossl_free_compression_methods_int(ctx->comp_methods); + ctx->comp_methods = NULL; + } +#endif + } static int context_deinit(OSSL_LIB_CTX *ctx) @@ -356,9 +369,7 @@ static int context_deinit(OSSL_LIB_CTX *ctx) ossl_crypto_cleanup_all_ex_data_int(ctx); - CRYPTO_THREAD_lock_free(ctx->rand_crngt_lock); CRYPTO_THREAD_lock_free(ctx->lock); - ctx->rand_crngt_lock = NULL; ctx->lock = NULL; CRYPTO_THREAD_cleanup_local(&ctx->rcu_local_key); return 1; @@ -549,8 +560,6 @@ int ossl_lib_ctx_is_global_default(OSSL_LIB_CTX *ctx) void *ossl_lib_ctx_get_data(OSSL_LIB_CTX *ctx, int index) { - void *p; - ctx = ossl_lib_ctx_get_concrete(ctx); if (ctx == NULL) return NULL; @@ -589,42 +598,14 @@ void *ossl_lib_ctx_get_data(OSSL_LIB_CTX *ctx, int index) return ctx->store_loader_store; case OSSL_LIB_CTX_SELF_TEST_CB_INDEX: return ctx->self_test_cb; + case OSSL_LIB_CTX_INDICATOR_CB_INDEX: + return ctx->indicator_cb; #endif #ifndef OPENSSL_NO_THREAD_POOL case OSSL_LIB_CTX_THREAD_INDEX: return ctx->threads; #endif - case OSSL_LIB_CTX_RAND_CRNGT_INDEX: { - - /* - * rand_crngt must be lazily initialized because it calls into - * libctx, so must not be called from context_init, else a deadlock - * will occur. - * - * We use a separate lock because code called by the instantiation - * of rand_crngt is liable to try and take the libctx lock. - */ - if (CRYPTO_THREAD_read_lock(ctx->rand_crngt_lock) != 1) - return NULL; - - if (ctx->rand_crngt == NULL) { - CRYPTO_THREAD_unlock(ctx->rand_crngt_lock); - - if (CRYPTO_THREAD_write_lock(ctx->rand_crngt_lock) != 1) - return NULL; - - if (ctx->rand_crngt == NULL) - ctx->rand_crngt = ossl_rand_crng_ctx_new(ctx); - } - - p = ctx->rand_crngt; - - CRYPTO_THREAD_unlock(ctx->rand_crngt_lock); - - return p; - } - #ifdef FIPS_MODULE case OSSL_LIB_CTX_THREAD_EVENT_HANDLER_INDEX: return ctx->thread_event_handler; @@ -633,11 +614,19 @@ void *ossl_lib_ctx_get_data(OSSL_LIB_CTX *ctx, int index) return ctx->fips_prov; #endif + case OSSL_LIB_CTX_COMP_METHODS: + return (void *)&ctx->comp_methods; + default: return NULL; } } +void *OSSL_LIB_CTX_get_data(OSSL_LIB_CTX *ctx, int index) +{ + return ossl_lib_ctx_get_data(ctx, index); +} + OSSL_EX_DATA_GLOBAL *ossl_lib_ctx_get_ex_data_global(OSSL_LIB_CTX *ctx) { ctx = ossl_lib_ctx_get_concrete(ctx); @@ -666,3 +655,19 @@ CRYPTO_THREAD_LOCAL *ossl_lib_ctx_get_rcukey(OSSL_LIB_CTX *libctx) return NULL; return &libctx->rcu_local_key; } + +int OSSL_LIB_CTX_get_conf_diagnostics(OSSL_LIB_CTX *libctx) +{ + libctx = ossl_lib_ctx_get_concrete(libctx); + if (libctx == NULL) + return 0; + return libctx->conf_diagnostics; +} + +void OSSL_LIB_CTX_set_conf_diagnostics(OSSL_LIB_CTX *libctx, int value) +{ + libctx = ossl_lib_ctx_get_concrete(libctx); + if (libctx == NULL) + return; + libctx->conf_diagnostics = value; +} diff --git a/crypto/core_namemap.c b/crypto/core_namemap.c index 1dcf390fc2..ead9a38ad7 100644 --- a/crypto/core_namemap.c +++ b/crypto/core_namemap.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -8,62 +8,55 @@ */ #include "internal/namemap.h" -#include -#include "crypto/lhash.h" /* ossl_lh_strcasehash */ #include "internal/tsan_assist.h" +#include "internal/hashtable.h" #include "internal/sizes.h" #include "crypto/context.h" -/*- - * The namenum entry - * ================= - */ -typedef struct { - char *name; - int number; -} NAMENUM_ENTRY; +#define NAMEMAP_HT_BUCKETS 2048 -DEFINE_LHASH_OF_EX(NAMENUM_ENTRY); +HT_START_KEY_DEFN(namenum_key) +HT_DEF_KEY_FIELD_CHAR_ARRAY(name, 64) +HT_END_KEY_DEFN(NAMENUM_KEY) /*- * The namemap itself * ================== */ +typedef char STRING; +typedef STACK_OF(STRING) NAMES; + +DEFINE_STACK_OF(STRING) +DEFINE_STACK_OF(NAMES) + struct ossl_namemap_st { /* Flags */ unsigned int stored:1; /* If 1, it's stored in a library context */ + HT *namenum_ht; /* Name->number mapping */ + CRYPTO_RWLOCK *lock; - LHASH_OF(NAMENUM_ENTRY) *namenum; /* Name->number mapping */ + STACK_OF(NAMES) *numnames; TSAN_QUALIFIER int max_number; /* Current max number */ }; -/* LHASH callbacks */ - -static unsigned long namenum_hash(const NAMENUM_ENTRY *n) +static void name_string_free(char *name) { - return ossl_lh_strcasehash(n->name); + OPENSSL_free(name); } -static int namenum_cmp(const NAMENUM_ENTRY *a, const NAMENUM_ENTRY *b) +static void names_free(NAMES *n) { - return OPENSSL_strcasecmp(a->name, b->name); -} - -static void namenum_free(NAMENUM_ENTRY *n) -{ - if (n != NULL) - OPENSSL_free(n->name); - OPENSSL_free(n); + sk_STRING_pop_free(n, name_string_free); } /* OSSL_LIB_CTX_METHOD functions for a namemap stored in a library context */ void *ossl_stored_namemap_new(OSSL_LIB_CTX *libctx) { - OSSL_NAMEMAP *namemap = ossl_namemap_new(); + OSSL_NAMEMAP *namemap = ossl_namemap_new(libctx); if (namemap != NULL) namemap->stored = 1; @@ -107,20 +100,6 @@ int ossl_namemap_empty(OSSL_NAMEMAP *namemap) #endif } -typedef struct doall_names_data_st { - int number; - const char **names; - int found; -} DOALL_NAMES_DATA; - -static void do_name(const NAMENUM_ENTRY *namenum, DOALL_NAMES_DATA *data) -{ - if (namenum->number == data->number) - data->names[data->found++] = namenum->name; -} - -IMPLEMENT_LHASH_DOALL_ARG_CONST(NAMENUM_ENTRY, DOALL_NAMES_DATA); - /* * Call the callback for all names in the namemap with the given number. * A return value 1 means that the callback was called for all names. A @@ -130,61 +109,41 @@ int ossl_namemap_doall_names(const OSSL_NAMEMAP *namemap, int number, void (*fn)(const char *name, void *data), void *data) { - DOALL_NAMES_DATA cbdata; - size_t num_names; int i; + NAMES *names; - cbdata.number = number; - cbdata.found = 0; - - if (namemap == NULL) + if (namemap == NULL || number <= 0) return 0; /* - * We collect all the names first under a read lock. Subsequently we call + * We duplicate the NAMES stack under a read lock. Subsequently we call * the user function, so that we're not holding the read lock when in user * code. This could lead to deadlocks. */ if (!CRYPTO_THREAD_read_lock(namemap->lock)) return 0; - num_names = lh_NAMENUM_ENTRY_num_items(namemap->namenum); - if (num_names == 0) { - CRYPTO_THREAD_unlock(namemap->lock); - return 0; - } - cbdata.names = OPENSSL_malloc(sizeof(*cbdata.names) * num_names); - if (cbdata.names == NULL) { - CRYPTO_THREAD_unlock(namemap->lock); - return 0; - } - lh_NAMENUM_ENTRY_doall_DOALL_NAMES_DATA(namemap->namenum, do_name, - &cbdata); - CRYPTO_THREAD_unlock(namemap->lock); + names = sk_NAMES_value(namemap->numnames, number - 1); + if (names != NULL) + names = sk_STRING_dup(names); - for (i = 0; i < cbdata.found; i++) - fn(cbdata.names[i], data); + CRYPTO_THREAD_unlock(namemap->lock); - OPENSSL_free(cbdata.names); - return 1; -} + if (names == NULL) + return 0; -/* This function is not thread safe, the namemap must be locked */ -static int namemap_name2num(const OSSL_NAMEMAP *namemap, - const char *name) -{ - NAMENUM_ENTRY *namenum_entry, namenum_tmpl; + for (i = 0; i < sk_STRING_num(names); i++) + fn(sk_STRING_value(names, i), data); - namenum_tmpl.name = (char *)name; - namenum_tmpl.number = 0; - namenum_entry = - lh_NAMENUM_ENTRY_retrieve(namemap->namenum, &namenum_tmpl); - return namenum_entry != NULL ? namenum_entry->number : 0; + sk_STRING_free(names); + return i > 0; } int ossl_namemap_name2num(const OSSL_NAMEMAP *namemap, const char *name) { - int number; + int number = 0; + HT_VALUE *val; + NAMENUM_KEY key; #ifndef FIPS_MODULE if (namemap == NULL) @@ -194,14 +153,19 @@ int ossl_namemap_name2num(const OSSL_NAMEMAP *namemap, const char *name) if (namemap == NULL) return 0; - if (!CRYPTO_THREAD_read_lock(namemap->lock)) - return 0; - number = namemap_name2num(namemap, name); - CRYPTO_THREAD_unlock(namemap->lock); + HT_INIT_KEY(&key); + HT_SET_KEY_STRING_CASE(&key, name, name); + + val = ossl_ht_get(namemap->namenum_ht, TO_HT_KEY(&key)); + + if (val != NULL) + /* We store a (small) int directly instead of a pointer to it. */ + number = (int)(intptr_t)val->value; return number; } +/* TODO: Optimize to avoid strndup() */ int ossl_namemap_name2num_n(const OSSL_NAMEMAP *namemap, const char *name, size_t name_len) { @@ -216,62 +180,97 @@ int ossl_namemap_name2num_n(const OSSL_NAMEMAP *namemap, return ret; } -struct num2name_data_st { - size_t idx; /* Countdown */ - const char *name; /* Result */ -}; - -static void do_num2name(const char *name, void *vdata) +const char *ossl_namemap_num2name(const OSSL_NAMEMAP *namemap, int number, + size_t idx) { - struct num2name_data_st *data = vdata; + NAMES *names; + const char *ret = NULL; + + if (namemap == NULL || number <= 0) + return NULL; - if (data->idx > 0) - data->idx--; - else if (data->name == NULL) - data->name = name; + if (!CRYPTO_THREAD_read_lock(namemap->lock)) + return NULL; + + names = sk_NAMES_value(namemap->numnames, number - 1); + if (names != NULL) + ret = sk_STRING_value(names, idx); + + CRYPTO_THREAD_unlock(namemap->lock); + + return ret; } -const char *ossl_namemap_num2name(const OSSL_NAMEMAP *namemap, int number, - size_t idx) +/* This function is not thread safe, the namemap must be locked */ +static int numname_insert(OSSL_NAMEMAP *namemap, int number, + const char *name) { - struct num2name_data_st data; + NAMES *names; + char *tmpname; + + if (number > 0) { + names = sk_NAMES_value(namemap->numnames, number - 1); + if (!ossl_assert(names != NULL)) { + /* cannot happen */ + return 0; + } + } else { + /* a completely new entry */ + names = sk_STRING_new_null(); + if (names == NULL) + return 0; + } - data.idx = idx; - data.name = NULL; - if (!ossl_namemap_doall_names(namemap, number, do_num2name, &data)) - return NULL; - return data.name; + if ((tmpname = OPENSSL_strdup(name)) == NULL) + goto err; + + if (!sk_STRING_push(names, tmpname)) + goto err; + + if (number <= 0) { + if (!sk_NAMES_push(namemap->numnames, names)) + goto err; + number = sk_NAMES_num(namemap->numnames); + } + return number; + + err: + if (number <= 0) + sk_STRING_free(names); + OPENSSL_free(tmpname); + return 0; } /* This function is not thread safe, the namemap must be locked */ static int namemap_add_name(OSSL_NAMEMAP *namemap, int number, const char *name) { - NAMENUM_ENTRY *namenum = NULL; - int tmp_number; + int ret; + HT_VALUE val = { 0 }; + NAMENUM_KEY key; /* If it already exists, we don't add it */ - if ((tmp_number = namemap_name2num(namemap, name)) != 0) - return tmp_number; + if ((ret = ossl_namemap_name2num(namemap, name)) != 0) + return ret; - if ((namenum = OPENSSL_zalloc(sizeof(*namenum))) == NULL) + if ((number = numname_insert(namemap, number, name)) == 0) return 0; - if ((namenum->name = OPENSSL_strdup(name)) == NULL) - goto err; - - /* The tsan_counter use here is safe since we're under lock */ - namenum->number = - number != 0 ? number : 1 + tsan_counter(&namemap->max_number); - (void)lh_NAMENUM_ENTRY_insert(namemap->namenum, namenum); - - if (lh_NAMENUM_ENTRY_error(namemap->namenum)) - goto err; - return namenum->number; + /* Using tsan_store alone here is safe since we're under lock */ + tsan_store(&namemap->max_number, number); - err: - namenum_free(namenum); - return 0; + HT_INIT_KEY(&key); + HT_SET_KEY_STRING_CASE(&key, name, name); + val.value = (void *)(intptr_t)number; + ret = ossl_ht_insert(namemap->namenum_ht, TO_HT_KEY(&key), &val, NULL); + if (!ossl_assert(ret != 0)) /* cannot happen as we are under write lock */ + return 0; + if (ret < 1) { + /* unable to insert due to too many collisions */ + ERR_raise(ERR_LIB_CRYPTO, CRYPTO_R_TOO_MANY_NAMES); + return 0; + } + return number; } int ossl_namemap_add_name(OSSL_NAMEMAP *namemap, int number, @@ -334,7 +333,7 @@ int ossl_namemap_add_names(OSSL_NAMEMAP *namemap, int number, goto end; } - this_number = namemap_name2num(namemap, p); + this_number = ossl_namemap_name2num(namemap, p); if (number == 0) { number = this_number; @@ -508,16 +507,28 @@ OSSL_NAMEMAP *ossl_namemap_stored(OSSL_LIB_CTX *libctx) return namemap; } -OSSL_NAMEMAP *ossl_namemap_new(void) +OSSL_NAMEMAP *ossl_namemap_new(OSSL_LIB_CTX *libctx) { OSSL_NAMEMAP *namemap; + HT_CONFIG htconf = { NULL, NULL, NULL, NAMEMAP_HT_BUCKETS, 1, 1 }; - if ((namemap = OPENSSL_zalloc(sizeof(*namemap))) != NULL - && (namemap->lock = CRYPTO_THREAD_lock_new()) != NULL - && (namemap->namenum = - lh_NAMENUM_ENTRY_new(namenum_hash, namenum_cmp)) != NULL) - return namemap; + htconf.ctx = libctx; + + if ((namemap = OPENSSL_zalloc(sizeof(*namemap))) == NULL) + goto err; + if ((namemap->lock = CRYPTO_THREAD_lock_new()) == NULL) + goto err; + + if ((namemap->namenum_ht = ossl_ht_new(&htconf)) == NULL) + goto err; + + if ((namemap->numnames = sk_NAMES_new_null()) == NULL) + goto err; + + return namemap; + + err: ossl_namemap_free(namemap); return NULL; } @@ -527,8 +538,9 @@ void ossl_namemap_free(OSSL_NAMEMAP *namemap) if (namemap == NULL || namemap->stored) return; - lh_NAMENUM_ENTRY_doall(namemap->namenum, namenum_free); - lh_NAMENUM_ENTRY_free(namemap->namenum); + sk_NAMES_pop_free(namemap->numnames, names_free); + + ossl_ht_free(namemap->namenum_ht); CRYPTO_THREAD_lock_free(namemap->lock); OPENSSL_free(namemap); diff --git a/crypto/cpt_err.c b/crypto/cpt_err.c index 02d631466c..bbcad8e51d 100644 --- a/crypto/cpt_err.c +++ b/crypto/cpt_err.c @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -65,6 +65,7 @@ static const ERR_STRING_DATA CRYPTO_str_reasons[] = { "secure malloc failure"}, {ERR_PACK(ERR_LIB_CRYPTO, 0, CRYPTO_R_STRING_TOO_LONG), "string too long"}, {ERR_PACK(ERR_LIB_CRYPTO, 0, CRYPTO_R_TOO_MANY_BYTES), "too many bytes"}, + {ERR_PACK(ERR_LIB_CRYPTO, 0, CRYPTO_R_TOO_MANY_NAMES), "too many names"}, {ERR_PACK(ERR_LIB_CRYPTO, 0, CRYPTO_R_TOO_MANY_RECORDS), "too many records"}, {ERR_PACK(ERR_LIB_CRYPTO, 0, CRYPTO_R_TOO_SMALL_BUFFER), diff --git a/crypto/crmf/crmf_asn.c b/crypto/crmf/crmf_asn.c index 85b4213934..c3dbc84e78 100644 --- a/crypto/crmf/crmf_asn.c +++ b/crypto/crmf/crmf_asn.c @@ -1,5 +1,5 @@ /*- - * Copyright 2007-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -146,6 +146,12 @@ ASN1_ADB(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) = { ADB_ENTRY(NID_id_regCtrl_protocolEncrKey, ASN1_SIMPLE(OSSL_CRMF_ATTRIBUTETYPEANDVALUE, value.protocolEncrKey, X509_PUBKEY)), + ADB_ENTRY(NID_id_regCtrl_algId, + ASN1_SIMPLE(OSSL_CRMF_ATTRIBUTETYPEANDVALUE, + value.algId, X509_ALGOR)), + ADB_ENTRY(NID_id_regCtrl_rsaKeyLen, + ASN1_SIMPLE(OSSL_CRMF_ATTRIBUTETYPEANDVALUE, + value.rsaKeyLen, ASN1_INTEGER)), ADB_ENTRY(NID_id_regInfo_utf8Pairs, ASN1_SIMPLE(OSSL_CRMF_ATTRIBUTETYPEANDVALUE, value.utf8Pairs, ASN1_UTF8STRING)), @@ -194,6 +200,7 @@ ASN1_SEQUENCE(OSSL_CRMF_CERTTEMPLATE) = { X509_EXTENSION, 9), } ASN1_SEQUENCE_END(OSSL_CRMF_CERTTEMPLATE) IMPLEMENT_ASN1_FUNCTIONS(OSSL_CRMF_CERTTEMPLATE) +IMPLEMENT_ASN1_DUP_FUNCTION(OSSL_CRMF_CERTTEMPLATE) ASN1_SEQUENCE(OSSL_CRMF_CERTREQUEST) = { ASN1_SIMPLE(OSSL_CRMF_CERTREQUEST, certReqId, ASN1_INTEGER), diff --git a/crypto/crmf/crmf_local.h b/crypto/crmf/crmf_local.h index e8937b4231..0b1b7964aa 100644 --- a/crypto/crmf/crmf_local.h +++ b/crypto/crmf/crmf_local.h @@ -1,5 +1,5 @@ /*- - * Copyright 2007-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -16,6 +16,7 @@ # include # include +# include "internal/crmf.h" /* for ossl_crmf_attributetypeandvalue_st */ /* explicit #includes not strictly needed since implied by the above: */ # include @@ -335,37 +336,6 @@ struct ossl_crmf_certrequest_st { DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_CERTREQUEST) DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_CERTREQUEST) -struct ossl_crmf_attributetypeandvalue_st { - ASN1_OBJECT *type; - union { - /* NID_id_regCtrl_regToken */ - ASN1_UTF8STRING *regToken; - - /* NID_id_regCtrl_authenticator */ - ASN1_UTF8STRING *authenticator; - - /* NID_id_regCtrl_pkiPublicationInfo */ - OSSL_CRMF_PKIPUBLICATIONINFO *pkiPublicationInfo; - - /* NID_id_regCtrl_oldCertID */ - OSSL_CRMF_CERTID *oldCertID; - - /* NID_id_regCtrl_protocolEncrKey */ - X509_PUBKEY *protocolEncrKey; - - /* NID_id_regInfo_utf8Pairs */ - ASN1_UTF8STRING *utf8Pairs; - - /* NID_id_regInfo_certReq */ - OSSL_CRMF_CERTREQUEST *certReq; - - ASN1_TYPE *other; - } value; -} /* OSSL_CRMF_ATTRIBUTETYPEANDVALUE */; -DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) -DEFINE_STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) -DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) - /*- * CertReqMessages ::= SEQUENCE SIZE (1..MAX) OF CertReqMsg * CertReqMsg ::= SEQUENCE { diff --git a/crypto/cversion.c b/crypto/cversion.c index 530b0e805e..87154645b0 100644 --- a/crypto/cversion.c +++ b/crypto/cversion.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2016 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -7,7 +7,12 @@ * https://www.openssl.org/source/license.html */ +#include +#include +#include "internal/e_os.h" #include "internal/cryptlib.h" +#include "internal/common.h" +#include "internal/thread_once.h" #include "buildinf.h" @@ -43,8 +48,41 @@ const char *OPENSSL_version_build_metadata(void) extern char ossl_cpu_info_str[]; +#if defined(_WIN32) && defined(OSSL_WINCTX) +/* size: MAX_PATH + sizeof("OPENSSLDIR: \"\"") */ +static char openssldir[MAX_PATH + 15]; + +/* size: MAX_PATH + sizeof("ENGINESDIR: \"\"") */ +static char enginesdir[MAX_PATH + 15]; + +/* size: MAX_PATH + sizeof("MODULESDIR: \"\"") */ +static char modulesdir[MAX_PATH + 15]; + +static CRYPTO_ONCE version_strings_once = CRYPTO_ONCE_STATIC_INIT; + +DEFINE_RUN_ONCE_STATIC(version_strings_setup) +{ + BIO_snprintf(openssldir, sizeof(openssldir), "OPENSSLDIR: \"%s\"", + ossl_get_openssldir()); + BIO_snprintf(enginesdir, sizeof(enginesdir), "ENGINESDIR: \"%s\"", + ossl_get_enginesdir()); + BIO_snprintf(modulesdir, sizeof(modulesdir), "MODULESDIR: \"%s\"", + ossl_get_modulesdir()); + return 1; +} + +# define TOSTR(x) #x +# define OSSL_WINCTX_STRING "OSSL_WINCTX: \"" ## TOSTR(OSSL_WINCTX) ## "\"" + +#endif + const char *OpenSSL_version(int t) { +#if defined(_WIN32) && defined(OSSL_WINCTX) + /* Cannot really fail but we would return empty strings anyway */ + (void)RUN_ONCE(&version_strings_once, version_strings_setup); +#endif + switch (t) { case OPENSSL_VERSION: return OPENSSL_VERSION_TEXT; @@ -58,29 +96,44 @@ const char *OpenSSL_version(int t) return compiler_flags; case OPENSSL_PLATFORM: return PLATFORM; +#if defined(_WIN32) && defined(OSSL_WINCTX) case OPENSSL_DIR: -#ifdef OPENSSLDIR - return "OPENSSLDIR: \"" OPENSSLDIR "\""; + return openssldir; + case OPENSSL_ENGINES_DIR: + return enginesdir; + case OPENSSL_MODULES_DIR: + return modulesdir; #else + case OPENSSL_DIR: +# ifdef OPENSSLDIR + return "OPENSSLDIR: \"" OPENSSLDIR "\""; +# else return "OPENSSLDIR: N/A"; -#endif +# endif case OPENSSL_ENGINES_DIR: -#ifdef ENGINESDIR +# ifdef ENGINESDIR return "ENGINESDIR: \"" ENGINESDIR "\""; -#else +# else return "ENGINESDIR: N/A"; -#endif +# endif case OPENSSL_MODULES_DIR: -#ifdef MODULESDIR +# ifdef MODULESDIR return "MODULESDIR: \"" MODULESDIR "\""; -#else +# else return "MODULESDIR: N/A"; +# endif #endif case OPENSSL_CPU_INFO: if (OPENSSL_info(OPENSSL_INFO_CPU_SETTINGS) != NULL) return ossl_cpu_info_str; else return "CPUINFO: N/A"; + case OPENSSL_WINCTX: +#if defined(_WIN32) && defined(OSSL_WINCTX) + return OSSL_WINCTX_STRING; +#else + return "OSSL_WINCTX: Undefined"; +#endif } return "not available"; } diff --git a/crypto/defaults.c b/crypto/defaults.c new file mode 100644 index 0000000000..908539cf31 --- /dev/null +++ b/crypto/defaults.c @@ -0,0 +1,200 @@ +/* + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include "internal/thread_once.h" +#include "internal/cryptlib.h" +#include "internal/e_os.h" + +#if defined(_WIN32) && defined(OSSL_WINCTX) + +# define TOSTR(x) #x +# define MAKESTR(x) TOSTR(x) +# define NOQUOTE(x) x +# if defined(OSSL_WINCTX) +# define REGISTRY_KEY "SOFTWARE\\WOW6432Node\\OpenSSL" ##"-"## MAKESTR(OPENSSL_VERSION_MAJOR) ##"."## MAKESTR(OPENSSL_VERSION_MINOR) ##"-"## MAKESTR(OSSL_WINCTX) +# endif + +/** + * @brief The directory where OpenSSL is installed. + */ +static char openssldir[MAX_PATH + 1]; + +/** + * @brief The pointer to the openssldir buffer + */ +static char *openssldirptr = NULL; + +/** + * @brief The directory where OpenSSL engines are located. + */ + +static char enginesdir[MAX_PATH + 1]; + +/** + * @brief The pointer to the enginesdir buffer + */ +static char *enginesdirptr = NULL; + +/** + * @brief The directory where OpenSSL modules are located. + */ +static char modulesdir[MAX_PATH + 1]; + +/** + * @brief The pointer to the modulesdir buffer + */ +static char *modulesdirptr = NULL; + +/** + * @brief Get the list of Windows registry directories. + * + * This function retrieves a list of Windows registry directories. + * + * @return A pointer to a char array containing the registry directories. + */ +static char *get_windows_regdirs(char *dst, LPCTSTR valuename) +{ + char *retval = NULL; +# ifdef REGISTRY_KEY + DWORD keysize; + DWORD ktype; + HKEY hkey; + LSTATUS ret; + DWORD index = 0; + LPCTCH tempstr = NULL; + + ret = RegOpenKeyEx(HKEY_LOCAL_MACHINE, + TEXT(REGISTRY_KEY), KEY_WOW64_32KEY, + KEY_QUERY_VALUE, &hkey); + if (ret != ERROR_SUCCESS) + goto out; + + ret = RegQueryValueEx(hkey, valuename, NULL, &ktype, NULL, + &keysize); + if (ret != ERROR_SUCCESS) + goto out; + if (ktype != REG_EXPAND_SZ) + goto out; + if (keysize > MAX_PATH) + goto out; + + keysize++; + tempstr = OPENSSL_zalloc(keysize * sizeof(TCHAR)); + + if (tempstr == NULL) + goto out; + + if (RegQueryValueEx(hkey, valuename, + NULL, &ktype, tempstr, &keysize) != ERROR_SUCCESS) + goto out; + + if (!WideCharToMultiByte(CP_UTF8, 0, tempstr, -1, dst, keysize, + NULL, NULL)) + goto out; + + retval = dst; +out: + OPENSSL_free(tempstr); + RegCloseKey(hkey); +# endif /* REGISTRY_KEY */ + return retval; +} + +static CRYPTO_ONCE defaults_setup_init = CRYPTO_ONCE_STATIC_INIT; + +/** + * @brief Function to setup default values to run once. + * Only used in Windows environments. Does run time initialization + * of openssldir/modulesdir/enginesdir from the registry + */ +DEFINE_RUN_ONCE_STATIC(do_defaults_setup) +{ + get_windows_regdirs(openssldir, TEXT("OPENSSLDIR")); + get_windows_regdirs(enginesdir, TEXT("ENGINESDIR")); + get_windows_regdirs(modulesdir, TEXT("MODULESDIR")); + + /* + * Set our pointers only if the directories are fetched properly + */ + if (strlen(openssldir) > 0) + openssldirptr = openssldir; + + if (strlen(enginesdir) > 0) + enginesdirptr = enginesdir; + + if (strlen(modulesdir) > 0) + modulesdirptr = modulesdir; + + return 1; +} +#endif /* defined(_WIN32) && defined(OSSL_WINCTX) */ + +/** + * @brief Get the directory where OpenSSL is installed. + * + * @return A pointer to a string containing the OpenSSL directory path. + */ +const char *ossl_get_openssldir(void) +{ +#if defined(_WIN32) && defined (OSSL_WINCTX) + if (!RUN_ONCE(&defaults_setup_init, do_defaults_setup)) + return NULL; + return (const char *)openssldirptr; +# else + return OPENSSLDIR; +#endif +} + +/** + * @brief Get the directory where OpenSSL engines are located. + * + * @return A pointer to a string containing the engines directory path. + */ +const char *ossl_get_enginesdir(void) +{ +#if defined(_WIN32) && defined (OSSL_WINCTX) + if (!RUN_ONCE(&defaults_setup_init, do_defaults_setup)) + return NULL; + return (const char *)enginesdirptr; +#else + return ENGINESDIR; +#endif +} + +/** + * @brief Get the directory where OpenSSL modules are located. + * + * @return A pointer to a string containing the modules directory path. + */ +const char *ossl_get_modulesdir(void) +{ +#if defined(_WIN32) && defined(OSSL_WINCTX) + if (!RUN_ONCE(&defaults_setup_init, do_defaults_setup)) + return NULL; + return (const char *)modulesdirptr; +#else + return MODULESDIR; +#endif +} + +/** + * @brief Get the build time defined windows installer context + * + * @return A char pointer to a string representing the windows install context + */ +const char *ossl_get_wininstallcontext(void) +{ +#if defined(_WIN32) && defined (OSSL_WINCTX) + return MAKESTR(OSSL_WINCTX); +#else + return "Undefined"; +#endif +} diff --git a/crypto/des/set_key.c b/crypto/des/set_key.c index 068fb9133b..5c958cdbb6 100644 --- a/crypto/des/set_key.c +++ b/crypto/des/set_key.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -324,8 +324,9 @@ int DES_set_key_checked(const_DES_cblock *key, DES_key_schedule *schedule) void DES_set_key_unchecked(const_DES_cblock *key, DES_key_schedule *schedule) { - static const int shifts2[16] = - { 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0 }; + static const int shifts2[16] = { + 0, 0, 1, 1, 1, 1, 1, 1, 0, 1, 1, 1, 1, 1, 1, 0 + }; register DES_LONG c, d, t, s, t2; register const unsigned char *in; register DES_LONG *k; diff --git a/crypto/dsa/dsa_ameth.c b/crypto/dsa/dsa_ameth.c index 15a5266ca4..169c1bb677 100644 --- a/crypto/dsa/dsa_ameth.c +++ b/crypto/dsa/dsa_ameth.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -516,26 +516,24 @@ static int dsa_pkey_copy(EVP_PKEY *to, EVP_PKEY *from) /* NB these are sorted in pkey_id order, lowest first */ -const EVP_PKEY_ASN1_METHOD ossl_dsa_asn1_meths[5] = { - - { - EVP_PKEY_DSA2, - EVP_PKEY_DSA, - ASN1_PKEY_ALIAS}, +const EVP_PKEY_ASN1_METHOD ossl_dsa_asn1_meths[4] = { + /* This aliases NID_dsa with NID_dsa_2 */ { EVP_PKEY_DSA1, EVP_PKEY_DSA, ASN1_PKEY_ALIAS}, + /* This aliases NID_dsaWithSHA with NID_dsaWithSHA_2 */ { EVP_PKEY_DSA4, - EVP_PKEY_DSA, + EVP_PKEY_DSA2, ASN1_PKEY_ALIAS}, + /* This aliases NID_dsaWithSHA with NID_dsaWithSHA1 */ { EVP_PKEY_DSA3, - EVP_PKEY_DSA, + EVP_PKEY_DSA2, ASN1_PKEY_ALIAS}, { diff --git a/crypto/dsa/dsa_pmeth.c b/crypto/dsa/dsa_pmeth.c index ba6be720a2..00ac18fdff 100644 --- a/crypto/dsa/dsa_pmeth.c +++ b/crypto/dsa/dsa_pmeth.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -78,7 +78,7 @@ static int pkey_dsa_sign(EVP_PKEY_CTX *ctx, unsigned char *sig, size_t *siglen, const unsigned char *tbs, size_t tbslen) { - int ret; + int ret, md_size; unsigned int sltmp; DSA_PKEY_CTX *dctx = ctx->data; /* @@ -88,8 +88,13 @@ static int pkey_dsa_sign(EVP_PKEY_CTX *ctx, unsigned char *sig, */ DSA *dsa = (DSA *)EVP_PKEY_get0_DSA(ctx->pkey); - if (dctx->md != NULL && tbslen != (size_t)EVP_MD_get_size(dctx->md)) - return 0; + if (dctx->md != NULL) { + md_size = EVP_MD_get_size(dctx->md); + if (md_size <= 0) + return 0; + if (tbslen != (size_t)md_size) + return 0; + } ret = DSA_sign(0, tbs, tbslen, sig, &sltmp, dsa); @@ -103,7 +108,7 @@ static int pkey_dsa_verify(EVP_PKEY_CTX *ctx, const unsigned char *sig, size_t siglen, const unsigned char *tbs, size_t tbslen) { - int ret; + int ret, md_size; DSA_PKEY_CTX *dctx = ctx->data; /* * Discard const. Its marked as const because this may be a cached copy of @@ -112,8 +117,13 @@ static int pkey_dsa_verify(EVP_PKEY_CTX *ctx, */ DSA *dsa = (DSA *)EVP_PKEY_get0_DSA(ctx->pkey); - if (dctx->md != NULL && tbslen != (size_t)EVP_MD_get_size(dctx->md)) - return 0; + if (dctx->md != NULL) { + md_size = EVP_MD_get_size(dctx->md); + if (md_size <= 0) + return 0; + if (tbslen != (size_t)md_size) + return 0; + } ret = DSA_verify(0, tbs, tbslen, sig, siglen, dsa); diff --git a/crypto/dso/dso_dl.c b/crypto/dso/dso_dl.c index 4515239111..7bfb02093b 100644 --- a/crypto/dso/dso_dl.c +++ b/crypto/dso/dso_dl.c @@ -229,13 +229,12 @@ static char *dl_name_converter(DSO *dso, const char *filename) ERR_raise(ERR_LIB_DSO, DSO_R_NAME_TRANSLATION_FAILED); return NULL; } - if (transform) { - if ((DSO_flags(dso) & DSO_FLAG_NAME_TRANSLATION_EXT_ONLY) == 0) - sprintf(translated, "lib%s%s", filename, DSO_EXTENSION); - else - sprintf(translated, "%s%s", filename, DSO_EXTENSION); - } else - sprintf(translated, "%s", filename); + if (transform) + BIO_snprintf(translated, rsize, + (DSO_flags(dso) & DSO_FLAG_NAME_TRANSLATION_EXT_ONLY) == 0 + ? "lib%s%s" : "%s%s", filename, DSO_EXTENSION); + else + BIO_snprintf(translated, rsize, "%s", filename); return translated; } diff --git a/crypto/dso/dso_dlfcn.c b/crypto/dso/dso_dlfcn.c index 76737fa7b8..b5a7b7be2c 100644 --- a/crypto/dso/dso_dlfcn.c +++ b/crypto/dso/dso_dlfcn.c @@ -265,11 +265,12 @@ static char *dlfcn_name_converter(DSO *dso, const char *filename) } if (transform) { if ((DSO_flags(dso) & DSO_FLAG_NAME_TRANSLATION_EXT_ONLY) == 0) - sprintf(translated, "lib%s" DSO_EXTENSION, filename); + BIO_snprintf(translated, rsize, "lib%s" DSO_EXTENSION, filename); else - sprintf(translated, "%s" DSO_EXTENSION, filename); - } else - sprintf(translated, "%s", filename); + BIO_snprintf(translated, rsize, "%s" DSO_EXTENSION, filename); + } else { + BIO_snprintf(translated, rsize, "%s", filename); + } return translated; } diff --git a/crypto/ec/asm/ecp_nistz256-x86_64.S b/crypto/ec/asm/ecp_nistz256-x86_64.S index 284c117489..0cf1f47a7e 100644 --- a/crypto/ec/asm/ecp_nistz256-x86_64.S +++ b/crypto/ec/asm/ecp_nistz256-x86_64.S @@ -1,4 +1,4 @@ -.text +.section .rodata .globl ecp_nistz256_precomputed .type ecp_nistz256_precomputed,@object .align 4096 @@ -2376,6 +2376,7 @@ ecp_nistz256_precomputed: +.section .rodata .align 64 .Lpoly: .quad 0xffffffffffffffff, 0x00000000ffffffff, 0x0000000000000000, 0xffffffff00000001 @@ -2398,6 +2399,7 @@ ecp_nistz256_precomputed: .quad 0xf3b9cac2fc632551, 0xbce6faada7179e84, 0xffffffffffffffff, 0xffffffff00000000 .LordK: .quad 0xccd1c8aaee00bc4f +.previous .globl ecp_nistz256_mul_by_2 .type ecp_nistz256_mul_by_2,@function diff --git a/crypto/ec/asm/ecp_nistz256-x86_64.pl b/crypto/ec/asm/ecp_nistz256-x86_64.pl index 430b14c86d..4da9a149a9 100755 --- a/crypto/ec/asm/ecp_nistz256-x86_64.pl +++ b/crypto/ec/asm/ecp_nistz256-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2014-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2014-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2014, Intel Corporation. All Rights Reserved. # Copyright (c) 2015 CloudFlare, Inc. # @@ -85,6 +85,7 @@ .extern OPENSSL_ia32cap_P # The polynomial +.section .rodata align=4096 .align 64 .Lpoly: .quad 0xffffffffffffffff, 0x00000000ffffffff, 0x0000000000000000, 0xffffffff00000001 @@ -107,6 +108,7 @@ .quad 0xf3b9cac2fc632551, 0xbce6faada7179e84, 0xffffffffffffffff, 0xffffffff00000000 .LordK: .quad 0xccd1c8aaee00bc4f +.previous ___ { @@ -4723,7 +4725,7 @@ () die "insane number of elements" if ($#arr != 64*16*37-1); print <<___; -.text +.section .rodata align=4096 .globl ecp_nistz256_precomputed .type ecp_nistz256_precomputed,\@object .align 4096 diff --git a/crypto/ec/curve25519.c b/crypto/ec/curve25519.c index cae2ac101d..68c06ae624 100644 --- a/crypto/ec/curve25519.c +++ b/crypto/ec/curve25519.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -5538,6 +5538,21 @@ ossl_ed25519_sign(uint8_t *out_sig, const uint8_t *tbs, size_t tbs_len, return res; } +/* + * This function should not be necessary since ossl_ed25519_verify() already + * does this check internally. + * For some reason the FIPS ACVP requires a EDDSA KeyVer test. + */ +int +ossl_ed25519_pubkey_verify(const uint8_t *pub, size_t pub_len) +{ + ge_p3 A; + + if (pub_len != ED25519_KEYLEN) + return 0; + return (ge_frombytes_vartime(&A, pub) == 0); +} + static const char allzeroes[15]; int diff --git a/crypto/ec/curve448/curve448.c b/crypto/ec/curve448/curve448.c index 2422d068a0..1db78ee5c6 100644 --- a/crypto/ec/curve448/curve448.c +++ b/crypto/ec/curve448/curve448.c @@ -1,5 +1,5 @@ /* - * Copyright 2017-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2015-2016 Cryptography Research, Inc. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -55,8 +55,9 @@ static void gf_invert(gf y, const gf x, int assert_nonzero) } /** identity = (0,1) */ -const curve448_point_t ossl_curve448_point_identity = - { {{{{0}}}, {{{1}}}, {{{1}}}, {{{0}}}} }; +const curve448_point_t ossl_curve448_point_identity = { + {{{{0}}}, {{{1}}}, {{{1}}}, {{{0}}}} +}; static void point_double_internal(curve448_point_t p, const curve448_point_t q, int before_double) diff --git a/crypto/ec/curve448/eddsa.c b/crypto/ec/curve448/eddsa.c index ff7f11dd34..080486e9f3 100644 --- a/crypto/ec/curve448/eddsa.c +++ b/crypto/ec/curve448/eddsa.c @@ -1,5 +1,5 @@ /* - * Copyright 2017-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2015-2016 Cryptography Research, Inc. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -272,6 +272,17 @@ ossl_c448_ed448_sign_prehash( context, context_len, propq); } +static c448_error_t +c448_ed448_pubkey_verify(const uint8_t *pub, size_t pub_len) +{ + curve448_point_t pk_point; + + if (pub_len != EDDSA_448_PUBLIC_BYTES) + return C448_FAILURE; + + return ossl_curve448_point_decode_like_eddsa_and_mul_by_ratio(pk_point, pub); +} + c448_error_t ossl_c448_ed448_verify( OSSL_LIB_CTX *ctx, @@ -380,6 +391,17 @@ ossl_ed448_sign(OSSL_LIB_CTX *ctx, uint8_t *out_sig, propq) == C448_SUCCESS; } +/* + * This function should not be necessary since ossl_ed448_verify() already + * does this check internally. + * For some reason the FIPS ACVP requires a EDDSA KeyVer test. + */ +int +ossl_ed448_pubkey_verify(const uint8_t *pub, size_t pub_len) +{ + return c448_ed448_pubkey_verify(pub, pub_len); +} + int ossl_ed448_verify(OSSL_LIB_CTX *ctx, const uint8_t *message, size_t message_len, diff --git a/crypto/ec/ec_asn1.c b/crypto/ec/ec_asn1.c index b32697fb85..de0b4926fb 100644 --- a/crypto/ec/ec_asn1.c +++ b/crypto/ec/ec_asn1.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -1156,7 +1156,7 @@ int i2o_ECPublicKey(const EC_KEY *a, unsigned char **out) size_t buf_len = 0; int new_buffer = 0; - if (a == NULL) { + if (a == NULL || a->pub_key == NULL) { ERR_raise(ERR_LIB_EC, ERR_R_PASSED_NULL_PARAMETER); return 0; } diff --git a/crypto/ec/ec_backend.c b/crypto/ec/ec_backend.c index b9ebc96465..f0191a7db3 100644 --- a/crypto/ec/ec_backend.c +++ b/crypto/ec/ec_backend.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -184,8 +184,7 @@ static int ec_group_explicit_todata(const EC_GROUP *group, OSSL_PARAM_BLD *tmpl, param_p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_EC_P); param_a = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_EC_A); param_b = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_EC_B); - if (tmpl != NULL || param_p != NULL || param_a != NULL || param_b != NULL) - { + if (tmpl != NULL || param_p != NULL || param_a != NULL || param_b != NULL) { BIGNUM *p = BN_CTX_get(bnctx); BIGNUM *a = BN_CTX_get(bnctx); BIGNUM *b = BN_CTX_get(bnctx); @@ -617,14 +616,8 @@ EC_KEY *ossl_ec_key_dup(const EC_KEY *src, int selection) || !EC_GROUP_copy(ret->group, src->group)) goto err; - if (src->meth != NULL) { -#if !defined(OPENSSL_NO_ENGINE) && !defined(FIPS_MODULE) - if (src->engine != NULL && ENGINE_init(src->engine) == 0) - goto err; - ret->engine = src->engine; -#endif + if (src->meth != NULL) ret->meth = src->meth; - } } /* copy the public key */ diff --git a/crypto/ec/ec_curve.c b/crypto/ec/ec_curve.c index d703d16b3c..f46aac5d33 100644 --- a/crypto/ec/ec_curve.c +++ b/crypto/ec/ec_curve.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -383,7 +383,7 @@ static const struct { static const struct { EC_CURVE_DATA h; - unsigned char data[20 + 32 * 6]; + unsigned char data[20 + 32 * 8]; } _EC_X9_62_PRIME_256V1 = { { NID_X9_62_prime_field, 20, 32, 1 @@ -415,7 +415,15 @@ static const struct { /* order */ 0xFF, 0xFF, 0xFF, 0xFF, 0x00, 0x00, 0x00, 0x00, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xBC, 0xE6, 0xFA, 0xAD, 0xA7, 0x17, 0x9E, 0x84, - 0xF3, 0xB9, 0xCA, 0xC2, 0xFC, 0x63, 0x25, 0x51 + 0xF3, 0xB9, 0xCA, 0xC2, 0xFC, 0x63, 0x25, 0x51, + /* RR for prime */ + 0x00, 0x00, 0x00, 0x04, 0xff, 0xff, 0xff, 0xfd, 0xff, 0xff, 0xff, 0xff, + 0xff, 0xff, 0xff, 0xfe, 0xff, 0xff, 0xff, 0xfb, 0xff, 0xff, 0xff, 0xff, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, + /* RR for order */ + 0x66, 0xe1, 0x2d, 0x94, 0xf3, 0xd9, 0x56, 0x20, 0x28, 0x45, 0xb2, 0x39, + 0x2b, 0x6b, 0xec, 0x59, 0x46, 0x99, 0x79, 0x9c, 0x49, 0xbd, 0x6f, 0xa6, + 0x83, 0x24, 0x4c, 0x95, 0xbe, 0x79, 0xee, 0xa2 } }; @@ -3168,6 +3176,24 @@ static EC_GROUP *ec_group_new_from_data(OSSL_LIB_CTX *libctx, seed_len = data->seed_len; param_len = data->param_len; params = (const unsigned char *)(data + 1); /* skip header */ + + if (curve.meth != NULL) { + meth = curve.meth(); + if ((group = ossl_ec_group_new_ex(libctx, propq, meth)) == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + if (group->meth->group_full_init != NULL) { + if (!group->meth->group_full_init(group, params)){ + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + EC_GROUP_set_curve_name(group, curve.nid); + BN_CTX_free(ctx); + return group; + } + } + params += seed_len; /* skip seed */ if ((p = BN_bin2bn(params + 0 * param_len, param_len, NULL)) == NULL @@ -3177,10 +3203,8 @@ static EC_GROUP *ec_group_new_from_data(OSSL_LIB_CTX *libctx, goto err; } - if (curve.meth != 0) { - meth = curve.meth(); - if (((group = ossl_ec_group_new_ex(libctx, propq, meth)) == NULL) || - (!(group->meth->group_set_curve(group, p, a, b, ctx)))) { + if (group != NULL) { + if (group->meth->group_set_curve(group, p, a, b, ctx) == 0) { ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); goto err; } diff --git a/crypto/ec/ec_key.c b/crypto/ec/ec_key.c index 9bc4e032c5..05224b31a4 100644 --- a/crypto/ec/ec_key.c +++ b/crypto/ec/ec_key.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -563,10 +563,16 @@ int ossl_ec_key_public_check(const EC_KEY *eckey, BN_CTX *ctx) int ret = 0; EC_POINT *point = NULL; const BIGNUM *order = NULL; + const BIGNUM *cofactor = EC_GROUP_get0_cofactor(eckey->group); if (!ossl_ec_key_public_check_quick(eckey, ctx)) return 0; + if (cofactor != NULL && BN_is_one(cofactor)) { + /* Skip the unnecessary expensive computation for curves with cofactor of 1. */ + return 1; + } + point = EC_POINT_new(eckey->group); if (point == NULL) return 0; diff --git a/crypto/ec/ec_lib.c b/crypto/ec/ec_lib.c index c92b4dcb0a..284fc05951 100644 --- a/crypto/ec/ec_lib.c +++ b/crypto/ec/ec_lib.c @@ -1,5 +1,5 @@ /* - * Copyright 2001-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2001-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -746,9 +746,13 @@ void EC_POINT_free(EC_POINT *point) if (point == NULL) return; +#ifdef FIPS_MODULE + EC_POINT_clear_free(point); +#else if (point->meth->point_finish != 0) point->meth->point_finish(point); OPENSSL_free(point); +#endif } void EC_POINT_clear_free(EC_POINT *point) diff --git a/crypto/ec/ec_local.h b/crypto/ec/ec_local.h index 2814d87394..91c3a71902 100644 --- a/crypto/ec/ec_local.h +++ b/crypto/ec/ec_local.h @@ -1,5 +1,5 @@ /* - * Copyright 2001-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2001-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -196,6 +196,7 @@ struct ec_method_st { int (*ladder_post)(const EC_GROUP *group, EC_POINT *r, EC_POINT *s, EC_POINT *p, BN_CTX *ctx); + int (*group_full_init)(EC_GROUP *group, const unsigned char *data); }; /* diff --git a/crypto/ec/ec_oct.c b/crypto/ec/ec_oct.c index 0ad3394c82..947d615741 100644 --- a/crypto/ec/ec_oct.c +++ b/crypto/ec/ec_oct.c @@ -1,5 +1,5 @@ /* - * Copyright 2011-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -74,6 +74,10 @@ size_t EC_POINT_point2oct(const EC_GROUP *group, const EC_POINT *point, point_conversion_form_t form, unsigned char *buf, size_t len, BN_CTX *ctx) { + if (point == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_PASSED_NULL_PARAMETER); + return 0; + } if (group->meth->point2oct == 0 && !(group->meth->flags & EC_FLAGS_DEFAULT_OCT)) { ERR_raise(ERR_LIB_EC, ERR_R_SHOULD_NOT_HAVE_BEEN_CALLED); diff --git a/crypto/ec/ec_print.c b/crypto/ec/ec_print.c index ffe112052f..e14ffc002c 100644 --- a/crypto/ec/ec_print.c +++ b/crypto/ec/ec_print.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -9,18 +9,17 @@ #include /* strlen */ #include +#include "internal/cryptlib.h" #include "ec_local.h" -static const char *HEX_DIGITS = "0123456789ABCDEF"; - /* the return value must be freed (using OPENSSL_free()) */ char *EC_POINT_point2hex(const EC_GROUP *group, const EC_POINT *point, point_conversion_form_t form, BN_CTX *ctx) { char *ret, *p; - size_t buf_len = 0, i; - unsigned char *buf = NULL, *pbuf; + size_t buf_len, i; + unsigned char *buf = NULL; buf_len = EC_POINT_point2buf(group, point, form, &buf, ctx); @@ -28,21 +27,16 @@ char *EC_POINT_point2hex(const EC_GROUP *group, return NULL; ret = OPENSSL_malloc(buf_len * 2 + 2); - if (ret == NULL) { - OPENSSL_free(buf); - return NULL; - } + if (ret == NULL) + goto err; + p = ret; - pbuf = buf; - for (i = buf_len; i > 0; i--) { - int v = (int)*(pbuf++); - *(p++) = HEX_DIGITS[v >> 4]; - *(p++) = HEX_DIGITS[v & 0x0F]; - } + for (i = 0; i < buf_len; ++i) + p += ossl_to_hex(p, buf[i]); *p = '\0'; + err: OPENSSL_free(buf); - return ret; } diff --git a/crypto/ec/ecdsa_ossl.c b/crypto/ec/ecdsa_ossl.c index 402a554245..6104e5cbfc 100644 --- a/crypto/ec/ecdsa_ossl.c +++ b/crypto/ec/ecdsa_ossl.c @@ -106,6 +106,10 @@ int ossl_ecdsa_deterministic_sign(const unsigned char *dgst, int dlen, ERR_raise(ERR_LIB_EC, ERR_R_PASSED_NULL_PARAMETER); return 0; } + if (digestname == NULL) { + ERR_raise(ERR_LIB_EC, EC_R_INVALID_DIGEST); + return 0; + } *siglen = 0; if (!ecdsa_sign_setup(eckey, NULL, &kinv, &r, dgst, dlen, diff --git a/crypto/ec/ecp_nistp256.c b/crypto/ec/ecp_nistp256.c index d28306a6bd..325ace67bc 100644 --- a/crypto/ec/ecp_nistp256.c +++ b/crypto/ec/ecp_nistp256.c @@ -1,5 +1,5 @@ /* - * Copyright 2011-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2011-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -118,8 +118,9 @@ typedef limb longfelem[NLIMBS * 2]; typedef u64 smallfelem[NLIMBS]; /* This is the value of the prime as four 64-bit words, little-endian. */ -static const u64 kPrime[4] = - { 0xfffffffffffffffful, 0xffffffff, 0, 0xffffffff00000001ul }; +static const u64 kPrime[4] = { + 0xfffffffffffffffful, 0xffffffff, 0, 0xffffffff00000001ul +}; static const u64 bottom63bits = 0x7ffffffffffffffful; /* @@ -292,8 +293,9 @@ static void felem_diff(felem out, const felem in) #define two107m43p11 (((limb)1) << 107) - (((limb)1) << 43) + (((limb)1) << 11) /* zero107 is 0 mod p */ -static const felem zero107 = - { two107m43m11, two107, two107m43p11, two107m43p11 }; +static const felem zero107 = { + two107m43m11, two107, two107m43p11, two107m43p11 +}; /*- * An alternative felem_diff for larger inputs |in| diff --git a/crypto/ec/ecp_nistp384.c b/crypto/ec/ecp_nistp384.c index ff68f9cc7a..e2a0e36488 100644 --- a/crypto/ec/ecp_nistp384.c +++ b/crypto/ec/ecp_nistp384.c @@ -1,5 +1,5 @@ /* - * Copyright 2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2023-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -596,7 +596,7 @@ static void felem_reduce(felem out, const widefelem in) acc[0] += (acc[7] & 0xffffffffffff) << 8; /*- - * acc[k] < in[k] + 2^124 + 2^121 + * acc[k] < in[k] + 2^124 + 2^121 * < in[k] + 2^125 * < 2^128, for k <= 6 */ @@ -621,7 +621,7 @@ static void felem_reduce(felem out, const widefelem in) /* [3]: Eliminate high bits of acc[6] */ temp = acc[6] >> 48; acc[6] &= 0x0000ffffffffffff; - + /* temp < 2^80 */ acc[3] += temp >> 40; @@ -865,7 +865,7 @@ static void felem_contract(felem out, const felem in) unsigned int i; memcpy(tmp, in, sizeof(felem)); - + /* Case 1: a = 1 iff |in| >= 2^384 */ a = (in[6] >> 48); tmp[0] += a; diff --git a/crypto/ec/ecp_nistz256.c b/crypto/ec/ecp_nistz256.c index 5760639a2e..55ae2651ac 100644 --- a/crypto/ec/ecp_nistz256.c +++ b/crypto/ec/ecp_nistz256.c @@ -1,5 +1,5 @@ /* - * Copyright 2014-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2014-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2014, Intel Corporation. All Rights Reserved. * Copyright (c) 2015, CloudFlare, Inc. * @@ -1445,6 +1445,131 @@ static int ecp_nistz256_inv_mod_ord(const EC_GROUP *group, BIGNUM *r, # define ecp_nistz256_inv_mod_ord NULL #endif +static int ecp_nistz256group_full_init(EC_GROUP *group, + const unsigned char *params) { + BN_CTX *ctx = NULL; + BN_MONT_CTX *mont = NULL, *ordmont = NULL; + const int param_len = 32; + const int seed_len = 20; + int ok = 0; + uint32_t hi_order_n = 0xccd1c8aa; + uint32_t lo_order_n = 0xee00bc4f; + BIGNUM *p = NULL, *a = NULL, *b = NULL, *x = NULL, *y = NULL, *one = NULL, + *order = NULL; + EC_POINT *P = NULL; + + if ((ctx = BN_CTX_new_ex(group->libctx)) == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_MALLOC_FAILURE); + return 0; + } + + if (!EC_GROUP_set_seed(group, params, seed_len)) { + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + params += seed_len; + + if ((p = BN_bin2bn(params + 0 * param_len, param_len, NULL)) == NULL + || (a = BN_bin2bn(params + 1 * param_len, param_len, NULL)) == NULL + || (b = BN_bin2bn(params + 2 * param_len, param_len, NULL)) == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_BN_LIB); + goto err; + } + + /* + * Set up curve params and montgomery for field + * Start by setting up montgomery and one + */ + mont = BN_MONT_CTX_new(); + if (mont == NULL) + goto err; + + if (!ossl_bn_mont_ctx_set(mont, p, 256, params + 6 * param_len, param_len, + 1, 0)) + goto err; + + one = BN_new(); + if (one == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_BN_LIB); + goto err; + } + if (!BN_to_montgomery(one, BN_value_one(), mont, ctx)){ + ERR_raise(ERR_LIB_EC, ERR_R_BN_LIB); + goto err; + } + group->field_data1 = mont; + mont = NULL; + group->field_data2 = one; + one = NULL; + + if (!ossl_ec_GFp_simple_group_set_curve(group, p, a, b, ctx)) { + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + + if ((P = EC_POINT_new(group)) == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + + if ((x = BN_bin2bn(params + 3 * param_len, param_len, NULL)) == NULL + || (y = BN_bin2bn(params + 4 * param_len, param_len, NULL)) == NULL) { + ERR_raise(ERR_LIB_EC, ERR_R_BN_LIB); + goto err; + } + if (!EC_POINT_set_affine_coordinates(group, P, x, y, ctx)) { + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + if ((order = BN_bin2bn(params + 5 * param_len, param_len, NULL)) == NULL + || !BN_set_word(x, (BN_ULONG)1)) { // cofactor is 1 + ERR_raise(ERR_LIB_EC, ERR_R_BN_LIB); + goto err; + } + + /* + * Set up generator and order and montgomery data + */ + group->generator = EC_POINT_new(group); + if (group->generator == NULL){ + ERR_raise(ERR_LIB_EC, ERR_R_EC_LIB); + goto err; + } + if (!EC_POINT_copy(group->generator, P)) + goto err; + if (!BN_copy(group->order, order)) + goto err; + if (!BN_set_word(group->cofactor, 1)) + goto err; + + ordmont = BN_MONT_CTX_new(); + if (ordmont == NULL) + goto err; + if (!ossl_bn_mont_ctx_set(ordmont, order, 256, params + 7 * param_len, + param_len, lo_order_n, hi_order_n)) + goto err; + + group->mont_data = ordmont; + ordmont = NULL; + + ok = 1; + + err: + EC_POINT_free(P); + BN_CTX_free(ctx); + BN_MONT_CTX_free(mont); + BN_MONT_CTX_free(ordmont); + BN_free(p); + BN_free(one); + BN_free(a); + BN_free(b); + BN_free(order); + BN_free(x); + BN_free(y); + + return ok; +} + const EC_METHOD *EC_GFp_nistz256_method(void) { static const EC_METHOD ret = { @@ -1501,7 +1626,8 @@ const EC_METHOD *EC_GFp_nistz256_method(void) 0, /* blind_coordinates */ 0, /* ladder_pre */ 0, /* ladder_step */ - 0 /* ladder_post */ + 0, /* ladder_post */ + ecp_nistz256group_full_init }; return &ret; diff --git a/crypto/engine/eng_list.c b/crypto/engine/eng_list.c index ee9471a1fd..0f24f2f450 100644 --- a/crypto/engine/eng_list.c +++ b/crypto/engine/eng_list.c @@ -408,7 +408,7 @@ static void engine_cpy(ENGINE *dest, const ENGINE *src) ENGINE *ENGINE_by_id(const char *id) { ENGINE *iterator; - char *load_dir = NULL; + const char *load_dir = NULL; if (id == NULL) { ERR_raise(ERR_LIB_ENGINE, ERR_R_PASSED_NULL_PARAMETER); return NULL; @@ -459,7 +459,7 @@ ENGINE *ENGINE_by_id(const char *id) */ if (strcmp(id, "dynamic")) { if ((load_dir = ossl_safe_getenv("OPENSSL_ENGINES")) == NULL) - load_dir = ENGINESDIR; + load_dir = ossl_get_enginesdir(); iterator = ENGINE_by_id("dynamic"); if (!iterator || !ENGINE_ctrl_cmd_string(iterator, "ID", id, 0) || !ENGINE_ctrl_cmd_string(iterator, "DIR_LOAD", "2", 0) || diff --git a/crypto/err/openssl.txt b/crypto/err/openssl.txt index 6882eebcd1..404be7517a 100644 --- a/crypto/err/openssl.txt +++ b/crypto/err/openssl.txt @@ -234,9 +234,13 @@ CMP_R_FAILED_BUILDING_OWN_CHAIN:164:failed building own chain CMP_R_FAILED_EXTRACTING_PUBKEY:141:failed extracting pubkey CMP_R_FAILURE_OBTAINING_RANDOM:110:failure obtaining random CMP_R_FAIL_INFO_OUT_OF_RANGE:129:fail info out of range +CMP_R_GENERATE_CERTREQTEMPLATE:197:generate certreqtemplate +CMP_R_GENERATE_CRLSTATUS:198:error creating crlstatus CMP_R_GETTING_GENP:192:getting genp +CMP_R_GET_ITAV:199:get itav CMP_R_INVALID_ARGS:100:invalid args CMP_R_INVALID_GENP:193:invalid genp +CMP_R_INVALID_KEYSPEC:202:invalid keyspec CMP_R_INVALID_OPTION:174:invalid option CMP_R_INVALID_ROOTCAKEYUPDATE:195:invalid rootcakeyupdate CMP_R_MISSING_CERTID:165:missing certid @@ -276,6 +280,7 @@ CMP_R_TRANSACTIONID_UNMATCHED:152:transactionid unmatched CMP_R_TRANSFER_ERROR:159:transfer error CMP_R_UNCLEAN_CTX:191:unclean ctx CMP_R_UNEXPECTED_CERTPROFILE:196:unexpected certprofile +CMP_R_UNEXPECTED_CRLSTATUSLIST:201:unexpected crlstatuslist CMP_R_UNEXPECTED_PKIBODY:133:unexpected pkibody CMP_R_UNEXPECTED_PKISTATUS:185:unexpected pkistatus CMP_R_UNEXPECTED_POLLREQ:105:unexpected pollreq @@ -283,6 +288,7 @@ CMP_R_UNEXPECTED_PVNO:153:unexpected pvno CMP_R_UNEXPECTED_SENDER:106:unexpected sender CMP_R_UNKNOWN_ALGORITHM_ID:134:unknown algorithm id CMP_R_UNKNOWN_CERT_TYPE:135:unknown cert type +CMP_R_UNKNOWN_CRL_ISSUER:200:unknown crl issuer CMP_R_UNKNOWN_PKISTATUS:186:unknown pkistatus CMP_R_UNSUPPORTED_ALGORITHM:136:unsupported algorithm CMP_R_UNSUPPORTED_KEY_TYPE:137:unsupported key type @@ -494,6 +500,7 @@ CRYPTO_R_RANDOM_SECTION_ERROR:119:random section error CRYPTO_R_SECURE_MALLOC_FAILURE:111:secure malloc failure CRYPTO_R_STRING_TOO_LONG:112:string too long CRYPTO_R_TOO_MANY_BYTES:113:too many bytes +CRYPTO_R_TOO_MANY_NAMES:132:too many names CRYPTO_R_TOO_MANY_RECORDS:114:too many records CRYPTO_R_TOO_SMALL_BUFFER:116:too small buffer CRYPTO_R_UNKNOWN_NAME_IN_RANDOM_SECTION:120:unknown name in random section @@ -732,6 +739,8 @@ EVP_R_EXPECTING_A_POLY1305_KEY:164:expecting a poly1305 key EVP_R_EXPECTING_A_SIPHASH_KEY:175:expecting a siphash key EVP_R_FINAL_ERROR:188:final error EVP_R_GENERATE_ERROR:214:generate error +EVP_R_GETTING_ALGORITHMIDENTIFIER_NOT_SUPPORTED:229:\ + getting AlgorithmIdentifier not supported EVP_R_GET_RAW_KEY_FAILED:182:get raw key failed EVP_R_ILLEGAL_SCRYPT_PARAMETERS:171:illegal scrypt parameters EVP_R_INACCESSIBLE_DOMAIN_PARAMETERS:204:inaccessible domain parameters @@ -773,6 +782,8 @@ EVP_R_ONLY_ONESHOT_SUPPORTED:177:only oneshot supported EVP_R_OPERATION_NOT_INITIALIZED:151:operation not initialized EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE:150:\ operation not supported for this keytype +EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_SIGNATURE_TYPE:226:\ + operation not supported for this signature type EVP_R_OUTPUT_WOULD_OVERFLOW:202:output would overflow EVP_R_PARAMETER_TOO_LARGE:187:parameter too large EVP_R_PARTIALLY_OVERLAPPING:162:partially overlapping buffers @@ -784,6 +795,8 @@ EVP_R_PRIVATE_KEY_ENCODE_ERROR:146:private key encode error EVP_R_PUBLIC_KEY_NOT_RSA:106:public key not rsa EVP_R_SETTING_XOF_FAILED:227:setting xof failed EVP_R_SET_DEFAULT_PROPERTY_FAILURE:209:set default property failure +EVP_R_SIGNATURE_TYPE_AND_KEY_TYPE_INCOMPATIBLE:228:\ + signature type and key type incompatible EVP_R_TOO_MANY_RECORDS:183:too many records EVP_R_UNABLE_TO_ENABLE_LOCKING:212:unable to enable locking EVP_R_UNABLE_TO_GET_MAXIMUM_REQUEST_SIZE:215:unable to get maximum request size @@ -1024,9 +1037,12 @@ PROV_R_BAD_LENGTH:142:bad length PROV_R_BAD_TLS_CLIENT_VERSION:161:bad tls client version PROV_R_BN_ERROR:160:bn error PROV_R_CIPHER_OPERATION_FAILED:102:cipher operation failed +PROV_R_COFACTOR_REQUIRED:236:cofactor required PROV_R_DERIVATION_FUNCTION_INIT_FAILED:205:derivation function init failed PROV_R_DIGEST_NOT_ALLOWED:174:digest not allowed PROV_R_EMS_NOT_ENABLED:233:ems not enabled +PROV_R_ENTROPY_SOURCE_FAILED_CONTINUOUS_TESTS:244:\ + entropy source failed continuous tests PROV_R_ENTROPY_SOURCE_STRENGTH_TOO_WEAK:186:entropy source strength too weak PROV_R_ERROR_INSTANTIATING_DRBG:188:error instantiating drbg PROV_R_ERROR_RETRIEVING_ENTROPY:189:error retrieving entropy @@ -1038,6 +1054,7 @@ PROV_R_FAILED_TO_GENERATE_KEY:121:failed to generate key PROV_R_FAILED_TO_GET_PARAMETER:103:failed to get parameter PROV_R_FAILED_TO_SET_PARAMETER:104:failed to set parameter PROV_R_FAILED_TO_SIGN:175:failed to sign +PROV_R_FINAL_CALL_OUT_OF_ORDER:237:final call out of order PROV_R_FIPS_MODULE_CONDITIONAL_ERROR:227:fips module conditional error PROV_R_FIPS_MODULE_ENTERING_ERROR_STATE:224:fips module entering error state PROV_R_FIPS_MODULE_IN_ERROR_STATE:225:fips module in error state @@ -1045,6 +1062,7 @@ PROV_R_GENERATE_ERROR:191:generate error PROV_R_ILLEGAL_OR_UNSUPPORTED_PADDING_MODE:165:\ illegal or unsupported padding mode PROV_R_INDICATOR_INTEGRITY_FAILURE:210:indicator integrity failure +PROV_R_INIT_CALL_OUT_OF_ORDER:238:init call out of order PROV_R_INSUFFICIENT_DRBG_STRENGTH:181:insufficient drbg strength PROV_R_INVALID_AAD:108:invalid aad PROV_R_INVALID_AEAD:231:invalid aead @@ -1056,6 +1074,8 @@ PROV_R_INVALID_DATA:115:invalid data PROV_R_INVALID_DIGEST:122:invalid digest PROV_R_INVALID_DIGEST_LENGTH:166:invalid digest length PROV_R_INVALID_DIGEST_SIZE:218:invalid digest size +PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION:243:\ + invalid eddsa instance for attempted operation PROV_R_INVALID_INPUT_LENGTH:230:invalid input length PROV_R_INVALID_ITERATION_COUNT:123:invalid iteration count PROV_R_INVALID_IV_LENGTH:109:invalid iv length @@ -1068,6 +1088,7 @@ PROV_R_INVALID_MGF1_MD:167:invalid mgf1 md PROV_R_INVALID_MODE:125:invalid mode PROV_R_INVALID_OUTPUT_LENGTH:217:invalid output length PROV_R_INVALID_PADDING_MODE:168:invalid padding mode +PROV_R_INVALID_PREHASHED_DIGEST_LENGTH:241:invalid prehashed digest length PROV_R_INVALID_PUBINFO:198:invalid pubinfo PROV_R_INVALID_SALT_LENGTH:112:invalid salt length PROV_R_INVALID_SEED_LENGTH:154:invalid seed length @@ -1105,8 +1126,10 @@ PROV_R_NOT_INSTANTIATED:193:not instantiated PROV_R_NOT_PARAMETERS:226:not parameters PROV_R_NOT_SUPPORTED:136:not supported PROV_R_NOT_XOF_OR_INVALID_LENGTH:113:not xof or invalid length +PROV_R_NO_INSTANCE_ALLOWED:242:no instance allowed PROV_R_NO_KEY_SET:114:no key set PROV_R_NO_PARAMETERS_SET:177:no parameters set +PROV_R_ONESHOT_CALL_OUT_OF_ORDER:239:oneshot call out of order PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE:178:\ operation not supported for this keytype PROV_R_OUTPUT_BUFFER_TOO_SMALL:106:output buffer too small @@ -1141,6 +1164,7 @@ PROV_R_UNSUPPORTED_CEK_ALG:145:unsupported cek alg PROV_R_UNSUPPORTED_KEY_SIZE:153:unsupported key size PROV_R_UNSUPPORTED_MAC_TYPE:137:unsupported mac type PROV_R_UNSUPPORTED_NUMBER_OF_ROUNDS:152:unsupported number of rounds +PROV_R_UPDATE_CALL_OUT_OF_ORDER:240:update call out of order PROV_R_URI_AUTHORITY_UNSUPPORTED:223:uri authority unsupported PROV_R_VALUE_ERROR:138:value error PROV_R_WRONG_FINAL_BLOCK_LENGTH:107:wrong final block length @@ -1396,6 +1420,7 @@ SSL_R_EMPTY_RAW_PUBLIC_KEY:349:empty raw public key SSL_R_EMPTY_SRTP_PROTECTION_PROFILE_LIST:354:empty srtp protection profile list SSL_R_ENCRYPTED_LENGTH_TOO_LONG:150:encrypted length too long SSL_R_ERROR_IN_RECEIVED_CIPHER_LIST:151:error in received cipher list +SSL_R_ERROR_IN_SYSTEM_DEFAULT_CONFIG:419:error in system default config SSL_R_ERROR_SETTING_TLSA_BASE_DOMAIN:204:error setting tlsa base domain SSL_R_EXCEEDS_MAX_FRAGMENT_SIZE:194:exceeds max fragment size SSL_R_EXCESSIVE_MESSAGE_SIZE:152:excessive message size @@ -1458,6 +1483,8 @@ SSL_R_MISSING_SIGALGS_EXTENSION:112:missing sigalgs extension SSL_R_MISSING_SIGNING_CERT:221:missing signing cert SSL_R_MISSING_SRP_PARAM:358:can't find SRP server param SSL_R_MISSING_SUPPORTED_GROUPS_EXTENSION:209:missing supported groups extension +SSL_R_MISSING_SUPPORTED_VERSIONS_EXTENSION:420:\ + missing supported versions extension SSL_R_MISSING_TMP_DH_KEY:171:missing tmp dh key SSL_R_MISSING_TMP_ECDH_KEY:311:missing tmp ecdh key SSL_R_MIXED_HANDSHAKE_AND_NON_HANDSHAKE_DATA:293:\ @@ -1834,5 +1861,6 @@ X509_R_UNKNOWN_PURPOSE_ID:121:unknown purpose id X509_R_UNKNOWN_SIGID_ALGS:144:unknown sigid algs X509_R_UNKNOWN_TRUST_ID:120:unknown trust id X509_R_UNSUPPORTED_ALGORITHM:111:unsupported algorithm +X509_R_UNSUPPORTED_VERSION:145:unsupported version X509_R_WRONG_LOOKUP_TYPE:112:wrong lookup type X509_R_WRONG_TYPE:122:wrong type diff --git a/crypto/evp/bio_b64.c b/crypto/evp/bio_b64.c index 8700315a6b..98a8fa5525 100644 --- a/crypto/evp/bio_b64.c +++ b/crypto/evp/bio_b64.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -103,9 +103,17 @@ static int b64_free(BIO *a) return 1; } +/* + * Unless `BIO_FLAGS_BASE64_NO_NL` is set, this BIO ignores leading lines that + * aren't exclusively composed of valid Base64 characters (followed by + * or ). Once a valid Base64 line is found, `ctx->start` is set to 0 and + * lines are processed until EOF or the first line that contains invalid Base64 + * characters. In a nod to PEM, lines that start with a '-' (hyphen) are + * treated as a soft EOF, rather than an error. + */ static int b64_read(BIO *b, char *out, int outl) { - int ret = 0, i, ii, j, k, x, n, num, ret_code = 0; + int ret = 0, i, ii, j, k, x, n, num, ret_code; BIO_B64_CTX *ctx; unsigned char *p, *q; BIO *next; @@ -128,7 +136,7 @@ static int b64_read(BIO *b, char *out, int outl) EVP_DecodeInit(ctx->base64); } - /* First check if there are bytes decoded/encoded */ + /* First check if there are buffered bytes already decoded */ if (ctx->buf_len > 0) { OPENSSL_assert(ctx->buf_len >= ctx->buf_off); i = ctx->buf_len - ctx->buf_off; @@ -146,14 +154,17 @@ static int b64_read(BIO *b, char *out, int outl) } } + /* Restore any non-retriable error condition (ctx->cont < 0) */ + ret_code = ctx->cont < 0 ? ctx->cont : 0; + /* - * At this point, we have room of outl bytes and an empty buffer, so we - * should read in some more. + * At this point, we have room of outl bytes and an either an empty buffer, + * or outl == 0, so we'll attempt to read in some more. */ - - ret_code = 0; while (outl > 0) { - if (ctx->cont <= 0) + int again = ctx->cont; + + if (again <= 0) break; i = BIO_read(next, &(ctx->tmp[ctx->tmp_len]), @@ -164,18 +175,22 @@ static int b64_read(BIO *b, char *out, int outl) /* Should we continue next time we are called? */ if (!BIO_should_retry(next)) { - ctx->cont = i; - /* If buffer empty break */ - if (ctx->tmp_len == 0) - break; - /* Fall through and process what we have */ - else - i = 0; + /* Incomplete final Base64 chunk in the decoder is an error */ + if (ctx->tmp_len == 0) { + if (EVP_DecodeFinal(ctx->base64, NULL, &num) < 0) + ret_code = -1; + EVP_DecodeInit(ctx->base64); + } + ctx->cont = ret_code; } - /* else we retry and add more data to buffer */ - else + if (ctx->tmp_len == 0) break; + /* Fall through and process what we have */ + i = 0; + /* But don't loop to top-up even if the buffer is not full! */ + again = 0; } + i += ctx->tmp_len; ctx->tmp_len = i; @@ -204,23 +219,23 @@ static int b64_read(BIO *b, char *out, int outl) } k = EVP_DecodeUpdate(ctx->base64, ctx->buf, &num, p, q - p); - if (k <= 0 && num == 0 && ctx->start) { - EVP_DecodeInit(ctx->base64); - } else { - if (p != ctx->tmp) { - i -= p - ctx->tmp; - for (x = 0; x < i; x++) - ctx->tmp[x] = p[x]; - } - EVP_DecodeInit(ctx->base64); - ctx->start = 0; - break; + EVP_DecodeInit(ctx->base64); + if (k <= 0 && num == 0) { + p = q; + continue; + } + + ctx->start = 0; + if (p != ctx->tmp) { + i -= p - ctx->tmp; + for (x = 0; x < i; x++) + ctx->tmp[x] = p[x]; } - p = q; + break; } /* we fell off the end without starting */ - if (j == i && num == 0) { + if (ctx->start) { /* * Is this is one long chunk?, if so, keep on reading until a * new line. @@ -231,18 +246,29 @@ static int b64_read(BIO *b, char *out, int outl) ctx->tmp_nl = 1; ctx->tmp_len = 0; } - } else if (p != q) { /* finished on a '\n' */ + } else if (p != q) { + /* Retain partial line at end of buffer */ n = q - p; for (ii = 0; ii < n; ii++) ctx->tmp[ii] = p[ii]; ctx->tmp_len = n; + } else { + /* All we have is newline terminated non-start data */ + ctx->tmp_len = 0; } - /* else finished on a '\n' */ - continue; + /* + * Try to read more if possible, otherwise we can't make + * progress unless the underlying BIO is retriable and may + * produce more data next time we're called. + */ + if (again > 0) + continue; + else + break; } else { ctx->tmp_len = 0; } - } else if (i < B64_BLOCK_SIZE && ctx->cont > 0) { + } else if (i < B64_BLOCK_SIZE && again > 0) { /* * If buffer isn't full and we can retry then restart to read in * more data. @@ -250,35 +276,9 @@ static int b64_read(BIO *b, char *out, int outl) continue; } - if ((BIO_get_flags(b) & BIO_FLAGS_BASE64_NO_NL) != 0) { - int z, jj; - - jj = i & ~3; /* process per 4 */ - z = EVP_DecodeBlock(ctx->buf, ctx->tmp, jj); - if (jj > 2) { - if (ctx->tmp[jj - 1] == '=') { - z--; - if (ctx->tmp[jj - 2] == '=') - z--; - } - } - /* - * z is now number of output bytes and jj is the number consumed - */ - if (jj != i) { - memmove(ctx->tmp, &ctx->tmp[jj], i - jj); - ctx->tmp_len = i - jj; - } - ctx->buf_len = 0; - if (z > 0) { - ctx->buf_len = z; - } - i = z; - } else { - i = EVP_DecodeUpdate(ctx->base64, ctx->buf, &ctx->buf_len, - ctx->tmp, i); - ctx->tmp_len = 0; - } + i = EVP_DecodeUpdate(ctx->base64, ctx->buf, &ctx->buf_len, + ctx->tmp, i); + ctx->tmp_len = 0; /* * If eof or an error was signalled, then the condition * 'ctx->cont <= 0' will prevent b64_read() from reading @@ -289,7 +289,7 @@ static int b64_read(BIO *b, char *out, int outl) ctx->buf_off = 0; if (i < 0) { - ret_code = 0; + ret_code = ctx->start ? 0 : i; ctx->buf_len = 0; break; } diff --git a/crypto/evp/bio_ok.c b/crypto/evp/bio_ok.c index 2aa1ed7558..20811ffded 100644 --- a/crypto/evp/bio_ok.c +++ b/crypto/evp/bio_ok.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -443,6 +443,8 @@ static int sig_out(BIO *b) md_size = EVP_MD_get_size(digest); md_data = EVP_MD_CTX_get0_md_data(md); + if (md_size <= 0) + goto berr; if (ctx->buf_len + 2 * md_size > OK_BLOCK_SIZE) return 1; @@ -485,7 +487,7 @@ static int sig_in(BIO *b) if ((md = ctx->md) == NULL) goto berr; digest = EVP_MD_CTX_get0_md(md); - if ((md_size = EVP_MD_get_size(digest)) < 0) + if ((md_size = EVP_MD_get_size(digest)) <= 0) goto berr; md_data = EVP_MD_CTX_get0_md_data(md); @@ -533,6 +535,8 @@ static int block_out(BIO *b) md = ctx->md; digest = EVP_MD_CTX_get0_md(md); md_size = EVP_MD_get_size(digest); + if (md_size <= 0) + goto berr; tl = ctx->buf_len - OK_BLOCK_BLOCK; ctx->buf[0] = (unsigned char)(tl >> 24); @@ -563,7 +567,7 @@ static int block_in(BIO *b) ctx = BIO_get_data(b); md = ctx->md; md_size = EVP_MD_get_size(EVP_MD_CTX_get0_md(md)); - if (md_size < 0) + if (md_size <= 0) goto berr; assert(sizeof(tl) >= OK_BLOCK_BLOCK); /* always true */ diff --git a/crypto/evp/dh_support.c b/crypto/evp/dh_support.c index 87296ffbee..d247287422 100644 --- a/crypto/evp/dh_support.c +++ b/crypto/evp/dh_support.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -12,7 +12,7 @@ #include "internal/nelem.h" #include "crypto/dh.h" -typedef struct dh_name2id_st{ +typedef struct dh_name2id_st { const char *name; int id; int type; @@ -28,8 +28,7 @@ typedef struct dh_name2id_st{ # define TYPE_DHX 0 #endif -static const DH_GENTYPE_NAME2ID dhtype2id[] = -{ +static const DH_GENTYPE_NAME2ID dhtype2id[] = { { "group", DH_PARAMGEN_TYPE_GROUP, TYPE_ANY }, { "generator", DH_PARAMGEN_TYPE_GENERATOR, TYPE_DH }, { "fips186_4", DH_PARAMGEN_TYPE_FIPS_186_4, TYPE_DHX }, diff --git a/crypto/evp/digest.c b/crypto/evp/digest.c index 3e835c9a76..9f7d6c928d 100644 --- a/crypto/evp/digest.c +++ b/crypto/evp/digest.c @@ -20,6 +20,7 @@ #include #include #include "internal/cryptlib.h" +#include "internal/nelem.h" #include "internal/provider.h" #include "internal/core.h" #include "crypto/evp.h" @@ -77,7 +78,6 @@ static int evp_md_ctx_reset_ex(EVP_MD_CTX *ctx, int keep_fetched) if (ctx == NULL) return 1; -#ifndef FIPS_MODULE /* * pctx should be freed by the user of EVP_MD_CTX * if EVP_MD_CTX_FLAG_KEEP_PKEY_CTX is set @@ -86,7 +86,6 @@ static int evp_md_ctx_reset_ex(EVP_MD_CTX *ctx, int keep_fetched) EVP_PKEY_CTX_free(ctx->pctx); ctx->pctx = NULL; } -#endif evp_md_ctx_clear_digest(ctx, 0, keep_fetched); if (!keep_fetched) @@ -447,22 +446,13 @@ int EVP_DigestFinal_ex(EVP_MD_CTX *ctx, unsigned char *md, unsigned int *isize) if (ctx->digest == NULL) return 0; - sz = EVP_MD_get_size(ctx->digest); + sz = EVP_MD_CTX_get_size(ctx); if (sz < 0) return 0; mdsize = sz; if (ctx->digest->prov == NULL) goto legacy; - if (ctx->digest->gettable_ctx_params != NULL) { - OSSL_PARAM params[] = { OSSL_PARAM_END, OSSL_PARAM_END }; - - params[0] = OSSL_PARAM_construct_size_t(OSSL_DIGEST_PARAM_SIZE, - &mdsize); - if (!EVP_MD_CTX_get_params(ctx, params)) - return 0; - } - if (ctx->digest->dfinal == NULL) { ERR_raise(ERR_LIB_EVP, EVP_R_FINAL_ERROR); return 0; @@ -543,7 +533,7 @@ int EVP_DigestFinalXOF(EVP_MD_CTX *ctx, unsigned char *md, size_t size) return ret; legacy: - if (ctx->digest->flags & EVP_MD_FLAG_XOF + if (EVP_MD_xof(ctx->digest) && size <= INT_MAX && ctx->digest->md_ctrl(ctx, EVP_MD_CTRL_XOF_LEN, (int)size, NULL)) { ret = ctx->digest->final(ctx, md); @@ -982,6 +972,11 @@ static int evp_md_cache_constants(EVP_MD *md) size_t mdsize = 0; OSSL_PARAM params[5]; + /* + * Note that these parameters are 'constants' that are only set up + * during the EVP_MD_fetch(). For this reason the XOF functions set the + * md_size to 0, since the output size is unknown. + */ params[0] = OSSL_PARAM_construct_size_t(OSSL_DIGEST_PARAM_BLOCK_SIZE, &blksz); params[1] = OSSL_PARAM_construct_size_t(OSSL_DIGEST_PARAM_SIZE, &mdsize); params[2] = OSSL_PARAM_construct_int(OSSL_DIGEST_PARAM_XOF, &xof); @@ -1183,3 +1178,56 @@ void EVP_MD_do_all_provided(OSSL_LIB_CTX *libctx, (void (*)(void *, void *))fn, arg, evp_md_from_algorithm, evp_md_up_ref, evp_md_free); } + +typedef struct { + int md_nid; + int hmac_nid; +} ossl_hmacmd_pair; + +static const ossl_hmacmd_pair ossl_hmacmd_pairs[] = { + {NID_sha1, NID_hmacWithSHA1}, + {NID_md5, NID_hmacWithMD5}, + {NID_sha224, NID_hmacWithSHA224}, + {NID_sha256, NID_hmacWithSHA256}, + {NID_sha384, NID_hmacWithSHA384}, + {NID_sha512, NID_hmacWithSHA512}, + {NID_id_GostR3411_94, NID_id_HMACGostR3411_94}, + {NID_id_GostR3411_2012_256, NID_id_tc26_hmac_gost_3411_2012_256}, + {NID_id_GostR3411_2012_512, NID_id_tc26_hmac_gost_3411_2012_512}, + {NID_sha3_224, NID_hmac_sha3_224}, + {NID_sha3_256, NID_hmac_sha3_256}, + {NID_sha3_384, NID_hmac_sha3_384}, + {NID_sha3_512, NID_hmac_sha3_512}, + {NID_sha512_224, NID_hmacWithSHA512_224}, + {NID_sha512_256, NID_hmacWithSHA512_256} +}; + +int ossl_hmac2mdnid(int hmac_nid) +{ + int md_nid = NID_undef; + size_t i; + + for (i = 0; i < OSSL_NELEM(ossl_hmacmd_pairs); i++) { + if (ossl_hmacmd_pairs[i].hmac_nid == hmac_nid) { + md_nid = ossl_hmacmd_pairs[i].md_nid; + break; + } + } + + return md_nid; +} + +int ossl_md2hmacnid(int md_nid) +{ + int hmac_nid = NID_undef; + size_t i; + + for (i = 0; i < OSSL_NELEM(ossl_hmacmd_pairs); i++) { + if (ossl_hmacmd_pairs[i].md_nid == md_nid) { + hmac_nid = ossl_hmacmd_pairs[i].hmac_nid; + break; + } + } + + return hmac_nid; +} diff --git a/crypto/evp/e_des3.c b/crypto/evp/e_des3.c index c0bc7fdd8f..8fdf17cdc0 100644 --- a/crypto/evp/e_des3.c +++ b/crypto/evp/e_des3.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -312,8 +312,9 @@ const EVP_CIPHER *EVP_des_ede3(void) # include -static const unsigned char wrap_iv[8] = - { 0x4a, 0xdd, 0xa2, 0x2c, 0x79, 0xe8, 0x21, 0x05 }; +static const unsigned char wrap_iv[8] = { + 0x4a, 0xdd, 0xa2, 0x2c, 0x79, 0xe8, 0x21, 0x05 +}; static int des_ede3_unwrap(EVP_CIPHER_CTX *ctx, unsigned char *out, const unsigned char *in, size_t inl) diff --git a/crypto/evp/encode.c b/crypto/evp/encode.c index 2c047fa039..309d32a35d 100644 --- a/crypto/evp/encode.c +++ b/crypto/evp/encode.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -443,7 +443,7 @@ static int evp_decodeblock_int(EVP_ENCODE_CTX *ctx, unsigned char *t, b = conv_ascii2bin(*(f++), table); c = conv_ascii2bin(*(f++), table); d = conv_ascii2bin(*(f++), table); - if ((a & 0x80) || (b & 0x80) || (c & 0x80) || (d & 0x80)) + if ((a | b | c | d) & 0x80) return -1; l = ((((unsigned long)a) << 18L) | (((unsigned long)b) << 12L) | diff --git a/crypto/evp/evp_enc.c b/crypto/evp/evp_enc.c index c289b2f7b0..f96d46f6d2 100644 --- a/crypto/evp/evp_enc.c +++ b/crypto/evp/evp_enc.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -1034,8 +1034,7 @@ int EVP_DecryptFinal_ex(EVP_CIPHER_CTX *ctx, unsigned char *out, int *outl) for (i = 0; i < n; i++) out[i] = ctx->final[i]; *outl = n; - } else - *outl = 0; + } return 1; } diff --git a/crypto/evp/evp_err.c b/crypto/evp/evp_err.c index 42dd7e4009..48dc60a1aa 100644 --- a/crypto/evp/evp_err.c +++ b/crypto/evp/evp_err.c @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,150 +16,156 @@ static const ERR_STRING_DATA EVP_str_reasons[] = { {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_AES_KEY_SETUP_FAILED), - "aes key setup failed"}, + "aes key setup failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_ARIA_KEY_SETUP_FAILED), - "aria key setup failed"}, + "aria key setup failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_BAD_ALGORITHM_NAME), "bad algorithm name"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_BAD_DECRYPT), "bad decrypt"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_BAD_KEY_LENGTH), "bad key length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_BUFFER_TOO_SMALL), "buffer too small"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CACHE_CONSTANTS_FAILED), - "cache constants failed"}, + "cache constants failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CAMELLIA_KEY_SETUP_FAILED), - "camellia key setup failed"}, + "camellia key setup failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CANNOT_GET_PARAMETERS), - "cannot get parameters"}, + "cannot get parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CANNOT_SET_PARAMETERS), - "cannot set parameters"}, + "cannot set parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CIPHER_NOT_GCM_MODE), - "cipher not gcm mode"}, + "cipher not gcm mode"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CIPHER_PARAMETER_ERROR), - "cipher parameter error"}, + "cipher parameter error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_COMMAND_NOT_SUPPORTED), - "command not supported"}, + "command not supported"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CONFLICTING_ALGORITHM_NAME), - "conflicting algorithm name"}, + "conflicting algorithm name"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_COPY_ERROR), "copy error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CTRL_NOT_IMPLEMENTED), - "ctrl not implemented"}, + "ctrl not implemented"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_CTRL_OPERATION_NOT_IMPLEMENTED), - "ctrl operation not implemented"}, + "ctrl operation not implemented"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_DATA_NOT_MULTIPLE_OF_BLOCK_LENGTH), - "data not multiple of block length"}, + "data not multiple of block length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_DECODE_ERROR), "decode error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_DEFAULT_QUERY_PARSE_ERROR), - "default query parse error"}, + "default query parse error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_DIFFERENT_KEY_TYPES), - "different key types"}, + "different key types"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_DIFFERENT_PARAMETERS), - "different parameters"}, + "different parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_ERROR_LOADING_SECTION), - "error loading section"}, + "error loading section"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_AN_HMAC_KEY), - "expecting an hmac key"}, + "expecting an hmac key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_AN_RSA_KEY), - "expecting an rsa key"}, + "expecting an rsa key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_DH_KEY), "expecting a dh key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_DSA_KEY), - "expecting a dsa key"}, + "expecting a dsa key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_ECX_KEY), - "expecting an ecx key"}, + "expecting an ecx key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_EC_KEY), "expecting an ec key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_POLY1305_KEY), - "expecting a poly1305 key"}, + "expecting a poly1305 key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_EXPECTING_A_SIPHASH_KEY), - "expecting a siphash key"}, + "expecting a siphash key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_FINAL_ERROR), "final error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_GENERATE_ERROR), "generate error"}, + {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_GETTING_ALGORITHMIDENTIFIER_NOT_SUPPORTED), + "getting AlgorithmIdentifier not supported"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_GET_RAW_KEY_FAILED), "get raw key failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_ILLEGAL_SCRYPT_PARAMETERS), - "illegal scrypt parameters"}, + "illegal scrypt parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INACCESSIBLE_DOMAIN_PARAMETERS), - "inaccessible domain parameters"}, + "inaccessible domain parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INACCESSIBLE_KEY), "inaccessible key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INITIALIZATION_ERROR), - "initialization error"}, + "initialization error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INPUT_NOT_INITIALIZED), - "input not initialized"}, + "input not initialized"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_CUSTOM_LENGTH), - "invalid custom length"}, + "invalid custom length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_DIGEST), "invalid digest"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_IV_LENGTH), "invalid iv length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY), "invalid key"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_KEY_LENGTH), "invalid key length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_LENGTH), "invalid length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_NULL_ALGORITHM), - "invalid null algorithm"}, + "invalid null algorithm"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_OPERATION), "invalid operation"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_PROVIDER_FUNCTIONS), - "invalid provider functions"}, + "invalid provider functions"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_SALT_LENGTH), - "invalid salt length"}, + "invalid salt length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_SECRET_LENGTH), - "invalid secret length"}, + "invalid secret length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_SEED_LENGTH), - "invalid seed length"}, + "invalid seed length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_INVALID_VALUE), "invalid value"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_KEYMGMT_EXPORT_FAILURE), - "keymgmt export failure"}, + "keymgmt export failure"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_KEY_SETUP_FAILED), "key setup failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_LOCKING_NOT_SUPPORTED), - "locking not supported"}, + "locking not supported"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_MEMORY_LIMIT_EXCEEDED), - "memory limit exceeded"}, + "memory limit exceeded"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_MESSAGE_DIGEST_IS_NULL), - "message digest is null"}, + "message digest is null"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_METHOD_NOT_SUPPORTED), - "method not supported"}, + "method not supported"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_MISSING_PARAMETERS), "missing parameters"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NOT_ABLE_TO_COPY_CTX), - "not able to copy ctx"}, + "not able to copy ctx"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NOT_XOF_OR_INVALID_LENGTH), - "not XOF or invalid length"}, + "not XOF or invalid length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_CIPHER_SET), "no cipher set"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_DEFAULT_DIGEST), "no default digest"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_DIGEST_SET), "no digest set"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_IMPORT_FUNCTION), "no import function"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_KEYMGMT_AVAILABLE), - "no keymgmt available"}, + "no keymgmt available"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_KEYMGMT_PRESENT), "no keymgmt present"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_KEY_SET), "no key set"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NO_OPERATION_SET), "no operation set"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_NULL_MAC_PKEY_CTX), "null mac pkey ctx"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_ONLY_ONESHOT_SUPPORTED), - "only oneshot supported"}, + "only oneshot supported"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_OPERATION_NOT_INITIALIZED), - "operation not initialized"}, + "operation not initialized"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE), - "operation not supported for this keytype"}, + "operation not supported for this keytype"}, + {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_SIGNATURE_TYPE), + "operation not supported for this signature type"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_OUTPUT_WOULD_OVERFLOW), - "output would overflow"}, + "output would overflow"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PARAMETER_TOO_LARGE), - "parameter too large"}, + "parameter too large"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PARTIALLY_OVERLAPPING), - "partially overlapping buffers"}, + "partially overlapping buffers"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PBKDF2_ERROR), "pbkdf2 error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PKEY_APPLICATION_ASN1_METHOD_ALREADY_REGISTERED), - "pkey application asn1 method already registered"}, + "pkey application asn1 method already registered"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PRIVATE_KEY_DECODE_ERROR), - "private key decode error"}, + "private key decode error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PRIVATE_KEY_ENCODE_ERROR), - "private key encode error"}, + "private key encode error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_PUBLIC_KEY_NOT_RSA), "public key not rsa"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_SETTING_XOF_FAILED), "setting xof failed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_SET_DEFAULT_PROPERTY_FAILURE), - "set default property failure"}, + "set default property failure"}, + {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_SIGNATURE_TYPE_AND_KEY_TYPE_INCOMPATIBLE), + "signature type and key type incompatible"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_TOO_MANY_RECORDS), "too many records"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNABLE_TO_ENABLE_LOCKING), - "unable to enable locking"}, + "unable to enable locking"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNABLE_TO_GET_MAXIMUM_REQUEST_SIZE), - "unable to get maximum request size"}, + "unable to get maximum request size"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNABLE_TO_GET_RANDOM_STRENGTH), - "unable to get random strength"}, + "unable to get random strength"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNABLE_TO_LOCK_CONTEXT), - "unable to lock context"}, + "unable to lock context"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNABLE_TO_SET_CALLBACKS), - "unable to set callbacks"}, + "unable to set callbacks"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_BITS), "unknown bits"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_CIPHER), "unknown cipher"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_DIGEST), "unknown digest"}, @@ -167,36 +173,36 @@ static const ERR_STRING_DATA EVP_str_reasons[] = { {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_MAX_SIZE), "unknown max size"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_OPTION), "unknown option"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_PBE_ALGORITHM), - "unknown pbe algorithm"}, + "unknown pbe algorithm"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNKNOWN_SECURITY_BITS), - "unknown security bits"}, + "unknown security bits"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_ALGORITHM), - "unsupported algorithm"}, + "unsupported algorithm"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_CIPHER), "unsupported cipher"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_KEYLENGTH), - "unsupported keylength"}, + "unsupported keylength"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_KEY_DERIVATION_FUNCTION), - "unsupported key derivation function"}, + "unsupported key derivation function"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_KEY_SIZE), - "unsupported key size"}, + "unsupported key size"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_KEY_TYPE), - "unsupported key type"}, + "unsupported key type"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_NUMBER_OF_ROUNDS), - "unsupported number of rounds"}, + "unsupported number of rounds"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_PRF), "unsupported prf"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_PRIVATE_KEY_ALGORITHM), - "unsupported private key algorithm"}, + "unsupported private key algorithm"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UNSUPPORTED_SALT_TYPE), - "unsupported salt type"}, + "unsupported salt type"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_UPDATE_ERROR), "update error"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_WRAP_MODE_NOT_ALLOWED), - "wrap mode not allowed"}, + "wrap mode not allowed"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_WRONG_FINAL_BLOCK_LENGTH), - "wrong final block length"}, + "wrong final block length"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_XTS_DATA_UNIT_IS_TOO_LARGE), - "xts data unit is too large"}, + "xts data unit is too large"}, {ERR_PACK(ERR_LIB_EVP, 0, EVP_R_XTS_DUPLICATED_KEYS), - "xts duplicated keys"}, + "xts duplicated keys"}, {0, NULL} }; diff --git a/crypto/evp/evp_lib.c b/crypto/evp/evp_lib.c index be95668c7e..4440582e4f 100644 --- a/crypto/evp/evp_lib.c +++ b/crypto/evp/evp_lib.c @@ -17,6 +17,7 @@ #include #include "internal/cryptlib.h" #include +#include #include #include #include @@ -127,37 +128,13 @@ int evp_cipher_param_to_asn1_ex(EVP_CIPHER_CTX *c, ASN1_TYPE *type, ret = EVP_CIPHER_set_asn1_iv(c, type); } } else if (cipher->prov != NULL) { - OSSL_PARAM params[3], *p = params; - unsigned char *der = NULL, *derp; + /* We cheat, there's no need for an object ID for this use */ + X509_ALGOR alg; - /* - * We make two passes, the first to get the appropriate buffer size, - * and the second to get the actual value. - */ - *p++ = OSSL_PARAM_construct_octet_string( - OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS, - NULL, 0); - *p = OSSL_PARAM_construct_end(); + alg.algorithm = NULL; + alg.parameter = type; - if (!EVP_CIPHER_CTX_get_params(c, params)) - goto err; - - /* ... but, we should get a return size too! */ - if (OSSL_PARAM_modified(params) - && params[0].return_size != 0 - && (der = OPENSSL_malloc(params[0].return_size)) != NULL) { - params[0].data = der; - params[0].data_size = params[0].return_size; - OSSL_PARAM_set_all_unmodified(params); - derp = der; - if (EVP_CIPHER_CTX_get_params(c, params) - && OSSL_PARAM_modified(params) - && d2i_ASN1_TYPE(&type, (const unsigned char **)&derp, - params[0].return_size) != NULL) { - ret = 1; - } - OPENSSL_free(der); - } + ret = EVP_CIPHER_CTX_get_algor_params(c, &alg); } else { ret = -2; } @@ -220,20 +197,13 @@ int evp_cipher_asn1_to_param_ex(EVP_CIPHER_CTX *c, ASN1_TYPE *type, ret = EVP_CIPHER_get_asn1_iv(c, type) >= 0 ? 1 : -1; } } else if (cipher->prov != NULL) { - OSSL_PARAM params[3], *p = params; - unsigned char *der = NULL; - int derl = -1; - - if ((derl = i2d_ASN1_TYPE(type, &der)) >= 0) { - *p++ = - OSSL_PARAM_construct_octet_string( - OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS, - der, (size_t)derl); - *p = OSSL_PARAM_construct_end(); - if (EVP_CIPHER_CTX_set_params(c, params)) - ret = 1; - OPENSSL_free(der); - } + /* We cheat, there's no need for an object ID for this use */ + X509_ALGOR alg; + + alg.algorithm = NULL; + alg.parameter = type; + + ret = EVP_CIPHER_CTX_set_algor_params(c, &alg); } else { ret = -2; } @@ -670,6 +640,9 @@ int EVP_CIPHER_get_key_length(const EVP_CIPHER *cipher) int EVP_CIPHER_CTX_get_key_length(const EVP_CIPHER_CTX *ctx) { + if (ctx->cipher == NULL) + return 0; + if (ctx->key_len <= 0 && ctx->cipher->prov != NULL) { int ok; OSSL_PARAM params[2] = { OSSL_PARAM_END, OSSL_PARAM_END }; @@ -841,6 +814,11 @@ int EVP_MD_get_size(const EVP_MD *md) return md->md_size; } +int EVP_MD_xof(const EVP_MD *md) +{ + return md != NULL && ((EVP_MD_get_flags(md) & EVP_MD_FLAG_XOF) != 0); +} + unsigned long EVP_MD_get_flags(const EVP_MD *md) { return md->flags; @@ -1055,6 +1033,34 @@ EVP_MD *EVP_MD_CTX_get1_md(EVP_MD_CTX *ctx) return md; } +int EVP_MD_CTX_get_size_ex(const EVP_MD_CTX *ctx) +{ + EVP_MD_CTX *c = (EVP_MD_CTX *)ctx; + const OSSL_PARAM *gettables; + + gettables = EVP_MD_CTX_gettable_params(c); + if (gettables != NULL + && OSSL_PARAM_locate_const(gettables, + OSSL_DIGEST_PARAM_SIZE) != NULL) { + OSSL_PARAM params[2] = { OSSL_PARAM_END, OSSL_PARAM_END }; + size_t sz = 0; + + /* + * For XOF's EVP_MD_get_size() returns 0 + * So try to get the xoflen instead. This will return -1 if the + * xof length has not been set. + */ + params[0] = OSSL_PARAM_construct_size_t(OSSL_DIGEST_PARAM_SIZE, &sz); + if (EVP_MD_CTX_get_params(c, params) != 1 + || sz == SIZE_MAX + || sz == 0) + return -1; + return sz; + } + /* Normal digests have a constant fixed size output */ + return EVP_MD_get_size(EVP_MD_CTX_get0_md(ctx)); +} + EVP_PKEY_CTX *EVP_MD_CTX_get_pkey_ctx(const EVP_MD_CTX *ctx) { return ctx->pctx; @@ -1245,4 +1251,248 @@ EVP_PKEY *EVP_PKEY_Q_keygen(OSSL_LIB_CTX *libctx, const char *propq, return ret; } +int EVP_CIPHER_CTX_set_algor_params(EVP_CIPHER_CTX *ctx, const X509_ALGOR *alg) +{ + int ret = -1; /* Assume the worst */ + unsigned char *der = NULL; + int derl = -1; + + if ((derl = i2d_ASN1_TYPE(alg->parameter, &der)) >= 0) { + const char *k_old = OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD; + const char *k_new = OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS; + OSSL_PARAM params[3]; + + /* + * Passing the same data with both the old (deprecated) and the + * new AlgID parameters OSSL_PARAM key. + */ + params[0] = OSSL_PARAM_construct_octet_string(k_old, der, (size_t)derl); + params[1] = OSSL_PARAM_construct_octet_string(k_new, der, (size_t)derl); + params[2] = OSSL_PARAM_construct_end(); + ret = EVP_CIPHER_CTX_set_params(ctx, params); + } + OPENSSL_free(der); + return ret; +} + +int EVP_CIPHER_CTX_get_algor_params(EVP_CIPHER_CTX *ctx, X509_ALGOR *alg) +{ + int ret = -1; /* Assume the worst */ + unsigned char *der = NULL; + size_t derl; + ASN1_TYPE *type = NULL; + int i = -1; + const char *k_old = OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD; + const char *k_new = OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS; + const char *derk; + OSSL_PARAM params[3]; + + /* + * We make two passes, the first to get the appropriate buffer size, + * and the second to get the actual value. + * Also, using both the old (deprecated) and the new AlgID parameters + * OSSL_PARAM key, and using whichever the provider responds to. + * Should the provider respond on both, the new key takes priority. + */ + params[0] = OSSL_PARAM_construct_octet_string(k_old, NULL, 0); + params[1] = OSSL_PARAM_construct_octet_string(k_new, NULL, 0); + params[2] = OSSL_PARAM_construct_end(); + + if (!EVP_CIPHER_CTX_get_params(ctx, params)) + goto err; + + /* ... but, we should get a return size too! */ + if (OSSL_PARAM_modified(¶ms[0]) && params[0].return_size != 0) + i = 0; + if (OSSL_PARAM_modified(¶ms[1]) && params[1].return_size != 0) + i = 1; + if (i < 0) + goto err; + + /* + * If alg->parameter is non-NULL, it will be changed by d2i_ASN1_TYPE() + * below. If it is NULL, the d2i_ASN1_TYPE() call will allocate new + * space for it. Either way, alg->parameter can be safely assigned + * with type after the d2i_ASN1_TYPE() call, with the safety that it + * will be ok. + */ + type = alg->parameter; + + derk = params[i].key; + derl = params[i].return_size; + if ((der = OPENSSL_malloc(derl)) != NULL) { + unsigned char *derp = der; + + params[i] = OSSL_PARAM_construct_octet_string(derk, der, derl); + if (EVP_CIPHER_CTX_get_params(ctx, params) + && OSSL_PARAM_modified(¶ms[i]) + && d2i_ASN1_TYPE(&type, (const unsigned char **)&derp, + (int)derl) != NULL) { + /* + * Don't free alg->parameter, see comment further up. + * Worst case, alg->parameter gets assigned its own value. + */ + alg->parameter = type; + ret = 1; + } + } + err: + OPENSSL_free(der); + return ret; +} + +int EVP_CIPHER_CTX_get_algor(EVP_CIPHER_CTX *ctx, X509_ALGOR **alg) +{ + int ret = -1; /* Assume the worst */ + OSSL_PARAM params[2]; + size_t aid_len = 0; + const char *k_aid = OSSL_SIGNATURE_PARAM_ALGORITHM_ID; + + params[0] = OSSL_PARAM_construct_octet_string(k_aid, NULL, 0); + params[1] = OSSL_PARAM_construct_end(); + + if (EVP_CIPHER_CTX_get_params(ctx, params) <= 0) + goto err; + + if (OSSL_PARAM_modified(¶ms[0])) + aid_len = params[0].return_size; + if (aid_len == 0) { + ERR_raise(ERR_LIB_EVP, EVP_R_GETTING_ALGORITHMIDENTIFIER_NOT_SUPPORTED); + ret = -2; + goto err; + } + if (alg != NULL) { + unsigned char *aid = NULL; + const unsigned char *pp = NULL; + + if ((aid = OPENSSL_malloc(aid_len)) != NULL) { + params[0] = OSSL_PARAM_construct_octet_string(k_aid, aid, aid_len); + pp = aid; + if (EVP_CIPHER_CTX_get_params(ctx, params) + && OSSL_PARAM_modified(¶ms[0]) + && d2i_X509_ALGOR(alg, &pp, aid_len) != NULL) + ret = 1; + } + OPENSSL_free(aid); + } + err: + return ret; +} + +int EVP_PKEY_CTX_set_algor_params(EVP_PKEY_CTX *ctx, const X509_ALGOR *alg) +{ + int ret = -1; /* Assume the worst */ + unsigned char *der = NULL; + int derl = -1; + + if ((derl = i2d_ASN1_TYPE(alg->parameter, &der)) >= 0) { + const char *k = OSSL_PKEY_PARAM_ALGORITHM_ID_PARAMS; + OSSL_PARAM params[2]; + + /* + * Passing the same data with both the old (deprecated) and the + * new AlgID parameters OSSL_PARAM key. + */ + params[0] = OSSL_PARAM_construct_octet_string(k, der, (size_t)derl); + params[1] = OSSL_PARAM_construct_end(); + ret = EVP_PKEY_CTX_set_params(ctx, params); + } + OPENSSL_free(der); + return ret; +} + +int EVP_PKEY_CTX_get_algor_params(EVP_PKEY_CTX *ctx, X509_ALGOR *alg) +{ + int ret = -1; /* Assume the worst */ + OSSL_PARAM params[2]; + unsigned char *der = NULL; + size_t derl; + ASN1_TYPE *type = NULL; + const char *k = OSSL_PKEY_PARAM_ALGORITHM_ID_PARAMS; + + /* + * We make two passes, the first to get the appropriate buffer size, + * and the second to get the actual value. + * Also, using both the old (deprecated) and the new AlgID parameters + * OSSL_PARAM key, and using whichever the provider responds to. + * Should the provider respond on both, the new key takes priority. + */ + params[0] = OSSL_PARAM_construct_octet_string(k, NULL, 0); + params[1] = OSSL_PARAM_construct_end(); + + if (!EVP_PKEY_CTX_get_params(ctx, params)) + goto err; + + /* + * If alg->parameter is non-NULL, it will be changed by d2i_ASN1_TYPE() + * below. If it is NULL, the d2i_ASN1_TYPE() call will allocate new + * space for it. Either way, alg->parameter can be safely assigned + * with type after the d2i_ASN1_TYPE() call, with the safety that it + * will be ok. + */ + type = alg->parameter; + + derl = params[0].return_size; + if (OSSL_PARAM_modified(¶ms[0]) + /* ... but, we should get a return size too! */ + && derl != 0 + && (der = OPENSSL_malloc(derl)) != NULL) { + unsigned char *derp = der; + + params[0] = OSSL_PARAM_construct_octet_string(k, der, derl); + if (EVP_PKEY_CTX_get_params(ctx, params) + && OSSL_PARAM_modified(¶ms[0]) + && d2i_ASN1_TYPE(&type, (const unsigned char **)&derp, + derl) != NULL) { + /* + * Don't free alg->parameter, see comment further up. + * Worst case, alg->parameter gets assigned its own value. + */ + alg->parameter = type; + ret = 1; + } + } + err: + OPENSSL_free(der); + return ret; +} + +int EVP_PKEY_CTX_get_algor(EVP_PKEY_CTX *ctx, X509_ALGOR **alg) +{ + int ret = -1; /* Assume the worst */ + OSSL_PARAM params[2]; + size_t aid_len = 0; + const char *k_aid = OSSL_SIGNATURE_PARAM_ALGORITHM_ID; + + params[0] = OSSL_PARAM_construct_octet_string(k_aid, NULL, 0); + params[1] = OSSL_PARAM_construct_end(); + + if (EVP_PKEY_CTX_get_params(ctx, params) <= 0) + goto err; + + if (OSSL_PARAM_modified(¶ms[0])) + aid_len = params[0].return_size; + if (aid_len == 0) { + ERR_raise(ERR_LIB_EVP, EVP_R_GETTING_ALGORITHMIDENTIFIER_NOT_SUPPORTED); + ret = -2; + goto err; + } + if (alg != NULL) { + unsigned char *aid = NULL; + const unsigned char *pp = NULL; + + if ((aid = OPENSSL_malloc(aid_len)) != NULL) { + params[0] = OSSL_PARAM_construct_octet_string(k_aid, aid, aid_len); + pp = aid; + if (EVP_PKEY_CTX_get_params(ctx, params) + && OSSL_PARAM_modified(¶ms[0]) + && d2i_X509_ALGOR(alg, &pp, aid_len) != NULL) + ret = 1; + } + OPENSSL_free(aid); + } + err: + return ret; +} + #endif /* !defined(FIPS_MODULE) */ diff --git a/crypto/evp/evp_local.h b/crypto/evp/evp_local.h index 8c1ff35cf3..ae8c7bb8a8 100644 --- a/crypto/evp/evp_local.h +++ b/crypto/evp/evp_local.h @@ -113,6 +113,8 @@ struct evp_keymgmt_st { /* Generation, a complex constructor */ OSSL_FUNC_keymgmt_gen_init_fn *gen_init; OSSL_FUNC_keymgmt_gen_set_template_fn *gen_set_template; + OSSL_FUNC_keymgmt_gen_get_params_fn *gen_get_params; + OSSL_FUNC_keymgmt_gen_gettable_params_fn *gen_gettable_params; OSSL_FUNC_keymgmt_gen_set_params_fn *gen_set_params; OSSL_FUNC_keymgmt_gen_settable_params_fn *gen_settable_params; OSSL_FUNC_keymgmt_gen_fn *gen; @@ -165,8 +167,14 @@ struct evp_signature_st { OSSL_FUNC_signature_newctx_fn *newctx; OSSL_FUNC_signature_sign_init_fn *sign_init; OSSL_FUNC_signature_sign_fn *sign; + OSSL_FUNC_signature_sign_message_init_fn *sign_message_init; + OSSL_FUNC_signature_sign_message_update_fn *sign_message_update; + OSSL_FUNC_signature_sign_message_final_fn *sign_message_final; OSSL_FUNC_signature_verify_init_fn *verify_init; OSSL_FUNC_signature_verify_fn *verify; + OSSL_FUNC_signature_verify_message_init_fn *verify_message_init; + OSSL_FUNC_signature_verify_message_update_fn *verify_message_update; + OSSL_FUNC_signature_verify_message_final_fn *verify_message_final; OSSL_FUNC_signature_verify_recover_init_fn *verify_recover_init; OSSL_FUNC_signature_verify_recover_fn *verify_recover; OSSL_FUNC_signature_digest_sign_init_fn *digest_sign_init; @@ -187,6 +195,9 @@ struct evp_signature_st { OSSL_FUNC_signature_gettable_ctx_md_params_fn *gettable_ctx_md_params; OSSL_FUNC_signature_set_ctx_md_params_fn *set_ctx_md_params; OSSL_FUNC_signature_settable_ctx_md_params_fn *settable_ctx_md_params; + + /* Signature object checking */ + OSSL_FUNC_signature_query_key_types_fn *query_key_types; } /* EVP_SIGNATURE */; struct evp_asym_cipher_st { diff --git a/crypto/evp/keymgmt_meth.c b/crypto/evp/keymgmt_meth.c index e3bec60abc..c9c09f7dac 100644 --- a/crypto/evp/keymgmt_meth.c +++ b/crypto/evp/keymgmt_meth.c @@ -60,6 +60,7 @@ static void *keymgmt_from_algorithm(int name_id, int setgenparamfncnt = 0; int importfncnt = 0, exportfncnt = 0; int importtypesfncnt = 0, exporttypesfncnt = 0; + int getgenparamfncnt = 0; if ((keymgmt = keymgmt_new()) == NULL) return NULL; @@ -100,6 +101,20 @@ static void *keymgmt_from_algorithm(int name_id, OSSL_FUNC_keymgmt_gen_settable_params(fns); } break; + case OSSL_FUNC_KEYMGMT_GEN_GET_PARAMS: + if (keymgmt->gen_get_params == NULL) { + getgenparamfncnt++; + keymgmt->gen_get_params = + OSSL_FUNC_keymgmt_gen_get_params(fns); + } + break; + case OSSL_FUNC_KEYMGMT_GEN_GETTABLE_PARAMS: + if (keymgmt->gen_gettable_params == NULL) { + getgenparamfncnt++; + keymgmt->gen_gettable_params = + OSSL_FUNC_keymgmt_gen_gettable_params(fns); + } + break; case OSSL_FUNC_KEYMGMT_GEN: if (keymgmt->gen == NULL) keymgmt->gen = OSSL_FUNC_keymgmt_gen(fns); @@ -225,6 +240,7 @@ static void *keymgmt_from_algorithm(int name_id, || (getparamfncnt != 0 && getparamfncnt != 2) || (setparamfncnt != 0 && setparamfncnt != 2) || (setgenparamfncnt != 0 && setgenparamfncnt != 2) + || (getgenparamfncnt != 0 && getgenparamfncnt != 2) || (importfncnt != 0 && importfncnt != 2) || (exportfncnt != 0 && exportfncnt != 2) || (keymgmt->gen != NULL @@ -405,6 +421,23 @@ const OSSL_PARAM *EVP_KEYMGMT_gen_settable_params(const EVP_KEYMGMT *keymgmt) return keymgmt->gen_settable_params(NULL, provctx); } +int evp_keymgmt_gen_get_params(const EVP_KEYMGMT *keymgmt, void *genctx, + OSSL_PARAM params[]) +{ + if (keymgmt->gen_get_params == NULL) + return 0; + return keymgmt->gen_get_params(genctx, params); +} + +const OSSL_PARAM *EVP_KEYMGMT_gen_gettable_params(const EVP_KEYMGMT *keymgmt) +{ + void *provctx = ossl_provider_ctx(EVP_KEYMGMT_get0_provider(keymgmt)); + + if (keymgmt->gen_gettable_params == NULL) + return NULL; + return keymgmt->gen_gettable_params(NULL, provctx); +} + void *evp_keymgmt_gen(const EVP_KEYMGMT *keymgmt, void *genctx, OSSL_CALLBACK *cb, void *cbarg) { diff --git a/crypto/evp/m_sigver.c b/crypto/evp/m_sigver.c index 3a979f4bd4..8845148176 100644 --- a/crypto/evp/m_sigver.c +++ b/crypto/evp/m_sigver.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,12 +17,12 @@ #include "evp_local.h" #ifndef FIPS_MODULE - static int update(EVP_MD_CTX *ctx, const void *data, size_t datalen) { ERR_raise(ERR_LIB_EVP, EVP_R_ONLY_ONESHOT_SUPPORTED); return 0; } +#endif /* * If we get the "NULL" md then the name comes back as "UNDEF". We want to use @@ -58,8 +58,10 @@ static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, reinit = 0; if (e == NULL) ctx->pctx = EVP_PKEY_CTX_new_from_pkey(libctx, pkey, props); +#ifndef FIPS_MODULE else ctx->pctx = EVP_PKEY_CTX_new(pkey, e); +#endif } if (ctx->pctx == NULL) return 0; @@ -241,6 +243,11 @@ static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, if (ctx->fetched_digest != NULL) { ctx->digest = ctx->reqdigest = ctx->fetched_digest; } else { +#ifdef FIPS_MODULE + (void)ERR_clear_last_mark(); + ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); + goto err; +#else /* legacy engine support : remove the mark when this is deleted */ ctx->reqdigest = ctx->digest = EVP_get_digestbyname(mdname); if (ctx->digest == NULL) { @@ -248,6 +255,7 @@ static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); goto err; } +#endif } (void)ERR_pop_to_mark(); } @@ -293,6 +301,9 @@ static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, EVP_KEYMGMT_free(tmp_keymgmt); tmp_keymgmt = NULL; +#ifdef FIPS_MODULE + return 0; +#else if (type == NULL && mdname != NULL) type = evp_get_digestbyname_ex(locpctx->libctx, mdname); @@ -355,7 +366,7 @@ static int do_sigver_init(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, ctx->pctx->flag_call_digest_custom = 1; ret = 1; - +#endif end: #ifndef FIPS_MODULE if (ret > 0) @@ -375,12 +386,14 @@ int EVP_DigestSignInit_ex(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, params); } +#ifndef FIPS_MODULE int EVP_DigestSignInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, const EVP_MD *type, ENGINE *e, EVP_PKEY *pkey) { return do_sigver_init(ctx, pctx, type, NULL, NULL, NULL, e, pkey, 0, NULL); } +#endif int EVP_DigestVerifyInit_ex(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, const char *mdname, OSSL_LIB_CTX *libctx, @@ -391,13 +404,14 @@ int EVP_DigestVerifyInit_ex(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, params); } +#ifndef FIPS_MODULE int EVP_DigestVerifyInit(EVP_MD_CTX *ctx, EVP_PKEY_CTX **pctx, const EVP_MD *type, ENGINE *e, EVP_PKEY *pkey) { return do_sigver_init(ctx, pctx, type, NULL, NULL, NULL, e, pkey, 1, NULL); } -#endif /* FIPS_MDOE */ +#endif /* FIPS_MODULE */ int EVP_DigestSignUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) { @@ -423,6 +437,10 @@ int EVP_DigestSignUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) data, dsize); legacy: +#ifdef FIPS_MODULE + ERR_raise(ERR_LIB_EVP, EVP_R_UPDATE_ERROR); + return 0; +#else if (pctx != NULL) { /* do_sigver_init() checked that |digest_custom| is non-NULL */ if (pctx->flag_call_digest_custom @@ -432,6 +450,7 @@ int EVP_DigestSignUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) } return EVP_DigestUpdate(ctx, data, dsize); +#endif } int EVP_DigestVerifyUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) @@ -458,6 +477,10 @@ int EVP_DigestVerifyUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) data, dsize); legacy: +#ifdef FIPS_MODULE + ERR_raise(ERR_LIB_EVP, EVP_R_UPDATE_ERROR); + return 0; +#else if (pctx != NULL) { /* do_sigver_init() checked that |digest_custom| is non-NULL */ if (pctx->flag_call_digest_custom @@ -467,13 +490,16 @@ int EVP_DigestVerifyUpdate(EVP_MD_CTX *ctx, const void *data, size_t dsize) } return EVP_DigestUpdate(ctx, data, dsize); +#endif } -#ifndef FIPS_MODULE int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, size_t *siglen) { - int sctx = 0, r = 0; +#ifndef FIPS_MODULE + int sctx = 0; +#endif + int r = 0; EVP_PKEY_CTX *dctx = NULL, *pctx = ctx->pctx; if ((ctx->flags & EVP_MD_CTX_FLAG_FINALISED) != 0) { @@ -487,12 +513,14 @@ int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, || pctx->op.sig.signature == NULL) goto legacy; +#ifndef FIPS_MODULE if (sigret != NULL && (ctx->flags & EVP_MD_CTX_FLAG_FINALISE) == 0) { /* try dup */ dctx = EVP_PKEY_CTX_dup(pctx); if (dctx != NULL) pctx = dctx; } +#endif r = pctx->op.sig.signature->digest_sign_final(pctx->op.sig.algctx, sigret, siglen, sigret == NULL ? 0 : *siglen); @@ -503,6 +531,10 @@ int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, return r; legacy: +#ifdef FIPS_MODULE + ERR_raise(ERR_LIB_EVP, EVP_R_UPDATE_ERROR); + return 0; +#else if (pctx == NULL || pctx->pmeth == NULL) { ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); return 0; @@ -569,11 +601,12 @@ int EVP_DigestSignFinal(EVP_MD_CTX *ctx, unsigned char *sigret, } else { int s = EVP_MD_get_size(ctx->digest); - if (s < 0 || EVP_PKEY_sign(pctx, sigret, siglen, NULL, s) <= 0) + if (s <= 0 || EVP_PKEY_sign(pctx, sigret, siglen, NULL, s) <= 0) return 0; } } return 1; +#endif } int EVP_DigestSign(EVP_MD_CTX *ctx, unsigned char *sigret, size_t *siglen, @@ -598,6 +631,11 @@ int EVP_DigestSign(EVP_MD_CTX *ctx, unsigned char *sigret, size_t *siglen, sigret == NULL ? 0 : *siglen, tbs, tbslen); } +#ifdef FIPS_MODULE + } + ERR_raise(ERR_LIB_EVP, EVP_R_FINAL_ERROR); + return 0; +#else } else { /* legacy */ if (ctx->pctx->pmeth != NULL && ctx->pctx->pmeth->digestsign != NULL) @@ -607,15 +645,18 @@ int EVP_DigestSign(EVP_MD_CTX *ctx, unsigned char *sigret, size_t *siglen, if (sigret != NULL && EVP_DigestSignUpdate(ctx, tbs, tbslen) <= 0) return 0; return EVP_DigestSignFinal(ctx, sigret, siglen); +#endif } int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig, size_t siglen) { +#ifndef FIPS_MODULE + int vctx = 0; + unsigned int mdlen = 0; unsigned char md[EVP_MAX_MD_SIZE]; +#endif int r = 0; - unsigned int mdlen = 0; - int vctx = 0; EVP_PKEY_CTX *dctx = NULL, *pctx = ctx->pctx; if ((ctx->flags & EVP_MD_CTX_FLAG_FINALISED) != 0) { @@ -629,12 +670,14 @@ int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig, || pctx->op.sig.signature == NULL) goto legacy; +#ifndef FIPS_MODULE if ((ctx->flags & EVP_MD_CTX_FLAG_FINALISE) == 0) { /* try dup */ dctx = EVP_PKEY_CTX_dup(pctx); if (dctx != NULL) pctx = dctx; } +#endif r = pctx->op.sig.signature->digest_verify_final(pctx->op.sig.algctx, sig, siglen); if (dctx == NULL) @@ -644,6 +687,10 @@ int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig, return r; legacy: +#ifdef FIPS_MODULE + ERR_raise(ERR_LIB_EVP, EVP_R_UPDATE_ERROR); + return 0; +#else if (pctx == NULL || pctx->pmeth == NULL) { ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); return 0; @@ -683,6 +730,7 @@ int EVP_DigestVerifyFinal(EVP_MD_CTX *ctx, const unsigned char *sig, if (vctx || !r) return r; return EVP_PKEY_verify(pctx, sig, siglen, md, mdlen); +#endif } int EVP_DigestVerify(EVP_MD_CTX *ctx, const unsigned char *sigret, @@ -705,14 +753,18 @@ int EVP_DigestVerify(EVP_MD_CTX *ctx, const unsigned char *sigret, sigret, siglen, tbs, tbslen); } +#ifdef FIPS_MODULE + } + ERR_raise(ERR_LIB_EVP, EVP_R_FINAL_ERROR); + return 0; +#else } else { /* legacy */ if (ctx->pctx->pmeth != NULL && ctx->pctx->pmeth->digestverify != NULL) return ctx->pctx->pmeth->digestverify(ctx, sigret, siglen, tbs, tbslen); } - if (EVP_DigestVerifyUpdate(ctx, tbs, tbslen) <= 0) return -1; return EVP_DigestVerifyFinal(ctx, sigret, siglen); +#endif } -#endif /* FIPS_MODULE */ diff --git a/crypto/evp/p5_crpt.c b/crypto/evp/p5_crpt.c index f3ac675ff2..eb8fbc09fb 100644 --- a/crypto/evp/p5_crpt.c +++ b/crypto/evp/p5_crpt.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -78,7 +78,7 @@ int PKCS5_PBE_keyivgen_ex(EVP_CIPHER_CTX *cctx, const char *pass, int passlen, passlen = strlen(pass); mdsize = EVP_MD_get_size(md); - if (mdsize < 0) + if (mdsize <= 0) goto err; kdf = EVP_KDF_fetch(libctx, OSSL_KDF_NAME_PBKDF1, propq); diff --git a/crypto/evp/p_lib.c b/crypto/evp/p_lib.c index b7377751bd..09bd185a25 100644 --- a/crypto/evp/p_lib.c +++ b/crypto/evp/p_lib.c @@ -525,8 +525,7 @@ EVP_PKEY *EVP_PKEY_new_raw_public_key(int type, ENGINE *e, return new_raw_key_int(NULL, NULL, NULL, type, e, pub, len, 0); } -struct raw_key_details_st -{ +struct raw_key_details_st { unsigned char **key; size_t *len; int selection; diff --git a/crypto/evp/pmeth_lib.c b/crypto/evp/pmeth_lib.c index 71485c949c..eb8c37eaf6 100644 --- a/crypto/evp/pmeth_lib.c +++ b/crypto/evp/pmeth_lib.c @@ -732,6 +732,12 @@ int EVP_PKEY_CTX_get_params(EVP_PKEY_CTX *ctx, OSSL_PARAM *params) return ctx->op.encap.kem->get_ctx_params(ctx->op.encap.algctx, params); + if (EVP_PKEY_CTX_IS_GEN_OP(ctx) + && ctx->keymgmt != NULL + && ctx->keymgmt->gen_get_params != NULL) + return + evp_keymgmt_gen_get_params(ctx->keymgmt, ctx->op.keymgmt.genctx, + params); break; #ifndef FIPS_MODULE case EVP_PKEY_STATE_UNKNOWN: @@ -777,6 +783,13 @@ const OSSL_PARAM *EVP_PKEY_CTX_gettable_params(const EVP_PKEY_CTX *ctx) return ctx->op.encap.kem->gettable_ctx_params(ctx->op.encap.algctx, provctx); } + if (EVP_PKEY_CTX_IS_GEN_OP(ctx) + && ctx->keymgmt != NULL + && ctx->keymgmt->gen_gettable_params != NULL) { + provctx = ossl_provider_ctx(EVP_KEYMGMT_get0_provider(ctx->keymgmt)); + return ctx->keymgmt->gen_gettable_params(ctx->op.keymgmt.genctx, + provctx); + } return NULL; } diff --git a/crypto/evp/signature.c b/crypto/evp/signature.c index c05eb78b51..7d619edfae 100644 --- a/crypto/evp/signature.c +++ b/crypto/evp/signature.c @@ -7,8 +7,10 @@ * https://www.openssl.org/source/license.html */ +#include #include #include +#include #include #include #include "internal/numbers.h" /* includes SIZE_MAX */ @@ -42,9 +44,13 @@ static void *evp_signature_from_algorithm(int name_id, { const OSSL_DISPATCH *fns = algodef->implementation; EVP_SIGNATURE *signature = NULL; - int ctxfncnt = 0, signfncnt = 0, verifyfncnt = 0, verifyrecfncnt = 0; - int digsignfncnt = 0, digverifyfncnt = 0; + /* Counts newctx / freectx */ + int ctxfncnt = 0; + /* Counts all init functions */ + int initfncnt = 0; + /* Counts all parameter functions */ int gparamfncnt = 0, sparamfncnt = 0, gmdparamfncnt = 0, smdparamfncnt = 0; + int valid = 0; if ((signature = evp_signature_new(prov)) == NULL) { ERR_raise(ERR_LIB_EVP, ERR_R_EVP_LIB); @@ -68,59 +74,93 @@ static void *evp_signature_from_algorithm(int name_id, if (signature->sign_init != NULL) break; signature->sign_init = OSSL_FUNC_signature_sign_init(fns); - signfncnt++; + initfncnt++; break; case OSSL_FUNC_SIGNATURE_SIGN: if (signature->sign != NULL) break; signature->sign = OSSL_FUNC_signature_sign(fns); - signfncnt++; + break; + case OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT: + if (signature->sign_message_init != NULL) + break; + signature->sign_message_init + = OSSL_FUNC_signature_sign_message_init(fns); + initfncnt++; + break; + case OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_UPDATE: + if (signature->sign_message_update != NULL) + break; + signature->sign_message_update + = OSSL_FUNC_signature_sign_message_update(fns); + break; + case OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_FINAL: + if (signature->sign_message_final != NULL) + break; + signature->sign_message_final + = OSSL_FUNC_signature_sign_message_final(fns); break; case OSSL_FUNC_SIGNATURE_VERIFY_INIT: if (signature->verify_init != NULL) break; signature->verify_init = OSSL_FUNC_signature_verify_init(fns); - verifyfncnt++; + initfncnt++; break; case OSSL_FUNC_SIGNATURE_VERIFY: if (signature->verify != NULL) break; signature->verify = OSSL_FUNC_signature_verify(fns); - verifyfncnt++; + break; + case OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT: + if (signature->verify_message_init != NULL) + break; + signature->verify_message_init + = OSSL_FUNC_signature_verify_message_init(fns); + initfncnt++; + break; + case OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_UPDATE: + if (signature->verify_message_update != NULL) + break; + signature->verify_message_update + = OSSL_FUNC_signature_verify_message_update(fns); + break; + case OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_FINAL: + if (signature->verify_message_final != NULL) + break; + signature->verify_message_final + = OSSL_FUNC_signature_verify_message_final(fns); break; case OSSL_FUNC_SIGNATURE_VERIFY_RECOVER_INIT: if (signature->verify_recover_init != NULL) break; signature->verify_recover_init = OSSL_FUNC_signature_verify_recover_init(fns); - verifyrecfncnt++; + initfncnt++; break; case OSSL_FUNC_SIGNATURE_VERIFY_RECOVER: if (signature->verify_recover != NULL) break; signature->verify_recover = OSSL_FUNC_signature_verify_recover(fns); - verifyrecfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT: if (signature->digest_sign_init != NULL) break; signature->digest_sign_init = OSSL_FUNC_signature_digest_sign_init(fns); + initfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_SIGN_UPDATE: if (signature->digest_sign_update != NULL) break; signature->digest_sign_update = OSSL_FUNC_signature_digest_sign_update(fns); - digsignfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_SIGN_FINAL: if (signature->digest_sign_final != NULL) break; signature->digest_sign_final = OSSL_FUNC_signature_digest_sign_final(fns); - digsignfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_SIGN: if (signature->digest_sign != NULL) @@ -133,20 +173,19 @@ static void *evp_signature_from_algorithm(int name_id, break; signature->digest_verify_init = OSSL_FUNC_signature_digest_verify_init(fns); + initfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_UPDATE: if (signature->digest_verify_update != NULL) break; signature->digest_verify_update = OSSL_FUNC_signature_digest_verify_update(fns); - digverifyfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_FINAL: if (signature->digest_verify_final != NULL) break; signature->digest_verify_final = OSSL_FUNC_signature_digest_verify_final(fns); - digverifyfncnt++; break; case OSSL_FUNC_SIGNATURE_DIGEST_VERIFY: if (signature->digest_verify != NULL) @@ -221,48 +260,107 @@ static void *evp_signature_from_algorithm(int name_id, = OSSL_FUNC_signature_settable_ctx_md_params(fns); smdparamfncnt++; break; + case OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES: + if (signature->query_key_types != NULL) + break; + signature->query_key_types + = OSSL_FUNC_signature_query_key_types(fns); + break; } } - if (ctxfncnt != 2 - || (signfncnt == 0 - && verifyfncnt == 0 - && verifyrecfncnt == 0 - && digsignfncnt == 0 - && digverifyfncnt == 0 + /* + * In order to be a consistent set of functions we must have at least + * a set of context functions (newctx and freectx) as well as a set of + * "signature" functions. Because there's an overlap between some sets + * of functions, counters don't always cut it, we must test known + * combinations. + * We start by assuming the implementation is valid, and then look for + * reasons it's not. + */ + valid = 1; + /* Start with the ones where counters say enough */ + if (ctxfncnt != 2) + /* newctx or freectx missing */ + valid = 0; + if (valid + && ((gparamfncnt != 0 && gparamfncnt != 2) + || (sparamfncnt != 0 && sparamfncnt != 2) + || (gmdparamfncnt != 0 && gmdparamfncnt != 2) + || (smdparamfncnt != 0 && smdparamfncnt != 2))) + /* + * Params functions are optional, but if defined, they must + * be pairwise complete sets, i.e. a getter must have an + * associated gettable, etc + */ + valid = 0; + if (valid && initfncnt == 0) + /* No init functions */ + valid = 0; + + /* Now we check for function combinations */ + if (valid + && ((signature->sign_init != NULL + && signature->sign == NULL) + || (signature->sign_message_init != NULL + && signature->sign == NULL + && (signature->sign_message_update == NULL + || signature->sign_message_final == NULL)))) + /* sign_init functions with no signing function? That's weird */ + valid = 0; + if (valid + && (signature->sign != NULL + || signature->sign_message_update != NULL + || signature->sign_message_final != NULL) + && signature->sign_init == NULL + && signature->sign_message_init == NULL) + /* signing functions with no sign_init? That's odd */ + valid = 0; + + if (valid + && ((signature->verify_init != NULL + && signature->verify == NULL) + || (signature->verify_message_init != NULL + && signature->verify == NULL + && (signature->verify_message_update == NULL + || signature->verify_message_final == NULL)))) + /* verify_init functions with no verification function? That's weird */ + valid = 0; + if (valid + && (signature->verify != NULL + || signature->verify_message_update != NULL + || signature->verify_message_final != NULL) + && signature->verify_init == NULL + && signature->verify_message_init == NULL) + /* verification functions with no verify_init? That's odd */ + valid = 0; + + if (valid + && (signature->verify_recover_init != NULL) + && (signature->verify_recover == NULL)) + /* verify_recover_init functions with no verify_recover? How quaint */ + valid = 0; + + if (valid + && (signature->digest_sign_init != NULL && signature->digest_sign == NULL - && signature->digest_verify == NULL) - || (signfncnt != 0 && signfncnt != 2) - || (verifyfncnt != 0 && verifyfncnt != 2) - || (verifyrecfncnt != 0 && verifyrecfncnt != 2) - || (digsignfncnt != 0 && digsignfncnt != 2) - || (digsignfncnt == 2 && signature->digest_sign_init == NULL) - || (digverifyfncnt != 0 && digverifyfncnt != 2) - || (digverifyfncnt == 2 && signature->digest_verify_init == NULL) - || (signature->digest_sign != NULL - && signature->digest_sign_init == NULL) - || (signature->digest_verify != NULL - && signature->digest_verify_init == NULL) - || (gparamfncnt != 0 && gparamfncnt != 2) - || (sparamfncnt != 0 && sparamfncnt != 2) - || (gmdparamfncnt != 0 && gmdparamfncnt != 2) - || (smdparamfncnt != 0 && smdparamfncnt != 2)) { + && (signature->digest_sign_update == NULL + || signature->digest_sign_final == NULL))) /* - * In order to be a consistent set of functions we must have at least - * a set of context functions (newctx and freectx) as well as a set of - * "signature" functions: - * (sign_init, sign) or - * (verify_init verify) or - * (verify_recover_init, verify_recover) or - * (digest_sign_init, digest_sign_update, digest_sign_final) or - * (digest_verify_init, digest_verify_update, digest_verify_final) or - * (digest_sign_init, digest_sign) or - * (digest_verify_init, digest_verify). - * - * set_ctx_params and settable_ctx_params are optional, but if one of - * them is present then the other one must also be present. The same - * applies to get_ctx_params and gettable_ctx_params. The same rules - * apply to the "md_params" functions. The dupctx function is optional. + * You can't have a digest_sign_init without *some* performing functions + */ + valid = 0; + + if (valid + && ((signature->digest_verify_init != NULL + && signature->digest_verify == NULL + && (signature->digest_verify_update == NULL + || signature->digest_verify_final == NULL)))) + /* + * You can't have a digest_verify_init without *some* performing functions */ + valid = 0; + + if (!valid) { ERR_raise(ERR_LIB_EVP, EVP_R_INVALID_PROVIDER_FUNCTIONS); goto err; } @@ -387,12 +485,11 @@ const OSSL_PARAM *EVP_SIGNATURE_settable_ctx_params(const EVP_SIGNATURE *sig) return sig->settable_ctx_params(NULL, provctx); } -static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, - const OSSL_PARAM params[]) +static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, EVP_SIGNATURE *signature, + int operation, const OSSL_PARAM params[]) { int ret = 0; void *provkey = NULL; - EVP_SIGNATURE *signature = NULL; EVP_KEYMGMT *tmp_keymgmt = NULL; const OSSL_PROVIDER *tmp_prov = NULL; const char *supported_sig = NULL; @@ -406,91 +503,30 @@ static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, evp_pkey_ctx_free_old_ops(ctx); ctx->operation = operation; - ERR_set_mark(); - - if (evp_pkey_ctx_is_legacy(ctx)) - goto legacy; - - if (ctx->pkey == NULL) { - ERR_clear_last_mark(); - ERR_raise(ERR_LIB_EVP, EVP_R_NO_KEY_SET); - goto err; - } - - /* - * Try to derive the supported signature from |ctx->keymgmt|. - */ - if (!ossl_assert(ctx->pkey->keymgmt == NULL - || ctx->pkey->keymgmt == ctx->keymgmt)) { - ERR_clear_last_mark(); - ERR_raise(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR); - goto err; - } - supported_sig = evp_keymgmt_util_query_operation_name(ctx->keymgmt, - OSSL_OP_SIGNATURE); - if (supported_sig == NULL) { - ERR_clear_last_mark(); - ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); - goto err; - } + if (signature != NULL) { + /* + * It's important to figure out what the key type should be, and if + * that is what we have in ctx. + */ - /* - * We perform two iterations: - * - * 1. Do the normal signature fetch, using the fetching data given by - * the EVP_PKEY_CTX. - * 2. Do the provider specific signature fetch, from the same provider - * as |ctx->keymgmt| - * - * We then try to fetch the keymgmt from the same provider as the - * signature, and try to export |ctx->pkey| to that keymgmt (when - * this keymgmt happens to be the same as |ctx->keymgmt|, the export - * is a no-op, but we call it anyway to not complicate the code even - * more). - * If the export call succeeds (returns a non-NULL provider key pointer), - * we're done and can perform the operation itself. If not, we perform - * the second iteration, or jump to legacy. - */ - for (iter = 1; iter < 3 && provkey == NULL; iter++) { EVP_KEYMGMT *tmp_keymgmt_tofree = NULL; - /* - * If we're on the second iteration, free the results from the first. - * They are NULL on the first iteration, so no need to check what - * iteration we're on. - */ - EVP_SIGNATURE_free(signature); - EVP_KEYMGMT_free(tmp_keymgmt); - - switch (iter) { - case 1: - signature = - EVP_SIGNATURE_fetch(ctx->libctx, supported_sig, ctx->propquery); - if (signature != NULL) - tmp_prov = EVP_SIGNATURE_get0_provider(signature); - break; - case 2: - tmp_prov = EVP_KEYMGMT_get0_provider(ctx->keymgmt); - signature = - evp_signature_fetch_from_prov((OSSL_PROVIDER *)tmp_prov, - supported_sig, ctx->propquery); - if (signature == NULL) - goto legacy; - break; + if (ctx->pkey == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_NO_KEY_SET); + goto err; } - if (signature == NULL) - continue; /* - * Ensure that the key is provided, either natively, or as a cached - * export. We start by fetching the keymgmt with the same name as - * |ctx->pkey|, but from the provider of the signature method, using - * the same property query as when fetching the signature method. - * With the keymgmt we found (if we did), we try to export |ctx->pkey| - * to it (evp_pkey_export_to_provider() is smart enough to only actually - - * export it if |tmp_keymgmt| is different from |ctx->pkey|'s keymgmt) + * Ensure that the key is provided, either natively, or as a + * cached export. We start by fetching the keymgmt with the same + * name as |ctx->pkey|, but from the provider of the signature + * method, using the same property query as when fetching the + * signature method. With the keymgmt we found (if we did), we + * try to export |ctx->pkey| to it (evp_pkey_export_to_provider() + * is smart enough to only actually export it if |tmp_keymgmt| + * is different from |ctx->pkey|'s keymgmt) */ + tmp_prov = EVP_SIGNATURE_get0_provider(signature); tmp_keymgmt_tofree = tmp_keymgmt = evp_keymgmt_fetch_from_prov((OSSL_PROVIDER *)tmp_prov, EVP_KEYMGMT_get0_name(ctx->keymgmt), @@ -500,14 +536,163 @@ static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, &tmp_keymgmt, ctx->propquery); if (tmp_keymgmt == NULL) EVP_KEYMGMT_free(tmp_keymgmt_tofree); - } - if (provkey == NULL) { - EVP_SIGNATURE_free(signature); - goto legacy; - } + if (provkey == NULL) + goto end; - ERR_pop_to_mark(); + /* + * Check that the signature matches the given key. This is not + * designed to work with legacy keys, so has to be done after we've + * ensured that the key is at least exported to a provider (above). + */ + if (signature->query_key_types != NULL) { + /* This is expect to be a NULL terminated array */ + const char **keytypes; + + keytypes = signature->query_key_types(); + for (; *keytypes != NULL; keytypes++) + if (EVP_PKEY_CTX_is_a(ctx, *keytypes)) + break; + if (*keytypes == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_SIGNATURE_TYPE_AND_KEY_TYPE_INCOMPATIBLE); + return -2; + } + } else { + /* + * Fallback 1: + * check if the keytype is the same as the signature algorithm name + */ + const char *keytype = EVP_KEYMGMT_get0_name(ctx->keymgmt); + int ok = EVP_SIGNATURE_is_a(signature, keytype); + + /* + * Fallback 2: + * query the pkey for a default signature algorithm name, and check + * if it matches the signature implementation + */ + if (!ok) { + const char *signame + = evp_keymgmt_util_query_operation_name(ctx->keymgmt, + OSSL_OP_SIGNATURE); + + ok = EVP_SIGNATURE_is_a(signature, signame); + } + + /* If none of the fallbacks helped, we're lost */ + if (!ok) { + ERR_raise(ERR_LIB_EVP, EVP_R_SIGNATURE_TYPE_AND_KEY_TYPE_INCOMPATIBLE); + return -2; + } + } + + if (!EVP_SIGNATURE_up_ref(signature)) + return 0; + } else { + /* Without a pre-fetched signature, it must be figured out somehow */ + ERR_set_mark(); + + if (evp_pkey_ctx_is_legacy(ctx)) + goto legacy; + + if (ctx->pkey == NULL) { + ERR_clear_last_mark(); + ERR_raise(ERR_LIB_EVP, EVP_R_NO_KEY_SET); + goto err; + } + + /* + * Try to derive the supported signature from |ctx->keymgmt|. + */ + if (!ossl_assert(ctx->pkey->keymgmt == NULL + || ctx->pkey->keymgmt == ctx->keymgmt)) { + ERR_clear_last_mark(); + ERR_raise(ERR_LIB_EVP, ERR_R_INTERNAL_ERROR); + goto err; + } + supported_sig + = evp_keymgmt_util_query_operation_name(ctx->keymgmt, + OSSL_OP_SIGNATURE); + if (supported_sig == NULL) { + ERR_clear_last_mark(); + ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); + goto err; + } + + /* + * We perform two iterations: + * + * 1. Do the normal signature fetch, using the fetching data given by + * the EVP_PKEY_CTX. + * 2. Do the provider specific signature fetch, from the same provider + * as |ctx->keymgmt| + * + * We then try to fetch the keymgmt from the same provider as the + * signature, and try to export |ctx->pkey| to that keymgmt (when + * this keymgmt happens to be the same as |ctx->keymgmt|, the export + * is a no-op, but we call it anyway to not complicate the code even + * more). + * If the export call succeeds (returns a non-NULL provider key pointer), + * we're done and can perform the operation itself. If not, we perform + * the second iteration, or jump to legacy. + */ + for (iter = 1; iter < 3 && provkey == NULL; iter++) { + EVP_KEYMGMT *tmp_keymgmt_tofree = NULL; + + /* + * If we're on the second iteration, free the results from the first. + * They are NULL on the first iteration, so no need to check what + * iteration we're on. + */ + EVP_SIGNATURE_free(signature); + EVP_KEYMGMT_free(tmp_keymgmt); + + switch (iter) { + case 1: + signature = + EVP_SIGNATURE_fetch(ctx->libctx, supported_sig, ctx->propquery); + if (signature != NULL) + tmp_prov = EVP_SIGNATURE_get0_provider(signature); + break; + case 2: + tmp_prov = EVP_KEYMGMT_get0_provider(ctx->keymgmt); + signature = + evp_signature_fetch_from_prov((OSSL_PROVIDER *)tmp_prov, + supported_sig, ctx->propquery); + if (signature == NULL) + goto legacy; + break; + } + if (signature == NULL) + continue; + + /* + * Ensure that the key is provided, either natively, or as a + * cached export. We start by fetching the keymgmt with the same + * name as |ctx->pkey|, but from the provider of the signature + * method, using the same property query as when fetching the + * signature method. With the keymgmt we found (if we did), we + * try to export |ctx->pkey| to it (evp_pkey_export_to_provider() + * is smart enough to only actually export it if |tmp_keymgmt| + * is different from |ctx->pkey|'s keymgmt) + */ + tmp_keymgmt_tofree = tmp_keymgmt = + evp_keymgmt_fetch_from_prov((OSSL_PROVIDER *)tmp_prov, + EVP_KEYMGMT_get0_name(ctx->keymgmt), + ctx->propquery); + if (tmp_keymgmt != NULL) + provkey = evp_pkey_export_to_provider(ctx->pkey, ctx->libctx, + &tmp_keymgmt, ctx->propquery); + if (tmp_keymgmt == NULL) + EVP_KEYMGMT_free(tmp_keymgmt_tofree); + } + + if (provkey == NULL) { + EVP_SIGNATURE_free(signature); + goto legacy; + } + + ERR_pop_to_mark(); + } /* No more legacy from here down to legacy: */ @@ -529,6 +714,14 @@ static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, } ret = signature->sign_init(ctx->op.sig.algctx, provkey, params); break; + case EVP_PKEY_OP_SIGNMSG: + if (signature->sign_message_init == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + ret = -2; + goto err; + } + ret = signature->sign_message_init(ctx->op.sig.algctx, provkey, params); + break; case EVP_PKEY_OP_VERIFY: if (signature->verify_init == NULL) { ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); @@ -537,14 +730,21 @@ static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, } ret = signature->verify_init(ctx->op.sig.algctx, provkey, params); break; + case EVP_PKEY_OP_VERIFYMSG: + if (signature->verify_message_init == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + ret = -2; + goto err; + } + ret = signature->verify_message_init(ctx->op.sig.algctx, provkey, params); + break; case EVP_PKEY_OP_VERIFYRECOVER: if (signature->verify_recover_init == NULL) { ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); ret = -2; goto err; } - ret = signature->verify_recover_init(ctx->op.sig.algctx, provkey, - params); + ret = signature->verify_recover_init(ctx->op.sig.algctx, provkey, params); break; default: ERR_raise(ERR_LIB_EVP, EVP_R_INITIALIZATION_ERROR); @@ -615,12 +815,69 @@ static int evp_pkey_signature_init(EVP_PKEY_CTX *ctx, int operation, int EVP_PKEY_sign_init(EVP_PKEY_CTX *ctx) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_SIGN, NULL); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_SIGN, NULL); } int EVP_PKEY_sign_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_SIGN, params); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_SIGN, params); +} + +int EVP_PKEY_sign_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]) +{ + return evp_pkey_signature_init(ctx, algo, EVP_PKEY_OP_SIGN, params); +} + +int EVP_PKEY_sign_message_init(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]) +{ + return evp_pkey_signature_init(ctx, algo, EVP_PKEY_OP_SIGNMSG, params); +} + +int EVP_PKEY_sign_message_update(EVP_PKEY_CTX *ctx, + const unsigned char *in, size_t inlen) +{ + if (ctx == NULL) { + ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER); + return -1; + } + + if (ctx->operation != EVP_PKEY_OP_SIGNMSG) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); + return -1; + } + + if (ctx->op.sig.signature->sign_message_update == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + return -2; + } + + return ctx->op.sig.signature->sign_message_update(ctx->op.sig.algctx, + in, inlen); +} + +int EVP_PKEY_sign_message_final(EVP_PKEY_CTX *ctx, + unsigned char *sig, size_t *siglen) +{ + if (ctx == NULL) { + ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER); + return -1; + } + + if (ctx->operation != EVP_PKEY_OP_SIGNMSG) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); + return -1; + } + + if (ctx->op.sig.signature->sign_message_final == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + return -2; + } + + return ctx->op.sig.signature->sign_message_final(ctx->op.sig.algctx, + sig, siglen, + (sig == NULL) ? 0 : *siglen); } int EVP_PKEY_sign(EVP_PKEY_CTX *ctx, @@ -634,7 +891,8 @@ int EVP_PKEY_sign(EVP_PKEY_CTX *ctx, return -1; } - if (ctx->operation != EVP_PKEY_OP_SIGN) { + if (ctx->operation != EVP_PKEY_OP_SIGN + && ctx->operation != EVP_PKEY_OP_SIGNMSG) { ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); return -1; } @@ -664,12 +922,88 @@ int EVP_PKEY_sign(EVP_PKEY_CTX *ctx, int EVP_PKEY_verify_init(EVP_PKEY_CTX *ctx) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_VERIFY, NULL); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_VERIFY, NULL); } int EVP_PKEY_verify_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_VERIFY, params); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_VERIFY, params); +} + +int EVP_PKEY_verify_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]) +{ + return evp_pkey_signature_init(ctx, algo, EVP_PKEY_OP_VERIFY, params); +} + +int EVP_PKEY_verify_message_init(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]) +{ + return evp_pkey_signature_init(ctx, algo, EVP_PKEY_OP_VERIFYMSG, params); +} + +int EVP_PKEY_CTX_set_signature(EVP_PKEY_CTX *ctx, + const unsigned char *sig, size_t siglen) +{ + OSSL_PARAM sig_params[2], *p = sig_params; + + if (ctx == NULL) { + ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER); + return 0; + } + + *p++ = OSSL_PARAM_construct_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, + /* + * Cast away the const. This is + * read only so should be safe + */ + (char *)sig, siglen); + *p = OSSL_PARAM_construct_end(); + + return EVP_PKEY_CTX_set_params(ctx, sig_params); +} + +int EVP_PKEY_verify_message_update(EVP_PKEY_CTX *ctx, + const unsigned char *in, size_t inlen) +{ + if (ctx == NULL) { + ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER); + return -1; + } + + if (ctx->operation != EVP_PKEY_OP_VERIFYMSG) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); + return -1; + } + + if (ctx->op.sig.signature->verify_message_update == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + return -2; + } + + return ctx->op.sig.signature->verify_message_update(ctx->op.sig.algctx, + in, inlen); +} + +int EVP_PKEY_verify_message_final(EVP_PKEY_CTX *ctx) +{ + if (ctx == NULL) { + ERR_raise(ERR_LIB_EVP, ERR_R_PASSED_NULL_PARAMETER); + return -1; + } + + if (ctx->operation != EVP_PKEY_OP_VERIFYMSG) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); + return -1; + } + + if (ctx->op.sig.signature->verify_message_final == NULL) { + ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + return -2; + } + + /* The signature must have been set with EVP_PKEY_CTX_set_signature() */ + return ctx->op.sig.signature->verify_message_final(ctx->op.sig.algctx); } int EVP_PKEY_verify(EVP_PKEY_CTX *ctx, @@ -683,7 +1017,8 @@ int EVP_PKEY_verify(EVP_PKEY_CTX *ctx, return -1; } - if (ctx->operation != EVP_PKEY_OP_VERIFY) { + if (ctx->operation != EVP_PKEY_OP_VERIFY + && ctx->operation != EVP_PKEY_OP_VERIFYMSG) { ERR_raise(ERR_LIB_EVP, EVP_R_OPERATION_NOT_INITIALIZED); return -1; } @@ -711,13 +1046,19 @@ int EVP_PKEY_verify(EVP_PKEY_CTX *ctx, int EVP_PKEY_verify_recover_init(EVP_PKEY_CTX *ctx) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_VERIFYRECOVER, NULL); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_VERIFYRECOVER, NULL); } int EVP_PKEY_verify_recover_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]) { - return evp_pkey_signature_init(ctx, EVP_PKEY_OP_VERIFYRECOVER, params); + return evp_pkey_signature_init(ctx, NULL, EVP_PKEY_OP_VERIFYRECOVER, params); +} + +int EVP_PKEY_verify_recover_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]) +{ + return evp_pkey_signature_init(ctx, algo, EVP_PKEY_OP_VERIFYRECOVER, params); } int EVP_PKEY_verify_recover(EVP_PKEY_CTX *ctx, diff --git a/crypto/ffc/ffc_params.c b/crypto/ffc/ffc_params.c index 680f85ffaf..d5cb310b7b 100644 --- a/crypto/ffc/ffc_params.c +++ b/crypto/ffc/ffc_params.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -27,11 +27,19 @@ void ossl_ffc_params_init(FFC_PARAMS *params) void ossl_ffc_params_cleanup(FFC_PARAMS *params) { +#ifdef FIPS_MODULE + BN_clear_free(params->p); + BN_clear_free(params->q); + BN_clear_free(params->g); + BN_clear_free(params->j); + OPENSSL_clear_free(params->seed, params->seedlen); +#else BN_free(params->p); BN_free(params->q); BN_free(params->g); BN_free(params->j); OPENSSL_free(params->seed); +#endif ossl_ffc_params_init(params); } diff --git a/crypto/ffc/ffc_params_generate.c b/crypto/ffc/ffc_params_generate.c index 8294fbec36..f6dc57fc99 100644 --- a/crypto/ffc/ffc_params_generate.c +++ b/crypto/ffc/ffc_params_generate.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -322,6 +322,9 @@ static int generate_q_fips186_4(BN_CTX *ctx, BIGNUM *q, const EVP_MD *evpmd, unsigned char *pmd; OSSL_LIB_CTX *libctx = ossl_bn_get_libctx(ctx); + if (mdsize <= 0) + goto err; + /* find q */ for (;;) { if (!BN_GENCB_call(cb, 0, m++)) @@ -814,6 +817,7 @@ int ossl_ffc_params_FIPS186_2_gen_verify(OSSL_LIB_CTX *libctx, BIGNUM *r0, *test, *tmp, *g = NULL, *q = NULL, *p = NULL; BN_MONT_CTX *mont = NULL; EVP_MD *md = NULL; + int md_size; size_t qsize; int n = 0, m = 0; int counter = 0, pcounter = 0, use_random_seed; @@ -842,8 +846,11 @@ int ossl_ffc_params_FIPS186_2_gen_verify(OSSL_LIB_CTX *libctx, } if (md == NULL) goto err; + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + goto err; if (N == 0) - N = EVP_MD_get_size(md) * 8; + N = md_size * 8; qsize = N >> 3; /* diff --git a/crypto/hashtable/build.info b/crypto/hashtable/build.info new file mode 100644 index 0000000000..514fcff6cf --- /dev/null +++ b/crypto/hashtable/build.info @@ -0,0 +1,6 @@ +LIBS=../../libcrypto +$COMMON=hashtable.c + +SOURCE[../../libcrypto]=$COMMON +SOURCE[../../providers/libfips.a]=$COMMON + diff --git a/crypto/hashtable/hashtable.c b/crypto/hashtable/hashtable.c new file mode 100644 index 0000000000..8d7f4751b2 --- /dev/null +++ b/crypto/hashtable/hashtable.c @@ -0,0 +1,760 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + * + * + * + * Notes On hash table design and layout + * This hashtable uses a hopscotch algorithm to do indexing. The data structure + * looks as follows: + * + * hash +--------------+ + * value+------->+ HT_VALUE | + * + +--------------+ + * +-------+ + * | | + * +---------------------------------------------------------+ + * | | | | | | + * | entry | entry | entry | entry | | + * | | | | | | + * +---------------------------------------------------------+ + * | | | + * | | | + * +---------------------------------------------------------+ + * | + + + + * | neighborhood[0] neighborhood[1] | + * | | + * | | + * +---------------------------------------------------------+ + * | + * + + * neighborhoods + * + * On lookup/insert/delete, the items key is hashed to a 64 bit value + * and the result is masked to provide an index into the neighborhoods + * table. Once a neighborhood is determined, an in-order search is done + * of the elements in the neighborhood indexes entries for a matching hash + * value, if found, the corresponding HT_VALUE is used for the respective + * operation. The number of entries in a neighborhood is determined at build + * time based on the cacheline size of the target CPU. The intent is for a + * neighborhood to have all entries in the neighborhood fit into a single cache + * line to speed up lookups. If all entries in a neighborhood are in use at the + * time of an insert, the table is expanded and rehashed. + * + * Lockless reads hash table is based on the same design but does not + * allow growing and deletion. Thus subsequent neighborhoods are always + * searched for a match until an empty entry is found. + */ + +#include +#include +#include +#include + +/* + * gcc defines __SANITIZE_THREAD__ + * but clang uses the feature attributes api + * map the latter to the former + */ +#if defined(__clang__) && defined(__has_feature) +# if __has_feature(thread_sanitizer) +# define __SANITIZE_THREADS__ +# endif +#endif + +#ifdef __SANITIZE_THREADS__ +# include +#endif + +#include "internal/numbers.h" +/* + * When we do a lookup/insert/delete, there is a high likelihood + * that we will iterate over at least part of the neighborhood list + * As such, because we design a neighborhood entry to fit into a single + * cache line it is advantageous, when supported to fetch the entire + * structure for faster lookups + */ +#if defined(__GNUC__) || defined(__CLANG__) +# define PREFETCH_NEIGHBORHOOD(x) __builtin_prefetch(x.entries) +# define PREFETCH(x) __builtin_prefetch(x) +#else +# define PREFETCH_NEIGHBORHOOD(x) +# define PREFETCH(x) +#endif + +static ossl_unused uint64_t fnv1a_hash(uint8_t *key, size_t len) +{ + uint64_t hash = 0xcbf29ce484222325ULL; + size_t i; + + for (i = 0; i < len; i++) { + hash ^= key[i]; + hash *= 0x00000100000001B3ULL; + } + return hash; +} + +/* + * Define our neighborhood list length + * Note: It should always be a power of 2 + */ +#define DEFAULT_NEIGH_LEN_LOG 4 +#define DEFAULT_NEIGH_LEN (1 << DEFAULT_NEIGH_LEN_LOG) + +/* + * For now assume cache line size is 64 bytes + */ +#define CACHE_LINE_BYTES 64 +#define CACHE_LINE_ALIGNMENT CACHE_LINE_BYTES + +#define NEIGHBORHOOD_LEN (CACHE_LINE_BYTES / sizeof(struct ht_neighborhood_entry_st)) +/* + * Defines our chains of values + */ +struct ht_internal_value_st { + HT_VALUE value; + HT *ht; +}; + +struct ht_neighborhood_entry_st { + uint64_t hash; + struct ht_internal_value_st *value; +}; + +struct ht_neighborhood_st { + struct ht_neighborhood_entry_st entries[NEIGHBORHOOD_LEN]; +}; + +/* + * Updates to data in this struct + * require an rcu sync after modification + * prior to free + */ +struct ht_mutable_data_st { + struct ht_neighborhood_st *neighborhoods; + void *neighborhood_ptr_to_free; + uint64_t neighborhood_mask; +}; + +/* + * Private data may be updated on the write + * side only, and so do not require rcu sync + */ +struct ht_write_private_data_st { + size_t neighborhood_len; + size_t value_count; + int need_sync; +}; + +struct ht_internal_st { + HT_CONFIG config; + CRYPTO_RCU_LOCK *lock; + CRYPTO_RWLOCK *atomic_lock; + struct ht_mutable_data_st *md; + struct ht_write_private_data_st wpd; +}; + +static void free_value(struct ht_internal_value_st *v); + +static struct ht_neighborhood_st *alloc_new_neighborhood_list(size_t len, + void **freeptr) +{ + struct ht_neighborhood_st *ret; + + ret = OPENSSL_aligned_alloc(sizeof(struct ht_neighborhood_st) * len, + CACHE_LINE_BYTES, freeptr); + + /* fall back to regular malloc */ + if (ret == NULL) { + ret = *freeptr = OPENSSL_malloc(sizeof(struct ht_neighborhood_st) * len); + if (ret == NULL) + return NULL; + } + memset(ret, 0, sizeof(struct ht_neighborhood_st) * len); + return ret; +} + +static void internal_free_nop(HT_VALUE *v) +{ + return; +} + +HT *ossl_ht_new(const HT_CONFIG *conf) +{ + HT *new = OPENSSL_zalloc(sizeof(*new)); + + if (new == NULL) + return NULL; + + new->atomic_lock = CRYPTO_THREAD_lock_new(); + if (new->atomic_lock == NULL) + goto err; + + memcpy(&new->config, conf, sizeof(*conf)); + + if (new->config.init_neighborhoods != 0) { + new->wpd.neighborhood_len = new->config.init_neighborhoods; + /* round up to the next power of 2 */ + new->wpd.neighborhood_len--; + new->wpd.neighborhood_len |= new->wpd.neighborhood_len >> 1; + new->wpd.neighborhood_len |= new->wpd.neighborhood_len >> 2; + new->wpd.neighborhood_len |= new->wpd.neighborhood_len >> 4; + new->wpd.neighborhood_len |= new->wpd.neighborhood_len >> 8; + new->wpd.neighborhood_len |= new->wpd.neighborhood_len >> 16; + new->wpd.neighborhood_len++; + } else { + new->wpd.neighborhood_len = DEFAULT_NEIGH_LEN; + } + + if (new->config.ht_free_fn == NULL) + new->config.ht_free_fn = internal_free_nop; + + new->md = OPENSSL_zalloc(sizeof(*new->md)); + if (new->md == NULL) + goto err; + + new->md->neighborhoods = + alloc_new_neighborhood_list(new->wpd.neighborhood_len, + &new->md->neighborhood_ptr_to_free); + if (new->md->neighborhoods == NULL) + goto err; + new->md->neighborhood_mask = new->wpd.neighborhood_len - 1; + + new->lock = ossl_rcu_lock_new(1, conf->ctx); + if (new->lock == NULL) + goto err; + + if (new->config.ht_hash_fn == NULL) + new->config.ht_hash_fn = fnv1a_hash; + + return new; + +err: + CRYPTO_THREAD_lock_free(new->atomic_lock); + ossl_rcu_lock_free(new->lock); + if (new->md != NULL) + OPENSSL_free(new->md->neighborhood_ptr_to_free); + OPENSSL_free(new->md); + OPENSSL_free(new); + return NULL; +} + +void ossl_ht_read_lock(HT *htable) +{ + ossl_rcu_read_lock(htable->lock); +} + +void ossl_ht_read_unlock(HT *htable) +{ + ossl_rcu_read_unlock(htable->lock); +} + +void ossl_ht_write_lock(HT *htable) +{ + ossl_rcu_write_lock(htable->lock); + htable->wpd.need_sync = 0; +} + +void ossl_ht_write_unlock(HT *htable) +{ + int need_sync = htable->wpd.need_sync; + + htable->wpd.need_sync = 0; + ossl_rcu_write_unlock(htable->lock); + if (need_sync) + ossl_synchronize_rcu(htable->lock); +} + +static void free_oldmd(void *arg) +{ + struct ht_mutable_data_st *oldmd = arg; + size_t i, j; + size_t neighborhood_len = (size_t)oldmd->neighborhood_mask + 1; + struct ht_internal_value_st *v; + + for (i = 0; i < neighborhood_len; i++) { + PREFETCH_NEIGHBORHOOD(oldmd->neighborhoods[i + 1]); + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + if (oldmd->neighborhoods[i].entries[j].value != NULL) { + v = oldmd->neighborhoods[i].entries[j].value; + v->ht->config.ht_free_fn((HT_VALUE *)v); + free_value(v); + } + } + } + + OPENSSL_free(oldmd->neighborhood_ptr_to_free); + OPENSSL_free(oldmd); +} + +static int ossl_ht_flush_internal(HT *h) +{ + struct ht_mutable_data_st *newmd = NULL; + struct ht_mutable_data_st *oldmd = NULL; + + newmd = OPENSSL_zalloc(sizeof(*newmd)); + if (newmd == NULL) + return 0; + + newmd->neighborhoods = alloc_new_neighborhood_list(DEFAULT_NEIGH_LEN, + &newmd->neighborhood_ptr_to_free); + if (newmd->neighborhoods == NULL) { + OPENSSL_free(newmd); + return 0; + } + + newmd->neighborhood_mask = DEFAULT_NEIGH_LEN - 1; + + /* Swap the old and new mutable data sets */ + oldmd = ossl_rcu_deref(&h->md); + ossl_rcu_assign_ptr(&h->md, &newmd); + + /* Set the number of entries to 0 */ + h->wpd.value_count = 0; + h->wpd.neighborhood_len = DEFAULT_NEIGH_LEN; + + ossl_rcu_call(h->lock, free_oldmd, oldmd); + h->wpd.need_sync = 1; + return 1; +} + +int ossl_ht_flush(HT *h) +{ + return ossl_ht_flush_internal(h); +} + +void ossl_ht_free(HT *h) +{ + if (h == NULL) + return; + + ossl_ht_write_lock(h); + ossl_ht_flush_internal(h); + ossl_ht_write_unlock(h); + /* Freeing the lock does a final sync for us */ + CRYPTO_THREAD_lock_free(h->atomic_lock); + ossl_rcu_lock_free(h->lock); + OPENSSL_free(h->md->neighborhood_ptr_to_free); + OPENSSL_free(h->md); + OPENSSL_free(h); + return; +} + +size_t ossl_ht_count(HT *h) +{ + size_t count; + + count = h->wpd.value_count; + return count; +} + +void ossl_ht_foreach_until(HT *h, int (*cb)(HT_VALUE *obj, void *arg), + void *arg) +{ + size_t i, j; + struct ht_mutable_data_st *md; + + md = ossl_rcu_deref(&h->md); + for (i = 0; i < md->neighborhood_mask + 1; i++) { + PREFETCH_NEIGHBORHOOD(md->neighborhoods[i + 1]); + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + if (md->neighborhoods[i].entries[j].value != NULL) { + if (!cb((HT_VALUE *)md->neighborhoods[i].entries[j].value, arg)) + goto out; + } + } + } +out: + return; +} + +HT_VALUE_LIST *ossl_ht_filter(HT *h, size_t max_len, + int (*filter)(HT_VALUE *obj, void *arg), + void *arg) +{ + struct ht_mutable_data_st *md; + HT_VALUE_LIST *list = OPENSSL_zalloc(sizeof(HT_VALUE_LIST) + + (sizeof(HT_VALUE *) * max_len)); + size_t i, j; + struct ht_internal_value_st *v; + + if (list == NULL) + return NULL; + + /* + * The list array lives just beyond the end of + * the struct + */ + list->list = (HT_VALUE **)(list + 1); + + md = ossl_rcu_deref(&h->md); + for (i = 0; i < md->neighborhood_mask + 1; i++) { + PREFETCH_NEIGHBORHOOD(md->neighborhoods[i+1]); + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + v = md->neighborhoods[i].entries[j].value; + if (v != NULL && filter((HT_VALUE *)v, arg)) { + list->list[list->list_len++] = (HT_VALUE *)v; + if (list->list_len == max_len) + goto out; + } + } + } +out: + return list; +} + +void ossl_ht_value_list_free(HT_VALUE_LIST *list) +{ + OPENSSL_free(list); +} + +static int compare_hash(uint64_t hash1, uint64_t hash2) +{ + return (hash1 == hash2); +} + +static void free_old_neigh_table(void *arg) +{ + struct ht_mutable_data_st *oldmd = arg; + + OPENSSL_free(oldmd->neighborhood_ptr_to_free); + OPENSSL_free(oldmd); +} + +/* + * Increase hash table bucket list + * must be called with write_lock held + */ +static int grow_hashtable(HT *h, size_t oldsize) +{ + struct ht_mutable_data_st *newmd; + struct ht_mutable_data_st *oldmd = ossl_rcu_deref(&h->md); + int rc = 0; + uint64_t oldi, oldj, newi, newj; + uint64_t oldhash; + struct ht_internal_value_st *oldv; + int rehashed; + size_t newsize = oldsize * 2; + + if (h->config.lockless_reads) + goto out; + + if ((newmd = OPENSSL_zalloc(sizeof(*newmd))) == NULL) + goto out; + + /* bucket list is always a power of 2 */ + newmd->neighborhoods = alloc_new_neighborhood_list(oldsize * 2, + &newmd->neighborhood_ptr_to_free); + if (newmd->neighborhoods == NULL) + goto out_free; + + /* being a power of 2 makes for easy mask computation */ + newmd->neighborhood_mask = (newsize - 1); + + /* + * Now we need to start rehashing entries + * Note we don't need to use atomics here as the new + * mutable data hasn't been published + */ + for (oldi = 0; oldi < h->wpd.neighborhood_len; oldi++) { + PREFETCH_NEIGHBORHOOD(oldmd->neighborhoods[oldi + 1]); + for (oldj = 0; oldj < NEIGHBORHOOD_LEN; oldj++) { + oldv = oldmd->neighborhoods[oldi].entries[oldj].value; + if (oldv == NULL) + continue; + oldhash = oldmd->neighborhoods[oldi].entries[oldj].hash; + newi = oldhash & newmd->neighborhood_mask; + rehashed = 0; + for (newj = 0; newj < NEIGHBORHOOD_LEN; newj++) { + if (newmd->neighborhoods[newi].entries[newj].value == NULL) { + newmd->neighborhoods[newi].entries[newj].value = oldv; + newmd->neighborhoods[newi].entries[newj].hash = oldhash; + rehashed = 1; + break; + } + } + if (rehashed == 0) { + /* we ran out of space in a neighborhood, grow again */ + OPENSSL_free(newmd->neighborhoods); + OPENSSL_free(newmd); + return grow_hashtable(h, newsize); + } + } + } + /* + * Now that our entries are all hashed into the new bucket list + * update our bucket_len and target_max_load + */ + h->wpd.neighborhood_len = newsize; + + /* + * Now we replace the old mutable data with the new + */ + ossl_rcu_assign_ptr(&h->md, &newmd); + ossl_rcu_call(h->lock, free_old_neigh_table, oldmd); + h->wpd.need_sync = 1; + /* + * And we're done + */ + rc = 1; + +out: + return rc; +out_free: + OPENSSL_free(newmd->neighborhoods); + OPENSSL_free(newmd); + goto out; +} + +static void free_old_ht_value(void *arg) +{ + HT_VALUE *h = (HT_VALUE *)arg; + + /* + * Note, this is only called on replacement, + * the caller is responsible for freeing the + * held data, we just need to free the wrapping + * struct here + */ + OPENSSL_free(h); +} + +static ossl_inline int match_key(HT_KEY *a, HT_KEY *b) +{ + /* + * keys match if they are both present, the same size + * and compare equal in memory + */ + PREFETCH(a->keybuf); + PREFETCH(b->keybuf); + if (a->keybuf != NULL && b->keybuf != NULL && a->keysize == b->keysize) + return !memcmp(a->keybuf, b->keybuf, a->keysize); + + return 1; +} + +static int ossl_ht_insert_locked(HT *h, uint64_t hash, + struct ht_internal_value_st *newval, + HT_VALUE **olddata) +{ + struct ht_mutable_data_st *md = h->md; + uint64_t neigh_idx_start = hash & md->neighborhood_mask; + uint64_t neigh_idx = neigh_idx_start; + size_t j; + uint64_t ihash; + HT_VALUE *ival; + size_t empty_idx = SIZE_MAX; + int lockless_reads = h->config.lockless_reads; + + do { + PREFETCH_NEIGHBORHOOD(md->neighborhoods[neigh_idx]); + + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + ival = ossl_rcu_deref(&md->neighborhoods[neigh_idx].entries[j].value); + if (ival == NULL) { + empty_idx = j; + /* lockless_reads implies no deletion, we can break out */ + if (lockless_reads) + goto not_found; + continue; + } + if (!CRYPTO_atomic_load(&md->neighborhoods[neigh_idx].entries[j].hash, + &ihash, h->atomic_lock)) + return 0; + if (compare_hash(hash, ihash) && match_key(&newval->value.key, + &ival->key)) { + if (olddata == NULL) { + /* This would insert a duplicate -> fail */ + return 0; + } + /* Do a replacement */ + if (!CRYPTO_atomic_store(&md->neighborhoods[neigh_idx].entries[j].hash, + hash, h->atomic_lock)) + return 0; + *olddata = (HT_VALUE *)md->neighborhoods[neigh_idx].entries[j].value; + ossl_rcu_assign_ptr(&md->neighborhoods[neigh_idx].entries[j].value, + &newval); + ossl_rcu_call(h->lock, free_old_ht_value, *olddata); + h->wpd.need_sync = 1; + return 1; + } + } + if (!lockless_reads) + break; + /* Continue search in subsequent neighborhoods */ + neigh_idx = (neigh_idx + 1) & md->neighborhood_mask; + } while (neigh_idx != neigh_idx_start); + + not_found: + /* If we get to here, its just an insert */ + if (empty_idx == SIZE_MAX) + return -1; /* out of space */ + if (!CRYPTO_atomic_store(&md->neighborhoods[neigh_idx].entries[empty_idx].hash, + hash, h->atomic_lock)) + return 0; + h->wpd.value_count++; + ossl_rcu_assign_ptr(&md->neighborhoods[neigh_idx].entries[empty_idx].value, + &newval); + return 1; +} + +static struct ht_internal_value_st *alloc_new_value(HT *h, HT_KEY *key, + void *data, + uintptr_t *type) +{ + struct ht_internal_value_st *tmp; + size_t nvsize = sizeof(*tmp); + + if (h->config.collision_check == 1) + nvsize += key->keysize; + + tmp = OPENSSL_malloc(nvsize); + + if (tmp == NULL) + return NULL; + + tmp->ht = h; + tmp->value.value = data; + tmp->value.type_id = type; + tmp->value.key.keybuf = NULL; + if (h->config.collision_check) { + tmp->value.key.keybuf = (uint8_t *)(tmp + 1); + tmp->value.key.keysize = key->keysize; + memcpy(tmp->value.key.keybuf, key->keybuf, key->keysize); + } + + + return tmp; +} + +static void free_value(struct ht_internal_value_st *v) +{ + OPENSSL_free(v); +} + +int ossl_ht_insert(HT *h, HT_KEY *key, HT_VALUE *data, HT_VALUE **olddata) +{ + struct ht_internal_value_st *newval = NULL; + uint64_t hash; + int rc = 0; + int i; + + if (data->value == NULL) + goto out; + + newval = alloc_new_value(h, key, data->value, data->type_id); + if (newval == NULL) + goto out; + + /* + * we have to take our lock here to prevent other changes + * to the bucket list + */ + hash = h->config.ht_hash_fn(key->keybuf, key->keysize); + + for (i = 0; + (rc = ossl_ht_insert_locked(h, hash, newval, olddata)) == -1 + && i < 4; + ++i) + if (!grow_hashtable(h, h->wpd.neighborhood_len)) { + rc = -1; + break; + } + + if (rc <= 0) + free_value(newval); + +out: + return rc; +} + +HT_VALUE *ossl_ht_get(HT *h, HT_KEY *key) +{ + struct ht_mutable_data_st *md; + uint64_t hash; + uint64_t neigh_idx_start; + uint64_t neigh_idx; + struct ht_internal_value_st *ival = NULL; + size_t j; + uint64_t ehash; + int lockless_reads = h->config.lockless_reads; + + hash = h->config.ht_hash_fn(key->keybuf, key->keysize); + + md = ossl_rcu_deref(&h->md); + neigh_idx = neigh_idx_start = hash & md->neighborhood_mask; + do { + PREFETCH_NEIGHBORHOOD(md->neighborhoods[neigh_idx]); + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + ival = ossl_rcu_deref(&md->neighborhoods[neigh_idx].entries[j].value); + if (ival == NULL) { + if (lockless_reads) + /* lockless_reads implies no deletion, we can break out */ + return NULL; + continue; + } + if (!CRYPTO_atomic_load(&md->neighborhoods[neigh_idx].entries[j].hash, + &ehash, h->atomic_lock)) + return NULL; + if (compare_hash(hash, ehash) && match_key(&ival->value.key, key)) + return (HT_VALUE *)ival; + } + if (!lockless_reads) + break; + /* Continue search in subsequent neighborhoods */ + neigh_idx = (neigh_idx + 1) & md->neighborhood_mask; + } while (neigh_idx != neigh_idx_start); + + return NULL; +} + +static void free_old_entry(void *arg) +{ + struct ht_internal_value_st *v = arg; + + v->ht->config.ht_free_fn((HT_VALUE *)v); + free_value(v); +} + +int ossl_ht_delete(HT *h, HT_KEY *key) +{ + uint64_t hash; + uint64_t neigh_idx; + size_t j; + struct ht_internal_value_st *v = NULL; + HT_VALUE *nv = NULL; + int rc = 0; + + if (h->config.lockless_reads) + return 0; + + hash = h->config.ht_hash_fn(key->keybuf, key->keysize); + + neigh_idx = hash & h->md->neighborhood_mask; + PREFETCH_NEIGHBORHOOD(h->md->neighborhoods[neigh_idx]); + for (j = 0; j < NEIGHBORHOOD_LEN; j++) { + v = (struct ht_internal_value_st *)h->md->neighborhoods[neigh_idx].entries[j].value; + if (v == NULL) + continue; + if (compare_hash(hash, h->md->neighborhoods[neigh_idx].entries[j].hash) + && match_key(key, &v->value.key)) { + if (!CRYPTO_atomic_store(&h->md->neighborhoods[neigh_idx].entries[j].hash, + 0, h->atomic_lock)) + break; + h->wpd.value_count--; + ossl_rcu_assign_ptr(&h->md->neighborhoods[neigh_idx].entries[j].value, + &nv); + rc = 1; + break; + } + } + if (rc == 1) { + ossl_rcu_call(h->lock, free_old_entry, v); + h->wpd.need_sync = 1; + } + return rc; +} diff --git a/crypto/hmac/build.info b/crypto/hmac/build.info index b828ab122e..90b43cf42b 100644 --- a/crypto/hmac/build.info +++ b/crypto/hmac/build.info @@ -2,5 +2,22 @@ LIBS=../../libcrypto $COMMON=hmac.c -SOURCE[../../libcrypto]=$COMMON -SOURCE[../../providers/libfips.a]=$COMMON +IF[{- !$disabled{asm} -}] + IF[{- ($target{perlasm_scheme} // '') ne '31' -}] + $HMACASM_s390x=hmac_s390x.c + $HMACDEF_s390x=OPENSSL_HMAC_S390X + ENDIF + + # Now that we have defined all the arch specific variables, use the + # appropriate ones, and define the appropriate macros + IF[$HMACASM_{- $target{asm_arch} -}] + $HMACASM=$HMACASM_{- $target{asm_arch} -} + $HMACDEF=$HMACDEF_{- $target{asm_arch} -} + ENDIF +ENDIF + +DEFINE[../../libcrypto]=$HMACDEF +DEFINE[../../providers/libfips.a]=$HMACDEF + +SOURCE[../../libcrypto]=$COMMON $HMACASM +SOURCE[../../providers/libfips.a]=$COMMON $HMACASM diff --git a/crypto/hmac/hmac.c b/crypto/hmac/hmac.c index 940d867ca6..19fc7d3b4f 100644 --- a/crypto/hmac/hmac.c +++ b/crypto/hmac/hmac.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -46,9 +46,15 @@ int HMAC_Init_ex(HMAC_CTX *ctx, const void *key, int len, * The HMAC construction is not allowed to be used with the * extendable-output functions (XOF) shake128 and shake256. */ - if ((EVP_MD_get_flags(md) & EVP_MD_FLAG_XOF) != 0) + if (EVP_MD_xof(md)) return 0; +#ifdef OPENSSL_HMAC_S390X + rv = s390x_HMAC_init(ctx, key, len, impl); + if (rv >= 1) + return rv; +#endif + if (key != NULL) { reset = 1; @@ -111,6 +117,12 @@ int HMAC_Update(HMAC_CTX *ctx, const unsigned char *data, size_t len) { if (!ctx->md) return 0; + +#ifdef OPENSSL_HMAC_S390X + if (ctx->plat.s390x.fc) + return s390x_HMAC_update(ctx, data, len); +#endif + return EVP_DigestUpdate(ctx->md_ctx, data, len); } @@ -122,6 +134,11 @@ int HMAC_Final(HMAC_CTX *ctx, unsigned char *md, unsigned int *len) if (!ctx->md) goto err; +#ifdef OPENSSL_HMAC_S390X + if (ctx->plat.s390x.fc) + return s390x_HMAC_final(ctx, md, len); +#endif + if (!EVP_DigestFinal_ex(ctx->md_ctx, buf, &i)) goto err; if (!EVP_MD_CTX_copy_ex(ctx->md_ctx, ctx->o_ctx)) @@ -161,6 +178,10 @@ static void hmac_ctx_cleanup(HMAC_CTX *ctx) EVP_MD_CTX_reset(ctx->o_ctx); EVP_MD_CTX_reset(ctx->md_ctx); ctx->md = NULL; + +#ifdef OPENSSL_HMAC_S390X + s390x_HMAC_CTX_cleanup(ctx); +#endif } void HMAC_CTX_free(HMAC_CTX *ctx) @@ -212,6 +233,12 @@ int HMAC_CTX_copy(HMAC_CTX *dctx, HMAC_CTX *sctx) if (!EVP_MD_CTX_copy_ex(dctx->md_ctx, sctx->md_ctx)) goto err; dctx->md = sctx->md; + +#ifdef OPENSSL_HMAC_S390X + if (s390x_HMAC_CTX_copy(dctx, sctx) == 0) + goto err; +#endif + return 1; err: hmac_ctx_cleanup(dctx); @@ -227,7 +254,7 @@ unsigned char *HMAC(const EVP_MD *evp_md, const void *key, int key_len, size_t temp_md_len = 0; unsigned char *ret = NULL; - if (size >= 0) { + if (size > 0) { ret = EVP_Q_mac(NULL, "HMAC", NULL, EVP_MD_get0_name(evp_md), NULL, key, key_len, data, data_len, md == NULL ? static_md : md, size, &temp_md_len); diff --git a/crypto/hmac/hmac_local.h b/crypto/hmac/hmac_local.h index 495b8593ff..1b871e7320 100644 --- a/crypto/hmac/hmac_local.h +++ b/crypto/hmac/hmac_local.h @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -10,6 +10,10 @@ #ifndef OSSL_CRYPTO_HMAC_LOCAL_H # define OSSL_CRYPTO_HMAC_LOCAL_H +# include "internal/common.h" +# include "internal/numbers.h" +# include "openssl/sha.h" + /* The current largest case is for SHA3-224 */ #define HMAC_MAX_MD_CBLOCK_SIZE 144 @@ -18,6 +22,45 @@ struct hmac_ctx_st { EVP_MD_CTX *md_ctx; EVP_MD_CTX *i_ctx; EVP_MD_CTX *o_ctx; + + /* Platform specific data */ + union { + int dummy; +# ifdef OPENSSL_HMAC_S390X + struct { + unsigned int fc; /* 0 if not supported by kmac instruction */ + int blk_size; + int ikp; + int iimp; + unsigned char *buf; + size_t size; /* must be multiple of digest block size */ + size_t num; + union { + OSSL_UNION_ALIGN; + struct { + uint32_t h[8]; + uint64_t imbl; + unsigned char key[64]; + } hmac_224_256; + struct { + uint64_t h[8]; + uint128_t imbl; + unsigned char key[128]; + } hmac_384_512; + } param; + } s390x; +# endif /* OPENSSL_HMAC_S390X */ + } plat; }; +# ifdef OPENSSL_HMAC_S390X +# define HMAC_S390X_BUF_NUM_BLOCKS 64 + +int s390x_HMAC_init(HMAC_CTX *ctx, const void *key, int key_len, ENGINE *impl); +int s390x_HMAC_update(HMAC_CTX *ctx, const unsigned char *data, size_t len); +int s390x_HMAC_final(HMAC_CTX *ctx, unsigned char *md, unsigned int *len); +int s390x_HMAC_CTX_copy(HMAC_CTX *dctx, HMAC_CTX *sctx); +int s390x_HMAC_CTX_cleanup(HMAC_CTX *ctx); +# endif /* OPENSSL_HMAC_S390X */ + #endif diff --git a/crypto/hmac/hmac_s390x.c b/crypto/hmac/hmac_s390x.c new file mode 100644 index 0000000000..02e1cd1dd6 --- /dev/null +++ b/crypto/hmac/hmac_s390x.c @@ -0,0 +1,329 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +/* We need to use some engine deprecated APIs */ +#define OPENSSL_SUPPRESS_DEPRECATED + +#include "crypto/s390x_arch.h" +#include "hmac_local.h" +#include "openssl/obj_mac.h" +#include "openssl/evp.h" +#if !defined(OPENSSL_NO_ENGINE) && !defined(FIPS_MODULE) +# include +#endif + +#ifdef OPENSSL_HMAC_S390X + +static int s390x_fc_from_md(const EVP_MD *md) +{ + int fc; + + if (EVP_MD_is_a(md, "SHA2-224")) + fc = S390X_HMAC_SHA_224; + else if (EVP_MD_is_a(md, "SHA2-256")) + fc = S390X_HMAC_SHA_256; + else if (EVP_MD_is_a(md, "SHA2-384")) + fc = S390X_HMAC_SHA_384; + else if (EVP_MD_is_a(md, "SHA2-512")) + fc = S390X_HMAC_SHA_512; + else + return 0; + + if ((OPENSSL_s390xcap_P.kmac[1] & S390X_CAPBIT(fc)) == 0) + return 0; + + return fc; +} + +static void s390x_call_kmac(HMAC_CTX *ctx, const unsigned char *in, size_t len) +{ + unsigned int fc = ctx->plat.s390x.fc; + + if (ctx->plat.s390x.ikp) + fc |= S390X_KMAC_IKP; + + if (ctx->plat.s390x.iimp) + fc |= S390X_KMAC_IIMP; + + switch (ctx->plat.s390x.fc) { + case S390X_HMAC_SHA_224: + case S390X_HMAC_SHA_256: + ctx->plat.s390x.param.hmac_224_256.imbl += ((uint64_t)len * 8); + break; + case S390X_HMAC_SHA_384: + case S390X_HMAC_SHA_512: + ctx->plat.s390x.param.hmac_384_512.imbl += ((uint128_t)len * 8); + break; + default: + break; + } + + s390x_kmac(in, len, fc, &ctx->plat.s390x.param); + + ctx->plat.s390x.ikp = 1; +} + +static int s390x_check_engine_used(const EVP_MD *md, ENGINE *impl) +{ +# if !defined(OPENSSL_NO_ENGINE) && !defined(FIPS_MODULE) + const EVP_MD *d; + + if (impl != NULL) { + if (!ENGINE_init(impl)) + return 0; + } else { + impl = ENGINE_get_digest_engine(EVP_MD_get_type(md)); + } + + if (impl == NULL) + return 0; + + d = ENGINE_get_digest(impl, EVP_MD_get_type(md)); + ENGINE_finish(impl); + + if (d != NULL) + return 1; +# endif + + return 0; +} + +int s390x_HMAC_init(HMAC_CTX *ctx, const void *key, int key_len, ENGINE *impl) +{ + unsigned char *key_param; + unsigned int key_param_len; + + ctx->plat.s390x.fc = s390x_fc_from_md(ctx->md); + if (ctx->plat.s390x.fc == 0) + return -1; /* Not supported by kmac instruction */ + + if (s390x_check_engine_used(ctx->md, impl)) { + ctx->plat.s390x.fc = 0; + return -1; /* An engine handles the digest, disable acceleration */ + } + + ctx->plat.s390x.blk_size = EVP_MD_get_block_size(ctx->md); + if (ctx->plat.s390x.blk_size < 0) + return 0; + + if (ctx->plat.s390x.size != + (size_t)(ctx->plat.s390x.blk_size * HMAC_S390X_BUF_NUM_BLOCKS)) { + OPENSSL_clear_free(ctx->plat.s390x.buf, ctx->plat.s390x.size); + ctx->plat.s390x.size = 0; + ctx->plat.s390x.buf = OPENSSL_zalloc(ctx->plat.s390x.blk_size * + HMAC_S390X_BUF_NUM_BLOCKS); + if (ctx->plat.s390x.buf == NULL) + return 0; + ctx->plat.s390x.size = ctx->plat.s390x.blk_size * + HMAC_S390X_BUF_NUM_BLOCKS; + } + ctx->plat.s390x.num = 0; + + ctx->plat.s390x.ikp = 0; + ctx->plat.s390x.iimp = 1; + + switch (ctx->plat.s390x.fc) { + case S390X_HMAC_SHA_224: + case S390X_HMAC_SHA_256: + ctx->plat.s390x.param.hmac_224_256.imbl = 0; + OPENSSL_cleanse(ctx->plat.s390x.param.hmac_224_256.h, + sizeof(ctx->plat.s390x.param.hmac_224_256.h)); + break; + case S390X_HMAC_SHA_384: + case S390X_HMAC_SHA_512: + ctx->plat.s390x.param.hmac_384_512.imbl = 0; + OPENSSL_cleanse(ctx->plat.s390x.param.hmac_384_512.h, + sizeof(ctx->plat.s390x.param.hmac_384_512.h)); + break; + default: + return 0; + } + + if (key != NULL) { + switch (ctx->plat.s390x.fc) { + case S390X_HMAC_SHA_224: + case S390X_HMAC_SHA_256: + OPENSSL_cleanse(&ctx->plat.s390x.param.hmac_224_256.key, + sizeof(ctx->plat.s390x.param.hmac_224_256.key)); + key_param = ctx->plat.s390x.param.hmac_224_256.key; + key_param_len = sizeof(ctx->plat.s390x.param.hmac_224_256.key); + break; + case S390X_HMAC_SHA_384: + case S390X_HMAC_SHA_512: + OPENSSL_cleanse(&ctx->plat.s390x.param.hmac_384_512.key, + sizeof(ctx->plat.s390x.param.hmac_384_512.key)); + key_param = ctx->plat.s390x.param.hmac_384_512.key; + key_param_len = sizeof(ctx->plat.s390x.param.hmac_384_512.key); + break; + default: + return 0; + } + + if (!ossl_assert(ctx->plat.s390x.blk_size <= (int)key_param_len)) + return 0; + + if (key_len > ctx->plat.s390x.blk_size) { + if (!EVP_DigestInit_ex(ctx->md_ctx, ctx->md, impl) + || !EVP_DigestUpdate(ctx->md_ctx, key, key_len) + || !EVP_DigestFinal_ex(ctx->md_ctx, key_param, + &key_param_len)) + return 0; + } else { + if (key_len < 0 || key_len > (int)key_param_len) + return 0; + memcpy(key_param, key, key_len); + /* remaining key bytes already zeroed out above */ + } + } + + return 1; +} + +int s390x_HMAC_update(HMAC_CTX *ctx, const unsigned char *data, size_t len) +{ + size_t remain, num; + + if (len == 0) + return 1; + + /* buffer is full, process it now */ + if (ctx->plat.s390x.num == ctx->plat.s390x.size) { + s390x_call_kmac(ctx, ctx->plat.s390x.buf, ctx->plat.s390x.num); + + ctx->plat.s390x.num = 0; + } + + remain = ctx->plat.s390x.size - ctx->plat.s390x.num; + if (len > remain) { + /* data does not fit into buffer */ + if (ctx->plat.s390x.num > 0) { + /* first fill buffer and process it */ + memcpy(&ctx->plat.s390x.buf[ctx->plat.s390x.num], data, remain); + ctx->plat.s390x.num += remain; + + s390x_call_kmac(ctx, ctx->plat.s390x.buf, ctx->plat.s390x.num); + + ctx->plat.s390x.num = 0; + + data += remain; + len -= remain; + } + + if (!ossl_assert(ctx->plat.s390x.num == 0)) + return 0; + + if (len > ctx->plat.s390x.size) { + /* + * remaining data is still larger than buffer, process remaining + * full blocks of input directly + */ + remain = len % ctx->plat.s390x.blk_size; + num = len - remain; + + s390x_call_kmac(ctx, data, num); + + data += num; + len -= num; + } + } + + /* add remaining input data (which is < buffer size) to buffer */ + if (!ossl_assert(len <= ctx->plat.s390x.size)) + return 0; + + if (len > 0) { + memcpy(&ctx->plat.s390x.buf[ctx->plat.s390x.num], data, len); + ctx->plat.s390x.num += len; + } + + return 1; +} + +int s390x_HMAC_final(HMAC_CTX *ctx, unsigned char *md, unsigned int *len) +{ + void *result; + unsigned int res_len; + + ctx->plat.s390x.iimp = 0; /* last block */ + s390x_call_kmac(ctx, ctx->plat.s390x.buf, ctx->plat.s390x.num); + + ctx->plat.s390x.num = 0; + + switch (ctx->plat.s390x.fc) { + case S390X_HMAC_SHA_224: + result = &ctx->plat.s390x.param.hmac_224_256.h[0]; + res_len = SHA224_DIGEST_LENGTH; + break; + case S390X_HMAC_SHA_256: + result = &ctx->plat.s390x.param.hmac_224_256.h[0]; + res_len = SHA256_DIGEST_LENGTH; + break; + case S390X_HMAC_SHA_384: + result = &ctx->plat.s390x.param.hmac_384_512.h[0]; + res_len = SHA384_DIGEST_LENGTH; + break; + case S390X_HMAC_SHA_512: + result = &ctx->plat.s390x.param.hmac_384_512.h[0]; + res_len = SHA512_DIGEST_LENGTH; + break; + default: + return 0; + } + + memcpy(md, result, res_len); + if (len != NULL) + *len = res_len; + + return 1; +} + +int s390x_HMAC_CTX_copy(HMAC_CTX *dctx, HMAC_CTX *sctx) +{ + dctx->plat.s390x.fc = sctx->plat.s390x.fc; + dctx->plat.s390x.blk_size = sctx->plat.s390x.blk_size; + dctx->plat.s390x.ikp = sctx->plat.s390x.ikp; + dctx->plat.s390x.iimp = sctx->plat.s390x.iimp; + + memcpy(&dctx->plat.s390x.param, &sctx->plat.s390x.param, + sizeof(dctx->plat.s390x.param)); + + OPENSSL_clear_free(dctx->plat.s390x.buf, dctx->plat.s390x.size); + dctx->plat.s390x.buf = NULL; + if (sctx->plat.s390x.buf != NULL) { + dctx->plat.s390x.buf = OPENSSL_memdup(sctx->plat.s390x.buf, + sctx->plat.s390x.size); + if (dctx->plat.s390x.buf == NULL) + return 0; + } + + dctx->plat.s390x.size = sctx->plat.s390x.size; + dctx->plat.s390x.num = sctx->plat.s390x.num; + + return 1; +} + +int s390x_HMAC_CTX_cleanup(HMAC_CTX *ctx) +{ + OPENSSL_clear_free(ctx->plat.s390x.buf, ctx->plat.s390x.size); + ctx->plat.s390x.buf = NULL; + ctx->plat.s390x.size = 0; + ctx->plat.s390x.num = 0; + + OPENSSL_cleanse(&ctx->plat.s390x.param, sizeof(ctx->plat.s390x.param)); + + ctx->plat.s390x.blk_size = 0; + ctx->plat.s390x.ikp = 0; + ctx->plat.s390x.iimp = 1; + + ctx->plat.s390x.fc = 0; + + return 1; +} + +#endif diff --git a/crypto/hpke/hpke.c b/crypto/hpke/hpke.c index a53488d9ec..5a403097c4 100644 --- a/crypto/hpke/hpke.c +++ b/crypto/hpke/hpke.c @@ -45,8 +45,7 @@ static const char OSSL_HPKE_SECRET_LABEL[] = "\x73\x65\x63\x72\x65\x74"; /** * @brief sender or receiver context */ -struct ossl_hpke_ctx_st -{ +struct ossl_hpke_ctx_st { OSSL_LIB_CTX *libctx; /* library context */ char *propq; /* properties */ int mode; /* HPKE mode */ diff --git a/crypto/http/http_client.c b/crypto/http/http_client.c index 9309954ef8..f508d5b1f4 100644 --- a/crypto/http/http_client.c +++ b/crypto/http/http_client.c @@ -928,6 +928,20 @@ int OSSL_HTTP_REQ_CTX_nbio_d2i(OSSL_HTTP_REQ_CTX *rctx, #ifndef OPENSSL_NO_SOCK +static const char *explict_or_default_port(const char *hostserv, const char *port, int use_ssl) +{ + if (port == NULL) { + char *service = NULL; + + if (!BIO_parse_hostserv(hostserv, NULL, &service, BIO_PARSE_PRIO_HOST)) + return NULL; + if (service == NULL) /* implicit port */ + port = use_ssl ? OSSL_HTTPS_PORT : OSSL_HTTP_PORT; + OPENSSL_free(service); + } /* otherwise take the explicitly given port */ + return port; +} + /* set up a new connection BIO, to HTTP server or to HTTP(S) proxy if given */ static BIO *http_new_bio(const char *server /* optionally includes ":port" */, const char *server_port /* explicit server port */, @@ -947,8 +961,7 @@ static BIO *http_new_bio(const char *server /* optionally includes ":port" */, port = proxy_port; } - if (port == NULL && strchr(host, ':') == NULL) - port = use_ssl ? OSSL_HTTPS_PORT : OSSL_HTTP_PORT; + port = explict_or_default_port(host, port, use_ssl); cbio = BIO_new_connect(host /* optionally includes ":port" */); if (cbio == NULL) @@ -1035,8 +1048,6 @@ OSSL_HTTP_REQ_CTX *OSSL_HTTP_open(const char *server, const char *port, } if (port != NULL && *port == '\0') port = NULL; - if (port == NULL && strchr(server, ':') == NULL) - port = use_ssl ? OSSL_HTTPS_PORT : OSSL_HTTP_PORT; proxy = OSSL_HTTP_adapt_proxy(proxy, no_proxy, server, use_ssl); if (proxy != NULL && !OSSL_HTTP_parse_url(proxy, NULL /* use_ssl */, NULL /* user */, diff --git a/crypto/http/http_lib.c b/crypto/http/http_lib.c index cd0e25c85e..5cd5bd2ee8 100644 --- a/crypto/http/http_lib.c +++ b/crypto/http/http_lib.c @@ -1,5 +1,5 @@ /* - * Copyright 2001-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2001-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -14,6 +14,13 @@ #include /* for BIO_snprintf() */ #include #include "internal/cryptlib.h" /* for ossl_assert() */ +#ifndef OPENSSL_NO_SOCK +# include "internal/bio_addr.h" /* for NI_MAXHOST */ +#endif +#ifndef NI_MAXHOST +# define NI_MAXHOST 255 +#endif +#include "crypto/ctype.h" /* for ossl_isspace() */ static void init_pstring(char **pstr) { @@ -251,10 +258,17 @@ static int use_proxy(const char *no_proxy, const char *server) { size_t sl; const char *found = NULL; + char host[NI_MAXHOST]; if (!ossl_assert(server != NULL)) return 0; sl = strlen(server); + if (sl >= 2 && sl < sizeof(host) + 2 && server[0] == '[' && server[sl - 1] == ']') { + /* strip leading '[' and trailing ']' from escaped IPv6 address */ + sl -= 2; + strncpy(host, server + 1, sl); + server = host; + } /* * using environment variable names, both lowercase and uppercase variants, @@ -268,8 +282,8 @@ static int use_proxy(const char *no_proxy, const char *server) if (no_proxy != NULL) found = strstr(no_proxy, server); while (found != NULL - && ((found != no_proxy && found[-1] != ' ' && found[-1] != ',') - || (found[sl] != '\0' && found[sl] != ' ' && found[sl] != ','))) + && ((found != no_proxy && !ossl_isspace(found[-1]) && found[-1] != ',') + || (found[sl] != '\0' && !ossl_isspace(found[sl]) && found[sl] != ','))) found = strstr(found + 1, server); return found == NULL; } diff --git a/crypto/indicator_core.c b/crypto/indicator_core.c new file mode 100644 index 0000000000..4b3c122717 --- /dev/null +++ b/crypto/indicator_core.c @@ -0,0 +1,55 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include "internal/cryptlib.h" +#include "crypto/context.h" + +typedef struct indicator_cb_st +{ + OSSL_INDICATOR_CALLBACK *cb; +} INDICATOR_CB; + +void *ossl_indicator_set_callback_new(OSSL_LIB_CTX *ctx) +{ + INDICATOR_CB *cb; + + cb = OPENSSL_zalloc(sizeof(*cb)); + return cb; +} + +void ossl_indicator_set_callback_free(void *cb) +{ + OPENSSL_free(cb); +} + +static INDICATOR_CB *get_indicator_callback(OSSL_LIB_CTX *libctx) +{ + return ossl_lib_ctx_get_data(libctx, OSSL_LIB_CTX_INDICATOR_CB_INDEX); +} + +void OSSL_INDICATOR_set_callback(OSSL_LIB_CTX *libctx, + OSSL_INDICATOR_CALLBACK *cb) +{ + INDICATOR_CB *icb = get_indicator_callback(libctx); + + if (icb != NULL) + icb->cb = cb; +} + +void OSSL_INDICATOR_get_callback(OSSL_LIB_CTX *libctx, + OSSL_INDICATOR_CALLBACK **cb) +{ + INDICATOR_CB *icb = get_indicator_callback(libctx); + + if (cb != NULL) + *cb = (icb != NULL ? icb->cb : NULL); +} diff --git a/crypto/info.c b/crypto/info.c index 9ef9ee4704..ad31c9ec31 100644 --- a/crypto/info.c +++ b/crypto/info.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -15,12 +15,20 @@ #include "internal/e_os.h" #include "buildinf.h" +#ifndef OPENSSL_NO_JITTER +# include +# include +#endif + #if defined(__arm__) || defined(__arm) || defined(__aarch64__) # include "arm_arch.h" # define CPU_INFO_STR_LEN 128 #elif defined(__s390__) || defined(__s390x__) # include "s390x_arch.h" # define CPU_INFO_STR_LEN 2048 +#elif defined(__riscv) +# include "crypto/riscv_arch.h" +# define CPU_INFO_STR_LEN 2048 #else # define CPU_INFO_STR_LEN 128 #endif @@ -98,6 +106,33 @@ DEFINE_RUN_ONCE_STATIC(init_info_strings) BIO_snprintf(ossl_cpu_info_str + strlen(ossl_cpu_info_str), sizeof(ossl_cpu_info_str) - strlen(ossl_cpu_info_str), " env:%s", env); +# elif defined(__riscv) + const char *env; + char sep = '='; + + BIO_snprintf(ossl_cpu_info_str, sizeof(ossl_cpu_info_str), + CPUINFO_PREFIX "OPENSSL_riscvcap"); + for (size_t i = 0; i < kRISCVNumCaps; ++i) { + if (OPENSSL_riscvcap_P[RISCV_capabilities[i].index] + & (1 << RISCV_capabilities[i].bit_offset)) { + /* Match, display the name */ + BIO_snprintf(ossl_cpu_info_str + strlen(ossl_cpu_info_str), + sizeof(ossl_cpu_info_str) - strlen(ossl_cpu_info_str), + "%c%s", sep, RISCV_capabilities[i].name); + /* Only the first sep is '=' */ + sep = '_'; + } + } + /* If no capability is found, add back the = */ + if (sep == '=') { + BIO_snprintf(ossl_cpu_info_str + strlen(ossl_cpu_info_str), + sizeof(ossl_cpu_info_str) - strlen(ossl_cpu_info_str), + "%c", sep); + } + if ((env = getenv("OPENSSL_riscvcap")) != NULL) + BIO_snprintf(ossl_cpu_info_str + strlen(ossl_cpu_info_str), + sizeof(ossl_cpu_info_str) - strlen(ossl_cpu_info_str), + " env:%s", env); # endif #endif @@ -141,9 +176,6 @@ DEFINE_RUN_ONCE_STATIC(init_info_strings) add_seeds_string("rdrand ( rdseed rdrand )"); # endif #endif -#ifdef OPENSSL_RAND_SEED_LIBRANDOM - add_seeds_string("C-library-random"); -#endif #ifdef OPENSSL_RAND_SEED_GETRANDOM add_seeds_string("getrandom-syscall"); #endif @@ -155,6 +187,14 @@ DEFINE_RUN_ONCE_STATIC(init_info_strings) #endif #ifdef OPENSSL_RAND_SEED_OS add_seeds_string("os-specific"); +#endif +#ifndef OPENSSL_NO_JITTER + { + char buf[32]; + + BIO_snprintf(buf, sizeof(buf), "JITTER (%d)", jent_version()); + add_seeds_string(buf); + } #endif seed_sources = seeds; } @@ -172,11 +212,11 @@ const char *OPENSSL_info(int t) switch (t) { case OPENSSL_INFO_CONFIG_DIR: - return OPENSSLDIR; + return ossl_get_openssldir(); case OPENSSL_INFO_ENGINES_DIR: - return ENGINESDIR; + return ossl_get_enginesdir(); case OPENSSL_INFO_MODULES_DIR: - return MODULESDIR; + return ossl_get_modulesdir(); case OPENSSL_INFO_DSO_EXTENSION: return DSO_EXTENSION; case OPENSSL_INFO_DIR_FILENAME_SEPARATOR: @@ -203,6 +243,8 @@ const char *OPENSSL_info(int t) if (ossl_cpu_info_str[0] != '\0') return ossl_cpu_info_str + strlen(CPUINFO_PREFIX); break; + case OPENSSL_INFO_WINDOWS_CONTEXT: + return ossl_get_wininstallcontext(); default: break; } diff --git a/crypto/initthread.c b/crypto/initthread.c index e4d830d7fc..c773e2054e 100644 --- a/crypto/initthread.c +++ b/crypto/initthread.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -266,9 +266,8 @@ void *ossl_thread_event_ctx_new(OSSL_LIB_CTX *libctx) if (tlocal == NULL) return NULL; - if (!CRYPTO_THREAD_init_local(tlocal, NULL)) { - goto err; - } + if (!CRYPTO_THREAD_init_local(tlocal, NULL)) + goto deinit; hands = OPENSSL_zalloc(sizeof(*hands)); if (hands == NULL) @@ -290,12 +289,15 @@ void *ossl_thread_event_ctx_new(OSSL_LIB_CTX *libctx) return tlocal; err: OPENSSL_free(hands); + CRYPTO_THREAD_cleanup_local(tlocal); + deinit: OPENSSL_free(tlocal); return NULL; } void ossl_thread_event_ctx_free(void *tlocal) { + CRYPTO_THREAD_cleanup_local(tlocal); OPENSSL_free(tlocal); } diff --git a/crypto/mem.c b/crypto/mem.c index eef1165708..032f2a9cd1 100644 --- a/crypto/mem.c +++ b/crypto/mem.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -226,6 +226,68 @@ void *CRYPTO_zalloc(size_t num, const char *file, int line) return ret; } +void *CRYPTO_aligned_alloc(size_t num, size_t alignment, void **freeptr, + const char *file, int line) +{ + void *ret; + + *freeptr = NULL; + +#if defined(OPENSSL_SMALL_FOOTPRINT) + ret = freeptr = NULL; + return ret; +#endif + + /* Allow non-malloc() allocations as long as no malloc_impl is provided. */ + if (malloc_impl == CRYPTO_malloc) { +#if defined(_BSD_SOURCE) || (defined(_POSIX_C_SOURCE) && _POSIX_C_SOURCE >= 200112L) + if (posix_memalign(&ret, alignment, num)) + return NULL; + *freeptr = ret; + return ret; +#elif defined(_ISOC11_SOURCE) + ret = *freeptr = aligned_alloc(alignment, num); + return ret; +#endif + } + + /* we have to do this the hard way */ + + /* + * Note: Windows supports an _aligned_malloc call, but we choose + * not to use it here, because allocations from that function + * require that they be freed via _aligned_free. Given that + * we can't differentiate plain malloc blocks from blocks obtained + * via _aligned_malloc, just avoid its use entirely + */ + + /* + * Step 1: Allocate an amount of memory that is + * bytes bigger than requested + */ + *freeptr = CRYPTO_malloc(num + alignment, file, line); + if (*freeptr == NULL) + return NULL; + + /* + * Step 2: Add bytes to the pointer + * This will cross the alignment boundary that is + * requested + */ + ret = (void *)((char *)*freeptr + (alignment - 1)); + + /* + * Step 3: Use the alignment as a mask to translate the + * least significant bits of the allocation at the alignment + * boundary to 0. ret now holds a pointer to the memory + * buffer at the requested alignment + * NOTE: It is a documented requirement that alignment be a + * power of 2, which is what allows this to work + */ + ret = (void *)((uintptr_t)ret & (uintptr_t)(~(alignment - 1))); + return ret; +} + void *CRYPTO_realloc(void *str, size_t num, const char *file, int line) { INCREMENT(realloc_count); diff --git a/crypto/mem_sec.c b/crypto/mem_sec.c index 269c7dcb6d..e8700ebaa4 100644 --- a/crypto/mem_sec.c +++ b/crypto/mem_sec.c @@ -1,5 +1,5 @@ /* - * Copyright 2015-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2004-2014, Akamai Technologies. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -321,14 +321,12 @@ size_t CRYPTO_secure_actual_size(void *ptr) ((char*)(p) >= (char*)sh.freelist && (char*)(p) < (char*)&sh.freelist[sh.freelist_size]) -typedef struct sh_list_st -{ +typedef struct sh_list_st { struct sh_list_st *next; struct sh_list_st **p_next; } SH_LIST; -typedef struct sh_st -{ +typedef struct sh_st { char* map_result; size_t map_size; char *arena; diff --git a/crypto/modes/asm/aes-gcm-avx512.S b/crypto/modes/asm/aes-gcm-avx512.S index 19ddba6df3..0d97b3fa41 100644 --- a/crypto/modes/asm/aes-gcm-avx512.S +++ b/crypto/modes/asm/aes-gcm-avx512.S @@ -135982,7 +135982,7 @@ ossl_gcm_gmult_avx512: .byte 0xf3,0xc3 .cfi_endproc .size ossl_gcm_gmult_avx512, .-ossl_gcm_gmult_avx512 -.data +.section .rodata .align 16 POLY:.quad 0x0000000000000001, 0xC200000000000000 diff --git a/crypto/modes/asm/aes-gcm-avx512.pl b/crypto/modes/asm/aes-gcm-avx512.pl index e150c9aa05..79ee59f9e0 100644 --- a/crypto/modes/asm/aes-gcm-avx512.pl +++ b/crypto/modes/asm/aes-gcm-avx512.pl @@ -1,4 +1,4 @@ -# Copyright 2021-2023 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. # Copyright (c) 2021, Intel Corporation. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use @@ -4812,7 +4812,7 @@ sub GCM_COMPLETE { } $code .= <<___; -.data +.section .rodata align=16 .align 16 POLY: .quad 0x0000000000000001, 0xC200000000000000 diff --git a/crypto/modes/asm/aesni-gcm-x86_64.S b/crypto/modes/asm/aesni-gcm-x86_64.S index e3813bf7ce..4a7eca0125 100644 --- a/crypto/modes/asm/aesni-gcm-x86_64.S +++ b/crypto/modes/asm/aesni-gcm-x86_64.S @@ -774,6 +774,7 @@ aesni_gcm_encrypt: .byte 0xf3,0xc3 .cfi_endproc .size aesni_gcm_encrypt,.-aesni_gcm_encrypt +.section .rodata .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -786,6 +787,7 @@ aesni_gcm_encrypt: .Lone_lsb: .byte 1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 .byte 65,69,83,45,78,73,32,71,67,77,32,109,111,100,117,108,101,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .align 64 .section ".note.gnu.property", "a" .p2align 3 diff --git a/crypto/modes/asm/aesni-gcm-x86_64.pl b/crypto/modes/asm/aesni-gcm-x86_64.pl index eaf4d9c755..872e13f8f1 100644 --- a/crypto/modes/asm/aesni-gcm-x86_64.pl +++ b/crypto/modes/asm/aesni-gcm-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -943,6 +943,7 @@ ___ $code.=<<___; +.section .rodata align=64 .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -955,6 +956,7 @@ .Lone_lsb: .byte 1,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0 .asciz "AES-NI GCM module for x86_64, CRYPTOGAMS by " +.previous .align 64 ___ if ($win64) { diff --git a/crypto/modes/asm/ghash-x86_64.S b/crypto/modes/asm/ghash-x86_64.S index 29dd9b13e9..894f152b26 100644 --- a/crypto/modes/asm/ghash-x86_64.S +++ b/crypto/modes/asm/ghash-x86_64.S @@ -708,6 +708,7 @@ gcm_ghash_4bit: .align 16 gcm_init_clmul: .cfi_startproc +.byte 243,15,30,250 .L_init_clmul: movdqu (%rsi),%xmm2 pshufd $78,%xmm2,%xmm2 @@ -1306,6 +1307,7 @@ gcm_ghash_clmul: .align 32 gcm_init_avx: .cfi_startproc +.byte 243,15,30,250 vzeroupper vmovdqu (%rsi),%xmm2 @@ -1798,6 +1800,7 @@ gcm_ghash_avx: .byte 0xf3,0xc3 .cfi_endproc .size gcm_ghash_avx,.-gcm_ghash_avx +.section .rodata .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -1851,6 +1854,7 @@ gcm_ghash_avx: .byte 71,72,65,83,72,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/modes/asm/ghash-x86_64.pl b/crypto/modes/asm/ghash-x86_64.pl index 6709f96492..6ef8e555d0 100644 --- a/crypto/modes/asm/ghash-x86_64.pl +++ b/crypto/modes/asm/ghash-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2010-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2010-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -534,6 +534,7 @@ sub reduction_alg9 { # 17/11 times faster than Intel version .align 16 gcm_init_clmul: .cfi_startproc + endbranch .L_init_clmul: ___ $code.=<<___ if ($win64); @@ -1027,6 +1028,7 @@ sub reduction_alg9 { # 17/11 times faster than Intel version .align 32 gcm_init_avx: .cfi_startproc + endbranch ___ if ($avx) { my ($Htbl,$Xip)=@_4args; @@ -1609,6 +1611,7 @@ sub reduction_avx { } $code.=<<___; +.section .rodata align=64 .align 64 .Lbswap_mask: .byte 15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0 @@ -1662,6 +1665,7 @@ sub reduction_avx { .asciz "GHASH for x86_64, CRYPTOGAMS by " .align 64 +.previous ___ # EXCEPTION_DISPOSITION handler (EXCEPTION_RECORD *rec,ULONG64 frame, diff --git a/crypto/modes/gcm128.c b/crypto/modes/gcm128.c index f8901ed07c..366fe11215 100644 --- a/crypto/modes/gcm128.c +++ b/crypto/modes/gcm128.c @@ -485,7 +485,11 @@ static void gcm_get_funcs(struct gcm_funcs_st *ctx) #elif defined(GHASH_ASM_ARM) /* ARM defaults */ ctx->gmult = gcm_gmult_4bit; +# if !defined(OPENSSL_SMALL_FOOTPRINT) ctx->ghash = gcm_ghash_4bit; +# else + ctx->ghash = NULL; +# endif # ifdef PMULL_CAPABLE if (PMULL_CAPABLE) { ctx->ginit = (gcm_init_fn)gcm_init_v8; diff --git a/crypto/o_fopen.c b/crypto/o_fopen.c index 09c28e0bf7..cee4eee8a9 100644 --- a/crypto/o_fopen.c +++ b/crypto/o_fopen.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -39,8 +39,14 @@ FILE *openssl_fopen(const char *filename, const char *mode) { FILE *file = NULL; # if defined(_WIN32) && defined(CP_UTF8) - int sz, len_0 = (int)strlen(filename) + 1; + int sz, len_0; DWORD flags; +# endif + + if (filename == NULL) + return NULL; +# if defined(_WIN32) && defined(CP_UTF8) + len_0 = (int)strlen(filename) + 1; /* * Basically there are three cases to cover: a) filename is diff --git a/crypto/o_str.c b/crypto/o_str.c index dfac215ac3..93af73561f 100644 --- a/crypto/o_str.c +++ b/crypto/o_str.c @@ -14,6 +14,7 @@ #include "crypto/ctype.h" #include "internal/cryptlib.h" #include "internal/thread_once.h" +#include "internal/to_hex.h" #define DEFAULT_SEPARATOR ':' #define CH_ZERO '\0' @@ -90,6 +91,74 @@ size_t OPENSSL_strlcat(char *dst, const char *src, size_t size) return l + OPENSSL_strlcpy(dst, src, size); } +/** + * @brief Converts a string to an unsigned long integer. + * + * This function attempts to convert a string representation of a number + * to an unsigned long integer, given a specified base. It also provides + * error checking and reports whether the conversion was successful. + * This function is just a wrapper around the POSIX strtoul function with + * additional error checking. This implies that errno for the caller is set + * on calls to this function. + * + * @param str The string containing the representation of the number. + * @param endptr A pointer to a pointer to character. If not NULL, it is set + * to the character immediately following the number in the + * string. + * @param base The base to use for the conversion, which must be between 2, + * and 36 inclusive, or be the special value 0. If the base is 0, + * the actual base is determined by the format of the initial + * characters of the string. + * @param num A pointer to an unsigned long where the result of the + * conversion is stored. + * + * @return 1 if the conversion was successful, 0 otherwise. Conversion is + * considered unsuccessful if no digits were consumed or if an error + * occurred during conversion. + * + * @note It is the caller's responsibility to check if the conversion is + * correct based on the expected consumption of the string as reported + * by endptr. + */ +int OPENSSL_strtoul(const char *str, char **endptr, int base, + unsigned long *num) +{ + char *tmp_endptr; + char **internal_endptr = endptr == NULL ? &tmp_endptr : endptr; + + errno = 0; + + *internal_endptr = (char *)str; + + if (num == NULL) + return 0; + + if (str == NULL) + return 0; + + /* Fail on negative input */ + if (*str == '-') + return 0; + + *num = strtoul(str, internal_endptr, base); + /* + * We return error from this function under the following conditions + * 1) If strtoul itself returned an error in translation + * 2) If the caller didn't pass in an endptr value, and **internal_endptr + * doesn't point to '\0'. The implication here is that if the caller + * doesn't care how much of a string is consumed, they expect the entire + * string to be consumed. As such, no pointing to the NULL terminator + * means there was some part of the string left over after translation + * 3) If no bytes of the string were consumed + */ + if (errno != 0 || + (endptr == NULL && **internal_endptr != '\0') || + (str == *internal_endptr)) + return 0; + + return 1; +} + int OPENSSL_hexchar2int(unsigned char c) { #ifdef CHARSET_EBCDIC @@ -218,12 +287,9 @@ static int buf2hexstr_sep(char *str, size_t str_n, size_t *strlength, const unsigned char *buf, size_t buflen, const char sep) { - static const char hexdig[] = "0123456789ABCDEF"; - const unsigned char *p; char *q; - size_t i; int has_sep = (sep != CH_ZERO); - size_t len = has_sep ? buflen * 3 : 1 + buflen * 2; + size_t i, len = has_sep ? buflen * 3 : 1 + buflen * 2; if (len == 0) ++len; @@ -238,9 +304,8 @@ static int buf2hexstr_sep(char *str, size_t str_n, size_t *strlength, } q = str; - for (i = 0, p = buf; i < buflen; i++, p++) { - *q++ = hexdig[(*p >> 4) & 0xf]; - *q++ = hexdig[*p & 0xf]; + for (i = 0; i < buflen; i++) { + q += ossl_to_hex(q, buf[i]); if (has_sep) *q++ = sep; } @@ -360,3 +425,10 @@ int OPENSSL_strncasecmp(const char *s1, const char *s2, size_t n) return 0; return 0; } + +size_t ossl_to_hex(char *buf, uint8_t n) +{ + static const char hexdig[] = "0123456789ABCDEF"; + + return to_hex(buf, n, hexdig); +} diff --git a/crypto/objects/obj_dat.h b/crypto/objects/obj_dat.h index eaf0981599..4c61e964fd 100644 --- a/crypto/objects/obj_dat.h +++ b/crypto/objects/obj_dat.h @@ -10,7 +10,7 @@ */ /* Serialized OID's */ -static const unsigned char so[8487] = { +static const unsigned char so[8504] = { 0x2A,0x86,0x48,0x86,0xF7,0x0D, /* [ 0] OBJ_rsadsi */ 0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01, /* [ 6] OBJ_pkcs */ 0x2A,0x86,0x48,0x86,0xF7,0x0D,0x02,0x02, /* [ 13] OBJ_md2 */ @@ -268,7 +268,7 @@ static const unsigned char so[8487] = { 0x2B,0x06,0x01,0x05,0x05,0x07,0x00,0x10, /* [ 2075] OBJ_id_mod_cmp2000 */ 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x02, /* [ 2083] OBJ_biometricInfo */ 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x03, /* [ 2091] OBJ_qcStatements */ - 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x04, /* [ 2099] OBJ_ac_auditEntity */ + 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x04, /* [ 2099] OBJ_ac_auditIdentity */ 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x05, /* [ 2107] OBJ_ac_targeting */ 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x06, /* [ 2115] OBJ_aaControls */ 0x2B,0x06,0x01,0x05,0x05,0x07,0x01,0x07, /* [ 2123] OBJ_sbgp_ipAddrBlock */ @@ -1183,9 +1183,11 @@ static const unsigned char so[8487] = { 0x55,0x1D,0x4A, /* [ 8469] OBJ_alt_signature_value */ 0x55,0x1D,0x4B, /* [ 8472] OBJ_associated_information */ 0x2A,0x86,0x48,0x86,0xF7,0x0D,0x01,0x09,0x10,0x01,0x33, /* [ 8475] OBJ_id_ct_rpkiSignedPrefixList */ + 0x2B,0x06,0x01,0x05,0x05,0x07,0x08,0x04, /* [ 8486] OBJ_id_on_hardwareModuleName */ + 0x2B,0x06,0x01,0x04,0x01,0x82,0xE4,0x25,0x01, /* [ 8494] OBJ_id_kp_wisun_fan_device */ }; -#define NUM_NID 1321 +#define NUM_NID 1324 static const ASN1_OBJECT nid_objs[NUM_NID] = { {"UNDEF", "undefined", NID_undef}, {"rsadsi", "RSA Data Security, Inc.", NID_rsadsi, 6, &so[0]}, @@ -1474,7 +1476,7 @@ static const ASN1_OBJECT nid_objs[NUM_NID] = { {"id-mod-cmp2000", "id-mod-cmp2000", NID_id_mod_cmp2000, 8, &so[2075]}, {"biometricInfo", "Biometric Info", NID_biometricInfo, 8, &so[2083]}, {"qcStatements", "qcStatements", NID_qcStatements, 8, &so[2091]}, - {"ac-auditEntity", "ac-auditEntity", NID_ac_auditEntity, 8, &so[2099]}, + {"ac-auditIdentity", "X509v3 Audit Identity", NID_ac_auditIdentity, 8, &so[2099]}, {"ac-targeting", "ac-targeting", NID_ac_targeting, 8, &so[2107]}, {"aaControls", "aaControls", NID_aaControls, 8, &so[2115]}, {"sbgp-ipAddrBlock", "sbgp-ipAddrBlock", NID_sbgp_ipAddrBlock, 8, &so[2123]}, @@ -2508,9 +2510,12 @@ static const ASN1_OBJECT nid_objs[NUM_NID] = { {"altSignatureValue", "X509v3 Alternative Signature Value", NID_alt_signature_value, 3, &so[8469]}, {"associatedInformation", "X509v3 Associated Information", NID_associated_information, 3, &so[8472]}, {"id-ct-rpkiSignedPrefixList", "id-ct-rpkiSignedPrefixList", NID_id_ct_rpkiSignedPrefixList, 11, &so[8475]}, + {"id-on-hardwareModuleName", "Hardware Module Name", NID_id_on_hardwareModuleName, 8, &so[8486]}, + {"id-kp-wisun-fan-device", "Wi-SUN Alliance Field Area Network (FAN)", NID_id_kp_wisun_fan_device, 9, &so[8494]}, + {"NULL", "NULL", NID_ac_auditEntity}, }; -#define NUM_SN 1312 +#define NUM_SN 1315 static const unsigned int sn_objs[NUM_SN] = { 364, /* "AD_DVCS" */ 419, /* "AES-128-CBC" */ @@ -2705,6 +2710,7 @@ static const unsigned int sn_objs[NUM_SN] = { 388, /* "Mail" */ 393, /* "NULL" */ 404, /* "NULL" */ + 1323, /* "NULL" */ 57, /* "Netscape" */ 366, /* "Nonce" */ 17, /* "O" */ @@ -2823,7 +2829,7 @@ static const unsigned int sn_objs[NUM_SN] = { 1307, /* "aAissuingDistributionPoint" */ 478, /* "aRecord" */ 289, /* "aaControls" */ - 287, /* "ac-auditEntity" */ + 287, /* "ac-auditIdentity" */ 397, /* "ac-proxying" */ 288, /* "ac-targeting" */ 1303, /* "acceptableCertPolicies" */ @@ -3217,6 +3223,7 @@ static const unsigned int sn_objs[NUM_SN] = { 128, /* "id-kp" */ 1221, /* "id-kp-BrandIndicatorforMessageIdentification" */ 1220, /* "id-kp-bgpsec-router" */ + 1322, /* "id-kp-wisun-fan-device" */ 280, /* "id-mod-attribute-cert" */ 274, /* "id-mod-cmc" */ 277, /* "id-mod-cmp" */ @@ -3236,6 +3243,7 @@ static const unsigned int sn_objs[NUM_SN] = { 1211, /* "id-on-NAIRealm" */ 1208, /* "id-on-SmtpUTF8Mailbox" */ 1210, /* "id-on-dnsSRV" */ + 1321, /* "id-on-hardwareModuleName" */ 858, /* "id-on-permanentIdentifier" */ 347, /* "id-on-personalData" */ 1209, /* "id-on-xmppAddr" */ @@ -3826,7 +3834,7 @@ static const unsigned int sn_objs[NUM_SN] = { 1289, /* "zstd" */ }; -#define NUM_LN 1312 +#define NUM_LN 1315 static const unsigned int ln_objs[NUM_LN] = { 363, /* "AD Time Stamping" */ 405, /* "ANSI X9.62" */ @@ -3921,6 +3929,7 @@ static const unsigned int ln_objs[NUM_LN] = { 988, /* "HMAC GOST 34.11-2012 256 bit" */ 989, /* "HMAC GOST 34.11-2012 512 bit" */ 810, /* "HMAC GOST 34.11-94" */ + 1321, /* "Hardware Module Name" */ 432, /* "Hold Instruction Call Issuer" */ 430, /* "Hold Instruction Code" */ 431, /* "Hold Instruction None" */ @@ -3959,6 +3968,7 @@ static const unsigned int ln_objs[NUM_LN] = { 1211, /* "NAIRealm" */ 393, /* "NULL" */ 404, /* "NULL" */ + 1323, /* "NULL" */ 72, /* "Netscape Base Url" */ 76, /* "Netscape CA Policy Url" */ 74, /* "Netscape CA Revocation Url" */ @@ -4029,6 +4039,7 @@ static const unsigned int ln_objs[NUM_LN] = { 133, /* "Time Stamping" */ 375, /* "Trust Root" */ 1283, /* "Trusted key usage (Oracle)" */ + 1322, /* "Wi-SUN Alliance Field Area Network (FAN)" */ 1034, /* "X25519" */ 1035, /* "X448" */ 12, /* "X509" */ @@ -4043,6 +4054,7 @@ static const unsigned int ln_objs[NUM_LN] = { 1307, /* "X509v3 Attribute Authority Issuing Distribution Point" */ 1300, /* "X509v3 Attribute Descriptor" */ 1312, /* "X509v3 Attribute Mappings" */ + 287, /* "X509v3 Audit Identity" */ 1295, /* "X509v3 Authority Attribute Identifier" */ 90, /* "X509v3 Authority Key Identifier" */ 1314, /* "X509v3 Authorization Validation" */ @@ -4088,7 +4100,6 @@ static const unsigned int ln_objs[NUM_LN] = { 1289, /* "Zstandard compression" */ 478, /* "aRecord" */ 289, /* "aaControls" */ - 287, /* "ac-auditEntity" */ 397, /* "ac-proxying" */ 288, /* "ac-targeting" */ 446, /* "account" */ @@ -5142,7 +5153,7 @@ static const unsigned int ln_objs[NUM_LN] = { 125, /* "zlib compression" */ }; -#define NUM_OBJ 1178 +#define NUM_OBJ 1181 static const unsigned int obj_objs[NUM_OBJ] = { 0, /* OBJ_undef 0 */ 181, /* OBJ_iso 1 */ @@ -5150,6 +5161,7 @@ static const unsigned int obj_objs[NUM_OBJ] = { 404, /* OBJ_ccitt OBJ_itu_t */ 645, /* OBJ_itu_t 0 */ 646, /* OBJ_joint_iso_itu_t 2 */ + 1323, /* OBJ_ac_auditEntity OBJ_ac_auditIdentity */ 1264, /* OBJ_itu_t_identified_organization 0 4 */ 434, /* OBJ_data 0 9 */ 182, /* OBJ_member_body 1 2 */ @@ -5771,7 +5783,7 @@ static const unsigned int obj_objs[NUM_OBJ] = { 177, /* OBJ_info_access 1 3 6 1 5 5 7 1 1 */ 285, /* OBJ_biometricInfo 1 3 6 1 5 5 7 1 2 */ 286, /* OBJ_qcStatements 1 3 6 1 5 5 7 1 3 */ - 287, /* OBJ_ac_auditEntity 1 3 6 1 5 5 7 1 4 */ + 287, /* OBJ_ac_auditIdentity 1 3 6 1 5 5 7 1 4 */ 288, /* OBJ_ac_targeting 1 3 6 1 5 5 7 1 5 */ 289, /* OBJ_aaControls 1 3 6 1 5 5 7 1 6 */ 290, /* OBJ_sbgp_ipAddrBlock 1 3 6 1 5 5 7 1 7 */ @@ -5862,6 +5874,7 @@ static const unsigned int obj_objs[NUM_OBJ] = { 346, /* OBJ_id_cmc_confirmCertAcceptance 1 3 6 1 5 5 7 7 24 */ 347, /* OBJ_id_on_personalData 1 3 6 1 5 5 7 8 1 */ 858, /* OBJ_id_on_permanentIdentifier 1 3 6 1 5 5 7 8 3 */ + 1321, /* OBJ_id_on_hardwareModuleName 1 3 6 1 5 5 7 8 4 */ 1209, /* OBJ_XmppAddr 1 3 6 1 5 5 7 8 5 */ 1210, /* OBJ_SRVName 1 3 6 1 5 5 7 8 7 */ 1211, /* OBJ_NAIRealm 1 3 6 1 5 5 7 8 8 */ @@ -5999,6 +6012,7 @@ static const unsigned int obj_objs[NUM_OBJ] = { 1293, /* OBJ_ms_cert_templ 1 3 6 1 4 1 311 21 7 */ 1294, /* OBJ_ms_app_policies 1 3 6 1 4 1 311 21 10 */ 1292, /* OBJ_ms_ntds_sec_ext 1 3 6 1 4 1 311 25 2 */ + 1322, /* OBJ_id_kp_wisun_fan_device 1 3 6 1 4 1 45605 1 */ 390, /* OBJ_dcObject 1 3 6 1 4 1 1466 344 */ 91, /* OBJ_bf_cbc 1 3 6 1 4 1 3029 1 2 */ 973, /* OBJ_id_scrypt 1 3 6 1 4 1 11591 4 11 */ diff --git a/crypto/objects/obj_dat.pl b/crypto/objects/obj_dat.pl index 60a5e5a683..510a906f57 100644 --- a/crypto/objects/obj_dat.pl +++ b/crypto/objects/obj_dat.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -134,7 +134,7 @@ sub der_it my $r = &der_it($v); my $z = ""; my $length = 0; - # Format using fixed-with because we use strcmp later. + # Format using fixed-width because we use strcmp later. foreach (unpack("C*",$r)) { $z .= sprintf("0x%02X,", $_); $length++; diff --git a/crypto/objects/obj_mac.num b/crypto/objects/obj_mac.num index 7a3e0d3cc7..572e02257a 100644 --- a/crypto/objects/obj_mac.num +++ b/crypto/objects/obj_mac.num @@ -284,7 +284,7 @@ id_mod_dvcs 283 id_mod_cmp2000 284 biometricInfo 285 qcStatements 286 -ac_auditEntity 287 +ac_auditIdentity 287 ac_targeting 288 aaControls 289 sbgp_ipAddrBlock 290 @@ -1318,3 +1318,6 @@ alt_signature_algorithm 1317 alt_signature_value 1318 associated_information 1319 id_ct_rpkiSignedPrefixList 1320 +id_on_hardwareModuleName 1321 +id_kp_wisun_fan_device 1322 +ac_auditEntity 1323 diff --git a/crypto/objects/objects.txt b/crypto/objects/objects.txt index 86c3960375..552bb6b9a8 100644 --- a/crypto/objects/objects.txt +++ b/crypto/objects/objects.txt @@ -519,7 +519,8 @@ id-pkix-mod 100 : id-mod-cmp2021-02 id-pe 1 : authorityInfoAccess : Authority Information Access id-pe 2 : biometricInfo : Biometric Info id-pe 3 : qcStatements -id-pe 4 : ac-auditEntity +id-pe 4 : ac-auditIdentity : X509v3 Audit Identity +!Alias ac-auditEntity ac-auditIdentity id-pe 5 : ac-targeting id-pe 6 : aaControls id-pe 7 : sbgp-ipAddrBlock @@ -657,6 +658,7 @@ id-cmc 24 : id-cmc-confirmCertAcceptance # other names id-on 1 : id-on-personalData id-on 3 : id-on-permanentIdentifier : Permanent Identifier +id-on 4 : id-on-hardwareModuleName : Hardware Module Name id-on 5 : id-on-xmppAddr : XmppAddr id-on 7 : id-on-dnsSRV : SRVName id-on 8 : id-on-NAIRealm : NAIRealm @@ -994,6 +996,9 @@ Private 1 : enterprises : Enterprises # RFC 2247 Enterprises 1466 344 : dcobject : dcObject +# Wi-SUN Assigned Value Registry +Enterprises 45605 1 : id-kp-wisun-fan-device : Wi-SUN Alliance Field Area Network (FAN) + # RFC 1495 Mail 1 : mime-mhs : MIME MHS mime-mhs 1 : mime-mhs-headings : mime-mhs-headings diff --git a/crypto/ocsp/ocsp_vfy.c b/crypto/ocsp/ocsp_vfy.c index b0827e9a22..b0c2d6fd12 100644 --- a/crypto/ocsp/ocsp_vfy.c +++ b/crypto/ocsp/ocsp_vfy.c @@ -1,5 +1,5 @@ /* - * Copyright 2001-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2001-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -328,7 +328,7 @@ static int ocsp_match_issuerid(X509 *cert, OCSP_CERTID *cid, (void)ERR_pop_to_mark(); mdlen = EVP_MD_get_size(dgst); - if (mdlen < 0) { + if (mdlen <= 0) { ERR_raise(ERR_LIB_OCSP, OCSP_R_DIGEST_SIZE_ERR); goto end; } diff --git a/crypto/params_idx.c b/crypto/params_idx.c index d03426b4ed..a39592724a 100644 --- a/crypto/params_idx.c +++ b/crypto/params_idx.c @@ -51,15 +51,63 @@ int ossl_param_find_pidx(const char *s) break; case '_': if (strcmp("id_param", s + 4) == 0) - return PIDX_CIPHER_PARAM_ALGORITHM_ID_PARAMS; + return PIDX_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD; break; case 'i': if (strcmp("d-absent", s + 4) == 0) return PIDX_DIGEST_PARAM_ALGID_ABSENT; break; case 'o': - if (strcmp("rithm-id", s + 4) == 0) - return PIDX_SIGNATURE_PARAM_ALGORITHM_ID; + switch(s[4]) { + default: + break; + case 'r': + switch(s[5]) { + default: + break; + case 'i': + switch(s[6]) { + default: + break; + case 't': + switch(s[7]) { + default: + break; + case 'h': + switch(s[8]) { + default: + break; + case 'm': + switch(s[9]) { + default: + break; + case '-': + switch(s[10]) { + default: + break; + case 'i': + switch(s[11]) { + default: + break; + case 'd': + switch(s[12]) { + default: + break; + case '-': + if (strcmp("params", s + 13) == 0) + return PIDX_ALG_PARAM_ALGORITHM_ID_PARAMS; + break; + case '\0': + return PIDX_ALG_PARAM_ALGORITHM_ID; + } + } + } + } + } + } + } + } + } } break; case 'i': @@ -255,8 +303,17 @@ int ossl_param_find_pidx(const char *s) default: break; case 'c': - if (strcmp("oded-from-explicit", s + 3) == 0) - return PIDX_PKEY_PARAM_EC_DECODED_FROM_EXPLICIT_PARAMS; + switch(s[3]) { + default: + break; + case 'o': + if (strcmp("ded-from-explicit", s + 4) == 0) + return PIDX_PKEY_PARAM_EC_DECODED_FROM_EXPLICIT_PARAMS; + break; + case 'r': + if (strcmp("ypt-only", s + 4) == 0) + return PIDX_CIPHER_PARAM_DECRYPT_ONLY; + } break; case 'f': if (strcmp("ault-digest", s + 3) == 0) @@ -295,6 +352,10 @@ int ossl_param_find_pidx(const char *s) switch(s[7]) { default: break; + case 'c': + if (strcmp("heck", s + 8) == 0) + return PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK; + break; case 'n': if (strcmp("oinit", s + 8) == 0) return PIDX_MAC_PARAM_DIGEST_NOINIT; @@ -328,6 +389,10 @@ int ossl_param_find_pidx(const char *s) if (strcmp("bg-no-trunc-md", s + 2) == 0) return PIDX_PROV_PARAM_DRBG_TRUNC_DIGEST; break; + case 's': + if (strcmp("a-sign-disabled", s + 2) == 0) + return PIDX_PROV_PARAM_DSA_SIGN_DISABLED; + break; case '\0': return PIDX_PKEY_PARAM_RSA_D; } @@ -341,8 +406,81 @@ int ossl_param_find_pidx(const char *s) return PIDX_KDF_PARAM_EARLY_CLEAN; break; case 'c': - if (strcmp("dh-cofactor-mode", s + 2) == 0) - return PIDX_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE; + switch(s[2]) { + default: + break; + case 'd': + switch(s[3]) { + default: + break; + case 'h': + switch(s[4]) { + default: + break; + case '-': + switch(s[5]) { + default: + break; + case 'c': + switch(s[6]) { + default: + break; + case 'o': + switch(s[7]) { + default: + break; + case 'f': + switch(s[8]) { + default: + break; + case 'a': + switch(s[9]) { + default: + break; + case 'c': + switch(s[10]) { + default: + break; + case 't': + switch(s[11]) { + default: + break; + case 'o': + switch(s[12]) { + default: + break; + case 'r': + switch(s[13]) { + default: + break; + case '-': + switch(s[14]) { + default: + break; + case 'c': + if (strcmp("heck", s + 15) == 0) + return PIDX_PROV_PARAM_ECDH_COFACTOR_CHECK; + break; + case 'm': + if (strcmp("ode", s + 15) == 0) + return PIDX_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE; + } + } + } + } + } + } + } + } + } + } + } + } + } + break; + case 'm': + if (strcmp("s_check", s + 2) == 0) + return PIDX_KDF_PARAM_FIPS_EMS_CHECK; break; case 'n': switch(s[2]) { @@ -371,8 +509,37 @@ int ossl_param_find_pidx(const char *s) } break; case 'r': - if (strcmp("ypt-level", s + 4) == 0) - return PIDX_ENCODER_PARAM_ENCRYPT_LEVEL; + switch(s[4]) { + default: + break; + case 'y': + switch(s[5]) { + default: + break; + case 'p': + switch(s[6]) { + default: + break; + case 't': + switch(s[7]) { + default: + break; + case '-': + switch(s[8]) { + default: + break; + case 'c': + if (strcmp("heck", s + 9) == 0) + return PIDX_CIPHER_PARAM_FIPS_ENCRYPT_CHECK; + break; + case 'l': + if (strcmp("evel", s + 9) == 0) + return PIDX_ENCODER_PARAM_ENCRYPT_LEVEL; + } + } + } + } + } } break; case 'g': @@ -435,6 +602,10 @@ int ossl_param_find_pidx(const char *s) case 'n': if (strcmp("gerprint", s + 3) == 0) return PIDX_STORE_PARAM_FINGERPRINT; + break; + case 'p': + if (strcmp("s-indicator", s + 3) == 0) + return PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR; } } break; @@ -530,6 +701,42 @@ int ossl_param_find_pidx(const char *s) case 'i': if (strcmp("ndex", s + 2) == 0) return PIDX_PKEY_PARAM_FFC_H; + break; + case 'k': + switch(s[2]) { + default: + break; + case 'd': + switch(s[3]) { + default: + break; + case 'f': + switch(s[4]) { + default: + break; + case '-': + switch(s[5]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 6) == 0) + return PIDX_PROV_PARAM_HKDF_DIGEST_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 6) == 0) + return PIDX_PROV_PARAM_HKDF_KEY_CHECK; + } + } + } + } + break; + case 'm': + if (strcmp("ac-key-check", s + 2) == 0) + return PIDX_PROV_PARAM_HMAC_KEY_CHECK; + break; + case 's': + if (strcmp("_padding", s + 2) == 0) + return PIDX_LIBSSL_RECORD_LAYER_PARAM_HS_PADDING; } break; case 'i': @@ -599,6 +806,10 @@ int ossl_param_find_pidx(const char *s) switch(s[2]) { default: break; + case '-': + if (strcmp("generated", s + 3) == 0) + return PIDX_CIPHER_PARAM_AEAD_IV_GENERATED; + break; case 'l': if (strcmp("en", s + 3) == 0) return PIDX_CIPHER_PARAM_IVLEN; @@ -648,6 +859,10 @@ int ossl_param_find_pidx(const char *s) if (strcmp("t", s + 2) == 0) return PIDX_SIGNATURE_PARAM_KAT; break; + case 'b': + if (strcmp("kdf-key-check", s + 2) == 0) + return PIDX_PROV_PARAM_KBKDF_KEY_CHECK; + break; case 'd': switch(s[2]) { default: @@ -720,6 +935,10 @@ int ossl_param_find_pidx(const char *s) switch(s[3]) { default: break; + case '-': + if (strcmp("check", s + 4) == 0) + return PIDX_PKEY_PARAM_FIPS_KEY_CHECK; + break; case 'b': if (strcmp("its", s + 4) == 0) return PIDX_CIPHER_PARAM_RC2_KEYBITS; @@ -732,6 +951,10 @@ int ossl_param_find_pidx(const char *s) return PIDX_MAC_PARAM_KEY; } } + break; + case 'm': + if (strcmp("ac-key-check", s + 2) == 0) + return PIDX_PROV_PARAM_KMAC_KEY_CHECK; } break; case 'l': @@ -940,6 +1163,10 @@ int ossl_param_find_pidx(const char *s) switch(s[2]) { default: break; + case '-': + if (strcmp("short-mac", s + 3) == 0) + return PIDX_PROV_PARAM_NO_SHORT_MAC; + break; case 'n': switch(s[3]) { default: @@ -1084,8 +1311,17 @@ int ossl_param_find_pidx(const char *s) } break; case 'b': - if (strcmp("its", s + 2) == 0) - return PIDX_PKEY_PARAM_FFC_PBITS; + switch(s[2]) { + default: + break; + case 'i': + if (strcmp("ts", s + 3) == 0) + return PIDX_PKEY_PARAM_FFC_PBITS; + break; + case 'k': + if (strcmp("df2-lower-bound-check", s + 3) == 0) + return PIDX_PROV_PARAM_PBKDF2_LOWER_BOUND_CHECK; + } break; case 'c': if (strcmp("ounter", s + 2) == 0) @@ -1716,6 +1952,23 @@ int ossl_param_find_pidx(const char *s) } } } + break; + case 'p': + switch(s[5]) { + default: + break; + case 'k': + if (strcmp("cs15-pad-disabled", s + 6) == 0) + return PIDX_PROV_PARAM_RSA_PKCS15_PAD_DISABLED; + break; + case 's': + if (strcmp("s-saltlen-check", s + 6) == 0) + return PIDX_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK; + } + break; + case 's': + if (strcmp("ign-x931-pad-disabled", s + 5) == 0) + return PIDX_PROV_PARAM_RSA_SIGN_X931_PAD_DISABLED; } } } @@ -1823,16 +2076,142 @@ int ossl_param_find_pidx(const char *s) } break; case 'i': - if (strcmp("ze", s + 2) == 0) - return PIDX_MAC_PARAM_SIZE; + switch(s[2]) { + default: + break; + case 'g': + switch(s[3]) { + default: + break; + case 'n': + switch(s[4]) { + default: + break; + case '-': + switch(s[5]) { + default: + break; + case 'c': + if (strcmp("heck", s + 6) == 0) + return PIDX_PKEY_PARAM_FIPS_SIGN_CHECK; + break; + case 'x': + if (strcmp("931-pad-check", s + 6) == 0) + return PIDX_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK; + } + break; + case 'a': + switch(s[5]) { + default: + break; + case 't': + switch(s[6]) { + default: + break; + case 'u': + switch(s[7]) { + default: + break; + case 'r': + switch(s[8]) { + default: + break; + case 'e': + switch(s[9]) { + default: + break; + case '-': + if (strcmp("digest-check", s + 10) == 0) + return PIDX_PROV_PARAM_SIGNATURE_DIGEST_CHECK; + break; + case '\0': + return PIDX_SIGNATURE_PARAM_SIGNATURE; + } + } + } + } + } + } + } + break; + case 'z': + if (strcmp("e", s + 3) == 0) + return PIDX_MAC_PARAM_SIZE; + } break; case 'p': if (strcmp("eed", s + 2) == 0) return PIDX_CIPHER_PARAM_SPEED; break; case 's': - if (strcmp("l3-ms", s + 2) == 0) - return PIDX_DIGEST_PARAM_SSL3_MS; + switch(s[2]) { + default: + break; + case 'h': + switch(s[3]) { + default: + break; + case 'k': + switch(s[4]) { + default: + break; + case 'd': + switch(s[5]) { + default: + break; + case 'f': + switch(s[6]) { + default: + break; + case '-': + switch(s[7]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 8) == 0) + return PIDX_PROV_PARAM_SSHKDF_DIGEST_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 8) == 0) + return PIDX_PROV_PARAM_SSHKDF_KEY_CHECK; + } + } + } + } + } + break; + case 'k': + switch(s[3]) { + default: + break; + case 'd': + switch(s[4]) { + default: + break; + case 'f': + switch(s[5]) { + default: + break; + case '-': + switch(s[6]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 7) == 0) + return PIDX_PROV_PARAM_SSKDF_DIGEST_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 7) == 0) + return PIDX_PROV_PARAM_SSKDF_KEY_CHECK; + } + } + } + } + break; + case 'l': + if (strcmp("3-ms", s + 3) == 0) + return PIDX_DIGEST_PARAM_SSL3_MS; + } break; case 't': switch(s[2]) { @@ -1955,6 +2334,10 @@ int ossl_param_find_pidx(const char *s) } } break; + case 'd': + if (strcmp("es-encrypt-disabled", s + 2) == 0) + return PIDX_PROV_PARAM_TDES_ENCRYPT_DISABLED; + break; case 'e': switch(s[2]) { default: @@ -2328,8 +2711,79 @@ int ossl_param_find_pidx(const char *s) default: break; case '-': - if (strcmp("prf-ems-check", s + 5) == 0) - return PIDX_PROV_PARAM_TLS1_PRF_EMS_CHECK; + switch(s[5]) { + default: + break; + case 'p': + switch(s[6]) { + default: + break; + case 'r': + switch(s[7]) { + default: + break; + case 'f': + switch(s[8]) { + default: + break; + case '-': + switch(s[9]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 10) == 0) + return PIDX_PROV_PARAM_TLS1_PRF_DIGEST_CHECK; + break; + case 'e': + if (strcmp("ms-check", s + 10) == 0) + return PIDX_PROV_PARAM_TLS1_PRF_EMS_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 10) == 0) + return PIDX_PROV_PARAM_TLS1_PRF_KEY_CHECK; + } + } + } + } + } + break; + case '3': + switch(s[5]) { + default: + break; + case '-': + switch(s[6]) { + default: + break; + case 'k': + switch(s[7]) { + default: + break; + case 'd': + switch(s[8]) { + default: + break; + case 'f': + switch(s[9]) { + default: + break; + case '-': + switch(s[10]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 11) == 0) + return PIDX_PROV_PARAM_TLS13_KDF_DIGEST_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 11) == 0) + return PIDX_PROV_PARAM_TLS13_KDF_KEY_CHECK; + } + } + } + } + } + } break; case 'm': switch(s[5]) { @@ -2626,14 +3080,75 @@ int ossl_param_find_pidx(const char *s) } break; case 'e': - if (strcmp("rsion", s + 2) == 0) - return PIDX_PROV_PARAM_VERSION; + switch(s[2]) { + default: + break; + case 'r': + switch(s[3]) { + default: + break; + case 'i': + if (strcmp("fy-message", s + 4) == 0) + return PIDX_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE; + break; + case 's': + if (strcmp("ion", s + 4) == 0) + return PIDX_PROV_PARAM_VERSION; + } + } } break; case 'x': switch(s[1]) { default: break; + case '9': + switch(s[2]) { + default: + break; + case '4': + if (strcmp("2kdf-key-check", s + 3) == 0) + return PIDX_PROV_PARAM_X942KDF_KEY_CHECK; + break; + case '6': + switch(s[3]) { + default: + break; + case '3': + switch(s[4]) { + default: + break; + case 'k': + switch(s[5]) { + default: + break; + case 'd': + switch(s[6]) { + default: + break; + case 'f': + switch(s[7]) { + default: + break; + case '-': + switch(s[8]) { + default: + break; + case 'd': + if (strcmp("igest-check", s + 9) == 0) + return PIDX_PROV_PARAM_X963KDF_DIGEST_CHECK; + break; + case 'k': + if (strcmp("ey-check", s + 9) == 0) + return PIDX_PROV_PARAM_X963KDF_KEY_CHECK; + } + } + } + } + } + } + } + break; case 'c': if (strcmp("ghash", s + 2) == 0) return PIDX_KDF_PARAM_SSHKDF_XCGHASH; diff --git a/crypto/pem/pem_pk8.c b/crypto/pem/pem_pk8.c index 1592e351ed..4571187e91 100644 --- a/crypto/pem/pem_pk8.c +++ b/crypto/pem/pem_pk8.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -173,7 +173,7 @@ EVP_PKEY *d2i_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY **x, pem_password_cb *cb, X509_SIG *p8 = NULL; int klen; EVP_PKEY *ret; - char psbuf[PEM_BUFSIZE]; + char psbuf[PEM_BUFSIZE + 1]; /* reserve one byte at the end */ p8 = d2i_PKCS8_bio(bp, NULL); if (p8 == NULL) @@ -182,7 +182,7 @@ EVP_PKEY *d2i_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY **x, pem_password_cb *cb, klen = cb(psbuf, PEM_BUFSIZE, 0, u); else klen = PEM_def_callback(psbuf, PEM_BUFSIZE, 0, u); - if (klen < 0) { + if (klen < 0 || klen > PEM_BUFSIZE) { ERR_raise(ERR_LIB_PEM, PEM_R_BAD_PASSWORD_READ); X509_SIG_free(p8); return NULL; diff --git a/crypto/pem/pem_pkey.c b/crypto/pem/pem_pkey.c index 4deee46ce5..b640d3a7ae 100644 --- a/crypto/pem/pem_pkey.c +++ b/crypto/pem/pem_pkey.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -334,7 +334,7 @@ PEM_write_cb_fnsig(PrivateKey, EVP_PKEY, BIO, write_bio) /* * Note: there is no way to tell a provided pkey encoder to use "traditional" - * encoding. Therefore, if the pkey is provided, we try to take a copy + * encoding. Therefore, if the pkey is provided, we try to take a copy */ int PEM_write_bio_PrivateKey_traditional(BIO *bp, const EVP_PKEY *x, const EVP_CIPHER *enc, diff --git a/crypto/perlasm/riscv.pm b/crypto/perlasm/riscv.pm index 2148d249bf..2402c052ca 100644 --- a/crypto/perlasm/riscv.pm +++ b/crypto/perlasm/riscv.pm @@ -598,6 +598,15 @@ sub vmv_v_v { return ".word ".($template | ($vs1 << 15) | ($vd << 7)); } +sub vor_vv { + # vor.vv vd, vs2, vs1 + my $template = 0b0010101_00000_00000_000_00000_1010111; + my $vd = read_vreg shift; + my $vs2 = read_vreg shift; + my $vs1 = read_vreg shift; + return ".word ".($template | ($vs2 << 20) | ($vs1 << 15) | ($vd << 7)); +} + sub vor_vv_v0t { # vor.vv vd, vs2, vs1, v0.t my $template = 0b0010100_00000_00000_000_00000_1010111; @@ -747,6 +756,15 @@ sub vsll_vi { return ".word ".($template | ($vs2 << 20) | ($uimm << 15) | ($vd << 7)); } +sub vsrl_vi { + # vsrl.vi vd, vs2, uimm, vm + my $template = 0b1010001_00000_00000_011_00000_1010111; + my $vd = read_vreg shift; + my $vs2 = read_vreg shift; + my $uimm = shift; + return ".word ".($template | ($vs2 << 20) | ($uimm << 15) | ($vd << 7)); +} + sub vsrl_vx { # vsrl.vx vd, vs2, rs1 my $template = 0b1010001_00000_00000_100_00000_1010111; diff --git a/crypto/perlasm/x86_64-xlate.pl b/crypto/perlasm/x86_64-xlate.pl index 6b93cfb84f..a850df4966 100755 --- a/crypto/perlasm/x86_64-xlate.pl +++ b/crypto/perlasm/x86_64-xlate.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2005-2022 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -156,6 +156,65 @@ } my $current_segment; +# +# I could not find equivalent of .previous directive for MASM (Microsoft +# assembler ML). Using of .previous got introduced to .pl files with +# placing of various constants into .rodata sections (segments). +# Each .rodata section is terminated by .previous directive which +# restores the preceding section to .rodata: +# +# .text +# ; this is is the text section/segment +# .rodata +# ; constant definitions go here +# .previous +# ; the .text section which precedes .rodata got restored here +# +# The equivalent form for masm reads as follows: +# +# .text$ SEGMENT ALIGN(256) 'CODE' +# ; this is is the text section/segment +# .text$ ENDS +# .rdata SEGMENT READONLY ALIGN(64) +# ; constant definitions go here +# .rdata$ ENDS +# .text$ SEGMENT ALIGN(256) 'CODE' +# ; text section follows +# .text$ ENDS +# +# The .previous directive typically terminates .roadata segments/sections which +# hold definitions of constants. In order to place constants into .rdata +# segments when using masm we need to introduce a segment_stack array so we can +# emit proper ENDS directive whenever we see .previous. +# +# The code is tailored to work current set of .pl/asm files. There are some +# inconsistencies. For example .text section is the first section in all those +# files except ecp_nistz256. So we need to take that into account. +# +# ; stack is empty +# .text +# ; push '.text ' section twice, the stack looks as +# ; follows: +# ; ('.text', '.text') +# .rodata +# ; pop() so we can generate proper 'ENDS' for masm. +# ; stack looks like: +# ; ('.text') +# ; push '.rodata', so we can create corresponding ENDS for masm. +# ; stack looks like: +# ; ('.rodata', '.text') +# .previous +# ; pop() '.rodata' from stack, so we create '.rodata ENDS' +# ; in masm flavour. For nasm flavour we just pop() because +# ; nasm does not use .rodata ENDS to close the current section +# ; the stack content is like this: +# ; ('.text', '.text') +# ; pop() again to find a previous section we need to restore. +# ; Depending on flavour we either generate .section .text +# ; or .text SEGMENT. The stack looks like: +# ; ('.text') +# +my @segment_stack = (); my $current_function; my %globals; @@ -844,19 +903,61 @@ } elsif (!$elf && $dir =~ /\.align/) { $self->{value} = ".p2align\t" . (log($$line)/log(2)); } elsif ($dir eq ".section") { - $current_segment=$$line; + # + # get rid off align option, it's not supported/tolerated + # by gcc. openssl project introduced the option as an aid + # to deal with nasm/masm assembly. + # + $self->{value} =~ s/(.+)\s+align\s*=.*$/$1/; + $current_segment = pop(@segment_stack); + if (not $current_segment) { + # if no previous section is defined, then assume .text + # so code does not land in .data section by accident. + # this deals with inconsistency of perl-assembly files. + push(@segment_stack, ".text"); + } + # + # $$line may still contains align= option. We do care + # about section type here. + # + $current_segment = $$line; + $current_segment =~ s/([^\s]+).*$/$1/; + push(@segment_stack, $current_segment); + if (!$elf && $current_segment eq ".rodata") { + if ($flavour eq "macosx") { $self->{value} = ".section\t__DATA,__const"; } + elsif ($flavour eq "mingw64") { $self->{value} = ".section\t.rodata"; } + } if (!$elf && $current_segment eq ".init") { if ($flavour eq "macosx") { $self->{value} = ".mod_init_func"; } elsif ($flavour eq "mingw64") { $self->{value} = ".section\t.ctors"; } } } elsif ($dir =~ /\.(text|data)/) { + $current_segment = pop(@segment_stack); + if (not $current_segment) { + # if no previous section is defined, then assume .text + # so code does not land in .data section by accident. + # this deals with inconsistency of perl-assembly files. + push(@segment_stack, ".text"); + } $current_segment=".$1"; + push(@segment_stack, $current_segment); } elsif ($dir =~ /\.hidden/) { if ($flavour eq "macosx") { $self->{value} = ".private_extern\t$prefix$$line"; } elsif ($flavour eq "mingw64") { $self->{value} = ""; } } elsif ($dir =~ /\.comm/) { $self->{value} = "$dir\t$prefix$$line"; $self->{value} =~ s|,([0-9]+),([0-9]+)$|",$1,".log($2)/log(2)|e if ($flavour eq "macosx"); + } elsif ($dir =~ /\.previous/) { + pop(@segment_stack); #pop ourselves + # just peek at the top of the stack here + $current_segment = @segment_stack[0]; + if (not $current_segment) { + # if no previous segment was defined assume .text so + # the code does not accidentally land in .data section. + $current_segment = ".text"; + push(@segment_stack, $current_segment); + } + $self->{value} = $current_segment if ($flavour eq "mingw64"); } $$line = ""; return $self; @@ -866,10 +967,21 @@ SWITCH: for ($dir) { /\.text/ && do { my $v=undef; if ($nasm) { + $current_segment = pop(@segment_stack); + if (not $current_segment) { + push(@segment_stack, ".text"); + } $v="section .text code align=64\n"; + $current_segment = ".text"; + push(@segment_stack, $current_segment); } else { + $current_segment = pop(@segment_stack); + if (not $current_segment) { + push(@segment_stack, ".text\$"); + } $v="$current_segment\tENDS\n" if ($current_segment); $current_segment = ".text\$"; + push(@segment_stack, $current_segment); $v.="$current_segment\tSEGMENT "; $v.=$masm>=$masmref ? "ALIGN(256)" : "PAGE"; $v.=" 'CODE'"; @@ -881,36 +993,76 @@ if ($nasm) { $v="section .data data align=8\n"; } else { + $current_segment = pop(@segment_stack); $v="$current_segment\tENDS\n" if ($current_segment); $current_segment = "_DATA"; + push(@segment_stack, $current_segment); $v.="$current_segment\tSEGMENT"; } $self->{value} = $v; last; }; /\.section/ && do { my $v=undef; - $$line =~ s/([^,]*).*/$1/; + my $align=undef; + # + # $$line may currently contain something like this + # .rodata align = 64 + # align part is optional + # + $align = $$line; + $align =~ s/(.*)(align\s*=\s*\d+$)/$2/; + $$line =~ s/(.*)(\s+align\s*=\s*\d+$)/$1/; + $$line =~ s/,.*//; $$line = ".CRT\$XCU" if ($$line eq ".init"); + $$line = ".rdata" if ($$line eq ".rodata"); if ($nasm) { + $current_segment = pop(@segment_stack); + if (not $current_segment) { + # + # This is a hack which deals with ecp_nistz256-x86_64.pl, + # The precomputed curve is stored in the first section + # in .asm file. Pushing extra .text section here + # allows our poor man's solution to stick to assumption + # .text section is always the first. + # + push(@segment_stack, ".text"); + } $v="section $$line"; - if ($$line=~/\.([px])data/) { - $v.=" rdata align="; - $v.=$1 eq "p"? 4 : 8; + if ($$line=~/\.([prx])data/) { + if ($align =~ /align\s*=\s*(\d+)/) { + $v.= " rdata align=$1" ; + } else { + $v.=" rdata align="; + $v.=$1 eq "p"? 4 : 8; + } } elsif ($$line=~/\.CRT\$/i) { $v.=" rdata align=8"; } } else { + $current_segment = pop(@segment_stack); + if (not $current_segment) { + # + # same hack for masm to keep ecp_nistz256-x86_64.pl + # happy. + # + push(@segment_stack, ".text\$"); + } $v="$current_segment\tENDS\n" if ($current_segment); $v.="$$line\tSEGMENT"; - if ($$line=~/\.([px])data/) { + if ($$line=~/\.([prx])data/) { $v.=" READONLY"; - $v.=" ALIGN(".($1 eq "p" ? 4 : 8).")" if ($masm>=$masmref); + if ($align =~ /align\s*=\s*(\d+)$/) { + $v.=" ALIGN($1)" if ($masm>=$masmref); + } else { + $v.=" ALIGN(".($1 eq "p" ? 4 : 8).")" if ($masm>=$masmref); + } } elsif ($$line=~/\.CRT\$/i) { $v.=" READONLY "; $v.=$masm>=$masmref ? "ALIGN(8)" : "DWORD"; } } $current_segment = $$line; + push(@segment_stack, $$line); $self->{value} = $v; last; }; @@ -973,14 +1125,44 @@ if ($nasm) { $v.="common $prefix@str[0] @str[1]"; } else { + $current_segment = pop(@segment_stack);; $v="$current_segment\tENDS\n" if ($current_segment); $current_segment = "_DATA"; + push(@segment_stack, $current_segment); $v.="$current_segment\tSEGMENT\n"; $v.="COMM @str[0]:DWORD:".@str[1]/4; } $self->{value} = $v; last; }; + /^.previous/ && do { + my $v=undef; + if ($nasm) { + pop(@segment_stack); # pop ourselves, we don't need to emit END directive + # pop section so we can emit proper .section name. + $current_segment = pop(@segment_stack); + $v="section $current_segment"; + # Hack again: + # push section/segment to stack. The .previous is currently paired + # with .rodata only. We have to keep extra '.text' on stack for + # situation where there is for example .pdata section 'terminated' + # by new '.text' section. + # + push(@segment_stack, $current_segment); + } else { + $current_segment = pop(@segment_stack); + $v="$current_segment\tENDS\n" if ($current_segment); + $current_segment = pop(@segment_stack); + if ($current_segment =~ /\.text\$/) { + $v.="$current_segment\tSEGMENT "; + $v.=$masm>=$masmref ? "ALIGN(256)" : "PAGE"; + $v.=" 'CODE'"; + push(@segment_stack, $current_segment); + } + } + $self->{value} = $v; + last; + }; } $$line = ""; } diff --git a/crypto/pkcs12/p12_crt.c b/crypto/pkcs12/p12_crt.c index d0e3761d43..e6a2a3c55b 100644 --- a/crypto/pkcs12/p12_crt.c +++ b/crypto/pkcs12/p12_crt.c @@ -280,7 +280,7 @@ PKCS12_SAFEBAG *PKCS12_add_key(STACK_OF(PKCS12_SAFEBAG) **pbags, NULL, NULL); } -PKCS12_SAFEBAG *PKCS12_add_secret(STACK_OF(PKCS12_SAFEBAG) **pbags, +PKCS12_SAFEBAG *PKCS12_add_secret(STACK_OF(PKCS12_SAFEBAG) **pbags, int nid_type, const unsigned char *value, int len) { PKCS12_SAFEBAG *bag = NULL; diff --git a/crypto/pkcs12/p12_key.c b/crypto/pkcs12/p12_key.c index 9f7012a2c9..b5102110cd 100644 --- a/crypto/pkcs12/p12_key.c +++ b/crypto/pkcs12/p12_key.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -43,7 +43,7 @@ int PKCS12_key_gen_asc(const char *pass, int passlen, unsigned char *salt, unsigned char *out, const EVP_MD *md_type) { return PKCS12_key_gen_asc_ex(pass, passlen, salt, saltlen, id, iter, n, - out, md_type, NULL, NULL); + out, md_type, NULL, NULL); } int PKCS12_key_gen_utf8_ex(const char *pass, int passlen, unsigned char *salt, diff --git a/crypto/pkcs12/p12_mutl.c b/crypto/pkcs12/p12_mutl.c index 4091e61d9d..b43c82f0ed 100644 --- a/crypto/pkcs12/p12_mutl.c +++ b/crypto/pkcs12/p12_mutl.c @@ -15,12 +15,19 @@ #include #include "internal/cryptlib.h" +#include "crypto/evp.h" #include #include #include #include #include "p12_local.h" +static int pkcs12_pbmac1_pbkdf2_key_gen(const char *pass, int passlen, + unsigned char *salt, int saltlen, + int id, int iter, int keylen, + unsigned char *out, + const EVP_MD *md_type); + int PKCS12_mac_present(const PKCS12 *p12) { return p12->mac ? 1 : 0; @@ -72,9 +79,83 @@ static int pkcs12_gen_gost_mac_key(const char *pass, int passlen, return 1; } -/* Generate a MAC */ +PBKDF2PARAM *PBMAC1_get1_pbkdf2_param(const X509_ALGOR *macalg) +{ + PBMAC1PARAM *param = NULL; + PBKDF2PARAM *pbkdf2_param = NULL; + const ASN1_OBJECT *kdf_oid; + + param = ASN1_TYPE_unpack_sequence(ASN1_ITEM_rptr(PBMAC1PARAM), macalg->parameter); + if (param == NULL) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_PASSED_INVALID_ARGUMENT); + return NULL; + } + + X509_ALGOR_get0(&kdf_oid, NULL, NULL, param->keyDerivationFunc); + if (OBJ_obj2nid(kdf_oid) != NID_id_pbkdf2) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_PASSED_INVALID_ARGUMENT); + PBMAC1PARAM_free(param); + return NULL; + } + + pbkdf2_param = ASN1_TYPE_unpack_sequence(ASN1_ITEM_rptr(PBKDF2PARAM), + param->keyDerivationFunc->parameter); + PBMAC1PARAM_free(param); + + return pbkdf2_param; +} + +static int PBMAC1_PBKDF2_HMAC(OSSL_LIB_CTX *ctx, const char *propq, + const char *pass, int passlen, + const X509_ALGOR *macalg, unsigned char *key) +{ + PBKDF2PARAM *pbkdf2_param = NULL; + const ASN1_OBJECT *kdf_hmac_oid; + int kdf_hmac_nid; + int ret = -1; + int keylen = 0; + EVP_MD *kdf_md = NULL; + const ASN1_OCTET_STRING *pbkdf2_salt = NULL; + + pbkdf2_param = PBMAC1_get1_pbkdf2_param(macalg); + if (pbkdf2_param == NULL) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_UNSUPPORTED); + goto err; + } + keylen = ASN1_INTEGER_get(pbkdf2_param->keylength); + pbkdf2_salt = pbkdf2_param->salt->value.octet_string; + + if (pbkdf2_param->prf == NULL) { + kdf_hmac_nid = NID_hmacWithSHA1; + } else { + X509_ALGOR_get0(&kdf_hmac_oid, NULL, NULL, pbkdf2_param->prf); + kdf_hmac_nid = OBJ_obj2nid(kdf_hmac_oid); + } + + kdf_md = EVP_MD_fetch(ctx, OBJ_nid2sn(ossl_hmac2mdnid(kdf_hmac_nid)), propq); + if (kdf_md == NULL) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_FETCH_FAILED); + goto err; + } + + if (PKCS5_PBKDF2_HMAC(pass, passlen, pbkdf2_salt->data, pbkdf2_salt->length, + ASN1_INTEGER_get(pbkdf2_param->iter), kdf_md, keylen, key) <= 0) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_INTERNAL_ERROR); + goto err; + } + ret = keylen; + + err: + EVP_MD_free(kdf_md); + PBKDF2PARAM_free(pbkdf2_param); + + return ret; +} + +/* Generate a MAC, also used for verification */ static int pkcs12_gen_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char *mac, unsigned int *maclen, + int pbmac1_md_nid, int pbmac1_kdf_nid, int (*pkcs12_key_gen)(const char *pass, int passlen, unsigned char *salt, int slen, int id, int iter, int n, @@ -88,8 +169,8 @@ static int pkcs12_gen_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char key[EVP_MAX_MD_SIZE], *salt; int saltlen, iter; char md_name[80]; - int md_size = 0; - int md_nid; + int keylen = 0; + int md_nid = NID_undef; const X509_ALGOR *macalg; const ASN1_OBJECT *macoid; @@ -111,9 +192,13 @@ static int pkcs12_gen_mac(PKCS12 *p12, const char *pass, int passlen, iter = ASN1_INTEGER_get(p12->mac->iter); X509_SIG_get0(p12->mac->dinfo, &macalg, NULL); X509_ALGOR_get0(&macoid, NULL, NULL, macalg); - if (OBJ_obj2txt(md_name, sizeof(md_name), macoid, 0) < 0) - return 0; - + if (OBJ_obj2nid(macoid) == NID_pbmac1) { + if (OBJ_obj2txt(md_name, sizeof(md_name), OBJ_nid2obj(pbmac1_md_nid), 0) < 0) + return 0; + } else { + if (OBJ_obj2txt(md_name, sizeof(md_name), macoid, 0) < 0) + return 0; + } (void)ERR_set_mark(); md = md_fetch = EVP_MD_fetch(p12->authsafes->ctx.libctx, md_name, p12->authsafes->ctx.propq); @@ -127,40 +212,65 @@ static int pkcs12_gen_mac(PKCS12 *p12, const char *pass, int passlen, } (void)ERR_pop_to_mark(); - md_size = EVP_MD_get_size(md); + keylen = EVP_MD_get_size(md); md_nid = EVP_MD_get_type(md); - if (md_size < 0) + if (keylen <= 0) goto err; - if ((md_nid == NID_id_GostR3411_94 - || md_nid == NID_id_GostR3411_2012_256 - || md_nid == NID_id_GostR3411_2012_512) - && ossl_safe_getenv("LEGACY_GOST_PKCS12") == NULL) { - md_size = TK26_MAC_KEY_LEN; + + /* For PBMAC1 we use a special keygen callback if not provided (e.g. on verification) */ + if (pbmac1_md_nid != NID_undef && pkcs12_key_gen == NULL) { + keylen = PBMAC1_PBKDF2_HMAC(p12->authsafes->ctx.libctx, p12->authsafes->ctx.propq, + pass, passlen, macalg, key); + if (keylen < 0) + goto err; + } else if ((md_nid == NID_id_GostR3411_94 + || md_nid == NID_id_GostR3411_2012_256 + || md_nid == NID_id_GostR3411_2012_512) + && ossl_safe_getenv("LEGACY_GOST_PKCS12") == NULL) { + keylen = TK26_MAC_KEY_LEN; if (!pkcs12_gen_gost_mac_key(pass, passlen, salt, saltlen, iter, - md_size, key, md)) { + keylen, key, md)) { ERR_raise(ERR_LIB_PKCS12, PKCS12_R_KEY_GEN_ERROR); goto err; } } else { + EVP_MD *hmac_md = (EVP_MD *)md; + int fetched = 0; + + if (pbmac1_kdf_nid != NID_undef) { + char hmac_md_name[128]; + + if (OBJ_obj2txt(hmac_md_name, sizeof(hmac_md_name), OBJ_nid2obj(pbmac1_kdf_nid), 0) < 0) + goto err; + hmac_md = EVP_MD_fetch(NULL, hmac_md_name, NULL); + if (hmac_md == NULL) + goto err; + fetched = 1; + } if (pkcs12_key_gen != NULL) { - if (!(*pkcs12_key_gen)(pass, passlen, salt, saltlen, PKCS12_MAC_ID, - iter, md_size, key, md)) { + int res = (*pkcs12_key_gen)(pass, passlen, salt, saltlen, PKCS12_MAC_ID, + iter, keylen, key, hmac_md); + + if (fetched) + EVP_MD_free(hmac_md); + if (res != 1) { ERR_raise(ERR_LIB_PKCS12, PKCS12_R_KEY_GEN_ERROR); goto err; } } else { + if (fetched) + EVP_MD_free(hmac_md); /* Default to UTF-8 password */ if (!PKCS12_key_gen_utf8_ex(pass, passlen, salt, saltlen, PKCS12_MAC_ID, - iter, md_size, key, md, - p12->authsafes->ctx.libctx, - p12->authsafes->ctx.propq)) { + iter, keylen, key, md, + p12->authsafes->ctx.libctx, p12->authsafes->ctx.propq)) { ERR_raise(ERR_LIB_PKCS12, PKCS12_R_KEY_GEN_ERROR); goto err; } } } if ((hmac = HMAC_CTX_new()) == NULL - || !HMAC_Init_ex(hmac, key, md_size, md, NULL) + || !HMAC_Init_ex(hmac, key, keylen, md, NULL) || !HMAC_Update(hmac, p12->authsafes->d.data->data, p12->authsafes->d.data->length) || !HMAC_Final(hmac, mac, maclen)) { @@ -178,7 +288,7 @@ static int pkcs12_gen_mac(PKCS12 *p12, const char *pass, int passlen, int PKCS12_gen_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char *mac, unsigned int *maclen) { - return pkcs12_gen_mac(p12, pass, passlen, mac, maclen, NULL); + return pkcs12_gen_mac(p12, pass, passlen, mac, maclen, NID_undef, NID_undef, NULL); } /* Verify the mac */ @@ -187,14 +297,40 @@ int PKCS12_verify_mac(PKCS12 *p12, const char *pass, int passlen) unsigned char mac[EVP_MAX_MD_SIZE]; unsigned int maclen; const ASN1_OCTET_STRING *macoct; + const X509_ALGOR *macalg; + const ASN1_OBJECT *macoid; if (p12->mac == NULL) { ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_ABSENT); return 0; } - if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, NULL)) { - ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_GENERATION_ERROR); - return 0; + + X509_SIG_get0(p12->mac->dinfo, &macalg, NULL); + X509_ALGOR_get0(&macoid, NULL, NULL, macalg); + if (OBJ_obj2nid(macoid) == NID_pbmac1) { + PBMAC1PARAM *param = NULL; + const ASN1_OBJECT *hmac_oid; + int md_nid = NID_undef; + + param = ASN1_TYPE_unpack_sequence(ASN1_ITEM_rptr(PBMAC1PARAM), macalg->parameter); + if (param == NULL) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_UNSUPPORTED); + return 0; + } + X509_ALGOR_get0(&hmac_oid, NULL, NULL, param->messageAuthScheme); + md_nid = ossl_hmac2mdnid(OBJ_obj2nid(hmac_oid)); + + if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, md_nid, NID_undef, NULL)) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_GENERATION_ERROR); + PBMAC1PARAM_free(param); + return 0; + } + PBMAC1PARAM_free(param); + } else { + if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, NID_undef, NID_undef, NULL)) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_GENERATION_ERROR); + return 0; + } } X509_SIG_get0(p12->mac->dinfo, NULL, &macoct); if ((maclen != (unsigned int)ASN1_STRING_length(macoct)) @@ -205,7 +341,6 @@ int PKCS12_verify_mac(PKCS12 *p12, const char *pass, int passlen) } /* Set a mac */ - int PKCS12_set_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char *salt, int saltlen, int iter, const EVP_MD *md_type) @@ -226,7 +361,7 @@ int PKCS12_set_mac(PKCS12 *p12, const char *pass, int passlen, /* * Note that output mac is forced to UTF-8... */ - if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, NULL)) { + if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, NID_undef, NID_undef, NULL)) { ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_GENERATION_ERROR); return 0; } @@ -238,9 +373,18 @@ int PKCS12_set_mac(PKCS12 *p12, const char *pass, int passlen, return 1; } -/* Set up a mac structure */ -int PKCS12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, - const EVP_MD *md_type) +static int pkcs12_pbmac1_pbkdf2_key_gen(const char *pass, int passlen, + unsigned char *salt, int saltlen, + int id, int iter, int keylen, + unsigned char *out, + const EVP_MD *md_type) +{ + return PKCS5_PBKDF2_HMAC(pass, passlen, salt, saltlen, iter, + md_type, keylen, out); +} + +static int pkcs12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, + int nid) { X509_ALGOR *macalg; @@ -274,11 +418,112 @@ int PKCS12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, memcpy(p12->mac->salt->data, salt, saltlen); } X509_SIG_getm(p12->mac->dinfo, &macalg, NULL); - if (!X509_ALGOR_set0(macalg, OBJ_nid2obj(EVP_MD_get_type(md_type)), - V_ASN1_NULL, NULL)) { + if (!X509_ALGOR_set0(macalg, OBJ_nid2obj(nid), V_ASN1_NULL, NULL)) { ERR_raise(ERR_LIB_PKCS12, ERR_R_ASN1_LIB); return 0; } return 1; } + +/* Set up a mac structure */ +int PKCS12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, + const EVP_MD *md_type) +{ + return pkcs12_setup_mac(p12, iter, salt, saltlen, EVP_MD_get_type(md_type)); +} + +int PKCS12_set_pbmac1_pbkdf2(PKCS12 *p12, const char *pass, int passlen, + unsigned char *salt, int saltlen, int iter, + const EVP_MD *md_type, const char *prf_md_name) +{ + unsigned char mac[EVP_MAX_MD_SIZE]; + unsigned int maclen; + ASN1_OCTET_STRING *macoct; + X509_ALGOR *alg = NULL; + int ret = 0; + int prf_md_nid = NID_undef, prf_nid = NID_undef, hmac_nid; + unsigned char *known_salt = NULL; + int keylen = 0; + PBMAC1PARAM *param = NULL; + X509_ALGOR *hmac_alg = NULL, *macalg = NULL; + + if (md_type == NULL) + /* No need to do a fetch as the md_type is used only to get a NID */ + md_type = EVP_sha256(); + + if (prf_md_name == NULL) + prf_md_nid = EVP_MD_get_type(md_type); + else + prf_md_nid = OBJ_txt2nid(prf_md_name); + + if (iter == 0) + iter = PKCS12_DEFAULT_ITER; + + keylen = EVP_MD_get_size(md_type); + + prf_nid = ossl_md2hmacnid(prf_md_nid); + hmac_nid = ossl_md2hmacnid(EVP_MD_get_type(md_type)); + + if (prf_nid == NID_undef || hmac_nid == NID_undef) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_UNKNOWN_DIGEST_ALGORITHM); + goto err; + } + + if (salt == NULL) { + known_salt = OPENSSL_malloc(saltlen); + if (known_salt == NULL) + goto err; + + if (RAND_bytes_ex(NULL, known_salt, saltlen, 0) <= 0) { + ERR_raise(ERR_LIB_PKCS12, ERR_R_RAND_LIB); + goto err; + } + } + + param = PBMAC1PARAM_new(); + hmac_alg = X509_ALGOR_new(); + alg = PKCS5_pbkdf2_set(iter, salt ? salt : known_salt, saltlen, prf_nid, keylen); + if (param == NULL || hmac_alg == NULL || alg == NULL) + goto err; + + if (pkcs12_setup_mac(p12, iter, salt ? salt : known_salt, saltlen, + NID_pbmac1) == PKCS12_ERROR) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_SETUP_ERROR); + goto err; + } + + if (!X509_ALGOR_set0(hmac_alg, OBJ_nid2obj(hmac_nid), V_ASN1_NULL, NULL)) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_SETUP_ERROR); + goto err; + } + + X509_ALGOR_free(param->keyDerivationFunc); + X509_ALGOR_free(param->messageAuthScheme); + param->keyDerivationFunc = alg; + param->messageAuthScheme = hmac_alg; + + X509_SIG_getm(p12->mac->dinfo, &macalg, &macoct); + if (!ASN1_TYPE_pack_sequence(ASN1_ITEM_rptr(PBMAC1PARAM), param, &macalg->parameter)) + goto err; + + /* + * Note that output mac is forced to UTF-8... + */ + if (!pkcs12_gen_mac(p12, pass, passlen, mac, &maclen, + EVP_MD_get_type(md_type), prf_md_nid, + pkcs12_pbmac1_pbkdf2_key_gen)) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_GENERATION_ERROR); + goto err; + } + if (!ASN1_OCTET_STRING_set(macoct, mac, maclen)) { + ERR_raise(ERR_LIB_PKCS12, PKCS12_R_MAC_STRING_SET_ERROR); + goto err; + } + ret = 1; + + err: + PBMAC1PARAM_free(param); + OPENSSL_free(known_salt); + return ret; +} diff --git a/crypto/pkcs12/p12_npas.c b/crypto/pkcs12/p12_npas.c index 78be2b5a8c..37abb3821d 100644 --- a/crypto/pkcs12/p12_npas.c +++ b/crypto/pkcs12/p12_npas.c @@ -212,8 +212,7 @@ static int alg_get(const X509_ALGOR *alg, int *pnid, int *piter, if (pbe2 == NULL) goto done; - X509_ALGOR_get0(&aoid, &aparamtype, &aparam, pbe2->keyfunc); - pbenid = OBJ_obj2nid(aoid); + X509_ALGOR_get0(NULL, &aparamtype, &aparam, pbe2->keyfunc); X509_ALGOR_get0(&aoid, NULL, NULL, pbe2->encryption); encnid = OBJ_obj2nid(aoid); diff --git a/crypto/pkcs7/pk7_attr.c b/crypto/pkcs7/pk7_attr.c index a12d65bb8e..df83574eaa 100644 --- a/crypto/pkcs7/pk7_attr.c +++ b/crypto/pkcs7/pk7_attr.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -28,6 +28,10 @@ int PKCS7_add_attrib_smimecap(PKCS7_SIGNER_INFO *si, } seq->length = ASN1_item_i2d((ASN1_VALUE *)cap, &seq->data, ASN1_ITEM_rptr(X509_ALGORS)); + if (seq->length <= 0 || seq->data == NULL) { + ASN1_STRING_free(seq); + return 1; + } if (!PKCS7_add_signed_attribute(si, NID_SMIMECapabilities, V_ASN1_SEQUENCE, seq)) { ASN1_STRING_free(seq); diff --git a/crypto/pkcs7/pk7_doit.c b/crypto/pkcs7/pk7_doit.c index 2155014186..751caf684b 100644 --- a/crypto/pkcs7/pk7_doit.c +++ b/crypto/pkcs7/pk7_doit.c @@ -920,7 +920,7 @@ int PKCS7_SIGNER_INFO_sign(PKCS7_SIGNER_INFO *si) alen = ASN1_item_i2d((ASN1_VALUE *)si->auth_attr, &abuf, ASN1_ITEM_rptr(PKCS7_ATTR_SIGN)); - if (!abuf) + if (alen < 0 || abuf == NULL) goto err; if (EVP_DigestSignUpdate(mctx, abuf, alen) <= 0) goto err; @@ -1018,6 +1018,7 @@ int PKCS7_signatureVerify(BIO *bio, PKCS7 *p7, PKCS7_SIGNER_INFO *si, STACK_OF(X509_ATTRIBUTE) *sk; BIO *btmp; EVP_PKEY *pkey; + unsigned char *abuf = NULL; const PKCS7_CTX *ctx = ossl_pkcs7_get0_ctx(p7); OSSL_LIB_CTX *libctx = ossl_pkcs7_ctx_get0_libctx(ctx); const char *propq = ossl_pkcs7_ctx_get0_propq(ctx); @@ -1067,7 +1068,7 @@ int PKCS7_signatureVerify(BIO *bio, PKCS7 *p7, PKCS7_SIGNER_INFO *si, sk = si->auth_attr; if ((sk != NULL) && (sk_X509_ATTRIBUTE_num(sk) != 0)) { - unsigned char md_dat[EVP_MAX_MD_SIZE], *abuf = NULL; + unsigned char md_dat[EVP_MAX_MD_SIZE]; unsigned int md_len; int alen; ASN1_OCTET_STRING *message_digest; @@ -1102,15 +1103,13 @@ int PKCS7_signatureVerify(BIO *bio, PKCS7 *p7, PKCS7_SIGNER_INFO *si, alen = ASN1_item_i2d((ASN1_VALUE *)sk, &abuf, ASN1_ITEM_rptr(PKCS7_ATTR_VERIFY)); - if (alen <= 0) { + if (alen <= 0 || abuf == NULL) { ERR_raise(ERR_LIB_PKCS7, ERR_R_ASN1_LIB); ret = -1; goto err; } if (!EVP_VerifyUpdate(mdc_tmp, abuf, alen)) goto err; - - OPENSSL_free(abuf); } os = si->enc_digest; @@ -1128,6 +1127,7 @@ int PKCS7_signatureVerify(BIO *bio, PKCS7 *p7, PKCS7_SIGNER_INFO *si, } ret = 1; err: + OPENSSL_free(abuf); EVP_MD_CTX_free(mdc_tmp); EVP_MD_free(fetched_md); return ret; diff --git a/crypto/pkcs7/pk7_lib.c b/crypto/pkcs7/pk7_lib.c index 7be2928542..043a8f9ced 100644 --- a/crypto/pkcs7/pk7_lib.c +++ b/crypto/pkcs7/pk7_lib.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -413,7 +413,7 @@ PKCS7_SIGNER_INFO *PKCS7_add_signature(PKCS7 *p7, X509 *x509, EVP_PKEY *pkey, return NULL; } -static STACK_OF(X509) *pkcs7_get_signer_certs(const PKCS7 *p7) +STACK_OF(X509) *pkcs7_get0_certificates(const PKCS7 *p7) { if (p7->d.ptr == NULL) return NULL; @@ -454,7 +454,7 @@ void ossl_pkcs7_resolve_libctx(PKCS7 *p7) rinfos = pkcs7_get_recipient_info(p7); sinfos = PKCS7_get_signer_info(p7); - certs = pkcs7_get_signer_certs(p7); + certs = pkcs7_get0_certificates(p7); for (i = 0; i < sk_X509_num(certs); i++) ossl_x509_set0_libctx(sk_X509_value(certs, i), libctx, propq); diff --git a/crypto/pkcs7/pk7_local.h b/crypto/pkcs7/pk7_local.h index 8deb342b79..79f909f3dd 100644 --- a/crypto/pkcs7/pk7_local.h +++ b/crypto/pkcs7/pk7_local.h @@ -1,5 +1,5 @@ /* - * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -9,6 +9,7 @@ #include "crypto/pkcs7.h" +STACK_OF(X509) *pkcs7_get0_certificates(const PKCS7 *p7); const PKCS7_CTX *ossl_pkcs7_get0_ctx(const PKCS7 *p7); OSSL_LIB_CTX *ossl_pkcs7_ctx_get0_libctx(const PKCS7_CTX *ctx); const char *ossl_pkcs7_ctx_get0_propq(const PKCS7_CTX *ctx); diff --git a/crypto/pkcs7/pk7_smime.c b/crypto/pkcs7/pk7_smime.c index 747c417718..3f9ba3b7d6 100644 --- a/crypto/pkcs7/pk7_smime.c +++ b/crypto/pkcs7/pk7_smime.c @@ -11,6 +11,7 @@ #include #include "internal/cryptlib.h" +#include "crypto/x509.h" #include #include #include "pk7_local.h" @@ -215,6 +216,8 @@ int PKCS7_verify(PKCS7 *p7, STACK_OF(X509) *certs, X509_STORE *store, BIO *indata, BIO *out, int flags) { STACK_OF(X509) *signers; + STACK_OF(X509) *included_certs; + STACK_OF(X509) *untrusted = NULL; X509 *signer; STACK_OF(PKCS7_SIGNER_INFO) *sinfos; PKCS7_SIGNER_INFO *si; @@ -272,21 +275,24 @@ int PKCS7_verify(PKCS7 *p7, STACK_OF(X509) *certs, X509_STORE *store, ossl_pkcs7_ctx_get0_propq(p7_ctx)); if (cert_ctx == NULL) goto err; - if (!(flags & PKCS7_NOVERIFY)) + if ((flags & PKCS7_NOVERIFY) == 0) { + if (!ossl_x509_add_certs_new(&untrusted, certs, X509_ADD_FLAG_NO_DUP)) + goto err; + included_certs = pkcs7_get0_certificates(p7); + if ((flags & PKCS7_NOCHAIN) == 0 + && !ossl_x509_add_certs_new(&untrusted, included_certs, + X509_ADD_FLAG_NO_DUP)) + goto err; + for (k = 0; k < sk_X509_num(signers); k++) { signer = sk_X509_value(signers, k); - if (!(flags & PKCS7_NOCHAIN)) { - if (!X509_STORE_CTX_init(cert_ctx, store, signer, - p7->d.sign->cert)) { - ERR_raise(ERR_LIB_PKCS7, ERR_R_X509_LIB); - goto err; - } - if (!X509_STORE_CTX_set_default(cert_ctx, "smime_sign")) - goto err; - } else if (!X509_STORE_CTX_init(cert_ctx, store, signer, NULL)) { + if (!X509_STORE_CTX_init(cert_ctx, store, signer, untrusted)) { ERR_raise(ERR_LIB_PKCS7, ERR_R_X509_LIB); goto err; } + if ((flags & PKCS7_NOCHAIN) == 0 + && !X509_STORE_CTX_set_default(cert_ctx, "smime_sign")) + goto err; if (!(flags & PKCS7_NOCRL)) X509_STORE_CTX_set0_crls(cert_ctx, p7->d.sign->crl); i = X509_verify_cert(cert_ctx); @@ -299,6 +305,7 @@ int PKCS7_verify(PKCS7 *p7, STACK_OF(X509) *certs, X509_STORE *store, } /* Check for revocation status here */ } + } if ((p7bio = PKCS7_dataInit(p7, indata)) == NULL) goto err; @@ -353,13 +360,14 @@ int PKCS7_verify(PKCS7 *p7, STACK_OF(X509) *certs, X509_STORE *store, BIO_pop(p7bio); BIO_free_all(p7bio); sk_X509_free(signers); + sk_X509_free(untrusted); return ret; } STACK_OF(X509) *PKCS7_get0_signers(PKCS7 *p7, STACK_OF(X509) *certs, int flags) { - STACK_OF(X509) *signers; + STACK_OF(X509) *signers, *included_certs; STACK_OF(PKCS7_SIGNER_INFO) *sinfos; PKCS7_SIGNER_INFO *si; PKCS7_ISSUER_AND_SERIAL *ias; @@ -375,6 +383,7 @@ STACK_OF(X509) *PKCS7_get0_signers(PKCS7 *p7, STACK_OF(X509) *certs, ERR_raise(ERR_LIB_PKCS7, PKCS7_R_WRONG_CONTENT_TYPE); return NULL; } + included_certs = pkcs7_get0_certificates(p7); /* Collect all the signers together */ @@ -395,14 +404,11 @@ STACK_OF(X509) *PKCS7_get0_signers(PKCS7 *p7, STACK_OF(X509) *certs, ias = si->issuer_and_serial; signer = NULL; /* If any certificates passed they take priority */ - if (certs != NULL) - signer = X509_find_by_issuer_and_serial(certs, + signer = X509_find_by_issuer_and_serial(certs, + ias->issuer, ias->serial); + if (signer == NULL && (flags & PKCS7_NOINTERN) == 0) + signer = X509_find_by_issuer_and_serial(included_certs, ias->issuer, ias->serial); - if (signer == NULL && !(flags & PKCS7_NOINTERN) - && p7->d.sign->cert) - signer = - X509_find_by_issuer_and_serial(p7->d.sign->cert, - ias->issuer, ias->serial); if (signer == NULL) { ERR_raise(ERR_LIB_PKCS7, PKCS7_R_SIGNER_CERTIFICATE_NOT_FOUND); sk_X509_free(signers); diff --git a/crypto/poly1305/asm/poly1305-x86_64.S b/crypto/poly1305/asm/poly1305-x86_64.S index 9f9df19a37..140884bb25 100644 --- a/crypto/poly1305/asm/poly1305-x86_64.S +++ b/crypto/poly1305/asm/poly1305-x86_64.S @@ -50,6 +50,7 @@ poly1305_init: .align 32 poly1305_blocks: .cfi_startproc +.byte 243,15,30,250 .Lblocks: shrq $4,%rdx jz .Lno_data @@ -165,6 +166,7 @@ poly1305_blocks: .align 32 poly1305_emit: .cfi_startproc +.byte 243,15,30,250 .Lemit: movq 0(%rdi),%r8 movq 8(%rdi),%r9 @@ -401,6 +403,7 @@ __poly1305_init_avx: .align 32 poly1305_blocks_avx: .cfi_startproc +.byte 243,15,30,250 movl 20(%rdi),%r8d cmpq $128,%rdx jae .Lblocks_avx @@ -1236,6 +1239,7 @@ poly1305_blocks_avx: .align 32 poly1305_emit_avx: .cfi_startproc +.byte 243,15,30,250 cmpl $0,20(%rdi) je .Lemit @@ -1292,6 +1296,7 @@ poly1305_emit_avx: .align 32 poly1305_blocks_avx2: .cfi_startproc +.byte 243,15,30,250 movl 20(%rdi),%r8d cmpq $128,%rdx jae .Lblocks_avx2 @@ -1932,6 +1937,7 @@ poly1305_blocks_avx2: .byte 0xf3,0xc3 .cfi_endproc .size poly1305_blocks_avx2,.-poly1305_blocks_avx2 +.section .rodata .align 64 .Lconst: .Lmask24: @@ -1963,6 +1969,7 @@ poly1305_blocks_avx2: .Lx_mask42: .quad 0x3ffffffffff,0x3ffffffffff,0x3ffffffffff,0x3ffffffffff .quad 0x3ffffffffff,0x3ffffffffff,0x3ffffffffff,0x3ffffffffff +.previous .byte 80,111,108,121,49,51,48,53,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 16 .globl xor128_encrypt_n_pad diff --git a/crypto/poly1305/asm/poly1305-x86_64.pl b/crypto/poly1305/asm/poly1305-x86_64.pl index 4cddca1c51..305099ca03 100755 --- a/crypto/poly1305/asm/poly1305-x86_64.pl +++ b/crypto/poly1305/asm/poly1305-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -229,6 +229,7 @@ sub poly1305_iteration { .align 32 poly1305_blocks: .cfi_startproc + endbranch .Lblocks: shr \$4,$len jz .Lno_data # too short @@ -303,6 +304,7 @@ sub poly1305_iteration { .align 32 poly1305_emit: .cfi_startproc + endbranch .Lemit: mov 0($ctx),%r8 # load hash value mov 8($ctx),%r9 @@ -524,6 +526,7 @@ sub poly1305_iteration { .align 32 poly1305_blocks_avx: .cfi_startproc + endbranch mov 20($ctx),%r8d # is_base2_26 cmp \$128,$len jae .Lblocks_avx @@ -1384,6 +1387,7 @@ sub poly1305_iteration { .align 32 poly1305_emit_avx: .cfi_startproc + endbranch cmpl \$0,20($ctx) # is_base2_26? je .Lemit @@ -1448,6 +1452,7 @@ sub poly1305_iteration { .align 32 poly1305_blocks_avx2: .cfi_startproc + endbranch mov 20($ctx),%r8d # is_base2_26 cmp \$128,$len jae .Lblocks_avx2 @@ -2144,6 +2149,7 @@ sub poly1305_iteration { .align 32 poly1305_blocks_avx512: .cfi_startproc + endbranch .Lblocks_avx512: mov \$15,%eax kmovw %eax,%k2 @@ -3778,6 +3784,7 @@ sub poly1305_iteration { ___ } } } $code.=<<___; +.section .rodata align=64 .align 64 .Lconst: .Lmask24: @@ -3809,6 +3816,7 @@ sub poly1305_iteration { .Lx_mask42: .quad 0x3ffffffffff,0x3ffffffffff,0x3ffffffffff,0x3ffffffffff .quad 0x3ffffffffff,0x3ffffffffff,0x3ffffffffff,0x3ffffffffff +.previous ___ } $code.=<<___; diff --git a/crypto/poly1305/poly1305.c b/crypto/poly1305/poly1305.c index b3bf2b117b..693decd4ee 100644 --- a/crypto/poly1305/poly1305.c +++ b/crypto/poly1305/poly1305.c @@ -1,5 +1,5 @@ /* - * Copyright 2015-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -168,7 +168,7 @@ poly1305_blocks(void *ctx, const unsigned char *inp, size_t len, u32 padbit) h1 = (u64)(d1 = (u128)h1 + (d0 >> 64) + U8TOU64(inp + 8)); /* * padbit can be zero only when original len was - * POLY1306_BLOCK_SIZE, but we don't check + * POLY1305_BLOCK_SIZE, but we don't check */ h2 += (u64)(d1 >> 64) + padbit; diff --git a/crypto/provider_core.c b/crypto/provider_core.c index 297b281a39..266423dda9 100644 --- a/crypto/provider_core.c +++ b/crypto/provider_core.c @@ -32,6 +32,7 @@ #include "crypto/context.h" #ifndef FIPS_MODULE # include +# include #endif /* @@ -920,7 +921,7 @@ static int provider_init(OSSL_PROVIDER *prov) if (load_dir == NULL) { load_dir = ossl_safe_getenv("OPENSSL_MODULES"); if (load_dir == NULL) - load_dir = MODULESDIR; + load_dir = ossl_get_modulesdir(); } DSO_ctrl(prov->module, DSO_CTRL_SET_FLAGS, @@ -1934,6 +1935,7 @@ OSSL_FUNC_BIO_up_ref_fn ossl_core_bio_up_ref; OSSL_FUNC_BIO_free_fn ossl_core_bio_free; OSSL_FUNC_BIO_vprintf_fn ossl_core_bio_vprintf; OSSL_FUNC_BIO_vsnprintf_fn BIO_vsnprintf; +static OSSL_FUNC_indicator_cb_fn core_indicator_get_callback; static OSSL_FUNC_self_test_cb_fn core_self_test_get_callback; static OSSL_FUNC_get_entropy_fn rand_get_entropy; static OSSL_FUNC_get_user_entropy_fn rand_get_user_entropy; @@ -2097,6 +2099,12 @@ static int core_pop_error_to_mark(const OSSL_CORE_HANDLE *handle) return ERR_pop_to_mark(); } +static void core_indicator_get_callback(OPENSSL_CORE_CTX *libctx, + OSSL_INDICATOR_CALLBACK **cb) +{ + OSSL_INDICATOR_get_callback((OSSL_LIB_CTX *)libctx, cb); +} + static void core_self_test_get_callback(OPENSSL_CORE_CTX *libctx, OSSL_CALLBACK **cb, void **cbarg) { @@ -2258,6 +2266,7 @@ static const OSSL_DISPATCH core_dispatch_[] = { { OSSL_FUNC_BIO_VPRINTF, (void (*)(void))ossl_core_bio_vprintf }, { OSSL_FUNC_BIO_VSNPRINTF, (void (*)(void))BIO_vsnprintf }, { OSSL_FUNC_SELF_TEST_CB, (void (*)(void))core_self_test_get_callback }, + { OSSL_FUNC_INDICATOR_CB, (void (*)(void))core_indicator_get_callback }, { OSSL_FUNC_GET_ENTROPY, (void (*)(void))rand_get_entropy }, { OSSL_FUNC_GET_USER_ENTROPY, (void (*)(void))rand_get_user_entropy }, { OSSL_FUNC_CLEANUP_ENTROPY, (void (*)(void))rand_cleanup_entropy }, diff --git a/crypto/rand/rand_lib.c b/crypto/rand/rand_lib.c index 14999540ab..5430290192 100644 --- a/crypto/rand/rand_lib.c +++ b/crypto/rand/rand_lib.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -20,6 +20,10 @@ #include "rand_local.h" #include "crypto/context.h" +#ifndef OPENSSL_DEFAULT_SEED_SRC +# define OPENSSL_DEFAULT_SEED_SRC SEED-SRC +#endif + #ifndef FIPS_MODULE # include # include @@ -593,7 +597,7 @@ static EVP_RAND_CTX *rand_new_seed(OSSL_LIB_CTX *libctx) propq = props; } } - name = "SEED-SRC"; + name = OPENSSL_MSTR(OPENSSL_DEFAULT_SEED_SRC); } rand = EVP_RAND_fetch(libctx, name, propq); @@ -638,7 +642,7 @@ EVP_RAND_CTX *ossl_rand_get0_seed_noncreating(OSSL_LIB_CTX *ctx) static EVP_RAND_CTX *rand_new_drbg(OSSL_LIB_CTX *libctx, EVP_RAND_CTX *parent, unsigned int reseed_interval, - time_t reseed_time_interval, int use_df) + time_t reseed_time_interval) { EVP_RAND *rand; RAND_GLOBAL *dgbl = rand_get_global(libctx); @@ -646,6 +650,7 @@ static EVP_RAND_CTX *rand_new_drbg(OSSL_LIB_CTX *libctx, EVP_RAND_CTX *parent, OSSL_PARAM params[8], *p = params; const OSSL_PARAM *settables; char *name, *cipher; + int use_df = 1; if (dgbl == NULL) return NULL; @@ -692,6 +697,33 @@ static EVP_RAND_CTX *rand_new_drbg(OSSL_LIB_CTX *libctx, EVP_RAND_CTX *parent, return ctx; } +#ifdef FIPS_MODULE +static EVP_RAND_CTX *rand_new_crngt(OSSL_LIB_CTX *libctx, EVP_RAND_CTX *parent) +{ + EVP_RAND *rand; + EVP_RAND_CTX *ctx; + + rand = EVP_RAND_fetch(libctx, "CRNG-TEST", "fips=no"); + if (rand == NULL) { + ERR_raise(ERR_LIB_RAND, RAND_R_UNABLE_TO_FETCH_DRBG); + return NULL; + } + ctx = EVP_RAND_CTX_new(rand, parent); + EVP_RAND_free(rand); + if (ctx == NULL) { + ERR_raise(ERR_LIB_RAND, RAND_R_UNABLE_TO_CREATE_DRBG); + return NULL; + } + + if (!EVP_RAND_instantiate(ctx, 0, 0, NULL, 0, NULL)) { + ERR_raise(ERR_LIB_RAND, RAND_R_ERROR_INSTANTIATING_DRBG); + EVP_RAND_CTX_free(ctx); + return NULL; + } + return ctx; +} +#endif + /* * Get the primary random generator. * Returns pointer to its EVP_RAND_CTX on success, NULL on failure. @@ -723,21 +755,23 @@ EVP_RAND_CTX *RAND_get0_primary(OSSL_LIB_CTX *ctx) return ret; } -#ifndef FIPS_MODULE +#ifdef FIPS_MODULE + ret = rand_new_crngt(ctx, dgbl->seed); +#else if (dgbl->seed == NULL) { ERR_set_mark(); dgbl->seed = rand_new_seed(ctx); ERR_pop_to_mark(); } + ret = rand_new_drbg(ctx, dgbl->seed, PRIMARY_RESEED_INTERVAL, + PRIMARY_RESEED_TIME_INTERVAL); #endif - ret = dgbl->primary = rand_new_drbg(ctx, dgbl->seed, - PRIMARY_RESEED_INTERVAL, - PRIMARY_RESEED_TIME_INTERVAL, 1); /* - * The primary DRBG may be shared between multiple threads so we must - * enable locking. - */ + * The primary DRBG may be shared between multiple threads so we must + * enable locking. + */ + dgbl->primary = ret; if (ret != NULL && !EVP_RAND_enable_locking(ret)) { ERR_raise(ERR_LIB_EVP, EVP_R_UNABLE_TO_ENABLE_LOCKING); EVP_RAND_CTX_free(ret); @@ -775,7 +809,7 @@ EVP_RAND_CTX *RAND_get0_public(OSSL_LIB_CTX *ctx) && !ossl_init_thread_start(NULL, ctx, rand_delete_thread_state)) return NULL; rand = rand_new_drbg(ctx, primary, SECONDARY_RESEED_INTERVAL, - SECONDARY_RESEED_TIME_INTERVAL, 0); + SECONDARY_RESEED_TIME_INTERVAL); CRYPTO_THREAD_set_local(&dgbl->public, rand); } return rand; @@ -808,7 +842,7 @@ EVP_RAND_CTX *RAND_get0_private(OSSL_LIB_CTX *ctx) && !ossl_init_thread_start(NULL, ctx, rand_delete_thread_state)) return NULL; rand = rand_new_drbg(ctx, primary, SECONDARY_RESEED_INTERVAL, - SECONDARY_RESEED_TIME_INTERVAL, 0); + SECONDARY_RESEED_TIME_INTERVAL); CRYPTO_THREAD_set_local(&dgbl->private, rand); } return rand; diff --git a/crypto/riscvcap.c b/crypto/riscvcap.c index db75c21b28..b87fe4c94e 100644 --- a/crypto/riscvcap.c +++ b/crypto/riscvcap.c @@ -1,5 +1,5 @@ /* - * Copyright 2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,6 +17,12 @@ #define OPENSSL_RISCVCAP_IMPL #include "crypto/riscv_arch.h" +#ifdef OSSL_RISCV_HWPROBE +# include +# include +# include +#endif + extern size_t riscv_vlen_asm(void); static void parse_env(const char *envstr); @@ -42,7 +48,7 @@ size_t OPENSSL_instrument_bus2(unsigned int *out, size_t cnt, size_t max) static void strtoupper(char *str) { for (char *x = str; *x; ++x) - *x = toupper(*x); + *x = toupper((unsigned char)*x); } /* parse_env() parses a RISC-V architecture string. An example of such a string @@ -71,6 +77,38 @@ static void parse_env(const char *envstr) } } +#ifdef OSSL_RISCV_HWPROBE +static long riscv_hwprobe(struct riscv_hwprobe *pairs, size_t pair_count, + size_t cpu_count, unsigned long *cpus, + unsigned int flags) +{ + return syscall(__NR_riscv_hwprobe, pairs, pair_count, cpu_count, cpus, flags); +} + +static void hwprobe_to_cap(void) +{ + long ret; + struct riscv_hwprobe pairs[OSSL_RISCV_HWPROBE_PAIR_COUNT] = { + OSSL_RISCV_HWPROBE_PAIR_CONTENT + }; + + ret = riscv_hwprobe(pairs, OSSL_RISCV_HWPROBE_PAIR_COUNT, 0, NULL, 0); + /* if hwprobe syscall does not exist, ret would be -ENOSYS */ + if (ret == 0) { + for (size_t i = 0; i < kRISCVNumCaps; ++i) { + for (size_t j = 0; j != OSSL_RISCV_HWPROBE_PAIR_COUNT; ++j) { + if (pairs[j].key == RISCV_capabilities[i].hwprobe_key + && (pairs[j].value & RISCV_capabilities[i].hwprobe_value) + != 0) + /* Match, set relevant bit in OPENSSL_riscvcap_P[] */ + OPENSSL_riscvcap_P[RISCV_capabilities[i].index] |= + (1 << RISCV_capabilities[i].bit_offset); + } + } + } +} +#endif /* OSSL_RISCV_HWPROBE */ + size_t riscv_vlen(void) { return vlen; @@ -91,6 +129,11 @@ void OPENSSL_cpuid_setup(void) if ((e = getenv("OPENSSL_riscvcap"))) { parse_env(e); } +#ifdef OSSL_RISCV_HWPROBE + else { + hwprobe_to_cap(); + } +#endif if (RISCV_HAS_V()) { vlen = riscv_vlen_asm(); diff --git a/crypto/rsa/rsa_ameth.c b/crypto/rsa/rsa_ameth.c index 148d0bbbd1..42b03fb2fd 100644 --- a/crypto/rsa/rsa_ameth.c +++ b/crypto/rsa/rsa_ameth.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -454,15 +454,19 @@ static RSA_PSS_PARAMS *rsa_ctx_to_pss(EVP_PKEY_CTX *pkctx) EVP_PKEY *pk = EVP_PKEY_CTX_get0_pkey(pkctx); int saltlen; int saltlenMax = -1; + int md_size; if (EVP_PKEY_CTX_get_signature_md(pkctx, &sigmd) <= 0) return NULL; + md_size = EVP_MD_get_size(sigmd); + if (md_size <= 0) + return NULL; if (EVP_PKEY_CTX_get_rsa_mgf1_md(pkctx, &mgf1md) <= 0) return NULL; if (EVP_PKEY_CTX_get_rsa_pss_saltlen(pkctx, &saltlen) <= 0) return NULL; if (saltlen == RSA_PSS_SALTLEN_DIGEST) { - saltlen = EVP_MD_get_size(sigmd); + saltlen = md_size; } else if (saltlen == RSA_PSS_SALTLEN_AUTO_DIGEST_MAX) { /* FIPS 186-4 section 5 "The RSA Digital Signature Algorithm", * subsection 5.5 "PKCS #1" says: "For RSASSA-PSS […] the length (in @@ -472,10 +476,10 @@ static RSA_PSS_PARAMS *rsa_ctx_to_pss(EVP_PKEY_CTX *pkctx) * Provide a way to use at most the digest length, so that the default * does not violate FIPS 186-4. */ saltlen = RSA_PSS_SALTLEN_MAX; - saltlenMax = EVP_MD_get_size(sigmd); + saltlenMax = md_size; } if (saltlen == RSA_PSS_SALTLEN_MAX || saltlen == RSA_PSS_SALTLEN_AUTO) { - saltlen = EVP_PKEY_get_size(pk) - EVP_MD_get_size(sigmd) - 2; + saltlen = EVP_PKEY_get_size(pk) - md_size - 2; if ((EVP_PKEY_get_bits(pk) & 0x7) == 1) saltlen--; if (saltlen < 0) @@ -719,7 +723,7 @@ static int rsa_sig_info_set(X509_SIG_INFO *siginf, const X509_ALGOR *sigalg, const ASN1_STRING *sig) { int rv = 0; - int mdnid, saltlen; + int mdnid, saltlen, md_size; uint32_t flags; const EVP_MD *mgf1md = NULL, *md = NULL; RSA_PSS_PARAMS *pss; @@ -732,6 +736,9 @@ static int rsa_sig_info_set(X509_SIG_INFO *siginf, const X509_ALGOR *sigalg, pss = ossl_rsa_pss_decode(sigalg); if (!ossl_rsa_pss_get_param(pss, &md, &mgf1md, &saltlen)) goto err; + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + goto err; mdnid = EVP_MD_get_type(md); /* * For TLS need SHA256, SHA384 or SHA512, digest and MGF1 digest must @@ -739,12 +746,12 @@ static int rsa_sig_info_set(X509_SIG_INFO *siginf, const X509_ALGOR *sigalg, */ if ((mdnid == NID_sha256 || mdnid == NID_sha384 || mdnid == NID_sha512) && mdnid == EVP_MD_get_type(mgf1md) - && saltlen == EVP_MD_get_size(md)) + && saltlen == md_size) flags = X509_SIG_INFO_TLS; else flags = 0; /* Note: security bits half number of digest bits */ - secbits = EVP_MD_get_size(md) * 4; + secbits = md_size * 4; /* * SHA1 and MD5 are known to be broken. Reduce security bits so that * they're no longer accepted at security level 1. The real values don't diff --git a/crypto/rsa/rsa_backend.c b/crypto/rsa/rsa_backend.c index 36ee283370..d6864dc237 100644 --- a/crypto/rsa/rsa_backend.c +++ b/crypto/rsa/rsa_backend.c @@ -229,6 +229,12 @@ int ossl_rsa_fromdata(RSA *rsa, const OSSL_PARAM params[], int include_private) } } + if (!ossl_rsa_check_factors(rsa)) { + ERR_raise_data(ERR_LIB_RSA, RSA_R_INVALID_KEYPAIR, + "RSA factors/exponents are too big for for n-modulus\n"); + goto err; + } + BN_clear_free(p); BN_clear_free(q); sk_BIGNUM_free(factors); diff --git a/crypto/rsa/rsa_gen.c b/crypto/rsa/rsa_gen.c index 75347d800e..c04a4ea3d9 100644 --- a/crypto/rsa/rsa_gen.c +++ b/crypto/rsa/rsa_gen.c @@ -649,47 +649,69 @@ static int rsa_keygen(OSSL_LIB_CTX *libctx, RSA *rsa, int bits, int primes, } /* - * For RSA key generation it is not known whether the key pair will be used - * for key transport or signatures. FIPS 140-2 IG 9.9 states that in this case - * either a signature verification OR an encryption operation may be used to - * perform the pairwise consistency check. The simpler encrypt/decrypt operation - * has been chosen for this case. + * AS10.35 (and its VEs/TEs) of the FIPS 140-3 standard requires a PCT for every + * generated key pair. There are 3 options: + * 1) If the key pair is to be used for key transport (asymmetric cipher), the + * PCT consists of encrypting a plaintext, verifying that the result + * (ciphertext) is not equal to the plaintext, decrypting the ciphertext, and + * verifying that the result is equal to the plaintext. + * 2) If the key pair is to be used for digital signatures, the PCT consists of + * computing and verifying a signature. + * 3) If the key pair is to be used for key agreement, the exact PCT is defined + * in the applicable standards. For RSA-based schemes, this is defined in + * SP 800-56Br2 (Section 6.4.1.1) as: + * "The owner shall perform a pair-wise consistency test by verifying that m + * = (m^e)^d mod n for some integer m satisfying 1 < m < (n - 1)." + * + * OpenSSL implements all three use cases: RSA-OAEP for key transport, + * RSA signatures with PKCS#1 v1.5 or PSS padding, and KAS-IFC-SSC (KAS1/KAS2) + * using RSASVE. + * + * According to FIPS 140-3 IG 10.3.A, if at the time when the PCT is performed + * the keys' intended usage is not known, then any of the three PCTs described + * in AS10.35 shall be performed on this key pair. + * + * Because of this allowance from the IG, the simplest option is 3, i.e. + * RSA_public_encrypt() and RSA_private_decrypt() with RSA_NO_PADDING. */ static int rsa_keygen_pairwise_test(RSA *rsa, OSSL_CALLBACK *cb, void *cbarg) { int ret = 0; + unsigned int plaintxt_len; + unsigned char *plaintxt = NULL; unsigned int ciphertxt_len; unsigned char *ciphertxt = NULL; - const unsigned char plaintxt[16] = {0}; unsigned char *decoded = NULL; unsigned int decoded_len; - unsigned int plaintxt_len = (unsigned int)sizeof(plaintxt_len); - int padding = RSA_PKCS1_PADDING; + int padding = RSA_NO_PADDING; OSSL_SELF_TEST *st = NULL; st = OSSL_SELF_TEST_new(cb, cbarg); if (st == NULL) goto err; OSSL_SELF_TEST_onbegin(st, OSSL_SELF_TEST_TYPE_PCT, - OSSL_SELF_TEST_DESC_PCT_RSA_PKCS1); + OSSL_SELF_TEST_DESC_PCT_RSA); - ciphertxt_len = RSA_size(rsa); /* - * RSA_private_encrypt() and RSA_private_decrypt() requires the 'to' - * parameter to be a maximum of RSA_size() - allocate space for both. + * For RSA_NO_PADDING, RSA_public_encrypt() and RSA_private_decrypt() + * require the 'to' and 'from' parameters to have equal length and a + * maximum of RSA_size() - allocate space for plaintxt, ciphertxt, and + * decoded. */ - ciphertxt = OPENSSL_zalloc(ciphertxt_len * 2); - if (ciphertxt == NULL) + plaintxt_len = RSA_size(rsa); + plaintxt = OPENSSL_zalloc(plaintxt_len * 3); + if (plaintxt == NULL) goto err; - decoded = ciphertxt + ciphertxt_len; + ciphertxt = plaintxt + plaintxt_len; + decoded = ciphertxt + plaintxt_len; + + /* SP 800-56Br2 Section 6.4.1.1 requires that plaintext is greater than 1 */ + plaintxt[plaintxt_len - 1] = 2; ciphertxt_len = RSA_public_encrypt(plaintxt_len, plaintxt, ciphertxt, rsa, padding); if (ciphertxt_len <= 0) goto err; - if (ciphertxt_len == plaintxt_len - && memcmp(ciphertxt, plaintxt, plaintxt_len) == 0) - goto err; OSSL_SELF_TEST_oncorrupt_byte(st, ciphertxt); @@ -703,7 +725,7 @@ static int rsa_keygen_pairwise_test(RSA *rsa, OSSL_CALLBACK *cb, void *cbarg) err: OSSL_SELF_TEST_onend(st, ret); OSSL_SELF_TEST_free(st); - OPENSSL_free(ciphertxt); + OPENSSL_free(plaintxt); return ret; } diff --git a/crypto/rsa/rsa_lib.c b/crypto/rsa/rsa_lib.c index 5350a4e659..071c6245f6 100644 --- a/crypto/rsa/rsa_lib.c +++ b/crypto/rsa/rsa_lib.c @@ -159,8 +159,13 @@ void RSA_free(RSA *r) CRYPTO_THREAD_lock_free(r->lock); CRYPTO_FREE_REF(&r->references); +#ifdef FIPS_MODULE + BN_clear_free(r->n); + BN_clear_free(r->e); +#else BN_free(r->n); BN_free(r->e); +#endif BN_clear_free(r->d); BN_clear_free(r->p); BN_clear_free(r->q); @@ -901,6 +906,56 @@ int ossl_rsa_get0_all_params(RSA *r, STACK_OF(BIGNUM_const) *primes, return 1; } +#define safe_BN_num_bits(_k_) (((_k_) == NULL) ? 0 : BN_num_bits((_k_))) +int ossl_rsa_check_factors(RSA *r) +{ + int valid = 0; + int n, i, bits; + STACK_OF(BIGNUM_const) *factors = sk_BIGNUM_const_new_null(); + STACK_OF(BIGNUM_const) *exps = sk_BIGNUM_const_new_null(); + STACK_OF(BIGNUM_const) *coeffs = sk_BIGNUM_const_new_null(); + + if (factors == NULL || exps == NULL || coeffs == NULL) + goto done; + + /* + * Simple sanity check for RSA key. All RSA key parameters + * must be less-than/equal-to RSA parameter n. + */ + ossl_rsa_get0_all_params(r, factors, exps, coeffs); + n = safe_BN_num_bits(RSA_get0_n(r)); + + if (safe_BN_num_bits(RSA_get0_d(r)) > n) + goto done; + + for (i = 0; i < sk_BIGNUM_const_num(exps); i++) { + bits = safe_BN_num_bits(sk_BIGNUM_const_value(exps, i)); + if (bits > n) + goto done; + } + + for (i = 0; i < sk_BIGNUM_const_num(factors); i++) { + bits = safe_BN_num_bits(sk_BIGNUM_const_value(factors, i)); + if (bits > n) + goto done; + } + + for (i = 0; i < sk_BIGNUM_const_num(coeffs); i++) { + bits = safe_BN_num_bits(sk_BIGNUM_const_value(coeffs, i)); + if (bits > n) + goto done; + } + + valid = 1; + +done: + sk_BIGNUM_const_free(factors); + sk_BIGNUM_const_free(exps); + sk_BIGNUM_const_free(coeffs); + + return valid; +} + #ifndef FIPS_MODULE /* Helpers to set or get diverse hash algorithm names */ static int int_set_rsa_md_name(EVP_PKEY_CTX *ctx, diff --git a/crypto/rsa/rsa_mp.c b/crypto/rsa/rsa_mp.c index cb2fb7d1e8..542daecc1f 100644 --- a/crypto/rsa/rsa_mp.c +++ b/crypto/rsa/rsa_mp.c @@ -1,5 +1,5 @@ /* - * Copyright 2017-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2017 BaishanCloud. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -97,7 +97,7 @@ int ossl_rsa_multip_calc_product(RSA *rsa) int ossl_rsa_multip_cap(int bits) { - int cap = 5; + int cap = RSA_MAX_PRIME_NUM; if (bits < 1024) cap = 2; diff --git a/crypto/rsa/rsa_oaep.c b/crypto/rsa/rsa_oaep.c index 4b5943b6bb..5a1c080fcd 100644 --- a/crypto/rsa/rsa_oaep.c +++ b/crypto/rsa/rsa_oaep.c @@ -76,6 +76,18 @@ int ossl_rsa_padding_add_PKCS1_OAEP_mgf1_ex(OSSL_LIB_CTX *libctx, if (mgf1md == NULL) mgf1md = md; +#ifdef FIPS_MODULE + /* XOF are approved as standalone; Shake256 in Ed448; MGF */ + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_RSA, RSA_R_DIGEST_NOT_ALLOWED); + return 0; + } + if (EVP_MD_xof(mgf1md)) { + ERR_raise(ERR_LIB_RSA, RSA_R_MGF1_DIGEST_NOT_ALLOWED); + return 0; + } +#endif + mdlen = EVP_MD_get_size(md); if (mdlen <= 0) { ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_LENGTH); @@ -182,6 +194,18 @@ int RSA_padding_check_PKCS1_OAEP_mgf1(unsigned char *to, int tlen, if (mgf1md == NULL) mgf1md = md; +#ifdef FIPS_MODULE + /* XOF are approved as standalone; Shake256 in Ed448; MGF */ + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_RSA, RSA_R_DIGEST_NOT_ALLOWED); + return -1; + } + if (EVP_MD_xof(mgf1md)) { + ERR_raise(ERR_LIB_RSA, RSA_R_MGF1_DIGEST_NOT_ALLOWED); + return -1; + } +#endif + mdlen = EVP_MD_get_size(md); if (tlen <= 0 || flen <= 0 || mdlen <= 0) @@ -336,7 +360,7 @@ int PKCS1_MGF1(unsigned char *mask, long len, if (c == NULL) goto err; mdlen = EVP_MD_get_size(dgst); - if (mdlen < 0) + if (mdlen <= 0) goto err; /* step 4 */ for (i = 0; outlen < len; i++) { diff --git a/crypto/rsa/rsa_ossl.c b/crypto/rsa/rsa_ossl.c index 14dfd457f9..0c0c73c65c 100644 --- a/crypto/rsa/rsa_ossl.c +++ b/crypto/rsa/rsa_ossl.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -155,10 +155,35 @@ static int rsa_ossl_public_encrypt(int flen, const unsigned char *from, if (BN_bin2bn(buf, num, f) == NULL) goto err; - if (BN_ucmp(f, rsa->n) >= 0) { - /* usually the padding functions would catch this */ - ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); - goto err; +#ifdef FIPS_MODULE + /* + * See SP800-56Br2, section 7.1.1.1 + * RSAEP: 1 < f < (n – 1). + * (where f is the plaintext). + */ + if (padding == RSA_NO_PADDING) { + BIGNUM *nminus1 = BN_CTX_get(ctx); + + if (BN_ucmp(f, BN_value_one()) <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_SMALL); + goto err; + } + if (nminus1 == NULL + || BN_copy(nminus1, rsa->n) == NULL + || !BN_sub_word(nminus1, 1)) + goto err; + if (BN_ucmp(f, nminus1) >= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); + goto err; + } + } else +#endif + { + if (BN_ucmp(f, rsa->n) >= 0) { + /* usually the padding functions would catch this */ + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); + goto err; + } } if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) @@ -546,11 +571,35 @@ static int rsa_ossl_private_decrypt(int flen, const unsigned char *from, if (BN_bin2bn(from, (int)flen, f) == NULL) goto err; - if (BN_ucmp(f, rsa->n) >= 0) { - ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); - goto err; - } +#ifdef FIPS_MODULE + /* + * See SP800-56Br2, section 7.1.2.1 + * RSADP: 1 < f < (n – 1) + * (where f is the ciphertext). + */ + if (padding == RSA_NO_PADDING) { + BIGNUM *nminus1 = BN_CTX_get(ctx); + if (BN_ucmp(f, BN_value_one()) <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_SMALL); + goto err; + } + if (nminus1 == NULL + || BN_copy(nminus1, rsa->n) == NULL + || !BN_sub_word(nminus1, 1)) + goto err; + if (BN_ucmp(f, nminus1) >= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); + goto err; + } + } else +#endif + { + if (BN_ucmp(f, rsa->n) >= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_DATA_TOO_LARGE_FOR_MODULUS); + goto err; + } + } if (rsa->flags & RSA_FLAG_CACHE_PUBLIC) if (!BN_MONT_CTX_set_locked(&rsa->_method_mod_n, rsa->lock, rsa->n, ctx)) @@ -720,6 +769,7 @@ static int rsa_ossl_public_decrypt(int flen, const unsigned char *from, rsa->_method_mod_n)) goto err; + /* For X9.31: Assuming e is odd it does a 12 mod 16 test */ if ((padding == RSA_X931_PADDING) && ((bn_get_words(ret)[0] & 0xf) != 12)) if (!BN_sub(ret, rsa->n, ret)) goto err; diff --git a/crypto/rsa/rsa_pmeth.c b/crypto/rsa/rsa_pmeth.c index fc3391ead2..8f89f748e7 100644 --- a/crypto/rsa/rsa_pmeth.c +++ b/crypto/rsa/rsa_pmeth.c @@ -1,5 +1,5 @@ /* - * Copyright 2006-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -144,9 +144,16 @@ static int pkey_rsa_sign(EVP_PKEY_CTX *ctx, unsigned char *sig, * be reflected back in the "original" key. */ RSA *rsa = (RSA *)EVP_PKEY_get0_RSA(ctx->pkey); + int md_size; if (rctx->md) { - if (tbslen != (size_t)EVP_MD_get_size(rctx->md)) { + md_size = EVP_MD_get_size(rctx->md); + if (md_size <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); + return -1; + } + + if (tbslen != (size_t)md_size) { ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); return -1; } @@ -266,12 +273,18 @@ static int pkey_rsa_verify(EVP_PKEY_CTX *ctx, */ RSA *rsa = (RSA *)EVP_PKEY_get0_RSA(ctx->pkey); size_t rslen; + int md_size; if (rctx->md) { if (rctx->pad_mode == RSA_PKCS1_PADDING) return RSA_verify(EVP_MD_get_type(rctx->md), tbs, tbslen, sig, siglen, rsa); - if (tbslen != (size_t)EVP_MD_get_size(rctx->md)) { + md_size = EVP_MD_get_size(rctx->md); + if (md_size <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); + return -1; + } + if (tbslen != (size_t)md_size) { ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); return -1; } @@ -436,6 +449,7 @@ static int check_padding_md(const EVP_MD *md, int padding) static int pkey_rsa_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2) { RSA_PKEY_CTX *rctx = ctx->data; + int md_size; switch (type) { case EVP_PKEY_CTRL_RSA_PADDING: @@ -485,8 +499,13 @@ static int pkey_rsa_ctrl(EVP_PKEY_CTX *ctx, int type, int p1, void *p2) ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_PSS_SALTLEN); return -2; } + md_size = EVP_MD_get_size(rctx->md); + if (md_size <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); + return -2; + } if ((p1 == RSA_PSS_SALTLEN_DIGEST - && rctx->min_saltlen > EVP_MD_get_size(rctx->md)) + && rctx->min_saltlen > md_size) || (p1 >= 0 && p1 < rctx->min_saltlen)) { ERR_raise(ERR_LIB_RSA, RSA_R_PSS_SALTLEN_TOO_SMALL); return 0; @@ -850,7 +869,7 @@ static int pkey_pss_init(EVP_PKEY_CTX *ctx) RSA_PKEY_CTX *rctx = ctx->data; const EVP_MD *md; const EVP_MD *mgf1md; - int min_saltlen, max_saltlen; + int min_saltlen, max_saltlen, md_size; /* Should never happen */ if (!pkey_ctx_is_pss(ctx)) @@ -864,7 +883,12 @@ static int pkey_pss_init(EVP_PKEY_CTX *ctx) return 0; /* See if minimum salt length exceeds maximum possible */ - max_saltlen = RSA_size(rsa) - EVP_MD_get_size(md); + md_size = EVP_MD_get_size(md); + if (md_size <= 0) { + ERR_raise(ERR_LIB_RSA, RSA_R_INVALID_DIGEST_LENGTH); + return 0; + } + max_saltlen = RSA_size(rsa) - md_size; if ((RSA_bits(rsa) & 0x7) == 1) max_saltlen--; if (min_saltlen > max_saltlen) { diff --git a/crypto/rsa/rsa_pss.c b/crypto/rsa/rsa_pss.c index 089730bbae..a2bc198a89 100644 --- a/crypto/rsa/rsa_pss.c +++ b/crypto/rsa/rsa_pss.c @@ -1,5 +1,5 @@ /* - * Copyright 2005-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -38,9 +38,17 @@ int RSA_verify_PKCS1_PSS(RSA *rsa, const unsigned char *mHash, int RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, const EVP_MD *Hash, const EVP_MD *mgf1Hash, const unsigned char *EM, int sLen) +{ + return ossl_rsa_verify_PKCS1_PSS_mgf1(rsa, mHash, Hash, mgf1Hash, EM, &sLen); +} + +int ossl_rsa_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, + const EVP_MD *Hash, const EVP_MD *mgf1Hash, + const unsigned char *EM, int *sLenOut) { int i; int ret = 0; + int sLen = *sLenOut; int hLen, maskedDBLen, MSBits, emLen; const unsigned char *H; unsigned char *DB = NULL; @@ -54,7 +62,7 @@ int RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, mgf1Hash = Hash; hLen = EVP_MD_get_size(Hash); - if (hLen < 0) + if (hLen <= 0) goto err; /*- * Negative sLen has special meanings: @@ -118,13 +126,15 @@ int RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, "expected: %d retrieved: %d", sLen, maskedDBLen - i); goto err; + } else { + sLen = maskedDBLen - i; } if (!EVP_DigestInit_ex(ctx, Hash, NULL) || !EVP_DigestUpdate(ctx, zeroes, sizeof(zeroes)) || !EVP_DigestUpdate(ctx, mHash, hLen)) goto err; - if (maskedDBLen - i) { - if (!EVP_DigestUpdate(ctx, DB + i, maskedDBLen - i)) + if (sLen != 0) { + if (!EVP_DigestUpdate(ctx, DB + i, sLen)) goto err; } if (!EVP_DigestFinal_ex(ctx, H_, NULL)) @@ -136,6 +146,7 @@ int RSA_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, ret = 1; } + *sLenOut = sLen; err: OPENSSL_free(DB); EVP_MD_CTX_free(ctx); @@ -155,9 +166,18 @@ int RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, const unsigned char *mHash, const EVP_MD *Hash, const EVP_MD *mgf1Hash, int sLen) +{ + return ossl_rsa_padding_add_PKCS1_PSS_mgf1(rsa, EM, mHash, Hash, mgf1Hash, &sLen); +} + +int ossl_rsa_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, + const unsigned char *mHash, + const EVP_MD *Hash, const EVP_MD *mgf1Hash, + int *sLenOut) { int i; int ret = 0; + int sLen = *sLenOut; int hLen, maskedDBLen, MSBits, emLen; unsigned char *H, *salt = NULL, *p; EVP_MD_CTX *ctx = NULL; @@ -167,7 +187,7 @@ int RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, mgf1Hash = Hash; hLen = EVP_MD_get_size(Hash); - if (hLen < 0) + if (hLen <= 0) goto err; /*- * Negative sLen has special meanings: @@ -187,7 +207,7 @@ int RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, if (sLen == RSA_PSS_SALTLEN_DIGEST) { sLen = hLen; } else if (sLen == RSA_PSS_SALTLEN_MAX_SIGN - || sLen == RSA_PSS_SALTLEN_AUTO) { + || sLen == RSA_PSS_SALTLEN_AUTO) { sLen = RSA_PSS_SALTLEN_MAX; } else if (sLen == RSA_PSS_SALTLEN_AUTO_DIGEST_MAX) { sLen = RSA_PSS_SALTLEN_MAX; @@ -261,6 +281,7 @@ int RSA_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, ret = 1; + *sLenOut = sLen; err: EVP_MD_CTX_free(ctx); OPENSSL_clear_free(salt, (size_t)sLen); /* salt != NULL implies sLen > 0 */ diff --git a/crypto/rsa/rsa_schemes.c b/crypto/rsa/rsa_schemes.c index 98ab13956d..435f44e016 100644 --- a/crypto/rsa/rsa_schemes.c +++ b/crypto/rsa/rsa_schemes.c @@ -1,5 +1,5 @@ /* - * Copyright 2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -38,7 +38,7 @@ static const char *nid2name(int meth, const OSSL_ITEM *items, size_t items_n) } /* - * The list of permitted hash functions are taken from + * The list of permitted hash functions are taken from * https://tools.ietf.org/html/rfc8017#appendix-A.2.1: * * OAEP-PSSDigestAlgorithms ALGORITHM-IDENTIFIER ::= { diff --git a/crypto/rsa/rsa_sign.c b/crypto/rsa/rsa_sign.c index b14b134080..78e4bad69e 100644 --- a/crypto/rsa/rsa_sign.c +++ b/crypto/rsa/rsa_sign.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -34,6 +34,9 @@ # ifndef OPENSSL_NO_RMD160 # include /* uses RIPEMD160_DIGEST_LENGTH */ # endif +# ifndef OPENSSL_NO_SM3 +# include "internal/sm3.h" /* uses SM3_DIGEST_LENGTH */ +# endif #endif #include /* uses SHA???_DIGEST_LENGTH */ #include "crypto/rsa.h" @@ -123,6 +126,16 @@ static const unsigned char digestinfo_ripemd160_der[] = { ASN1_OCTET_STRING, RIPEMD160_DIGEST_LENGTH }; # endif +# ifndef OPENSSL_NO_SM3 +/* SM3 (1 2 156 10197 1 401) */ +static const unsigned char digestinfo_sm3_der[] = { + ASN1_SEQUENCE, 0x0f + SM3_DIGEST_LENGTH, + ASN1_SEQUENCE, 0x0c, + ASN1_OID, 0x08, 1 * 40 + 2, 0x81, 0x1c, 0xcf, 0x55, 1, 0x83, 0x78, + ASN1_NULL, 0x00, + ASN1_OCTET_STRING, SM3_DIGEST_LENGTH +}; +# endif #endif /* FIPS_MODULE */ /* SHA-1 (1 3 14 3 2 26) */ @@ -169,6 +182,9 @@ const unsigned char *ossl_rsa_digestinfo_encoding(int md_nid, size_t *len) # ifndef OPENSSL_NO_RMD160 MD_CASE(ripemd160) # endif +# ifndef OPENSSL_NO_SM3 + MD_CASE(sm3) +# endif #endif /* FIPS_MODULE */ MD_CASE(sha1) MD_CASE(sha224) diff --git a/crypto/rsa/rsa_sp800_56b_gen.c b/crypto/rsa/rsa_sp800_56b_gen.c index b0d9104b79..c741cf3c3b 100644 --- a/crypto/rsa/rsa_sp800_56b_gen.c +++ b/crypto/rsa/rsa_sp800_56b_gen.c @@ -147,11 +147,15 @@ int ossl_rsa_fips186_4_gen_prob_primes(RSA *rsa, RSA_ACVP_TEST *test, ret = 1; err: /* Zeroize any internally generated values that are not returned */ - if (Xpo != NULL) - BN_clear(Xpo); - if (Xqo != NULL) - BN_clear(Xqo); + BN_clear(Xpo); + BN_clear(Xqo); BN_clear(tmp); + if (ret != 1) { + BN_clear_free(rsa->p); + rsa->p = NULL; + BN_clear_free(rsa->q); + rsa->q = NULL; + } BN_CTX_end(ctx); return ret; diff --git a/crypto/rsa/rsa_x931.c b/crypto/rsa/rsa_x931.c index 9d331ab9a7..f84ea9815c 100644 --- a/crypto/rsa/rsa_x931.c +++ b/crypto/rsa/rsa_x931.c @@ -1,5 +1,5 @@ /* - * Copyright 2005-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -19,6 +19,27 @@ #include #include +/* + * X9.31 Embeds the hash inside the following data structure + * + * header (4 bits = 0x6) + * padding (consisting of zero or more 4 bit values of a sequence of 0xB, + * ending with the terminator 0xA) + * hash(Msg) hash of a message (the output size is related to the hash function) + * trailer (consists of 2 bytes) + * The 1st byte is related to a part number for a hash algorithm + * (See RSA_X931_hash_id()), followed by the fixed value 0xCC + * + * The RSA modulus size n (which for X9.31 is 1024 + 256*s) is the size of the data + * structure, which determines the padding size. + * i.e. len(padding) = n - len(header) - len(hash) - len(trailer) + * + * Params: + * to The output buffer to write the data structure to. + * tolen The size of 'to' in bytes (it is the size of the n) + * from The input hash followed by the 1st byte of the trailer. + * flen The size of the input hash + 1 (trailer byte) + */ int RSA_padding_add_X931(unsigned char *to, int tlen, const unsigned char *from, int flen) { @@ -26,10 +47,9 @@ int RSA_padding_add_X931(unsigned char *to, int tlen, unsigned char *p; /* - * Absolute minimum amount of padding is 1 header nibble, 1 padding - * nibble and 2 trailer bytes: but 1 hash if is already in 'from'. + * We need at least 1 byte for header + padding (0x6A) + * And 2 trailer bytes (but we subtract 1 since flen includes 1 trailer byte) */ - j = tlen - flen - 2; if (j < 0) { @@ -101,7 +121,12 @@ int RSA_padding_check_X931(unsigned char *to, int tlen, return j; } -/* Translate between X931 hash ids and NIDs */ +/* + * Translate between X9.31 hash ids and NIDs + * The returned values relate to ISO/IEC 10118 part numbers which consist of + * a hash algorithm and hash number. The returned values are used as the + * first byte of the 'trailer'. + */ int RSA_X931_hash_id(int nid) { diff --git a/crypto/s390x_arch.h b/crypto/s390x_arch.h index fdc682af06..2bb82347ff 100644 --- a/crypto/s390x_arch.h +++ b/crypto/s390x_arch.h @@ -1,5 +1,5 @@ /* - * Copyright 2017-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -115,6 +115,7 @@ extern int OPENSSL_s390xcex; # define S390X_MSA5 57 /* message-security-assist-ext. 5 */ # define S390X_MSA3 76 /* message-security-assist-ext. 3 */ # define S390X_MSA4 77 /* message-security-assist-ext. 4 */ +# define S390X_MSA12 86 /* message-security-assist-ext. 12 */ # define S390X_VX 129 /* vector */ # define S390X_VXD 134 /* vector packed decimal */ # define S390X_VXE 135 /* vector enhancements 1 */ @@ -150,6 +151,14 @@ extern int OPENSSL_s390xcex; /* km */ # define S390X_XTS_AES_128 50 # define S390X_XTS_AES_256 52 +# define S390X_XTS_AES_128_MSA10 82 +# define S390X_XTS_AES_256_MSA10 84 + +/* kmac */ +# define S390X_HMAC_SHA_224 112 +# define S390X_HMAC_SHA_256 113 +# define S390X_HMAC_SHA_384 114 +# define S390X_HMAC_SHA_512 115 /* prno */ # define S390X_SHA_512_DRNG 3 @@ -182,6 +191,12 @@ extern int OPENSSL_s390xcex; # define S390X_KMA_LAAD 0x200 # define S390X_KMA_HS 0x400 # define S390X_KDSA_D 0x80 +# define S390X_KIMD_NIP 0x8000 +# define S390X_KLMD_DUFOP 0x4000 +# define S390X_KLMD_NIP 0x8000 # define S390X_KLMD_PS 0x100 +# define S390X_KMAC_IKP 0x8000 +# define S390X_KMAC_IIMP 0x4000 +# define S390X_KMAC_CCUP 0x2000 #endif diff --git a/crypto/s390xcpuid.pl b/crypto/s390xcpuid.pl index 560a2f09e9..bb2f68810d 100755 --- a/crypto/s390xcpuid.pl +++ b/crypto/s390xcpuid.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2009-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2009-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -308,7 +308,7 @@ llgfr %r0,$fc lgr %r1,$param - .long 0xb93e0002 # kimd %r0,%r2 + .long 0xb93e8002 # kimd %r0,%r2[,M3] brc 1,.-4 # pay attention to "partial completion" br $ra @@ -329,7 +329,7 @@ llgfr %r0,$fc l${g} %r1,$stdframe($sp) - .long 0xb93f0042 # klmd %r4,%r2 + .long 0xb93f8042 # klmd %r4,%r2[,M3] brc 1,.-4 # pay attention to "partial completion" br $ra diff --git a/crypto/self_test_core.c b/crypto/self_test_core.c index f31fce57c8..1496a37b80 100644 --- a/crypto/self_test_core.c +++ b/crypto/self_test_core.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,14 +13,12 @@ #include "internal/cryptlib.h" #include "crypto/context.h" -typedef struct self_test_cb_st -{ +typedef struct self_test_cb_st { OSSL_CALLBACK *cb; void *cbarg; } SELF_TEST_CB; -struct ossl_self_test_st -{ +struct ossl_self_test_st { /* local state variables */ const char *phase; const char *type; diff --git a/crypto/sha/asm/keccak1600-x86_64.S b/crypto/sha/asm/keccak1600-x86_64.S index c8854544eb..021d34601f 100644 --- a/crypto/sha/asm/keccak1600-x86_64.S +++ b/crypto/sha/asm/keccak1600-x86_64.S @@ -494,6 +494,7 @@ SHA3_squeeze: .byte 0xf3,0xc3 .cfi_endproc .size SHA3_squeeze,.-SHA3_squeeze +.section .rodata .align 256 .quad 0,0,0,0,0,0,0,0 .type iotas,@object diff --git a/crypto/sha/asm/keccak1600-x86_64.pl b/crypto/sha/asm/keccak1600-x86_64.pl index 78aa5c64af..3dbf17731e 100755 --- a/crypto/sha/asm/keccak1600-x86_64.pl +++ b/crypto/sha/asm/keccak1600-x86_64.pl @@ -1,5 +1,5 @@ #!/usr/bin/env perl -# Copyright 2017-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -567,6 +567,7 @@ ___ } $code.=<<___; +.section .rodata align=256 .align 256 .quad 0,0,0,0,0,0,0,0 .type iotas,\@object diff --git a/crypto/sha/asm/sha1-mb-x86_64.S b/crypto/sha/asm/sha1-mb-x86_64.S index b835e0b6c9..012a5094ac 100644 --- a/crypto/sha/asm/sha1-mb-x86_64.S +++ b/crypto/sha/asm/sha1-mb-x86_64.S @@ -7286,7 +7286,7 @@ _avx2_shortcut: .byte 0xf3,0xc3 .cfi_endproc .size sha1_multi_block_avx2,.-sha1_multi_block_avx2 - +.section .rodata .align 256 .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 @@ -7301,6 +7301,7 @@ K_XX_XX: .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f .byte 0xf,0xe,0xd,0xc,0xb,0xa,0x9,0x8,0x7,0x6,0x5,0x4,0x3,0x2,0x1,0x0 .byte 83,72,65,49,32,109,117,108,116,105,45,98,108,111,99,107,32,116,114,97,110,115,102,111,114,109,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/sha/asm/sha1-mb-x86_64.pl b/crypto/sha/asm/sha1-mb-x86_64.pl index 67faba136d..d9d1630d16 100644 --- a/crypto/sha/asm/sha1-mb-x86_64.pl +++ b/crypto/sha/asm/sha1-mb-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -1374,7 +1374,7 @@ sub BODY_40_59_avx { ___ } }}} $code.=<<___; - +.section .rodata align=256 .align 256 .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 # K_00_19 .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 # K_00_19 @@ -1389,6 +1389,7 @@ sub BODY_40_59_avx { .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f # pbswap .byte 0xf,0xe,0xd,0xc,0xb,0xa,0x9,0x8,0x7,0x6,0x5,0x4,0x3,0x2,0x1,0x0 .asciz "SHA1 multi-block transform for x86_64, CRYPTOGAMS by " +.previous ___ if ($win64) { diff --git a/crypto/sha/asm/sha1-x86_64.S b/crypto/sha/asm/sha1-x86_64.S index 85e9a2909f..234e625cfe 100644 --- a/crypto/sha/asm/sha1-x86_64.S +++ b/crypto/sha/asm/sha1-x86_64.S @@ -5433,6 +5433,7 @@ _avx2_shortcut: .byte 0xf3,0xc3 .cfi_endproc .size sha1_block_data_order_avx2,.-sha1_block_data_order_avx2 +.section .rodata .align 64 K_XX_XX: .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 @@ -5446,6 +5447,7 @@ K_XX_XX: .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f .byte 0xf,0xe,0xd,0xc,0xb,0xa,0x9,0x8,0x7,0x6,0x5,0x4,0x3,0x2,0x1,0x0 +.previous .byte 83,72,65,49,32,98,108,111,99,107,32,116,114,97,110,115,102,111,114,109,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 .align 64 .section ".note.gnu.property", "a" diff --git a/crypto/sha/asm/sha1-x86_64.pl b/crypto/sha/asm/sha1-x86_64.pl index c66b8fca87..30c545cf41 100755 --- a/crypto/sha/asm/sha1-x86_64.pl +++ b/crypto/sha/asm/sha1-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2006-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -1832,6 +1832,7 @@ () } } $code.=<<___; +.section .rodata align=64 .align 64 K_XX_XX: .long 0x5a827999,0x5a827999,0x5a827999,0x5a827999 # K_00_19 @@ -1845,6 +1846,7 @@ () .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f # pbswap mask .long 0x00010203,0x04050607,0x08090a0b,0x0c0d0e0f # pbswap mask .byte 0xf,0xe,0xd,0xc,0xb,0xa,0x9,0x8,0x7,0x6,0x5,0x4,0x3,0x2,0x1,0x0 +.previous ___ }}} $code.=<<___; diff --git a/crypto/sha/asm/sha256-mb-x86_64.S b/crypto/sha/asm/sha256-mb-x86_64.S index 8ac342f9ce..aabed290b1 100644 --- a/crypto/sha/asm/sha256-mb-x86_64.S +++ b/crypto/sha/asm/sha256-mb-x86_64.S @@ -7831,6 +7831,7 @@ _avx2_shortcut: .byte 0xf3,0xc3 .cfi_endproc .size sha256_multi_block_avx2,.-sha256_multi_block_avx2 +.section .rodata .align 256 K256: .long 1116352408,1116352408,1116352408,1116352408 @@ -7982,6 +7983,7 @@ K256_shaext: .long 0x748f82ee,0x78a5636f,0x84c87814,0x8cc70208 .long 0x90befffa,0xa4506ceb,0xbef9a3f7,0xc67178f2 .byte 83,72,65,50,53,54,32,109,117,108,116,105,45,98,108,111,99,107,32,116,114,97,110,115,102,111,114,109,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .section ".note.gnu.property", "a" .p2align 3 .long 1f - 0f diff --git a/crypto/sha/asm/sha256-mb-x86_64.pl b/crypto/sha/asm/sha256-mb-x86_64.pl index fa2ca86046..9398b7954a 100644 --- a/crypto/sha/asm/sha256-mb-x86_64.pl +++ b/crypto/sha/asm/sha256-mb-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2013-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2013-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -1340,6 +1340,7 @@ sub ROUND_16_XX_avx { ___ } }}} $code.=<<___; +.section .rodata align=256 .align 256 K256: ___ @@ -1389,6 +1390,7 @@ sub TABLE { .long 0x748f82ee,0x78a5636f,0x84c87814,0x8cc70208 .long 0x90befffa,0xa4506ceb,0xbef9a3f7,0xc67178f2 .asciz "SHA256 multi-block transform for x86_64, CRYPTOGAMS by " +.previous ___ if ($win64) { diff --git a/crypto/sha/asm/sha256-x86_64.S b/crypto/sha/asm/sha256-x86_64.S index e82bbec164..cb42c58633 100644 --- a/crypto/sha/asm/sha256-x86_64.S +++ b/crypto/sha/asm/sha256-x86_64.S @@ -1728,6 +1728,7 @@ sha256_block_data_order: .byte 0xf3,0xc3 .cfi_endproc .size sha256_block_data_order,.-sha256_block_data_order +.section .rodata .align 64 .type K256,@object K256: @@ -1771,6 +1772,7 @@ K256: .long 0xffffffff,0xffffffff,0x03020100,0x0b0a0908 .long 0xffffffff,0xffffffff,0x03020100,0x0b0a0908 .byte 83,72,65,50,53,54,32,98,108,111,99,107,32,116,114,97,110,115,102,111,114,109,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .type sha256_block_data_order_shaext,@function .align 64 sha256_block_data_order_shaext: diff --git a/crypto/sha/asm/sha512-x86_64.S b/crypto/sha/asm/sha512-x86_64.S index a76d017ba7..880b3fdbac 100644 --- a/crypto/sha/asm/sha512-x86_64.S +++ b/crypto/sha/asm/sha512-x86_64.S @@ -1726,6 +1726,7 @@ sha512_block_data_order: .byte 0xf3,0xc3 .cfi_endproc .size sha512_block_data_order,.-sha512_block_data_order +.section .rodata .align 64 .type K512,@object K512: @@ -1813,6 +1814,7 @@ K512: .quad 0x0001020304050607,0x08090a0b0c0d0e0f .quad 0x0001020304050607,0x08090a0b0c0d0e0f .byte 83,72,65,53,49,50,32,98,108,111,99,107,32,116,114,97,110,115,102,111,114,109,32,102,111,114,32,120,56,54,95,54,52,44,32,67,82,89,80,84,79,71,65,77,83,32,98,121,32,60,97,112,112,114,111,64,111,112,101,110,115,115,108,46,111,114,103,62,0 +.previous .type sha512_block_data_order_xop,@function .align 64 sha512_block_data_order_xop: diff --git a/crypto/sha/asm/sha512-x86_64.pl b/crypto/sha/asm/sha512-x86_64.pl index 1bd0256954..b37058ae03 100755 --- a/crypto/sha/asm/sha512-x86_64.pl +++ b/crypto/sha/asm/sha512-x86_64.pl @@ -1,5 +1,5 @@ #! /usr/bin/env perl -# Copyright 2005-2020 The OpenSSL Project Authors. All Rights Reserved. +# Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. # # Licensed under the Apache License 2.0 (the "License"). You may not use # this file except in compliance with the License. You can obtain a copy @@ -418,6 +418,7 @@ () if ($SZ==4) { $code.=<<___; +.section .rodata align=64 .align 64 .type $TABLE,\@object $TABLE: @@ -461,9 +462,11 @@ () .long 0xffffffff,0xffffffff,0x03020100,0x0b0a0908 .long 0xffffffff,0xffffffff,0x03020100,0x0b0a0908 .asciz "SHA256 block transform for x86_64, CRYPTOGAMS by " +.previous ___ } else { $code.=<<___; +.section .rodata align=64 .align 64 .type $TABLE,\@object $TABLE: @@ -551,6 +554,7 @@ () .quad 0x0001020304050607,0x08090a0b0c0d0e0f .quad 0x0001020304050607,0x08090a0b0c0d0e0f .asciz "SHA512 block transform for x86_64, CRYPTOGAMS by " +.previous ___ } diff --git a/crypto/sha/keccak1600.c b/crypto/sha/keccak1600.c index 6682367be1..5d6abeb463 100644 --- a/crypto/sha/keccak1600.c +++ b/crypto/sha/keccak1600.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -11,6 +11,8 @@ #include #include +#include "internal/nelem.h" + size_t SHA3_absorb(uint64_t A[5][5], const unsigned char *inp, size_t len, size_t r); void SHA3_squeeze(uint64_t A[5][5], unsigned char *out, size_t len, size_t r, int next); @@ -231,7 +233,7 @@ static void Chi(uint64_t A[5][5]) static void Iota(uint64_t A[5][5], size_t i) { - assert(i < (sizeof(iotas) / sizeof(iotas[0]))); + assert(i < OSSL_NELEM(iotas)); A[0][0] ^= iotas[i]; } @@ -264,7 +266,7 @@ static void Round(uint64_t A[5][5], size_t i) uint64_t C[5], E[2]; /* registers */ uint64_t D[5], T[2][5]; /* memory */ - assert(i < (sizeof(iotas) / sizeof(iotas[0]))); + assert(i < OSSL_NELEM(iotas)); C[0] = A[0][0] ^ A[1][0] ^ A[2][0] ^ A[3][0] ^ A[4][0]; C[1] = A[0][1] ^ A[1][1] ^ A[2][1] ^ A[3][1] ^ A[4][1]; @@ -391,7 +393,7 @@ static void Round(uint64_t A[5][5], size_t i) { uint64_t C[5], D[5]; - assert(i < (sizeof(iotas) / sizeof(iotas[0]))); + assert(i < OSSL_NELEM(iotas)); C[0] = A[0][0] ^ A[1][0] ^ A[2][0] ^ A[3][0] ^ A[4][0]; C[1] = A[0][1] ^ A[1][1] ^ A[2][1] ^ A[3][1] ^ A[4][1]; @@ -536,7 +538,7 @@ static void Round(uint64_t R[5][5], uint64_t A[5][5], size_t i) { uint64_t C[5], D[5]; - assert(i < (sizeof(iotas) / sizeof(iotas[0]))); + assert(i < OSSL_NELEM(iotas)); C[0] = A[0][0] ^ A[1][0] ^ A[2][0] ^ A[3][0] ^ A[4][0]; C[1] = A[0][1] ^ A[1][1] ^ A[2][1] ^ A[3][1] ^ A[4][1]; @@ -694,7 +696,7 @@ static void FourRounds(uint64_t A[5][5], size_t i) { uint64_t B[5], C[5], D[5]; - assert(i <= (sizeof(iotas) / sizeof(iotas[0]) - 4)); + assert(i <= OSSL_NELEM(iotas) - 4); /* Round 4*n */ C[0] = A[0][0] ^ A[1][0] ^ A[2][0] ^ A[3][0] ^ A[4][0]; diff --git a/crypto/sha/sha256.c b/crypto/sha/sha256.c index 6ef218e86e..6a19657bf8 100644 --- a/crypto/sha/sha256.c +++ b/crypto/sha/sha256.c @@ -1,5 +1,5 @@ /* - * Copyright 2004-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2004-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -88,27 +88,31 @@ int SHA224_Final(unsigned char *md, SHA256_CTX *c) #define HASH_MAKE_STRING(c,s) do { \ unsigned long ll; \ unsigned int nn; \ - switch ((c)->md_len) \ - { case SHA256_192_DIGEST_LENGTH: \ - for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); } \ + switch ((c)->md_len) { \ + case SHA256_192_DIGEST_LENGTH: \ + for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); \ + } \ break; \ case SHA224_DIGEST_LENGTH: \ - for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); } \ + for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); \ + } \ break; \ case SHA256_DIGEST_LENGTH: \ - for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); } \ + for (nn=0;nnh[nn]; (void)HOST_l2c(ll,(s)); \ + } \ break; \ default: \ if ((c)->md_len > SHA256_DIGEST_LENGTH) \ return 0; \ - for (nn=0;nn<(c)->md_len/4;nn++) \ - { ll=(c)->h[nn]; (void)HOST_l2c(ll,(s)); } \ + for (nn=0;nn<(c)->md_len/4;nn++) { \ + ll=(c)->h[nn]; (void)HOST_l2c(ll,(s)); \ + } \ break; \ } \ - } while (0) + } while (0) #define HASH_UPDATE SHA256_Update #define HASH_TRANSFORM SHA256_Transform diff --git a/crypto/sha/sha3.c b/crypto/sha/sha3.c index 2411b3f1f8..951d5c8883 100644 --- a/crypto/sha/sha3.c +++ b/crypto/sha/sha3.c @@ -1,5 +1,5 @@ /* - * Copyright 2017-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -8,13 +8,19 @@ */ #include +#if defined(__s390x__) && defined(OPENSSL_CPUID_OBJ) +# include "crypto/s390x_arch.h" +#endif #include "internal/sha3.h" void SHA3_squeeze(uint64_t A[5][5], unsigned char *out, size_t len, size_t r, int next); void ossl_sha3_reset(KECCAK1600_CTX *ctx) { - memset(ctx->A, 0, sizeof(ctx->A)); +#if defined(__s390x__) && defined(OPENSSL_CPUID_OBJ) + if (!(OPENSSL_s390xcap_P.stfle[1] & S390X_CAPBIT(S390X_MSA12))) +#endif + memset(ctx->A, 0, sizeof(ctx->A)); ctx->bufsz = 0; ctx->xof_state = XOF_STATE_INIT; } @@ -34,12 +40,12 @@ int ossl_sha3_init(KECCAK1600_CTX *ctx, unsigned char pad, size_t bitlen) return 0; } -int ossl_keccak_kmac_init(KECCAK1600_CTX *ctx, unsigned char pad, size_t bitlen) +int ossl_keccak_init(KECCAK1600_CTX *ctx, unsigned char pad, size_t bitlen, size_t mdlen) { int ret = ossl_sha3_init(ctx, pad, bitlen); if (ret) - ctx->md_size *= 2; + ctx->md_size = mdlen / 8; return ret; } diff --git a/crypto/sha/sha512.c b/crypto/sha/sha512.c index bc547d7cdc..ac5e9233b9 100644 --- a/crypto/sha/sha512.c +++ b/crypto/sha/sha512.c @@ -1,5 +1,5 @@ /* - * Copyright 2004-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2004-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -18,16 +18,16 @@ /*- * IMPLEMENTATION NOTES. * - * As you might have noticed 32-bit hash algorithms: + * As you might have noticed, 32-bit hash algorithms: * * - permit SHA_LONG to be wider than 32-bit * - optimized versions implement two transform functions: one operating - * on [aligned] data in host byte order and one - on data in input + * on [aligned] data in host byte order, and one operating on data in input * stream byte order; * - share common byte-order neutral collector and padding function * implementations, crypto/md32_common.h; * - * Neither of the above applies to this SHA-512 implementations. Reasons + * Neither of the above applies to this SHA-512 implementation. Reasons * [in reverse order] are: * * - it's the only 64-bit hash algorithm for the moment of this writing, diff --git a/crypto/sleep.c b/crypto/sleep.c index 73467fb859..dbd0f78025 100644 --- a/crypto/sleep.c +++ b/crypto/sleep.c @@ -12,30 +12,59 @@ /* system-specific variants defining OSSL_sleep() */ #if defined(OPENSSL_SYS_UNIX) || defined(__DJGPP__) -#include +# if defined(OPENSSL_USE_USLEEP) \ + || defined(__DJGPP__) \ + || (defined(__TANDEM) && defined(_REENTRANT)) + +/* + * usleep() was made obsolete by POSIX.1-2008, and nanosleep() + * should be used instead. However, nanosleep() isn't implemented + * on the platforms given above, so we still use it for those. + * Also, OPENSSL_USE_USLEEP can be defined to enable the use of + * usleep, if it turns out that nanosleep() is unavailable. + */ + +# include void OSSL_sleep(uint64_t millis) { -# ifdef OPENSSL_SYS_VXWORKS - struct timespec ts; + unsigned int s = (unsigned int)(millis / 1000); + unsigned int us = (unsigned int)((millis % 1000) * 1000); + + if (s > 0) + sleep(s); + /* + * On NonStop with the PUT thread model, thread context switch is + * cooperative, with usleep() being a "natural" context switch point. + * We avoid checking us > 0 here, to allow that context switch to + * happen. + */ + usleep(us); +} - ts.tv_sec = (long int) (millis / 1000); - ts.tv_nsec = (long int) (millis % 1000) * 1000000ul; - nanosleep(&ts, NULL); # elif defined(__TANDEM) && !defined(_REENTRANT) -# include +# include +void OSSL_sleep(uint64_t millis) +{ /* HPNS does not support usleep for non threaded apps */ PROCESS_DELAY_(millis * 1000); +} + # else - unsigned int s = (unsigned int)(millis / 1000); - unsigned int us = (unsigned int)((millis % 1000) * 1000); - if (s > 0) - sleep(s); - usleep(us); -# endif +/* nanosleep is defined by POSIX.1-2001 */ +# include +void OSSL_sleep(uint64_t millis) +{ + struct timespec ts; + + ts.tv_sec = (long int) (millis / 1000); + ts.tv_nsec = (long int) (millis % 1000) * 1000000ul; + nanosleep(&ts, NULL); } + +# endif #elif defined(_WIN32) && !defined(OPENSSL_SYS_UEFI) # include diff --git a/crypto/sm2/sm2_crypt.c b/crypto/sm2/sm2_crypt.c index b7303af522..0e5017cff6 100644 --- a/crypto/sm2/sm2_crypt.c +++ b/crypto/sm2/sm2_crypt.c @@ -91,7 +91,7 @@ int ossl_sm2_ciphertext_size(const EC_KEY *key, const EVP_MD *digest, const int md_size = EVP_MD_get_size(digest); size_t sz; - if (field_size == 0 || md_size < 0) + if (field_size == 0 || md_size <= 0) return 0; /* Integer and string are simple type; set constructed = 0, means primitive and definite length encoding. */ diff --git a/crypto/sm2/sm2_sign.c b/crypto/sm2/sm2_sign.c index 9ddf889ede..a02d30d854 100644 --- a/crypto/sm2/sm2_sign.c +++ b/crypto/sm2/sm2_sign.c @@ -160,7 +160,7 @@ static BIGNUM *sm2_compute_msg_hash(const EVP_MD *digest, OSSL_LIB_CTX *libctx = ossl_ec_key_get_libctx(key); const char *propq = ossl_ec_key_get0_propq(key); - if (md_size < 0) { + if (md_size <= 0) { ERR_raise(ERR_LIB_SM2, SM2_R_INVALID_DIGEST); goto done; } diff --git a/crypto/sm4/sm4.c b/crypto/sm4/sm4.c index 4c58c25fa7..194ef7e4bb 100644 --- a/crypto/sm4/sm4.c +++ b/crypto/sm4/sm4.c @@ -1,5 +1,5 @@ /* - * Copyright 2017-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2017-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2017 Ribose Inc. All Rights Reserved. * Ported from Ribose contributions from Botan. * @@ -283,8 +283,9 @@ int ossl_sm4_set_key(const uint8_t *key, SM4_KEY *ks) /* * Family Key */ - static const uint32_t FK[4] = - { 0xa3b1bac6, 0x56aa3350, 0x677d9197, 0xb27022dc }; + static const uint32_t FK[4] = { + 0xa3b1bac6, 0x56aa3350, 0x677d9197, 0xb27022dc + }; /* * Constant Key diff --git a/crypto/sparse_array.c b/crypto/sparse_array.c index bbbc9cdb36..a41936517e 100644 --- a/crypto/sparse_array.c +++ b/crypto/sparse_array.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -19,7 +19,7 @@ * depth of the tree but potentially wastes more memory. That is, this is a * direct space versus time tradeoff. * - * The default is to use four bits which means that the are 16 + * The default is to use four bits which means that there are 16 * pointers in each tree node. * * The library builder is also permitted to define other sizes in the closed diff --git a/crypto/srp/srp_vfy.c b/crypto/srp/srp_vfy.c index e89f58b200..81084ab536 100644 --- a/crypto/srp/srp_vfy.c +++ b/crypto/srp/srp_vfy.c @@ -1,5 +1,5 @@ /* - * Copyright 2004-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2004-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2004, EdelKey Project. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -214,6 +214,8 @@ int SRP_user_pwd_set1_ids(SRP_user_pwd *vinfo, const char *id, { OPENSSL_free(vinfo->id); OPENSSL_free(vinfo->info); + vinfo->id = NULL; + vinfo->info = NULL; if (id != NULL && NULL == (vinfo->id = OPENSSL_strdup(id))) return 0; return (info == NULL || NULL != (vinfo->info = OPENSSL_strdup(info))); diff --git a/crypto/store/store_lib.c b/crypto/store/store_lib.c index 0b55123d81..82874e8a52 100644 --- a/crypto/store/store_lib.c +++ b/crypto/store/store_lib.c @@ -933,15 +933,22 @@ OSSL_STORE_SEARCH *OSSL_STORE_SEARCH_by_key_fingerprint(const EVP_MD *digest, *bytes, size_t len) { OSSL_STORE_SEARCH *search = OPENSSL_zalloc(sizeof(*search)); + int md_size; if (search == NULL) return NULL; - if (digest != NULL && len != (size_t)EVP_MD_get_size(digest)) { + md_size = EVP_MD_get_size(digest); + if (md_size <= 0) { + OPENSSL_free(search); + return NULL; + } + + if (digest != NULL && len != (size_t)md_size) { ERR_raise_data(ERR_LIB_OSSL_STORE, OSSL_STORE_R_FINGERPRINT_SIZE_DOES_NOT_MATCH_DIGEST, "%s size is %d, fingerprint size is %zu", - EVP_MD_get0_name(digest), EVP_MD_get_size(digest), len); + EVP_MD_get0_name(digest), md_size, len); OPENSSL_free(search); return NULL; } diff --git a/crypto/store/store_strings.c b/crypto/store/store_strings.c index 3d4a8ea730..45c3f52acb 100644 --- a/crypto/store/store_strings.c +++ b/crypto/store/store_strings.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -9,6 +9,8 @@ #include +#include "internal/nelem.h" + static char *type_strings[] = { "Name", /* OSSL_STORE_INFO_NAME */ "Parameters", /* OSSL_STORE_INFO_PARAMS */ @@ -20,7 +22,7 @@ static char *type_strings[] = { const char *OSSL_STORE_INFO_type_string(int type) { - int types = sizeof(type_strings) / sizeof(type_strings[0]); + int types = OSSL_NELEM(type_strings); if (type < 1 || type > types) return NULL; diff --git a/crypto/thread/build.info b/crypto/thread/build.info index 191e25e20d..b3bada0ed3 100644 --- a/crypto/thread/build.info +++ b/crypto/thread/build.info @@ -14,7 +14,7 @@ ELSE IF[{- !$disabled{quic} -}] SOURCE[../../libssl]=$THREADS_ARCH ENDIF - $THREADS=api.c + $THREADS=api.c arch/thread_win.c ENDIF SOURCE[../../libcrypto]=$THREADS diff --git a/crypto/threads_none.c b/crypto/threads_none.c index 66ef99f497..7506979260 100644 --- a/crypto/threads_none.c +++ b/crypto/threads_none.c @@ -211,6 +211,24 @@ int CRYPTO_atomic_add(int *val, int amount, int *ret, CRYPTO_RWLOCK *lock) return 1; } +int CRYPTO_atomic_add64(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ + *val += op; + *ret = *val; + + return 1; +} + +int CRYPTO_atomic_and(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ + *val &= op; + *ret = *val; + + return 1; +} + int CRYPTO_atomic_or(uint64_t *val, uint64_t op, uint64_t *ret, CRYPTO_RWLOCK *lock) { @@ -227,6 +245,13 @@ int CRYPTO_atomic_load(uint64_t *val, uint64_t *ret, CRYPTO_RWLOCK *lock) return 1; } +int CRYPTO_atomic_store(uint64_t *dst, uint64_t val, CRYPTO_RWLOCK *lock) +{ + *dst = val; + + return 1; +} + int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock) { *ret = *val; diff --git a/crypto/threads_pthread.c b/crypto/threads_pthread.c index dda6893b01..b44559e373 100644 --- a/crypto/threads_pthread.c +++ b/crypto/threads_pthread.c @@ -16,6 +16,24 @@ #include "internal/rcu.h" #include "rcu_internal.h" +#if defined(__clang__) && defined(__has_feature) +# if __has_feature(thread_sanitizer) +# define __SANITIZE_THREAD__ +# endif +#endif + +#if defined(__SANITIZE_THREAD__) +# include +# define TSAN_FAKE_UNLOCK(x) __tsan_mutex_pre_unlock((x), 0); \ +__tsan_mutex_post_unlock((x), 0) + +# define TSAN_FAKE_LOCK(x) __tsan_mutex_pre_lock((x), 0); \ +__tsan_mutex_post_lock((x), 0, 0) +#else +# define TSAN_FAKE_UNLOCK(x) +# define TSAN_FAKE_LOCK(x) +#endif + #if defined(__sun) # include #endif @@ -41,7 +59,11 @@ # include -# ifdef PTHREAD_RWLOCK_INITIALIZER +/* + * The Non-Stop KLT thread model currently seems broken in its rwlock + * implementation + */ +# if defined(PTHREAD_RWLOCK_INITIALIZER) && !defined(_KLT_MODEL_) # define USE_RWLOCK # endif @@ -81,8 +103,8 @@ typedef struct rcu_cb_item *prcu_cb_item; * 1) We are building on a target that defines __APPLE__ AND * 2) We are building on a target using clang (__clang__) AND * 3) We are building for an M1 processor (__aarch64__) - * Then we shold not use __atomic_load_n and instead implement our own - * function to issue the ldar instruction instead, which procuces the proper + * Then we should not use __atomic_load_n and instead implement our own + * function to issue the ldar instruction instead, which produces the proper * sequencing guarantees */ static inline void *apple_atomic_load_n_pvoid(void **p, @@ -96,6 +118,7 @@ static inline void *apple_atomic_load_n_pvoid(void **p, } /* For uint64_t, we should be fine, though */ +# define apple_atomic_load_n_uint32_t(p, o) __atomic_load_n(p, o) # define apple_atomic_load_n_uint64_t(p, o) __atomic_load_n(p, o) # define ATOMIC_LOAD_N(t, p, o) apple_atomic_load_n_##t(p, o) @@ -123,6 +146,7 @@ static pthread_mutex_t atomic_sim_lock = PTHREAD_MUTEX_INITIALIZER; pthread_mutex_unlock(&atomic_sim_lock); \ return ret; \ } +IMPL_fallback_atomic_load_n(uint32_t) IMPL_fallback_atomic_load_n(uint64_t) IMPL_fallback_atomic_load_n(pvoid) @@ -139,6 +163,7 @@ IMPL_fallback_atomic_load_n(pvoid) pthread_mutex_unlock(&atomic_sim_lock); \ return ret; \ } +IMPL_fallback_atomic_store_n(uint32_t) IMPL_fallback_atomic_store_n(uint64_t) # define ATOMIC_STORE_N(t, p, v, o) fallback_atomic_store_n_##t(p, v) @@ -247,17 +272,19 @@ static ossl_inline uint64_t fallback_atomic_or_fetch(uint64_t *p, uint64_t m) /* * users is broken up into 2 parts * bits 0-15 current readers - * bit 32-63 - ID + * bit 32-63 ID */ # define READER_SHIFT 0 # define ID_SHIFT 32 +/* TODO: READER_SIZE 32 in threads_win.c */ # define READER_SIZE 16 # define ID_SIZE 32 # define READER_MASK (((uint64_t)1 << READER_SIZE) - 1) # define ID_MASK (((uint64_t)1 << ID_SIZE) - 1) -# define READER_COUNT(x) (((uint64_t)(x) >> READER_SHIFT) & READER_MASK) -# define ID_VAL(x) (((uint64_t)(x) >> ID_SHIFT) & ID_MASK) +# define READER_COUNT(x) ((uint32_t)(((uint64_t)(x) >> READER_SHIFT) & \ + READER_MASK)) +# define ID_VAL(x) ((uint32_t)(((uint64_t)(x) >> ID_SHIFT) & ID_MASK)) # define VAL_READER ((uint64_t)1 << READER_SHIFT) # define VAL_ID(x) ((uint64_t)x << ID_SHIFT) @@ -304,20 +331,21 @@ struct rcu_lock_st { /* rcu generation counter for in-order retirement */ uint32_t id_ctr; + /* TODO: can be moved before id_ctr for better alignment */ /* Array of quiescent points for synchronization */ struct rcu_qp *qp_group; /* Number of elements in qp_group array */ - size_t group_count; + uint32_t group_count; /* Index of the current qp in the qp_group array */ - uint64_t reader_idx; + uint32_t reader_idx; /* value of the next id_ctr value to be retired */ uint32_t next_to_retire; /* index of the next free rcu_qp in the qp_group */ - uint64_t current_alloc_idx; + uint32_t current_alloc_idx; /* number of qp's in qp_group array currently being retired */ uint32_t writers_alloced; @@ -341,7 +369,7 @@ struct rcu_lock_st { /* Read side acquisition of the current qp */ static struct rcu_qp *get_hold_current_qp(struct rcu_lock_st *lock) { - uint64_t qp_idx; + uint32_t qp_idx; /* get the current qp index */ for (;;) { @@ -357,7 +385,7 @@ static struct rcu_qp *get_hold_current_qp(struct rcu_lock_st *lock) * systems like x86, but is relevant on other arches * Note: This applies to the reload below as well */ - qp_idx = ATOMIC_LOAD_N(uint64_t, &lock->reader_idx, __ATOMIC_ACQUIRE); + qp_idx = ATOMIC_LOAD_N(uint32_t, &lock->reader_idx, __ATOMIC_ACQUIRE); /* * Notes of use of __ATOMIC_RELEASE @@ -370,7 +398,7 @@ static struct rcu_qp *get_hold_current_qp(struct rcu_lock_st *lock) __ATOMIC_RELEASE); /* if the idx hasn't changed, we're good, else try again */ - if (qp_idx == ATOMIC_LOAD_N(uint64_t, &lock->reader_idx, __ATOMIC_ACQUIRE)) + if (qp_idx == ATOMIC_LOAD_N(uint32_t, &lock->reader_idx, __ATOMIC_ACQUIRE)) break; /* @@ -476,7 +504,7 @@ void ossl_rcu_read_unlock(CRYPTO_RCU_LOCK *lock) static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) { uint64_t new_id; - uint64_t current_idx; + uint32_t current_idx; pthread_mutex_lock(&lock->alloc_lock); @@ -499,10 +527,9 @@ static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) (lock->current_alloc_idx + 1) % lock->group_count; /* get and insert a new id */ - new_id = lock->id_ctr; + new_id = VAL_ID(lock->id_ctr); lock->id_ctr++; - new_id = VAL_ID(new_id); /* * Even though we are under a write side lock here * We need to use atomic instructions to ensure that the results @@ -520,7 +547,7 @@ static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) * of __ATOMIC_ACQUIRE in get_hold_current_qp, as we want any publication * of this value to be seen on the read side immediately after it happens */ - ATOMIC_STORE_N(uint64_t, &lock->reader_idx, lock->current_alloc_idx, + ATOMIC_STORE_N(uint32_t, &lock->reader_idx, lock->current_alloc_idx, __ATOMIC_RELEASE); /* wake up any waiters */ @@ -537,6 +564,8 @@ static void retire_qp(CRYPTO_RCU_LOCK *lock, struct rcu_qp *qp) pthread_mutex_unlock(&lock->alloc_lock); } +/* TODO: count should be unsigned, e.g uint32_t */ +/* a negative value could result in unexpected behaviour */ static struct rcu_qp *allocate_new_qp_group(CRYPTO_RCU_LOCK *lock, int count) { @@ -550,10 +579,12 @@ static struct rcu_qp *allocate_new_qp_group(CRYPTO_RCU_LOCK *lock, void ossl_rcu_write_lock(CRYPTO_RCU_LOCK *lock) { pthread_mutex_lock(&lock->write_lock); + TSAN_FAKE_UNLOCK(&lock->write_lock); } void ossl_rcu_write_unlock(CRYPTO_RCU_LOCK *lock) { + TSAN_FAKE_LOCK(&lock->write_lock); pthread_mutex_unlock(&lock->write_lock); } @@ -563,12 +594,10 @@ void ossl_synchronize_rcu(CRYPTO_RCU_LOCK *lock) uint64_t count; struct rcu_cb_item *cb_items, *tmpcb; - /* - * __ATOMIC_ACQ_REL is used here to ensure that we get any prior published - * writes before we read, and publish our write immediately - */ - cb_items = ATOMIC_EXCHANGE_N(prcu_cb_item, &lock->cb_items, NULL, - __ATOMIC_ACQ_REL); + pthread_mutex_lock(&lock->write_lock); + cb_items = lock->cb_items; + lock->cb_items = NULL; + pthread_mutex_unlock(&lock->write_lock); qp = update_qp(lock); @@ -854,6 +883,58 @@ int CRYPTO_atomic_add(int *val, int amount, int *ret, CRYPTO_RWLOCK *lock) return 1; } +int CRYPTO_atomic_add64(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ +# if defined(__GNUC__) && defined(__ATOMIC_ACQ_REL) && !defined(BROKEN_CLANG_ATOMICS) + if (__atomic_is_lock_free(sizeof(*val), val)) { + *ret = __atomic_add_fetch(val, op, __ATOMIC_ACQ_REL); + return 1; + } +# elif defined(__sun) && (defined(__SunOS_5_10) || defined(__SunOS_5_11)) + /* This will work for all future Solaris versions. */ + if (ret != NULL) { + *ret = atomic_add_64_nv(val, op); + return 1; + } +# endif + if (lock == NULL || !CRYPTO_THREAD_write_lock(lock)) + return 0; + *val += op; + *ret = *val; + + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + + return 1; +} + +int CRYPTO_atomic_and(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ +# if defined(__GNUC__) && defined(__ATOMIC_ACQ_REL) && !defined(BROKEN_CLANG_ATOMICS) + if (__atomic_is_lock_free(sizeof(*val), val)) { + *ret = __atomic_and_fetch(val, op, __ATOMIC_ACQ_REL); + return 1; + } +# elif defined(__sun) && (defined(__SunOS_5_10) || defined(__SunOS_5_11)) + /* This will work for all future Solaris versions. */ + if (ret != NULL) { + *ret = atomic_and_64_nv(val, op); + return 1; + } +# endif + if (lock == NULL || !CRYPTO_THREAD_write_lock(lock)) + return 0; + *val &= op; + *ret = *val; + + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + + return 1; +} + int CRYPTO_atomic_or(uint64_t *val, uint64_t op, uint64_t *ret, CRYPTO_RWLOCK *lock) { @@ -903,6 +984,29 @@ int CRYPTO_atomic_load(uint64_t *val, uint64_t *ret, CRYPTO_RWLOCK *lock) return 1; } +int CRYPTO_atomic_store(uint64_t *dst, uint64_t val, CRYPTO_RWLOCK *lock) +{ +# if defined(__GNUC__) && defined(__ATOMIC_ACQUIRE) && !defined(BROKEN_CLANG_ATOMICS) + if (__atomic_is_lock_free(sizeof(*dst), dst)) { + __atomic_store(dst, &val, __ATOMIC_RELEASE); + return 1; + } +# elif defined(__sun) && (defined(__SunOS_5_10) || defined(__SunOS_5_11)) + /* This will work for all future Solaris versions. */ + if (ret != NULL) { + atomic_swap_64(dst, val); + return 1; + } +# endif + if (lock == NULL || !CRYPTO_THREAD_write_lock(lock)) + return 0; + *dst = val; + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + + return 1; +} + int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock) { # if defined(__GNUC__) && defined(__ATOMIC_ACQUIRE) && !defined(BROKEN_CLANG_ATOMICS) @@ -913,7 +1017,7 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock) # elif defined(__sun) && (defined(__SunOS_5_10) || defined(__SunOS_5_11)) /* This will work for all future Solaris versions. */ if (ret != NULL) { - *ret = (int *)atomic_or_uint_nv((unsigned int *)val, 0); + *ret = (int)atomic_or_uint_nv((unsigned int *)val, 0); return 1; } # endif diff --git a/crypto/threads_win.c b/crypto/threads_win.c index bc430ef1b9..83e2a7c774 100644 --- a/crypto/threads_win.c +++ b/crypto/threads_win.c @@ -23,7 +23,7 @@ * only VC++ 2008 or earlier x86 compilers. */ -#if (defined(_MSC_VER) && defined(_M_IX86) && _MSC_VER <= 1600) +#if ((defined(_MSC_VER) && defined(_M_IX86) && _MSC_VER <= 1600) || (defined(__MINGW32__) && !defined(__MINGW64__))) # define NO_INTERLOCKEDOR64 #endif @@ -43,17 +43,24 @@ typedef struct { } CRYPTO_win_rwlock; # endif +/* + * users is broken up into 2 parts + * bits 0-31 current readers + * bit 32-63 ID + */ # define READER_SHIFT 0 -# define ID_SHIFT 32 -# define READER_SIZE 32 -# define ID_SIZE 32 - -# define READER_MASK (((LONG64)1 << READER_SIZE)-1) -# define ID_MASK (((LONG64)1 << ID_SIZE)-1) -# define READER_COUNT(x) (((LONG64)(x) >> READER_SHIFT) & READER_MASK) -# define ID_VAL(x) (((LONG64)(x) >> ID_SHIFT) & ID_MASK) -# define VAL_READER ((LONG64)1 << READER_SHIFT) -# define VAL_ID(x) ((LONG64)x << ID_SHIFT) +# define ID_SHIFT 32 +/* TODO: READER_SIZE 16 in threads_pthread.c */ +# define READER_SIZE 32 +# define ID_SIZE 32 + +# define READER_MASK (((uint64_t)1 << READER_SIZE) - 1) +# define ID_MASK (((uint64_t)1 << ID_SIZE) - 1) +# define READER_COUNT(x) ((uint32_t)(((uint64_t)(x) >> READER_SHIFT) & \ + READER_MASK)) +# define ID_VAL(x) ((uint32_t)(((uint64_t)(x) >> ID_SHIFT) & ID_MASK)) +# define VAL_READER ((int64_t)1 << READER_SHIFT) +# define VAL_ID(x) ((uint64_t)x << ID_SHIFT) /* * This defines a quescent point (qp) @@ -62,7 +69,7 @@ typedef struct { * atomically updated */ struct rcu_qp { - volatile LONG64 users; + volatile uint64_t users; }; struct thread_qp { @@ -89,22 +96,55 @@ struct rcu_thr_data { * it is cast from CRYPTO_RCU_LOCK */ struct rcu_lock_st { + /* Callbacks to call for next ossl_synchronize_rcu */ struct rcu_cb_item *cb_items; + + /* The context we are being created against */ OSSL_LIB_CTX *ctx; + + /* rcu generation counter for in-order retirement */ uint32_t id_ctr; + + /* TODO: can be moved before id_ctr for better alignment */ + /* Array of quiescent points for synchronization */ struct rcu_qp *qp_group; - size_t group_count; + + /* Number of elements in qp_group array */ + uint32_t group_count; + + /* Index of the current qp in the qp_group array */ + uint32_t reader_idx; + + /* value of the next id_ctr value to be retired */ uint32_t next_to_retire; - volatile long int reader_idx; + + /* index of the next free rcu_qp in the qp_group */ uint32_t current_alloc_idx; + + /* number of qp's in qp_group array currently being retired */ uint32_t writers_alloced; + + /* lock protecting write side operations */ CRYPTO_MUTEX *write_lock; + + /* lock protecting updates to writers_alloced/current_alloc_idx */ CRYPTO_MUTEX *alloc_lock; + + /* signal to wake threads waiting on alloc_lock */ CRYPTO_CONDVAR *alloc_signal; + + /* lock to enforce in-order retirement */ CRYPTO_MUTEX *prior_lock; + + /* signal to wake threads waiting on prior_lock */ CRYPTO_CONDVAR *prior_signal; + + /* lock used with NO_INTERLOCKEDOR64: VS2010 x86 */ + CRYPTO_RWLOCK *rw_lock; }; +/* TODO: count should be unsigned, e.g uint32_t */ +/* a negative value could result in unexpected behaviour */ static struct rcu_qp *allocate_new_qp_group(struct rcu_lock_st *lock, int count) { @@ -132,6 +172,7 @@ CRYPTO_RCU_LOCK *ossl_rcu_lock_new(int num_writers, OSSL_LIB_CTX *ctx) return NULL; new->ctx = ctx; + new->rw_lock = CRYPTO_THREAD_lock_new(); new->write_lock = ossl_crypto_mutex_new(); new->alloc_signal = ossl_crypto_condvar_new(); new->prior_signal = ossl_crypto_condvar_new(); @@ -143,7 +184,9 @@ CRYPTO_RCU_LOCK *ossl_rcu_lock_new(int num_writers, OSSL_LIB_CTX *ctx) || new->prior_signal == NULL || new->write_lock == NULL || new->alloc_lock == NULL - || new->prior_lock == NULL) { + || new->prior_lock == NULL + || new->rw_lock == NULL) { + CRYPTO_THREAD_lock_free(new->rw_lock); OPENSSL_free(new->qp_group); ossl_crypto_condvar_free(&new->alloc_signal); ossl_crypto_condvar_free(&new->prior_signal); @@ -159,6 +202,7 @@ CRYPTO_RCU_LOCK *ossl_rcu_lock_new(int num_writers, OSSL_LIB_CTX *ctx) void ossl_rcu_lock_free(CRYPTO_RCU_LOCK *lock) { + CRYPTO_THREAD_lock_free(lock->rw_lock); OPENSSL_free(lock->qp_group); ossl_crypto_condvar_free(&lock->alloc_signal); ossl_crypto_condvar_free(&lock->prior_signal); @@ -168,17 +212,25 @@ void ossl_rcu_lock_free(CRYPTO_RCU_LOCK *lock) OPENSSL_free(lock); } +/* Read side acquisition of the current qp */ static ossl_inline struct rcu_qp *get_hold_current_qp(CRYPTO_RCU_LOCK *lock) { uint32_t qp_idx; + uint32_t tmp; + uint64_t tmp64; /* get the current qp index */ for (;;) { - qp_idx = InterlockedOr(&lock->reader_idx, 0); - InterlockedAdd64(&lock->qp_group[qp_idx].users, VAL_READER); - if (qp_idx == InterlockedOr(&lock->reader_idx, 0)) + CRYPTO_atomic_load_int((int *)&lock->reader_idx, (int *)&qp_idx, + lock->rw_lock); + CRYPTO_atomic_add64(&lock->qp_group[qp_idx].users, VAL_READER, &tmp64, + lock->rw_lock); + CRYPTO_atomic_load_int((int *)&lock->reader_idx, (int *)&tmp, + lock->rw_lock); + if (qp_idx == tmp) break; - InterlockedAdd64(&lock->qp_group[qp_idx].users, -VAL_READER); + CRYPTO_atomic_add64(&lock->qp_group[qp_idx].users, -VAL_READER, &tmp64, + lock->rw_lock); } return &lock->qp_group[qp_idx]; @@ -254,7 +306,9 @@ void ossl_rcu_read_unlock(CRYPTO_RCU_LOCK *lock) if (data->thread_qps[i].lock == lock) { data->thread_qps[i].depth--; if (data->thread_qps[i].depth == 0) { - ret = InterlockedAdd64(&data->thread_qps[i].qp->users, -VAL_READER); + CRYPTO_atomic_add64(&data->thread_qps[i].qp->users, + -VAL_READER, (uint64_t *)&ret, + lock->rw_lock); OPENSSL_assert(ret >= 0); data->thread_qps[i].qp = NULL; data->thread_qps[i].lock = NULL; @@ -264,11 +318,16 @@ void ossl_rcu_read_unlock(CRYPTO_RCU_LOCK *lock) } } +/* + * Write side allocation routine to get the current qp + * and replace it with a new one + */ static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) { uint64_t new_id; uint32_t current_idx; uint32_t tmp; + uint64_t tmp64; ossl_crypto_mutex_lock(lock->alloc_lock); /* @@ -277,9 +336,11 @@ static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) * one that isn't yet being waited on */ while (lock->group_count - lock->writers_alloced < 2) + /* we have to wait for one to be free */ ossl_crypto_condvar_wait(lock->alloc_signal, lock->alloc_lock); current_idx = lock->current_alloc_idx; + /* Allocate the qp */ lock->writers_alloced++; @@ -288,16 +349,23 @@ static struct rcu_qp *update_qp(CRYPTO_RCU_LOCK *lock) (lock->current_alloc_idx + 1) % lock->group_count; /* get and insert a new id */ - new_id = lock->id_ctr; + new_id = VAL_ID(lock->id_ctr); lock->id_ctr++; - new_id = VAL_ID(new_id); - InterlockedAnd64(&lock->qp_group[current_idx].users, ID_MASK); - InterlockedAdd64(&lock->qp_group[current_idx].users, new_id); + /* + * Even though we are under a write side lock here + * We need to use atomic instructions to ensure that the results + * of this update are published to the read side prior to updating the + * reader idx below + */ + CRYPTO_atomic_and(&lock->qp_group[current_idx].users, ID_MASK, &tmp64, + lock->rw_lock); + CRYPTO_atomic_add64(&lock->qp_group[current_idx].users, new_id, &tmp64, + lock->rw_lock); /* update the reader index to be the prior qp */ tmp = lock->current_alloc_idx; - InterlockedExchange(&lock->reader_idx, tmp); + InterlockedExchange((LONG volatile *)&lock->reader_idx, tmp); /* wake up any waiters */ ossl_crypto_condvar_broadcast(lock->alloc_signal); @@ -328,7 +396,7 @@ void ossl_synchronize_rcu(CRYPTO_RCU_LOCK *lock) /* wait for the reader count to reach zero */ do { - count = InterlockedOr64(&qp->users, 0); + CRYPTO_atomic_load(&qp->users, &count, lock->rw_lock); } while (READER_COUNT(count) != 0); /* retire in order */ @@ -358,17 +426,14 @@ void ossl_synchronize_rcu(CRYPTO_RCU_LOCK *lock) int ossl_rcu_call(CRYPTO_RCU_LOCK *lock, rcu_cb_fn cb, void *data) { struct rcu_cb_item *new; - struct rcu_cb_item *prev; new = OPENSSL_zalloc(sizeof(struct rcu_cb_item)); if (new == NULL) return 0; - prev = new; new->data = data; new->fn = cb; - InterlockedExchangePointer((void * volatile *)&lock->cb_items, prev); - new->next = prev; + new->next = InterlockedExchangePointer((void * volatile *)&lock->cb_items, new); return 1; } @@ -558,8 +623,47 @@ int CRYPTO_THREAD_compare_id(CRYPTO_THREAD_ID a, CRYPTO_THREAD_ID b) int CRYPTO_atomic_add(int *val, int amount, int *ret, CRYPTO_RWLOCK *lock) { - *ret = (int)InterlockedExchangeAdd((long volatile *)val, (long)amount) + amount; + *ret = (int)InterlockedExchangeAdd((LONG volatile *)val, (LONG)amount) + + amount; + return 1; +} + +int CRYPTO_atomic_add64(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ +#if (defined(NO_INTERLOCKEDOR64)) + if (lock == NULL || !CRYPTO_THREAD_write_lock(lock)) + return 0; + *val += op; + *ret = *val; + + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + + return 1; +#else + *ret = (uint64_t)InterlockedAdd64((LONG64 volatile *)val, (LONG64)op); + return 1; +#endif +} + +int CRYPTO_atomic_and(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock) +{ +#if (defined(NO_INTERLOCKEDOR64)) + if (lock == NULL || !CRYPTO_THREAD_write_lock(lock)) + return 0; + *val &= op; + *ret = *val; + + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + return 1; +#else + *ret = (uint64_t)InterlockedAnd64((LONG64 volatile *)val, (LONG64)op) & op; + return 1; +#endif } int CRYPTO_atomic_or(uint64_t *val, uint64_t op, uint64_t *ret, @@ -597,6 +701,22 @@ int CRYPTO_atomic_load(uint64_t *val, uint64_t *ret, CRYPTO_RWLOCK *lock) #endif } +int CRYPTO_atomic_store(uint64_t *dst, uint64_t val, CRYPTO_RWLOCK *lock) +{ +#if (defined(NO_INTERLOCKEDOR64)) + if (lock == NULL || !CRYPTO_THREAD_read_lock(lock)) + return 0; + *dst = val; + if (!CRYPTO_THREAD_unlock(lock)) + return 0; + + return 1; +#else + InterlockedExchange64(dst, val); + return 1; +#endif +} + int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock) { #if (defined(NO_INTERLOCKEDOR64)) @@ -608,7 +728,7 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock) return 1; #else - /* On Windows, LONG is always the same size as int. */ + /* On Windows, LONG (but not long) is always the same size as int. */ *ret = (int)InterlockedOr((LONG volatile *)val, 0); return 1; #endif diff --git a/crypto/ui/ui_util.c b/crypto/ui/ui_util.c index 59b00b225a..4add8bbd7c 100644 --- a/crypto/ui/ui_util.c +++ b/crypto/ui/ui_util.c @@ -1,5 +1,5 @@ /* - * Copyright 2002-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2002-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -105,14 +105,18 @@ static int ui_read(UI *ui, UI_STRING *uis) switch (UI_get_string_type(uis)) { case UIT_PROMPT: { - char result[PEM_BUFSIZE + 1]; + int len; + char result[PEM_BUFSIZE + 1]; /* reserve one byte at the end */ const struct pem_password_cb_data *data = UI_method_get_ex_data(UI_get_method(ui), ui_method_data_index); int maxsize = UI_get_result_maxsize(uis); - int len = data->cb(result, - maxsize > PEM_BUFSIZE ? PEM_BUFSIZE : maxsize, - data->rwflag, UI_get0_user_data(ui)); + if (maxsize > PEM_BUFSIZE) + maxsize = PEM_BUFSIZE; + len = data->cb(result, maxsize, data->rwflag, + UI_get0_user_data(ui)); + if (len > maxsize) + return -1; if (len >= 0) result[len] = '\0'; if (len < 0) diff --git a/crypto/x509/build.info b/crypto/x509/build.info index 3f70f3ff36..8f3e052846 100644 --- a/crypto/x509/build.info +++ b/crypto/x509/build.info @@ -15,7 +15,9 @@ SOURCE[../../libcrypto]=\ v3_pcia.c v3_pci.c v3_ist.c \ pcy_cache.c pcy_node.c pcy_data.c pcy_map.c pcy_tree.c pcy_lib.c \ v3_asid.c v3_addr.c v3_tlsf.c v3_admis.c v3_no_rev_avail.c \ - v3_soa_id.c v3_no_ass.c v3_group_ac.c v3_single_use.c v3_ind_iss.c + v3_soa_id.c v3_no_ass.c v3_group_ac.c v3_single_use.c v3_ind_iss.c \ + x509_acert.c x509aset.c t_acert.c x_ietfatt.c v3_ac_tgt.c v3_sda.c \ + v3_usernotice.c v3_battcons.c v3_audit_id.c v3_iobo.c IF[{- !$disabled{'deprecated-3.0'} -}] SOURCE[../../libcrypto]=x509type.c diff --git a/crypto/x509/by_store.c b/crypto/x509/by_store.c index ee92f4b16f..9ba5b31a44 100644 --- a/crypto/x509/by_store.c +++ b/crypto/x509/by_store.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -111,14 +111,7 @@ static int by_store_ctrl_ex(X509_LOOKUP *ctx, int cmd, const char *argp, { switch (cmd) { case X509_L_ADD_STORE: - /* If no URI is given, use the default cert dir as default URI */ - if (argp == NULL) - argp = ossl_safe_getenv(X509_get_default_cert_dir_env()); - - if (argp == NULL) - argp = X509_get_default_cert_dir(); - - { + if (argp != NULL) { STACK_OF(OPENSSL_STRING) *uris = X509_LOOKUP_get_method_data(ctx); char *data = OPENSSL_strdup(argp); @@ -131,12 +124,15 @@ static int by_store_ctrl_ex(X509_LOOKUP *ctx, int cmd, const char *argp, } return sk_OPENSSL_STRING_push(uris, data) > 0; } + /* NOP if no URI is given. */ + return 1; case X509_L_LOAD_STORE: /* This is a shortcut for quick loading of specific containers */ return cache_objects(ctx, argp, NULL, 0, libctx, propq); + default: + /* Unsupported command */ + return 0; } - - return 0; } static int by_store_ctrl(X509_LOOKUP *ctx, int cmd, diff --git a/crypto/x509/ext_dat.h b/crypto/x509/ext_dat.h index 1ffc816e5e..9a52ba238a 100644 --- a/crypto/x509/ext_dat.h +++ b/crypto/x509/ext_dat.h @@ -1,5 +1,5 @@ /* - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -31,3 +31,14 @@ extern const X509V3_EXT_METHOD ossl_v3_no_assertion; extern const X509V3_EXT_METHOD ossl_v3_no_rev_avail; extern const X509V3_EXT_METHOD ossl_v3_single_use; extern const X509V3_EXT_METHOD ossl_v3_indirect_issuer; +extern const X509V3_EXT_METHOD ossl_v3_targeting_information; +extern const X509V3_EXT_METHOD ossl_v3_holder_name_constraints; +extern const X509V3_EXT_METHOD ossl_v3_delegated_name_constraints; +extern const X509V3_EXT_METHOD ossl_v3_subj_dir_attrs; +extern const X509V3_EXT_METHOD ossl_v3_associated_info; +extern const X509V3_EXT_METHOD ossl_v3_acc_cert_policies; +extern const X509V3_EXT_METHOD ossl_v3_acc_priv_policies; +extern const X509V3_EXT_METHOD ossl_v3_user_notice; +extern const X509V3_EXT_METHOD ossl_v3_battcons; +extern const X509V3_EXT_METHOD ossl_v3_audit_identity; +extern const X509V3_EXT_METHOD ossl_v3_issued_on_behalf_of; diff --git a/crypto/x509/pcy_tree.c b/crypto/x509/pcy_tree.c index d7307b12da..7692dc21e6 100644 --- a/crypto/x509/pcy_tree.c +++ b/crypto/x509/pcy_tree.c @@ -1,5 +1,5 @@ /* - * Copyright 2004-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2004-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -110,6 +110,8 @@ static int tree_init(X509_POLICY_TREE **ptree, STACK_OF(X509) *certs, *ptree = NULL; + if (n < 0) + return X509_PCY_TREE_INTERNAL; /* Can't do anything with just a trust anchor */ if (n == 0) return X509_PCY_TREE_EMPTY; diff --git a/crypto/x509/standard_exts.h b/crypto/x509/standard_exts.h index 87a564b238..4da6ebb8a5 100644 --- a/crypto/x509/standard_exts.h +++ b/crypto/x509/standard_exts.h @@ -1,5 +1,5 @@ /* - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -39,6 +39,7 @@ static const X509V3_EXT_METHOD *standard_exts[] = { #endif &ossl_v3_sxnet, &ossl_v3_info, + &ossl_v3_audit_identity, #ifndef OPENSSL_NO_RFC3779 &ossl_v3_addr, &ossl_v3_asid, @@ -53,6 +54,7 @@ static const X509V3_EXT_METHOD *standard_exts[] = { #endif &ossl_v3_sinfo, &ossl_v3_policy_constraints, + &ossl_v3_targeting_information, &ossl_v3_no_rev_avail, #ifndef OPENSSL_NO_OCSP &ossl_v3_crl_hold, @@ -61,6 +63,7 @@ static const X509V3_EXT_METHOD *standard_exts[] = { &ossl_v3_name_constraints, &ossl_v3_policy_mappings, &ossl_v3_inhibit_anyp, + &ossl_v3_subj_dir_attrs, &ossl_v3_idp, &ossl_v3_alt[2], &ossl_v3_freshest_crl, @@ -73,11 +76,19 @@ static const X509V3_EXT_METHOD *standard_exts[] = { &ossl_v3_issuer_sign_tool, &ossl_v3_tls_feature, &ossl_v3_ext_admission, + &ossl_v3_battcons, + &ossl_v3_delegated_name_constraints, + &ossl_v3_user_notice, &ossl_v3_soa_identifier, + &ossl_v3_acc_cert_policies, + &ossl_v3_acc_priv_policies, &ossl_v3_indirect_issuer, &ossl_v3_no_assertion, + &ossl_v3_issued_on_behalf_of, &ossl_v3_single_use, - &ossl_v3_group_ac + &ossl_v3_group_ac, + &ossl_v3_holder_name_constraints, + &ossl_v3_associated_info, }; /* Number of standard extensions */ diff --git a/crypto/x509/t_acert.c b/crypto/x509/t_acert.c new file mode 100644 index 0000000000..088454bc65 --- /dev/null +++ b/crypto/x509/t_acert.c @@ -0,0 +1,285 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include "internal/cryptlib.h" +#include +#include +#include +#include + +static int print_attribute(BIO *bp, X509_ATTRIBUTE *a) +{ + ASN1_OBJECT *aobj; + int i, j, count; + int ret = 0; + + aobj = X509_ATTRIBUTE_get0_object(a); + if (BIO_printf(bp, "%12s", "") <= 0) + goto err; + + if ((j = i2a_ASN1_OBJECT(bp, aobj)) <= 0) + goto err; + + count = X509_ATTRIBUTE_count(a); + if (count == 0) { + ERR_raise(ERR_LIB_X509, X509_R_INVALID_ATTRIBUTES); + goto err; + } + + if (j < 25 && (BIO_printf(bp, "%*s", 25 - j, " ") <= 0)) + goto err; + + if (BIO_puts(bp, ":") <= 0) + goto err; + + for (i = 0; i < count; i++) { + ASN1_TYPE *at; + int type; + ASN1_BIT_STRING *bs; + + at = X509_ATTRIBUTE_get0_type(a, i); + type = at->type; + + switch (type) { + case V_ASN1_PRINTABLESTRING: + case V_ASN1_T61STRING: + case V_ASN1_NUMERICSTRING: + case V_ASN1_UTF8STRING: + case V_ASN1_IA5STRING: + bs = at->value.asn1_string; + if (BIO_write(bp, (char *)bs->data, bs->length) != bs->length) + goto err; + if (BIO_puts(bp, "\n") <= 0) + goto err; + break; + case V_ASN1_SEQUENCE: + if (BIO_puts(bp, "\n") <= 0) + goto err; + ASN1_parse_dump(bp, at->value.sequence->data, + at->value.sequence->length, i, 1); + break; + default: + if (BIO_printf(bp, "unable to print attribute of type 0x%X\n", + type) < 0) + goto err; + break; + } + } + ret = 1; +err: + return ret; +} + +int X509_ACERT_print_ex(BIO *bp, X509_ACERT *x, unsigned long nmflags, + unsigned long cflag) +{ + int i; + char mlch = ' '; + + if ((nmflags & XN_FLAG_SEP_MASK) == XN_FLAG_SEP_MULTILINE) { + mlch = '\n'; + } + + if ((cflag & X509_FLAG_NO_HEADER) == 0) { + if (BIO_printf(bp, "Attribute Certificate:\n") <= 0) + goto err; + if (BIO_printf(bp, "%4sData:\n", "") <= 0) + goto err; + } + + if ((cflag & X509_FLAG_NO_VERSION) == 0) { + long l; + + l = X509_ACERT_get_version(x); + if (l == X509_ACERT_VERSION_2) { + if (BIO_printf(bp, "%8sVersion: %ld (0x%lx)\n", "", l + 1, + (unsigned long)l) <= 0) + goto err; + } else { + if (BIO_printf(bp, "%8sVersion: Unknown (%ld)\n", "", l) <= 0) + goto err; + } + } + + if ((cflag & X509_FLAG_NO_SERIAL) == 0) { + const ASN1_INTEGER *serial; + + serial = X509_ACERT_get0_serialNumber(x); + + if (BIO_printf(bp, "%8sSerial Number: ", "") <= 0) + goto err; + + if (i2a_ASN1_INTEGER(bp, serial) <= 0) + goto err; + + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + + if ((cflag & X509_FLAG_NO_SUBJECT) == 0) { + const GENERAL_NAMES *holderEntities; + const OSSL_ISSUER_SERIAL *holder_bcid; + const X509_NAME *holderIssuer = NULL; + + if (BIO_printf(bp, "%8sHolder:\n", "") <= 0) + goto err; + + holderEntities = X509_ACERT_get0_holder_entityName(x); + if (holderEntities != NULL) { + for (i = 0; i < sk_GENERAL_NAME_num(holderEntities); i++) { + GENERAL_NAME *entity; + + entity = sk_GENERAL_NAME_value(holderEntities, i); + + if (BIO_printf(bp, "%12sName:%c", "", mlch) <= 0) + goto err; + if (GENERAL_NAME_print(bp, entity) <= 0) + goto err; + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + } + + if ((holder_bcid = X509_ACERT_get0_holder_baseCertId(x)) != NULL) + holderIssuer = OSSL_ISSUER_SERIAL_get0_issuer(holder_bcid); + + if (holderIssuer != NULL) { + const ASN1_INTEGER *holder_serial; + const ASN1_BIT_STRING *iuid; + + if (BIO_printf(bp, "%12sIssuer:%c", "", mlch) <= 0) + goto err; + + if (X509_NAME_print_ex(bp, holderIssuer, 0, nmflags) <= 0) + goto err; + + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + + if (BIO_printf(bp, "%12sSerial: ", "") <= 0) + goto err; + + holder_serial = OSSL_ISSUER_SERIAL_get0_serial(holder_bcid); + + if (i2a_ASN1_INTEGER(bp, holder_serial) <= 0) + goto err; + + iuid = OSSL_ISSUER_SERIAL_get0_issuerUID(holder_bcid); + if (iuid != NULL) { + if (BIO_printf(bp, "%12sIssuer UID: ", "") <= 0) + goto err; + if (X509_signature_dump(bp, iuid, 24) <= 0) + goto err; + } + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + } + + if ((cflag & X509_FLAG_NO_ISSUER) == 0) { + const X509_NAME *issuer; + + if (BIO_printf(bp, "%8sIssuer:%c", "", mlch) <= 0) + goto err; + issuer = X509_ACERT_get0_issuerName(x); + if (issuer) { + if (X509_NAME_print_ex(bp, issuer, 0, nmflags) < 0) + goto err; + } else { + if (BIO_printf(bp, "Unsupported Issuer Type") <= 0) + goto err; + } + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + + if ((cflag & X509_FLAG_NO_VALIDITY) == 0) { + if (BIO_printf(bp, "%8sValidity\n", "") <= 0) + goto err; + if (BIO_printf(bp, "%12sNot Before: ", "") <= 0) + goto err; + if (ASN1_GENERALIZEDTIME_print(bp, X509_ACERT_get0_notBefore(x)) == 0) + goto err; + if (BIO_printf(bp, "\n%12sNot After : ", "") <= 0) + goto err; + if (ASN1_GENERALIZEDTIME_print(bp, X509_ACERT_get0_notAfter(x)) == 0) + goto err; + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + + if ((cflag & X509_FLAG_NO_ATTRIBUTES) == 0) { + if (BIO_printf(bp, "%8sAttributes:\n", "") <= 0) + goto err; + + if (X509_ACERT_get_attr_count(x) == 0) { + if (BIO_printf(bp, "%12s(none)\n", "") <= 0) + goto err; + } else { + for (i = 0; i < X509_ACERT_get_attr_count(x); i++) { + if (print_attribute(bp, X509_ACERT_get_attr(x, i)) == 0) + goto err; + } + } + } + + if ((cflag & X509_FLAG_NO_EXTENSIONS) == 0) { + const STACK_OF(X509_EXTENSION) *exts; + + exts = X509_ACERT_get0_extensions(x); + if (exts != NULL) { + if (BIO_printf(bp, "%8sExtensions:\n", "") <= 0) + goto err; + for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) { + ASN1_OBJECT *obj; + X509_EXTENSION *ex; + int critical; + + ex = sk_X509_EXTENSION_value(exts, i); + if (BIO_printf(bp, "%12s", "") <= 0) + goto err; + obj = X509_EXTENSION_get_object(ex); + if (i2a_ASN1_OBJECT(bp, obj) <= 0) + goto err; + critical = X509_EXTENSION_get_critical(ex); + if (BIO_printf(bp, ": %s\n", critical ? "critical" : "") <= 0) + goto err; + if (X509V3_EXT_print(bp, ex, cflag, 20) <= 0) { + if (BIO_printf(bp, "%16s", "") <= 0) + goto err; + if (ASN1_STRING_print(bp, X509_EXTENSION_get_data(ex)) <= 0) + goto err; + } + if (BIO_write(bp, "\n", 1) <= 0) + goto err; + } + } + } + + if ((cflag & X509_FLAG_NO_SIGDUMP) == 0) { + const X509_ALGOR *sig_alg; + const ASN1_BIT_STRING *sig; + + X509_ACERT_get0_signature(x, &sig, &sig_alg); + if (X509_signature_print(bp, sig_alg, sig) <= 0) + return 0; + } + + return 1; + +err: + ERR_raise(ERR_LIB_X509, ERR_R_BUF_LIB); + return 0; +} + +int X509_ACERT_print(BIO *bp, X509_ACERT *x) +{ + return X509_ACERT_print_ex(bp, x, XN_FLAG_COMPAT, X509_FLAG_COMPAT); +} diff --git a/crypto/x509/v3_ac_tgt.c b/crypto/x509/v3_ac_tgt.c new file mode 100644 index 0000000000..c6b3701b4e --- /dev/null +++ b/crypto/x509/v3_ac_tgt.c @@ -0,0 +1,239 @@ +/* + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include "internal/cryptlib.h" +#include +#include +#include +#include +#include "ext_dat.h" +#include "x509_local.h" +#include "crypto/asn1.h" + +static int i2r_ISSUER_SERIAL(X509V3_EXT_METHOD *method, + OSSL_ISSUER_SERIAL *iss, + BIO *out, int indent); +static int i2r_OBJECT_DIGEST_INFO(X509V3_EXT_METHOD *method, + OSSL_OBJECT_DIGEST_INFO *odi, + BIO *out, int indent); +static int i2r_TARGET_CERT(X509V3_EXT_METHOD *method, + OSSL_TARGET_CERT *tc, + BIO *out, int indent); +static int i2r_TARGET(X509V3_EXT_METHOD *method, + OSSL_TARGET *target, + BIO *out, int indent); +static int i2r_TARGETING_INFORMATION(X509V3_EXT_METHOD *method, + OSSL_TARGETING_INFORMATION *tinfo, + BIO *out, int indent); + +ASN1_SEQUENCE(OSSL_ISSUER_SERIAL) = { + ASN1_SEQUENCE_OF(OSSL_ISSUER_SERIAL, issuer, GENERAL_NAME), + ASN1_EMBED(OSSL_ISSUER_SERIAL, serial, ASN1_INTEGER), + ASN1_OPT(OSSL_ISSUER_SERIAL, issuerUID, ASN1_BIT_STRING), +} static_ASN1_SEQUENCE_END(OSSL_ISSUER_SERIAL) + +ASN1_SEQUENCE(OSSL_OBJECT_DIGEST_INFO) = { + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, digestedObjectType, ASN1_ENUMERATED), + ASN1_OPT(OSSL_OBJECT_DIGEST_INFO, otherObjectTypeID, ASN1_OBJECT), + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, digestAlgorithm, X509_ALGOR), + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, objectDigest, ASN1_BIT_STRING), +} static_ASN1_SEQUENCE_END(OSSL_OBJECT_DIGEST_INFO) + +ASN1_SEQUENCE(OSSL_TARGET_CERT) = { + ASN1_SIMPLE(OSSL_TARGET_CERT, targetCertificate, OSSL_ISSUER_SERIAL), + ASN1_OPT(OSSL_TARGET_CERT, targetName, GENERAL_NAME), + ASN1_OPT(OSSL_TARGET_CERT, certDigestInfo, OSSL_OBJECT_DIGEST_INFO), +} static_ASN1_SEQUENCE_END(OSSL_TARGET_CERT) + +ASN1_CHOICE(OSSL_TARGET) = { + ASN1_EXP(OSSL_TARGET, choice.targetName, GENERAL_NAME, 0), + ASN1_EXP(OSSL_TARGET, choice.targetGroup, GENERAL_NAME, 1), + ASN1_IMP(OSSL_TARGET, choice.targetCert, OSSL_TARGET_CERT, 2), +} ASN1_CHOICE_END(OSSL_TARGET) + +ASN1_ITEM_TEMPLATE(OSSL_TARGETS) = + ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, Targets, OSSL_TARGET) +ASN1_ITEM_TEMPLATE_END(OSSL_TARGETS) + +ASN1_ITEM_TEMPLATE(OSSL_TARGETING_INFORMATION) = + ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, TargetingInformation, OSSL_TARGETS) +ASN1_ITEM_TEMPLATE_END(OSSL_TARGETING_INFORMATION) + +IMPLEMENT_ASN1_FUNCTIONS(OSSL_TARGET) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_TARGETS) +IMPLEMENT_ASN1_FUNCTIONS(OSSL_TARGETING_INFORMATION) + +static int i2r_ISSUER_SERIAL(X509V3_EXT_METHOD *method, + OSSL_ISSUER_SERIAL *iss, + BIO *out, int indent) +{ + if (iss->issuer != NULL) { + BIO_printf(out, "%*sIssuer Names:\n", indent, ""); + OSSL_GENERAL_NAMES_print(out, iss->issuer, indent); + BIO_puts(out, "\n"); + } + BIO_printf(out, "%*sIssuer Serial: ", indent, ""); + if (i2a_ASN1_INTEGER(out, &(iss->serial)) <= 0) + return 0; + BIO_puts(out, "\n"); + if (iss->issuerUID != NULL) { + BIO_printf(out, "%*sIssuer UID: ", indent, ""); + if (i2a_ASN1_STRING(out, iss->issuerUID, V_ASN1_BIT_STRING) <= 0) + return 0; + BIO_puts(out, "\n"); + } + return 1; +} + +static int i2r_OBJECT_DIGEST_INFO(X509V3_EXT_METHOD *method, + OSSL_OBJECT_DIGEST_INFO *odi, + BIO *out, int indent) +{ + int64_t dot = 0; + int sig_nid; + X509_ALGOR *digalg; + ASN1_STRING *sig; + + if (odi == NULL) { + ERR_raise(ERR_LIB_ASN1, ERR_R_PASSED_NULL_PARAMETER); + return 0; + } + digalg = &odi->digestAlgorithm; + sig = &odi->objectDigest; + if (!ASN1_ENUMERATED_get_int64(&dot, &odi->digestedObjectType)) { + return 0; + } + switch (dot) { + case OSSL_ODI_TYPE_PUBLIC_KEY: + BIO_printf(out, "%*sDigest Type: Public Key\n", indent, ""); + break; + case OSSL_ODI_TYPE_PUBLIC_KEY_CERT: + BIO_printf(out, "%*sDigest Type: Public Key Certificate\n", indent, ""); + break; + case OSSL_ODI_TYPE_OTHER: + BIO_printf(out, "%*sDigest Type: Other\n", indent, ""); + break; + } + if (odi->otherObjectTypeID != NULL) { + BIO_printf(out, "%*sDigest Type Identifier: ", indent, ""); + i2a_ASN1_OBJECT(out, odi->otherObjectTypeID); + BIO_puts(out, "\n"); + } + if (BIO_printf(out, "%*sSignature Algorithm: ", indent, "") <= 0) + return 0; + if (i2a_ASN1_OBJECT(out, odi->digestAlgorithm.algorithm) <= 0) + return 0; + BIO_puts(out, "\n"); + if (BIO_printf(out, "\n%*sSignature Value: ", indent, "") <= 0) + return 0; + sig_nid = OBJ_obj2nid(odi->digestAlgorithm.algorithm); + if (sig_nid != NID_undef) { + int pkey_nid, dig_nid; + const EVP_PKEY_ASN1_METHOD *ameth; + if (OBJ_find_sigid_algs(sig_nid, &dig_nid, &pkey_nid)) { + ameth = EVP_PKEY_asn1_find(NULL, pkey_nid); + if (ameth && ameth->sig_print) + return ameth->sig_print(out, digalg, sig, indent + 4, 0); + } + } + if (BIO_write(out, "\n", 1) != 1) + return 0; + if (sig) + return X509_signature_dump(out, sig, indent + 4); + return 1; +} + +static int i2r_TARGET_CERT(X509V3_EXT_METHOD *method, + OSSL_TARGET_CERT *tc, + BIO *out, int indent) +{ + BIO_printf(out, "%*s", indent, ""); + if (tc->targetCertificate != NULL) { + BIO_puts(out, "Target Certificate:\n"); + i2r_ISSUER_SERIAL(method, tc->targetCertificate, out, indent + 2); + } + if (tc->targetName != NULL) { + BIO_printf(out, "%*sTarget Name: ", indent, ""); + GENERAL_NAME_print(out, tc->targetName); + BIO_puts(out, "\n"); + } + if (tc->certDigestInfo != NULL) { + BIO_printf(out, "%*sCertificate Digest Info:\n", indent, ""); + i2r_OBJECT_DIGEST_INFO(method, tc->certDigestInfo, out, indent + 2); + } + BIO_puts(out, "\n"); + return 1; +} + +static int i2r_TARGET(X509V3_EXT_METHOD *method, + OSSL_TARGET *target, + BIO *out, int indent) +{ + switch (target->type) { + case OSSL_TGT_TARGET_NAME: + BIO_printf(out, "%*sTarget Name: ", indent, ""); + GENERAL_NAME_print(out, target->choice.targetName); + BIO_puts(out, "\n"); + break; + case OSSL_TGT_TARGET_GROUP: + BIO_printf(out, "%*sTarget Group: ", indent, ""); + GENERAL_NAME_print(out, target->choice.targetGroup); + BIO_puts(out, "\n"); + break; + case OSSL_TGT_TARGET_CERT: + BIO_printf(out, "%*sTarget Cert:\n", indent, ""); + i2r_TARGET_CERT(method, target->choice.targetCert, out, indent + 2); + break; + } + return 1; +} + +static int i2r_TARGETS(X509V3_EXT_METHOD *method, + OSSL_TARGETS *targets, + BIO *out, int indent) +{ + int i; + OSSL_TARGET *target; + + for (i = 0; i < sk_OSSL_TARGET_num(targets); i++) { + BIO_printf(out, "%*sTarget:\n", indent, ""); + target = sk_OSSL_TARGET_value(targets, i); + i2r_TARGET(method, target, out, indent + 2); + } + return 1; +} + +static int i2r_TARGETING_INFORMATION(X509V3_EXT_METHOD *method, + OSSL_TARGETING_INFORMATION *tinfo, + BIO *out, int indent) +{ + int i; + OSSL_TARGETS *targets; + + for (i = 0; i < sk_OSSL_TARGETS_num(tinfo); i++) { + BIO_printf(out, "%*sTargets:\n", indent, ""); + targets = sk_OSSL_TARGETS_value(tinfo, i); + i2r_TARGETS(method, targets, out, indent + 2); + } + return 1; +} + +const X509V3_EXT_METHOD ossl_v3_targeting_information = { + NID_target_information, 0, ASN1_ITEM_ref(OSSL_TARGETING_INFORMATION), + 0, 0, 0, 0, + 0, + 0, + 0, 0, + (X509V3_EXT_I2R)i2r_TARGETING_INFORMATION, + 0, + NULL +}; diff --git a/crypto/x509/v3_audit_id.c b/crypto/x509/v3_audit_id.c new file mode 100644 index 0000000000..22535cd412 --- /dev/null +++ b/crypto/x509/v3_audit_id.c @@ -0,0 +1,20 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include "ext_dat.h" + +const X509V3_EXT_METHOD ossl_v3_audit_identity = { + NID_ac_auditIdentity, 0, ASN1_ITEM_ref(ASN1_OCTET_STRING), + 0, 0, 0, 0, + (X509V3_EXT_I2S)i2s_ASN1_OCTET_STRING, + (X509V3_EXT_S2I)s2i_ASN1_OCTET_STRING, + 0, 0, 0, 0, + NULL +}; diff --git a/crypto/x509/v3_battcons.c b/crypto/x509/v3_battcons.c new file mode 100644 index 0000000000..fd767fe7d7 --- /dev/null +++ b/crypto/x509/v3_battcons.c @@ -0,0 +1,86 @@ +/* + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include "internal/cryptlib.h" +#include +#include +#include +#include "x509_local.h" +#include "ext_dat.h" + +static STACK_OF(CONF_VALUE) *i2v_OSSL_BASIC_ATTR_CONSTRAINTS( + X509V3_EXT_METHOD *method, + OSSL_BASIC_ATTR_CONSTRAINTS *battcons, + STACK_OF(CONF_VALUE) + *extlist); +static OSSL_BASIC_ATTR_CONSTRAINTS *v2i_OSSL_BASIC_ATTR_CONSTRAINTS( + X509V3_EXT_METHOD *method, + X509V3_CTX *ctx, + STACK_OF(CONF_VALUE) *values); + +const X509V3_EXT_METHOD ossl_v3_battcons = { + NID_basic_att_constraints, 0, + ASN1_ITEM_ref(OSSL_BASIC_ATTR_CONSTRAINTS), + 0, 0, 0, 0, + 0, 0, + (X509V3_EXT_I2V) i2v_OSSL_BASIC_ATTR_CONSTRAINTS, + (X509V3_EXT_V2I)v2i_OSSL_BASIC_ATTR_CONSTRAINTS, + NULL, NULL, + NULL +}; + +ASN1_SEQUENCE(OSSL_BASIC_ATTR_CONSTRAINTS) = { + ASN1_OPT(OSSL_BASIC_ATTR_CONSTRAINTS, authority, ASN1_FBOOLEAN), + ASN1_OPT(OSSL_BASIC_ATTR_CONSTRAINTS, pathlen, ASN1_INTEGER) +} ASN1_SEQUENCE_END(OSSL_BASIC_ATTR_CONSTRAINTS) + +IMPLEMENT_ASN1_FUNCTIONS(OSSL_BASIC_ATTR_CONSTRAINTS) + +static STACK_OF(CONF_VALUE) *i2v_OSSL_BASIC_ATTR_CONSTRAINTS( + X509V3_EXT_METHOD *method, + OSSL_BASIC_ATTR_CONSTRAINTS *battcons, + STACK_OF(CONF_VALUE) *extlist) +{ + X509V3_add_value_bool("authority", battcons->authority, &extlist); + X509V3_add_value_int("pathlen", battcons->pathlen, &extlist); + return extlist; +} + +static OSSL_BASIC_ATTR_CONSTRAINTS *v2i_OSSL_BASIC_ATTR_CONSTRAINTS( + X509V3_EXT_METHOD *method, + X509V3_CTX *ctx, + STACK_OF(CONF_VALUE) *values) +{ + OSSL_BASIC_ATTR_CONSTRAINTS *battcons = NULL; + CONF_VALUE *val; + int i; + + if ((battcons = OSSL_BASIC_ATTR_CONSTRAINTS_new()) == NULL) { + ERR_raise(ERR_LIB_X509V3, ERR_R_ASN1_LIB); + return NULL; + } + for (i = 0; i < sk_CONF_VALUE_num(values); i++) { + val = sk_CONF_VALUE_value(values, i); + if (strcmp(val->name, "authority") == 0) { + if (!X509V3_get_value_bool(val, &battcons->authority)) + goto err; + } else if (strcmp(val->name, "pathlen") == 0) { + if (!X509V3_get_value_int(val, &battcons->pathlen)) + goto err; + } else { + ERR_raise(ERR_LIB_X509V3, X509V3_R_INVALID_NAME); + X509V3_conf_add_error_name_value(val); + goto err; + } + } + return battcons; + err: + OSSL_BASIC_ATTR_CONSTRAINTS_free(battcons); + return NULL; +} diff --git a/crypto/x509/v3_crld.c b/crypto/x509/v3_crld.c index 8f560e171c..ae772cdd80 100644 --- a/crypto/x509/v3_crld.c +++ b/crypto/x509/v3_crld.c @@ -327,6 +327,7 @@ ASN1_CHOICE_cb(DIST_POINT_NAME, dpn_cb) = { IMPLEMENT_ASN1_FUNCTIONS(DIST_POINT_NAME) +IMPLEMENT_ASN1_DUP_FUNCTION(DIST_POINT_NAME) ASN1_SEQUENCE(DIST_POINT) = { ASN1_EXP_OPT(DIST_POINT, distpoint, DIST_POINT_NAME, 0), @@ -418,23 +419,11 @@ static void *v2i_idp(const X509V3_EXT_METHOD *method, X509V3_CTX *ctx, return NULL; } -static int print_gens(BIO *out, STACK_OF(GENERAL_NAME) *gens, int indent) -{ - int i; - for (i = 0; i < sk_GENERAL_NAME_num(gens); i++) { - if (i > 0) - BIO_puts(out, "\n"); - BIO_printf(out, "%*s", indent + 2, ""); - GENERAL_NAME_print(out, sk_GENERAL_NAME_value(gens, i)); - } - return 1; -} - static int print_distpoint(BIO *out, DIST_POINT_NAME *dpn, int indent) { if (dpn->type == 0) { BIO_printf(out, "%*sFull Name:\n", indent, ""); - print_gens(out, dpn->name.fullname, indent); + OSSL_GENERAL_NAMES_print(out, dpn->name.fullname, indent); } else { X509_NAME ntmp; ntmp.entries = dpn->name.relativename; @@ -485,7 +474,7 @@ static int i2r_crldp(const X509V3_EXT_METHOD *method, void *pcrldp, BIO *out, print_reasons(out, "Reasons", point->reasons, indent); if (point->CRLissuer) { BIO_printf(out, "%*sCRL Issuer:\n", indent, ""); - print_gens(out, point->CRLissuer, indent); + OSSL_GENERAL_NAMES_print(out, point->CRLissuer, indent); } } return 1; diff --git a/crypto/x509/v3_extku.c b/crypto/x509/v3_extku.c index 22c951e251..cb95c5bb79 100644 --- a/crypto/x509/v3_extku.c +++ b/crypto/x509/v3_extku.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -44,6 +44,30 @@ const X509V3_EXT_METHOD ossl_v3_ocsp_accresp = { NULL }; +/* Acceptable Certificate Policies also is a SEQUENCE OF OBJECT */ +const X509V3_EXT_METHOD ossl_v3_acc_cert_policies = { + NID_acceptable_cert_policies, 0, + ASN1_ITEM_ref(EXTENDED_KEY_USAGE), + 0, 0, 0, 0, + 0, 0, + i2v_EXTENDED_KEY_USAGE, + v2i_EXTENDED_KEY_USAGE, + 0, 0, + NULL +}; + +/* Acceptable Privilege Policies also is a SEQUENCE OF OBJECT */ +const X509V3_EXT_METHOD ossl_v3_acc_priv_policies = { + NID_acceptable_privilege_policies, 0, + ASN1_ITEM_ref(EXTENDED_KEY_USAGE), + 0, 0, 0, 0, + 0, 0, + i2v_EXTENDED_KEY_USAGE, + v2i_EXTENDED_KEY_USAGE, + 0, 0, + NULL +}; + ASN1_ITEM_TEMPLATE(EXTENDED_KEY_USAGE) = ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, EXTENDED_KEY_USAGE, ASN1_OBJECT) ASN1_ITEM_TEMPLATE_END(EXTENDED_KEY_USAGE) diff --git a/crypto/x509/v3_genn.c b/crypto/x509/v3_genn.c index 1f67bf2f63..fd48b51927 100644 --- a/crypto/x509/v3_genn.c +++ b/crypto/x509/v3_genn.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -58,6 +58,35 @@ GENERAL_NAME *GENERAL_NAME_dup(const GENERAL_NAME *a) (char *)a); } +int GENERAL_NAME_set1_X509_NAME(GENERAL_NAME **tgt, const X509_NAME *src) +{ + GENERAL_NAME *name; + + if (tgt == NULL) { + ERR_raise(ERR_LIB_X509V3, X509V3_R_INVALID_NULL_ARGUMENT); + return 0; + } + + if ((name = GENERAL_NAME_new()) == NULL) + return 0; + name->type = GEN_DIRNAME; + + if (src == NULL) { /* NULL-DN */ + if ((name->d.directoryName = X509_NAME_new()) == NULL) + goto err; + } else if (!X509_NAME_set(&name->d.directoryName, src)) { + goto err; + } + + GENERAL_NAME_free(*tgt); + *tgt = name; + return 1; + + err: + GENERAL_NAME_free(name); + return 0; +} + static int edipartyname_cmp(const EDIPARTYNAME *a, const EDIPARTYNAME *b) { int res; diff --git a/crypto/x509/v3_iobo.c b/crypto/x509/v3_iobo.c new file mode 100644 index 0000000000..23f991f6b6 --- /dev/null +++ b/crypto/x509/v3_iobo.c @@ -0,0 +1,32 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include "ext_dat.h" + +static int i2r_ISSUED_ON_BEHALF_OF(X509V3_EXT_METHOD *method, + GENERAL_NAME *gn, BIO *out, + int indent) +{ + if (BIO_printf(out, "%*s", indent, "") <= 0) + return 0; + if (GENERAL_NAME_print(out, gn) <= 0) + return 0; + return BIO_puts(out, "\n") > 0; +} + +const X509V3_EXT_METHOD ossl_v3_issued_on_behalf_of = { + NID_issued_on_behalf_of, 0, ASN1_ITEM_ref(GENERAL_NAME), + 0, 0, 0, 0, + 0, 0, + 0, 0, + (X509V3_EXT_I2R)i2r_ISSUED_ON_BEHALF_OF, + 0, + NULL +}; diff --git a/crypto/x509/v3_ncons.c b/crypto/x509/v3_ncons.c index a6817b9e17..481e1e2044 100644 --- a/crypto/x509/v3_ncons.c +++ b/crypto/x509/v3_ncons.c @@ -1,5 +1,5 @@ /* - * Copyright 2003-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2003-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -53,6 +53,26 @@ const X509V3_EXT_METHOD ossl_v3_name_constraints = { NULL }; +const X509V3_EXT_METHOD ossl_v3_holder_name_constraints = { + NID_holder_name_constraints, 0, + ASN1_ITEM_ref(NAME_CONSTRAINTS), + 0, 0, 0, 0, + 0, 0, + 0, v2i_NAME_CONSTRAINTS, + i2r_NAME_CONSTRAINTS, 0, + NULL +}; + +const X509V3_EXT_METHOD ossl_v3_delegated_name_constraints = { + NID_delegated_name_constraints, 0, + ASN1_ITEM_ref(NAME_CONSTRAINTS), + 0, 0, 0, 0, + 0, 0, + 0, v2i_NAME_CONSTRAINTS, + i2r_NAME_CONSTRAINTS, 0, + NULL +}; + ASN1_SEQUENCE(GENERAL_SUBTREE) = { ASN1_SIMPLE(GENERAL_SUBTREE, base, GENERAL_NAME), ASN1_IMP_OPT(GENERAL_SUBTREE, minimum, ASN1_INTEGER, 0), diff --git a/crypto/x509/v3_pci.c b/crypto/x509/v3_pci.c index 8b8b6e3ab8..1549a244ac 100644 --- a/crypto/x509/v3_pci.c +++ b/crypto/x509/v3_pci.c @@ -1,5 +1,5 @@ /* - * Copyright 2004-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2004-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -54,8 +54,8 @@ static int i2r_pci(X509V3_EXT_METHOD *method, PROXY_CERT_INFO_EXTENSION *ext, static PROXY_CERT_INFO_EXTENSION *r2i_pci(X509V3_EXT_METHOD *method, X509V3_CTX *ctx, char *str); -const X509V3_EXT_METHOD ossl_v3_pci = - { NID_proxyCertInfo, 0, ASN1_ITEM_ref(PROXY_CERT_INFO_EXTENSION), +const X509V3_EXT_METHOD ossl_v3_pci = { + NID_proxyCertInfo, 0, ASN1_ITEM_ref(PROXY_CERT_INFO_EXTENSION), 0, 0, 0, 0, 0, 0, NULL, NULL, diff --git a/crypto/x509/v3_san.c b/crypto/x509/v3_san.c index 9adf494707..6146062b0d 100644 --- a/crypto/x509/v3_san.c +++ b/crypto/x509/v3_san.c @@ -1,5 +1,5 @@ /* - * Copyright 1999-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -88,7 +88,7 @@ STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method, switch (OBJ_obj2nid(gen->d.otherName->type_id)) { case NID_id_on_SmtpUTF8Mailbox: if (gen->d.otherName->value->type != V_ASN1_UTF8STRING - || !x509v3_add_len_value_uchar("othername: SmtpUTF8Mailbox:", + || !x509v3_add_len_value_uchar("othername: SmtpUTF8Mailbox", gen->d.otherName->value->value.utf8string->data, gen->d.otherName->value->value.utf8string->length, &ret)) @@ -96,7 +96,7 @@ STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method, break; case NID_XmppAddr: if (gen->d.otherName->value->type != V_ASN1_UTF8STRING - || !x509v3_add_len_value_uchar("othername: XmppAddr:", + || !x509v3_add_len_value_uchar("othername: XmppAddr", gen->d.otherName->value->value.utf8string->data, gen->d.otherName->value->value.utf8string->length, &ret)) @@ -104,7 +104,7 @@ STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method, break; case NID_SRVName: if (gen->d.otherName->value->type != V_ASN1_IA5STRING - || !x509v3_add_len_value_uchar("othername: SRVName:", + || !x509v3_add_len_value_uchar("othername: SRVName", gen->d.otherName->value->value.ia5string->data, gen->d.otherName->value->value.ia5string->length, &ret)) @@ -112,7 +112,7 @@ STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method, break; case NID_ms_upn: if (gen->d.otherName->value->type != V_ASN1_UTF8STRING - || !x509v3_add_len_value_uchar("othername: UPN:", + || !x509v3_add_len_value_uchar("othername: UPN", gen->d.otherName->value->value.utf8string->data, gen->d.otherName->value->value.utf8string->length, &ret)) @@ -120,32 +120,32 @@ STACK_OF(CONF_VALUE) *i2v_GENERAL_NAME(X509V3_EXT_METHOD *method, break; case NID_NAIRealm: if (gen->d.otherName->value->type != V_ASN1_UTF8STRING - || !x509v3_add_len_value_uchar("othername: NAIRealm:", + || !x509v3_add_len_value_uchar("othername: NAIRealm", gen->d.otherName->value->value.utf8string->data, gen->d.otherName->value->value.utf8string->length, &ret)) return NULL; break; default: - if (OBJ_obj2txt(oline, sizeof(oline), gen->d.otherName->type_id, 0) > 0) - BIO_snprintf(othername, sizeof(othername), "othername: %s:", + if (OBJ_obj2txt(oline, sizeof(oline), gen->d.otherName->type_id, 0) > 0) + BIO_snprintf(othername, sizeof(othername), "othername: %s", oline); else - OPENSSL_strlcpy(othername, "othername:", sizeof(othername)); + OPENSSL_strlcpy(othername, "othername", sizeof(othername)); /* check if the value is something printable */ if (gen->d.otherName->value->type == V_ASN1_IA5STRING) { if (x509v3_add_len_value_uchar(othername, gen->d.otherName->value->value.ia5string->data, gen->d.otherName->value->value.ia5string->length, - &ret)) + &ret)) return ret; } if (gen->d.otherName->value->type == V_ASN1_UTF8STRING) { if (x509v3_add_len_value_uchar(othername, gen->d.otherName->value->value.utf8string->data, gen->d.otherName->value->value.utf8string->length, - &ret)) + &ret)) return ret; } if (!X509V3_add_value(othername, "", &ret)) diff --git a/crypto/x509/v3_sda.c b/crypto/x509/v3_sda.c new file mode 100644 index 0000000000..a27c31711a --- /dev/null +++ b/crypto/x509/v3_sda.c @@ -0,0 +1,90 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include "ext_dat.h" + +ASN1_ITEM_TEMPLATE(OSSL_ATTRIBUTES_SYNTAX) = + ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, Attributes, X509_ATTRIBUTE) +ASN1_ITEM_TEMPLATE_END(OSSL_ATTRIBUTES_SYNTAX) + +IMPLEMENT_ASN1_FUNCTIONS(OSSL_ATTRIBUTES_SYNTAX) + +static int i2r_ATTRIBUTES_SYNTAX(X509V3_EXT_METHOD *method, + OSSL_ATTRIBUTES_SYNTAX *attrlst, + BIO *out, int indent) +{ + X509_ATTRIBUTE *attr; + ASN1_TYPE *av; + int i, j, attr_nid; + + if (!attrlst) { + if (BIO_printf(out, "\n") <= 0) + return 0; + return 1; + } + if (!sk_X509_ATTRIBUTE_num(attrlst)) { + if (BIO_printf(out, "\n") <= 0) + return 0; + return 1; + } + + for (i = 0; i < sk_X509_ATTRIBUTE_num(attrlst); i++) { + ASN1_OBJECT *attr_obj; + attr = sk_X509_ATTRIBUTE_value(attrlst, i); + attr_obj = X509_ATTRIBUTE_get0_object(attr); + attr_nid = OBJ_obj2nid(attr_obj); + if (indent && BIO_printf(out, "%*s", indent, "") <= 0) + return 0; + if (attr_nid == NID_undef) { + if (i2a_ASN1_OBJECT(out, attr_obj) <= 0) + return 0; + if (BIO_puts(out, ":\n") <= 0) + return 0; + } else if (BIO_printf(out, "%s:\n", OBJ_nid2ln(attr_nid)) <= 0) { + return 0; + } + + if (X509_ATTRIBUTE_count(attr)) { + for (j = 0; j < X509_ATTRIBUTE_count(attr); j++) + { + av = X509_ATTRIBUTE_get0_type(attr, j); + if (ossl_print_attribute_value(out, attr_nid, av, indent + 4) <= 0) + return 0; + if (BIO_puts(out, "\n") <= 0) + return 0; + } + } else if (BIO_printf(out, "%*s\n", indent + 4, "") <= 0) { + return 0; + } + } + return 1; +} + +const X509V3_EXT_METHOD ossl_v3_subj_dir_attrs = { + NID_subject_directory_attributes, X509V3_EXT_MULTILINE, + ASN1_ITEM_ref(OSSL_ATTRIBUTES_SYNTAX), + 0, 0, 0, 0, + 0, 0, 0, 0, + (X509V3_EXT_I2R)i2r_ATTRIBUTES_SYNTAX, + 0, + NULL +}; + +const X509V3_EXT_METHOD ossl_v3_associated_info = { + NID_associated_information, X509V3_EXT_MULTILINE, + ASN1_ITEM_ref(OSSL_ATTRIBUTES_SYNTAX), + 0, 0, 0, 0, + 0, 0, 0, 0, + (X509V3_EXT_I2R)i2r_ATTRIBUTES_SYNTAX, + 0, + NULL +}; diff --git a/crypto/x509/v3_usernotice.c b/crypto/x509/v3_usernotice.c new file mode 100644 index 0000000000..cc99132525 --- /dev/null +++ b/crypto/x509/v3_usernotice.c @@ -0,0 +1,94 @@ +/* + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include "ext_dat.h" + +ASN1_ITEM_TEMPLATE(OSSL_USER_NOTICE_SYNTAX) = + ASN1_EX_TEMPLATE_TYPE(ASN1_TFLG_SEQUENCE_OF, 0, OSSL_USER_NOTICE_SYNTAX, USERNOTICE) +ASN1_ITEM_TEMPLATE_END(OSSL_USER_NOTICE_SYNTAX) + +IMPLEMENT_ASN1_FUNCTIONS(OSSL_USER_NOTICE_SYNTAX) + +static int print_notice(BIO *out, USERNOTICE *notice, int indent) +{ + int i; + ASN1_INTEGER *num; + char *tmp; + + if (notice->noticeref) { + NOTICEREF *ref; + ref = notice->noticeref; + if (BIO_printf(out, "%*sOrganization: %.*s\n", indent, "", + ref->organization->length, + ref->organization->data) <= 0) + return 0; + if (BIO_printf(out, "%*sNumber%s: ", indent, "", + sk_ASN1_INTEGER_num(ref->noticenos) > 1 ? "s" : "") <= 0) + return 0; + for (i = 0; i < sk_ASN1_INTEGER_num(ref->noticenos); i++) { + num = sk_ASN1_INTEGER_value(ref->noticenos, i); + if (i && BIO_puts(out, ", ") <= 0) + return 0; + if (num == NULL && BIO_puts(out, "(null)") <= 0) + return 0; + else { + tmp = i2s_ASN1_INTEGER(NULL, num); + if (tmp == NULL) + return 0; + if (BIO_puts(out, tmp) <= 0) { + OPENSSL_free(tmp); + return 0; + } + OPENSSL_free(tmp); + } + } + if (notice->exptext && BIO_puts(out, "\n") <= 0) + return 0; + } + if (notice->exptext == NULL) + return 1; + + return BIO_printf(out, "%*sExplicit Text: %.*s", indent, "", + notice->exptext->length, + notice->exptext->data) >= 0; +} + +static int i2r_USER_NOTICE_SYNTAX(X509V3_EXT_METHOD *method, + OSSL_USER_NOTICE_SYNTAX *uns, + BIO *out, int indent) +{ + int i; + USERNOTICE *unotice; + + if (BIO_printf(out, "%*sUser Notices:\n", indent, "") <= 0) + return 0; + + for (i = 0; i < sk_USERNOTICE_num(uns); i++) { + unotice = sk_USERNOTICE_value(uns, i); + if (!print_notice(out, unotice, indent + 4)) + return 0; + if (BIO_puts(out, "\n\n") <= 0) + return 0; + } + return 1; +} + +const X509V3_EXT_METHOD ossl_v3_user_notice = { + NID_user_notice, 0, + ASN1_ITEM_ref(OSSL_USER_NOTICE_SYNTAX), + 0, 0, 0, 0, + 0, + 0, + 0, 0, + (X509V3_EXT_I2R)i2r_USER_NOTICE_SYNTAX, + 0, + NULL +}; diff --git a/crypto/x509/v3_utl.c b/crypto/x509/v3_utl.c index 1fa25ad3a3..40eef9eb31 100644 --- a/crypto/x509/v3_utl.c +++ b/crypto/x509/v3_utl.c @@ -1179,23 +1179,60 @@ int ossl_a2i_ipadd(unsigned char *ipout, const char *ipasc) } } -static int ipv4_from_asc(unsigned char *v4, const char *in) -{ - const char *p; - int a0, a1, a2, a3, n; +/* + * get_ipv4_component consumes one IPv4 component, terminated by either '.' or + * the end of the string, from *str. On success, it returns one, sets *out + * to the component, and advances *str to the first unconsumed character. On + * invalid input, it returns zero. + */ +static int get_ipv4_component(uint8_t *out_byte, const char **str) { + /* Store a slightly larger intermediary so the overflow check is easier. */ + uint32_t out = 0; - if (sscanf(in, "%d.%d.%d.%d%n", &a0, &a1, &a2, &a3, &n) != 4) - return 0; - if ((a0 < 0) || (a0 > 255) || (a1 < 0) || (a1 > 255) - || (a2 < 0) || (a2 > 255) || (a3 < 0) || (a3 > 255)) - return 0; - p = in + n; - if (!(*p == '\0' || ossl_isspace(*p))) + for (;;) { + if (!ossl_isdigit(**str)) { + return 0; + } + out = (out * 10) + (**str - '0'); + if (out > 255) { + /* Components must be 8-bit. */ + return 0; + } + (*str)++; + if ((**str) == '.' || (**str) == '\0') { + *out_byte = (uint8_t)out; + return 1; + } + if (out == 0) { + /* Reject extra leading zeros. Parsers sometimes treat them as + * octal, so accepting them would misinterpret input. + */ + return 0; + } + } +} + +/* + * get_ipv4_dot consumes a '.' from *str and advances it. It returns one on + * success and zero if *str does not point to a '.'. + */ +static int get_ipv4_dot(const char **str) +{ + if (**str != '.') { return 0; - v4[0] = a0; - v4[1] = a1; - v4[2] = a2; - v4[3] = a3; + } + (*str)++; + return 1; +} + +static int ipv4_from_asc(unsigned char *v4, const char *in) +{ + if (!get_ipv4_component(&v4[0], &in) || !get_ipv4_dot(&in) + || !get_ipv4_component(&v4[1], &in) || !get_ipv4_dot(&in) + || !get_ipv4_component(&v4[2], &in) || !get_ipv4_dot(&in) + || !get_ipv4_component(&v4[3], &in) || *in != '\0') { + return 0; + } return 1; } @@ -1384,3 +1421,16 @@ int X509V3_NAME_from_section(X509_NAME *nm, STACK_OF(CONF_VALUE) *dn_sk, } return 1; } + +int OSSL_GENERAL_NAMES_print(BIO *out, GENERAL_NAMES *gens, int indent) +{ + int i; + + for (i = 0; i < sk_GENERAL_NAME_num(gens); i++) { + if (i > 0) + BIO_puts(out, "\n"); + BIO_printf(out, "%*s", indent + 2, ""); + GENERAL_NAME_print(out, sk_GENERAL_NAME_value(gens, i)); + } + return 1; +} diff --git a/crypto/x509/x509_acert.c b/crypto/x509/x509_acert.c new file mode 100644 index 0000000000..d97648ca0c --- /dev/null +++ b/crypto/x509/x509_acert.c @@ -0,0 +1,328 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include +#include +#include +#include "x509_acert.h" + +/* + * OpenSSL ASN.1 template translation of RFC 5755 4.1. + */ + +ASN1_SEQUENCE(OSSL_OBJECT_DIGEST_INFO) = { + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, digestedObjectType, ASN1_ENUMERATED), + ASN1_OPT(OSSL_OBJECT_DIGEST_INFO, otherObjectTypeID, ASN1_OBJECT), + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, digestAlgorithm, X509_ALGOR), + ASN1_EMBED(OSSL_OBJECT_DIGEST_INFO, objectDigest, ASN1_BIT_STRING), +} ASN1_SEQUENCE_END(OSSL_OBJECT_DIGEST_INFO) + +ASN1_SEQUENCE(OSSL_ISSUER_SERIAL) = { + ASN1_SEQUENCE_OF(OSSL_ISSUER_SERIAL, issuer, GENERAL_NAME), + ASN1_EMBED(OSSL_ISSUER_SERIAL, serial, ASN1_INTEGER), + ASN1_OPT(OSSL_ISSUER_SERIAL, issuerUID, ASN1_BIT_STRING), +} ASN1_SEQUENCE_END(OSSL_ISSUER_SERIAL) + +ASN1_SEQUENCE(X509_ACERT_ISSUER_V2FORM) = { + ASN1_SEQUENCE_OF_OPT(X509_ACERT_ISSUER_V2FORM, issuerName, GENERAL_NAME), + ASN1_IMP_OPT(X509_ACERT_ISSUER_V2FORM, baseCertificateId, OSSL_ISSUER_SERIAL, 0), + ASN1_IMP_OPT(X509_ACERT_ISSUER_V2FORM, objectDigestInfo, OSSL_OBJECT_DIGEST_INFO, 1), +} ASN1_SEQUENCE_END(X509_ACERT_ISSUER_V2FORM) + +ASN1_CHOICE(X509_ACERT_ISSUER) = { + ASN1_SEQUENCE_OF(X509_ACERT_ISSUER, u.v1Form, GENERAL_NAME), + ASN1_IMP(X509_ACERT_ISSUER, u.v2Form, X509_ACERT_ISSUER_V2FORM, 0), +} ASN1_CHOICE_END(X509_ACERT_ISSUER) + +ASN1_SEQUENCE(X509_HOLDER) = { + ASN1_IMP_OPT(X509_HOLDER, baseCertificateID, OSSL_ISSUER_SERIAL, 0), + ASN1_IMP_SEQUENCE_OF_OPT(X509_HOLDER, entityName, GENERAL_NAME, 1), + ASN1_IMP_OPT(X509_HOLDER, objectDigestInfo, OSSL_OBJECT_DIGEST_INFO, 2), +} ASN1_SEQUENCE_END(X509_HOLDER) + +ASN1_SEQUENCE(X509_ACERT_INFO) = { + ASN1_EMBED(X509_ACERT_INFO, version, ASN1_INTEGER), + ASN1_EMBED(X509_ACERT_INFO, holder, X509_HOLDER), + ASN1_EMBED(X509_ACERT_INFO, issuer, X509_ACERT_ISSUER), + ASN1_EMBED(X509_ACERT_INFO, signature, X509_ALGOR), + ASN1_EMBED(X509_ACERT_INFO, serialNumber, ASN1_INTEGER), + ASN1_EMBED(X509_ACERT_INFO, validityPeriod, X509_VAL), + ASN1_SEQUENCE_OF(X509_ACERT_INFO, attributes, X509_ATTRIBUTE), + ASN1_OPT(X509_ACERT_INFO, issuerUID, ASN1_BIT_STRING), + ASN1_SEQUENCE_OF_OPT(X509_ACERT_INFO, extensions, X509_EXTENSION), +} ASN1_SEQUENCE_END(X509_ACERT_INFO) + +ASN1_SEQUENCE(X509_ACERT) = { + ASN1_SIMPLE(X509_ACERT, acinfo, X509_ACERT_INFO), + ASN1_EMBED(X509_ACERT, sig_alg, X509_ALGOR), + ASN1_EMBED(X509_ACERT, signature, ASN1_BIT_STRING), +} ASN1_SEQUENCE_END(X509_ACERT) + +IMPLEMENT_ASN1_FUNCTIONS(X509_ACERT) +IMPLEMENT_ASN1_DUP_FUNCTION(X509_ACERT) +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(X509_ACERT_INFO) +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(OSSL_ISSUER_SERIAL) +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(OSSL_OBJECT_DIGEST_INFO) +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(X509_ACERT_ISSUER_V2FORM) + +IMPLEMENT_PEM_rw(X509_ACERT, X509_ACERT, PEM_STRING_ACERT, X509_ACERT) + +static X509_NAME *get_dirName(const GENERAL_NAMES *names) +{ + GENERAL_NAME *dirName; + + if (sk_GENERAL_NAME_num(names) != 1) + return NULL; + + dirName = sk_GENERAL_NAME_value(names, 0); + if (dirName->type != GEN_DIRNAME) + return NULL; + + return dirName->d.directoryName; +} + +void OSSL_OBJECT_DIGEST_INFO_get0_digest(const OSSL_OBJECT_DIGEST_INFO *o, + int *digestedObjectType, + const X509_ALGOR **digestAlgorithm, + const ASN1_BIT_STRING **digest) +{ + if (digestedObjectType != NULL) + *digestedObjectType = ASN1_ENUMERATED_get(&o->digestedObjectType); + if (digestAlgorithm != NULL) + *digestAlgorithm = &o->digestAlgorithm; + if (digest != NULL) + *digest = &o->objectDigest; +} + +const X509_NAME *OSSL_ISSUER_SERIAL_get0_issuer(const OSSL_ISSUER_SERIAL *isss) +{ + return get_dirName(isss->issuer); +} + +const ASN1_INTEGER *OSSL_ISSUER_SERIAL_get0_serial(const OSSL_ISSUER_SERIAL *isss) +{ + return &isss->serial; +} + +const ASN1_BIT_STRING *OSSL_ISSUER_SERIAL_get0_issuerUID(const OSSL_ISSUER_SERIAL *isss) +{ + return isss->issuerUID; +} + +long X509_ACERT_get_version(const X509_ACERT *x) +{ + return ASN1_INTEGER_get(&x->acinfo->version); +} + +void X509_ACERT_get0_signature(const X509_ACERT *x, + const ASN1_BIT_STRING **psig, + const X509_ALGOR **palg) +{ + if (psig != NULL) + *psig = &x->signature; + if (palg != NULL) + *palg = &x->sig_alg; +} + +int X509_ACERT_get_signature_nid(const X509_ACERT *x) +{ + return OBJ_obj2nid(x->sig_alg.algorithm); +} + +const GENERAL_NAMES *X509_ACERT_get0_holder_entityName(const X509_ACERT *x) +{ + return x->acinfo->holder.entityName; +} + +const OSSL_ISSUER_SERIAL *X509_ACERT_get0_holder_baseCertId(const X509_ACERT *x) +{ + return x->acinfo->holder.baseCertificateID; +} + +const OSSL_OBJECT_DIGEST_INFO *X509_ACERT_get0_holder_digest(const X509_ACERT *x) +{ + return x->acinfo->holder.objectDigestInfo; +} + +const X509_NAME *X509_ACERT_get0_issuerName(const X509_ACERT *x) +{ + if (x->acinfo->issuer.type != X509_ACERT_ISSUER_V2 + || x->acinfo->issuer.u.v2Form == NULL) + return NULL; + + return get_dirName(x->acinfo->issuer.u.v2Form->issuerName); +} + +const ASN1_BIT_STRING *X509_ACERT_get0_issuerUID(const X509_ACERT *x) +{ + return x->acinfo->issuerUID; +} + +const X509_ALGOR *X509_ACERT_get0_info_sigalg(const X509_ACERT *x) +{ + return &x->acinfo->signature; +} + +const ASN1_INTEGER *X509_ACERT_get0_serialNumber(const X509_ACERT *x) +{ + return &x->acinfo->serialNumber; +} + +const ASN1_GENERALIZEDTIME *X509_ACERT_get0_notBefore(const X509_ACERT *x) +{ + return x->acinfo->validityPeriod.notBefore; +} + +const ASN1_GENERALIZEDTIME *X509_ACERT_get0_notAfter(const X509_ACERT *x) +{ + return x->acinfo->validityPeriod.notAfter; +} + +/* Attribute management functions */ + +int X509_ACERT_get_attr_count(const X509_ACERT *x) +{ + return X509at_get_attr_count(x->acinfo->attributes); +} + +int X509_ACERT_get_attr_by_NID(const X509_ACERT *x, int nid, int lastpos) +{ + return X509at_get_attr_by_NID(x->acinfo->attributes, nid, lastpos); +} + +int X509_ACERT_get_attr_by_OBJ(const X509_ACERT *x, const ASN1_OBJECT *obj, + int lastpos) +{ + return X509at_get_attr_by_OBJ(x->acinfo->attributes, obj, lastpos); +} + +X509_ATTRIBUTE *X509_ACERT_get_attr(const X509_ACERT *x, int loc) +{ + return X509at_get_attr(x->acinfo->attributes, loc); +} + +X509_ATTRIBUTE *X509_ACERT_delete_attr(X509_ACERT *x, int loc) +{ + return X509at_delete_attr(x->acinfo->attributes, loc); +} + +int X509_ACERT_add1_attr(X509_ACERT *x, X509_ATTRIBUTE *attr) +{ + STACK_OF(X509_ATTRIBUTE) **attrs = &x->acinfo->attributes; + + return X509at_add1_attr(attrs, attr) != NULL; +} + +int X509_ACERT_add1_attr_by_OBJ(X509_ACERT *x, const ASN1_OBJECT *obj, + int type, const void *bytes, int len) +{ + STACK_OF(X509_ATTRIBUTE) **attrs = &x->acinfo->attributes; + + return X509at_add1_attr_by_OBJ(attrs, obj, type, bytes, len) != NULL; +} + +int X509_ACERT_add1_attr_by_NID(X509_ACERT *x, int nid, int type, + const void *bytes, int len) +{ + STACK_OF(X509_ATTRIBUTE) **attrs = &x->acinfo->attributes; + + return X509at_add1_attr_by_NID(attrs, nid, type, bytes, len) != NULL; +} + +int X509_ACERT_add1_attr_by_txt(X509_ACERT *x, const char *attrname, int type, + const unsigned char *bytes, int len) +{ + STACK_OF(X509_ATTRIBUTE) **attrs = &x->acinfo->attributes; + + return X509at_add1_attr_by_txt(attrs, attrname, type, bytes, len) != NULL; +} + +static int check_asn1_attribute(const char **value) +{ + const char *p = *value; + + if (strncmp(p, "ASN1:", 5) != 0) + return 0; + + p += 5; + while (ossl_isspace(*p)) + p++; + + *value = p; + return 1; +} + +int X509_ACERT_add_attr_nconf(CONF *conf, const char *section, + X509_ACERT *acert) +{ + int ret = 0, i; + STACK_OF(CONF_VALUE) *attr_sk = NCONF_get_section(conf, section); + + if (attr_sk == NULL) + goto err; + + for (i = 0; i < sk_CONF_VALUE_num(attr_sk); i++) { + CONF_VALUE *v = sk_CONF_VALUE_value(attr_sk, i); + const char *value = v->value; + + if (value == NULL) { + ERR_raise_data(ERR_LIB_X509, X509_R_INVALID_ATTRIBUTES, + "name=%s,section=%s",v->name, section); + goto err; + } + + if (check_asn1_attribute(&value) == 1) { + int att_len; + unsigned char *att_data = NULL; + ASN1_TYPE *asn1 = ASN1_generate_nconf(value, conf); + + if (asn1 == NULL) + goto err; + + att_len = i2d_ASN1_TYPE(asn1, &att_data); + + ret = X509_ACERT_add1_attr_by_txt(acert, v->name, V_ASN1_SEQUENCE, + att_data, att_len); + OPENSSL_free(att_data); + ASN1_TYPE_free(asn1); + + if (!ret) + goto err; + } else { + ret = X509_ACERT_add1_attr_by_txt(acert, v->name, + V_ASN1_OCTET_STRING, + (unsigned char *)value, + strlen(value)); + if (!ret) + goto err; + } + } + ret = 1; +err: + return ret; +} + +void *X509_ACERT_get_ext_d2i(const X509_ACERT *x, int nid, int *crit, int *idx) +{ + return X509V3_get_d2i(x->acinfo->extensions, nid, crit, idx); +} + +int X509_ACERT_add1_ext_i2d(X509_ACERT *x, int nid, void *value, int crit, + unsigned long flags) +{ + return X509V3_add1_i2d(&x->acinfo->extensions, nid, value, crit, flags); +} + +const STACK_OF(X509_EXTENSION) *X509_ACERT_get0_extensions(const X509_ACERT *x) +{ + return x->acinfo->extensions; +} diff --git a/crypto/x509/x509_acert.h b/crypto/x509/x509_acert.h new file mode 100644 index 0000000000..f6d212bdbd --- /dev/null +++ b/crypto/x509/x509_acert.h @@ -0,0 +1,22 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OSSL_CRYPTO_X509_X509_ACERT_H +# define OSSL_CRYPTO_X509_X509_ACERT_H + +#include + +# define X509_ACERT_ISSUER_V2 1 + +DECLARE_ASN1_ITEM(OSSL_OBJECT_DIGEST_INFO) +DECLARE_ASN1_ITEM(OSSL_ISSUER_SERIAL) +DECLARE_ASN1_ITEM(X509_ACERT_ISSUER_V2FORM) +DECLARE_ASN1_ITEM(X509_ACERT_ISSUER) +DECLARE_ASN1_ITEM(X509_HOLDER) +#endif diff --git a/crypto/x509/x509_att.c b/crypto/x509/x509_att.c index 5b002832c1..b21aa4d299 100644 --- a/crypto/x509/x509_att.c +++ b/crypto/x509/x509_att.c @@ -80,7 +80,7 @@ X509_ATTRIBUTE *X509at_delete_attr(STACK_OF(X509_ATTRIBUTE) *x, int loc) } STACK_OF(X509_ATTRIBUTE) *ossl_x509at_add1_attr(STACK_OF(X509_ATTRIBUTE) **x, - X509_ATTRIBUTE *attr) + const X509_ATTRIBUTE *attr) { X509_ATTRIBUTE *new_attr = NULL; STACK_OF(X509_ATTRIBUTE) *sk = NULL; @@ -123,7 +123,8 @@ STACK_OF(X509_ATTRIBUTE) *X509at_add1_attr(STACK_OF(X509_ATTRIBUTE) **x, return NULL; } if (*x != NULL && X509at_get_attr_by_OBJ(*x, attr->object, -1) != -1) { - ERR_raise(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE); + ERR_raise_data(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE, + "name=%s", OBJ_nid2sn(OBJ_obj2nid(attr->object))); return NULL; } @@ -158,7 +159,8 @@ STACK_OF(X509_ATTRIBUTE) *X509at_add1_attr_by_OBJ(STACK_OF(X509_ATTRIBUTE) return NULL; } if (*x != NULL && X509at_get_attr_by_OBJ(*x, obj, -1) != -1) { - ERR_raise(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE); + ERR_raise_data(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE, + "name=%s", OBJ_nid2sn(OBJ_obj2nid(obj))); return NULL; } @@ -191,7 +193,8 @@ STACK_OF(X509_ATTRIBUTE) *X509at_add1_attr_by_NID(STACK_OF(X509_ATTRIBUTE) return NULL; } if (*x != NULL && X509at_get_attr_by_NID(*x, nid, -1) != -1) { - ERR_raise(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE); + ERR_raise_data(ERR_LIB_X509, X509_R_DUPLICATE_ATTRIBUTE, + "name=%s", OBJ_nid2sn(nid)); return NULL; } diff --git a/crypto/x509/x509_d2.c b/crypto/x509/x509_d2.c index 7838b703d4..dd18bcd586 100644 --- a/crypto/x509/x509_d2.c +++ b/crypto/x509/x509_d2.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -30,6 +30,11 @@ int X509_STORE_set_default_paths_ex(X509_STORE *ctx, OSSL_LIB_CTX *libctx, lookup = X509_STORE_add_lookup(ctx, X509_LOOKUP_store()); if (lookup == NULL) return 0; + /* + * The NULL URI argument will activate any default URIs (presently none), + * DO NOT pass the default CApath or CAfile, they're already handled above, + * likely much more efficiently. + */ X509_LOOKUP_add_store_ex(lookup, NULL, libctx, propq); /* clear any errors */ diff --git a/crypto/x509/x509_def.c b/crypto/x509/x509_def.c index 2851fbcd9f..7d5b642c45 100644 --- a/crypto/x509/x509_def.c +++ b/crypto/x509/x509_def.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -8,28 +8,101 @@ */ #include +#include "internal/e_os.h" #include "internal/cryptlib.h" +#include "internal/thread_once.h" #include #include +#if defined(_WIN32) + +static char x509_private_dir[MAX_PATH + 1]; +static char *x509_private_dirptr = NULL; + +static char x509_cert_area[MAX_PATH + 1]; +static char *x509_cert_areaptr = NULL; + +static char x509_cert_dir[MAX_PATH + 1]; +static char *x509_cert_dirptr = NULL; + +static char x509_cert_file[MAX_PATH + 1]; +static char *x509_cert_fileptr = NULL; + +static void get_windows_default_path(char *pathname, const char *suffix) +{ + char *ossldir; + + ossldir = ossl_get_openssldir(); + + if (ossldir == NULL) + return; + + OPENSSL_strlcpy(pathname, ossldir, MAX_PATH - 1); + if (MAX_PATH - strlen(pathname) > strlen(suffix)) + strcat(pathname, suffix); +} + +static CRYPTO_ONCE openssldir_setup_init = CRYPTO_ONCE_STATIC_INIT; +DEFINE_RUN_ONCE_STATIC(do_openssldir_setup) +{ + get_windows_default_path(x509_private_dir, "\\private"); + if (strlen(x509_private_dir) > 0) + x509_private_dirptr = x509_private_dir; + + get_windows_default_path(x509_cert_area, "\\"); + if (strlen(x509_cert_area) > 0) + x509_cert_areaptr = x509_cert_area; + + get_windows_default_path(x509_cert_dir, "\\certs"); + if (strlen(x509_cert_dir) > 0) + x509_cert_dirptr = x509_cert_dir; + + get_windows_default_path(x509_cert_file, "\\cert.pem"); + if (strlen(x509_cert_file) > 0) + x509_cert_fileptr = x509_cert_file; + + return 1; +} +#endif + const char *X509_get_default_private_dir(void) { +#if defined (_WIN32) + RUN_ONCE(&openssldir_setup_init, do_openssldir_setup); + return x509_private_dirptr; +#else return X509_PRIVATE_DIR; +#endif } const char *X509_get_default_cert_area(void) { +#if defined (_WIN32) + RUN_ONCE(&openssldir_setup_init, do_openssldir_setup); + return x509_cert_areaptr; +#else return X509_CERT_AREA; +#endif } const char *X509_get_default_cert_dir(void) { +#if defined (_WIN32) + RUN_ONCE(&openssldir_setup_init, do_openssldir_setup); + return x509_cert_dirptr; +#else return X509_CERT_DIR; +#endif } const char *X509_get_default_cert_file(void) { +#if defined (_WIN32) + RUN_ONCE(&openssldir_setup_init, do_openssldir_setup); + return x509_cert_fileptr; +#else return X509_CERT_FILE; +#endif } const char *X509_get_default_cert_dir_env(void) diff --git a/crypto/x509/x509_err.c b/crypto/x509/x509_err.c index 226e45a737..607d38f3be 100644 --- a/crypto/x509/x509_err.c +++ b/crypto/x509/x509_err.c @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -79,6 +79,8 @@ static const ERR_STRING_DATA X509_str_reasons[] = { {ERR_PACK(ERR_LIB_X509, 0, X509_R_UNKNOWN_TRUST_ID), "unknown trust id"}, {ERR_PACK(ERR_LIB_X509, 0, X509_R_UNSUPPORTED_ALGORITHM), "unsupported algorithm"}, + {ERR_PACK(ERR_LIB_X509, 0, X509_R_UNSUPPORTED_VERSION), + "unsupported version"}, {ERR_PACK(ERR_LIB_X509, 0, X509_R_WRONG_LOOKUP_TYPE), "wrong lookup type"}, {ERR_PACK(ERR_LIB_X509, 0, X509_R_WRONG_TYPE), "wrong type"}, {0, NULL} diff --git a/crypto/x509/x509_obj.c b/crypto/x509/x509_obj.c index 2af7203b01..a55ee1a73e 100644 --- a/crypto/x509/x509_obj.c +++ b/crypto/x509/x509_obj.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -32,7 +32,6 @@ char *X509_NAME_oneline(const X509_NAME *a, char *buf, int len) char *p; unsigned char *q; BUF_MEM *b = NULL; - static const char hex[17] = "0123456789ABCDEF"; int gs_doit[4]; char tmp_buf[80]; #ifdef CHARSET_EBCDIC @@ -147,8 +146,7 @@ char *X509_NAME_oneline(const X509_NAME *a, char *buf, int len) if ((n < ' ') || (n > '~')) { *(p++) = '\\'; *(p++) = 'x'; - *(p++) = hex[(n >> 4) & 0x0f]; - *(p++) = hex[n & 0x0f]; + p += ossl_to_hex(p, n); } else { if (n == '/' || n == '+') *(p++) = '\\'; @@ -159,8 +157,7 @@ char *X509_NAME_oneline(const X509_NAME *a, char *buf, int len) if ((n < os_toascii[' ']) || (n > os_toascii['~'])) { *(p++) = '\\'; *(p++) = 'x'; - *(p++) = hex[(n >> 4) & 0x0f]; - *(p++) = hex[n & 0x0f]; + p += ossl_to_hex(p, n); } else { if (n == os_toascii['/'] || n == os_toascii['+']) *(p++) = '\\'; diff --git a/crypto/x509/x509_req.c b/crypto/x509/x509_req.c index 74d1d29938..4085b587a5 100644 --- a/crypto/x509/x509_req.c +++ b/crypto/x509/x509_req.c @@ -117,26 +117,19 @@ void X509_REQ_set_extension_nids(int *nids) ext_nids = nids; } -STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req) +static STACK_OF(X509_EXTENSION) *get_extensions_by_nid(const X509_REQ *req, + int nid) { X509_ATTRIBUTE *attr; ASN1_TYPE *ext = NULL; - int idx, *pnid; const unsigned char *p; + int idx = X509_REQ_get_attr_by_NID(req, nid, -1); - if (req == NULL || !ext_nids) - return NULL; - for (pnid = ext_nids; *pnid != NID_undef; pnid++) { - idx = X509_REQ_get_attr_by_NID(req, *pnid, -1); - if (idx < 0) - continue; - attr = X509_REQ_get_attr(req, idx); - ext = X509_ATTRIBUTE_get0_type(attr, 0); - break; - } - if (ext == NULL) /* no extensions is not an error */ + if (idx < 0) /* no extensions is not an error */ return sk_X509_EXTENSION_new_null(); - if (ext->type != V_ASN1_SEQUENCE) { + attr = X509_REQ_get_attr(req, idx); + ext = X509_ATTRIBUTE_get0_type(attr, 0); + if (ext == NULL || ext->type != V_ASN1_SEQUENCE) { ERR_raise(ERR_LIB_X509, X509_R_WRONG_TYPE); return NULL; } @@ -146,6 +139,25 @@ STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req) ASN1_ITEM_rptr(X509_EXTENSIONS)); } +STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(OSSL_FUTURE_CONST X509_REQ *req) +{ + STACK_OF(X509_EXTENSION) *exts = NULL; + int *pnid; + + if (req == NULL || ext_nids == NULL) + return NULL; + for (pnid = ext_nids; *pnid != NID_undef; pnid++) { + exts = get_extensions_by_nid(req, *pnid); + if (exts == NULL) + return NULL; + if (sk_X509_EXTENSION_num(exts) > 0) + return exts; + sk_X509_EXTENSION_free(exts); + } + /* no extensions is not an error */ + return sk_X509_EXTENSION_new_null(); +} + /* * Add a STACK_OF extensions to a certificate request: allow alternative OIDs * in case we want to create a non standard one. @@ -156,14 +168,39 @@ int X509_REQ_add_extensions_nid(X509_REQ *req, int extlen; int rv = 0; unsigned char *ext = NULL; + STACK_OF(X509_EXTENSION) *mod_exts = NULL; + int loc; + + if (sk_X509_EXTENSION_num(exts) <= 0) + return 1; /* adding NULL or empty list of exts is a no-op */ + + loc = X509at_get_attr_by_NID(req->req_info.attributes, nid, -1); + if (loc != -1) { + if ((mod_exts = get_extensions_by_nid(req, nid)) == NULL) + return 0; + if (X509v3_add_extensions(&mod_exts, exts) == NULL) + goto end; + } /* Generate encoding of extensions */ - extlen = ASN1_item_i2d((const ASN1_VALUE *)exts, &ext, - ASN1_ITEM_rptr(X509_EXTENSIONS)); + extlen = ASN1_item_i2d((const ASN1_VALUE *) + (mod_exts == NULL ? exts : mod_exts), + &ext, ASN1_ITEM_rptr(X509_EXTENSIONS)); if (extlen <= 0) - return 0; + goto end; + if (mod_exts != NULL) { + X509_ATTRIBUTE *att = X509at_delete_attr(req->req_info.attributes, loc); + + if (att == NULL) + goto end; + X509_ATTRIBUTE_free(att); + } + rv = X509_REQ_add1_attr_by_NID(req, nid, V_ASN1_SEQUENCE, ext, extlen); OPENSSL_free(ext); + + end: + sk_X509_EXTENSION_pop_free(mod_exts, X509_EXTENSION_free); return rv; } diff --git a/crypto/x509/x509_set.c b/crypto/x509/x509_set.c index 0881be7292..2aba0e8c14 100644 --- a/crypto/x509/x509_set.c +++ b/crypto/x509/x509_set.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -212,7 +212,7 @@ int X509_get_signature_info(X509 *x, int *mdnid, int *pknid, int *secbits, static int x509_sig_info_init(X509_SIG_INFO *siginf, const X509_ALGOR *alg, const ASN1_STRING *sig, const EVP_PKEY *pubkey) { - int pknid, mdnid; + int pknid, mdnid, md_size; const EVP_MD *md; const EVP_PKEY_ASN1_METHOD *ameth; @@ -279,7 +279,10 @@ static int x509_sig_info_init(X509_SIG_INFO *siginf, const X509_ALGOR *alg, ERR_raise(ERR_LIB_X509, X509_R_ERROR_GETTING_MD_BY_NID); return 0; } - siginf->secbits = EVP_MD_get_size(md) * 4; + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + return 0; + siginf->secbits = md_size * 4; break; } switch (mdnid) { diff --git a/crypto/x509/x509_v3.c b/crypto/x509/x509_v3.c index c29856e5b1..50ab8f66ae 100644 --- a/crypto/x509/x509_v3.c +++ b/crypto/x509/x509_v3.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -61,7 +61,7 @@ int X509v3_get_ext_by_OBJ(const STACK_OF(X509_EXTENSION) *sk, int X509v3_get_ext_by_critical(const STACK_OF(X509_EXTENSION) *sk, int crit, int lastpos) { - int n; + int n, c; X509_EXTENSION *ex; if (sk == NULL) @@ -72,7 +72,9 @@ int X509v3_get_ext_by_critical(const STACK_OF(X509_EXTENSION) *sk, int crit, n = sk_X509_EXTENSION_num(sk); for (; lastpos < n; lastpos++) { ex = sk_X509_EXTENSION_value(sk, lastpos); - if (((ex->critical > 0) && crit) || ((ex->critical <= 0) && !crit)) + c = X509_EXTENSION_get_critical(ex); + crit = crit != 0; + if (c == crit) return lastpos; } return -1; @@ -140,6 +142,36 @@ STACK_OF(X509_EXTENSION) *X509v3_add_ext(STACK_OF(X509_EXTENSION) **x, return NULL; } +STACK_OF(X509_EXTENSION) + *X509v3_add_extensions(STACK_OF(X509_EXTENSION) **target, + const STACK_OF(X509_EXTENSION) *exts) +{ + int i; + + if (target == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_PASSED_NULL_PARAMETER); + return NULL; + } + + for (i = 0; i < sk_X509_EXTENSION_num(exts); i++) { + X509_EXTENSION *ext = sk_X509_EXTENSION_value(exts, i); + ASN1_OBJECT *obj = X509_EXTENSION_get_object(ext); + int idx = X509v3_get_ext_by_OBJ(*target, obj, -1); + + /* Does extension exist in target? */ + if (idx != -1) { + /* Delete all extensions of same type */ + do { + X509_EXTENSION_free(sk_X509_EXTENSION_delete(*target, idx)); + idx = X509v3_get_ext_by_OBJ(*target, obj, -1); + } while (idx != -1); + } + if (!X509v3_add_ext(target, ext, -1)) + return NULL; + } + return *target; +} + X509_EXTENSION *X509_EXTENSION_create_by_NID(X509_EXTENSION **ex, int nid, int crit, ASN1_OCTET_STRING *data) @@ -201,7 +233,7 @@ int X509_EXTENSION_set_critical(X509_EXTENSION *ex, int crit) { if (ex == NULL) return 0; - ex->critical = (crit) ? 0xFF : -1; + ex->critical = (crit) ? 0xFF : 0; return 1; } diff --git a/crypto/x509/x509aset.c b/crypto/x509/x509aset.c new file mode 100644 index 0000000000..8200ea4440 --- /dev/null +++ b/crypto/x509/x509aset.c @@ -0,0 +1,177 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include "x509_acert.h" + +static int replace_gentime(ASN1_STRING **dest, const ASN1_GENERALIZEDTIME *src) +{ + ASN1_STRING *s; + + if (src->type != V_ASN1_GENERALIZEDTIME) + return 0; + + if (*dest == src) + return 1; + + s = ASN1_STRING_dup(src); + if (s == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + return 0; + } + + ASN1_STRING_free(*dest); + *dest = s; + + return 1; +} + +static int replace_dirName(GENERAL_NAMES **names, const X509_NAME *dirName) +{ + GENERAL_NAME *gen_name = NULL; + STACK_OF(GENERAL_NAME) *new_names = NULL; + X509_NAME *name_copy; + + if ((name_copy = X509_NAME_dup(dirName)) == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + goto err; + } + + if ((new_names = sk_GENERAL_NAME_new_null()) == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + goto err; + } + + if ((gen_name = GENERAL_NAME_new()) == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + goto err; + } + + if (sk_GENERAL_NAME_push(new_names, gen_name) <= 0) { + ERR_raise(ERR_LIB_X509, ERR_R_CRYPTO_LIB); + goto err; + } + + GENERAL_NAME_set0_value(gen_name, GEN_DIRNAME, name_copy); + + GENERAL_NAMES_free(*names); + *names = new_names; + + return 1; + +err: + GENERAL_NAME_free(gen_name); + sk_GENERAL_NAME_free(new_names); + X509_NAME_free(name_copy); + return 0; +} + +int OSSL_OBJECT_DIGEST_INFO_set1_digest(OSSL_OBJECT_DIGEST_INFO *o, + int digestedObjectType, + X509_ALGOR *digestAlgorithm, + ASN1_BIT_STRING *digest) +{ + + if (ASN1_ENUMERATED_set(&o->digestedObjectType, digestedObjectType) <= 0) + return 0; + + if (X509_ALGOR_copy(&o->digestAlgorithm, digestAlgorithm) <= 0) + return 0; + + if (ASN1_STRING_copy(&o->objectDigest, digest) <= 0) + return 0; + + return 1; +} + +int OSSL_ISSUER_SERIAL_set1_issuer(OSSL_ISSUER_SERIAL *isss, + const X509_NAME *issuer) +{ + return replace_dirName(&isss->issuer, issuer); +} + +int OSSL_ISSUER_SERIAL_set1_serial(OSSL_ISSUER_SERIAL *isss, + const ASN1_INTEGER *serial) +{ + return ASN1_STRING_copy(&isss->serial, serial); +} + +int OSSL_ISSUER_SERIAL_set1_issuerUID(OSSL_ISSUER_SERIAL *isss, + const ASN1_BIT_STRING *uid) +{ + ASN1_BIT_STRING_free(isss->issuerUID); + isss->issuerUID = ASN1_STRING_dup(uid); + if (isss->issuerUID == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + return 0; + } + return 1; +} + +int X509_ACERT_set_version(X509_ACERT *x, long version) +{ + return ASN1_INTEGER_set(&x->acinfo->version, version); +} + +void X509_ACERT_set0_holder_entityName(X509_ACERT *x, GENERAL_NAMES *names) +{ + GENERAL_NAMES_free(x->acinfo->holder.entityName); + x->acinfo->holder.entityName = names; +} + +void X509_ACERT_set0_holder_baseCertId(X509_ACERT *x, + OSSL_ISSUER_SERIAL *isss) +{ + OSSL_ISSUER_SERIAL_free(x->acinfo->holder.baseCertificateID); + x->acinfo->holder.baseCertificateID = isss; +} + +void X509_ACERT_set0_holder_digest(X509_ACERT *x, + OSSL_OBJECT_DIGEST_INFO *dinfo) +{ + OSSL_OBJECT_DIGEST_INFO_free(x->acinfo->holder.objectDigestInfo); + x->acinfo->holder.objectDigestInfo = dinfo; +} + +int X509_ACERT_set1_issuerName(X509_ACERT *x, const X509_NAME *name) +{ + X509_ACERT_ISSUER_V2FORM *v2Form; + + v2Form = x->acinfo->issuer.u.v2Form; + + /* only v2Form is supported, so always create that version */ + if (v2Form == NULL) { + v2Form = X509_ACERT_ISSUER_V2FORM_new(); + if (v2Form == NULL) { + ERR_raise(ERR_LIB_X509, ERR_R_ASN1_LIB); + return 0; + } + x->acinfo->issuer.u.v2Form = v2Form; + x->acinfo->issuer.type = X509_ACERT_ISSUER_V2; + } + + return replace_dirName(&v2Form->issuerName, name); +} + +int X509_ACERT_set1_serialNumber(X509_ACERT *x, const ASN1_INTEGER *serial) +{ + return ASN1_STRING_copy(&x->acinfo->serialNumber, serial); +} + +int X509_ACERT_set1_notBefore(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time) +{ + return replace_gentime(&x->acinfo->validityPeriod.notBefore, time); +} + +int X509_ACERT_set1_notAfter(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time) +{ + return replace_gentime(&x->acinfo->validityPeriod.notAfter, time); +} diff --git a/crypto/x509/x509rset.c b/crypto/x509/x509rset.c index 344993d4c7..1dd61f1f86 100644 --- a/crypto/x509/x509rset.c +++ b/crypto/x509/x509rset.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,8 +17,10 @@ int X509_REQ_set_version(X509_REQ *x, long version) { - if (x == NULL) + if (x == NULL || version != X509_REQ_VERSION_1) { + ERR_raise(ERR_LIB_X509, ERR_R_PASSED_INVALID_ARGUMENT); return 0; + } x->req_info.enc.modified = 1; return ASN1_INTEGER_set(x->req_info.version, version); } diff --git a/crypto/x509/x_all.c b/crypto/x509/x_all.c index 3e4c852b70..d3f79591d7 100644 --- a/crypto/x509/x_all.c +++ b/crypto/x509/x_all.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -19,6 +19,7 @@ #include #include #include +#include #include #include #include @@ -26,6 +27,7 @@ #include "internal/asn1.h" #include "crypto/pkcs7.h" #include "crypto/x509.h" +#include "crypto/x509_acert.h" #include "crypto/rsa.h" int X509_verify(X509 *a, EVP_PKEY *r) @@ -41,6 +43,11 @@ int X509_verify(X509 *a, EVP_PKEY *r) int X509_REQ_verify_ex(X509_REQ *a, EVP_PKEY *r, OSSL_LIB_CTX *libctx, const char *propq) { + if (X509_REQ_get_version(a) != X509_REQ_VERSION_1) { + ERR_raise(ERR_LIB_X509, X509_R_UNSUPPORTED_VERSION); + return -1; + } + return ASN1_item_verify_ex(ASN1_ITEM_rptr(X509_REQ_INFO), &a->sig_alg, a->signature, &a->req_info, a->distinguishing_id, r, libctx, propq); @@ -51,6 +58,16 @@ int X509_REQ_verify(X509_REQ *a, EVP_PKEY *r) return X509_REQ_verify_ex(a, r, NULL, NULL); } +int X509_ACERT_verify(X509_ACERT *a, EVP_PKEY *r) +{ + if (X509_ALGOR_cmp(&a->sig_alg, &a->acinfo->signature) != 0) + return 0; + + return ASN1_item_verify_ex(ASN1_ITEM_rptr(X509_ACERT_INFO), &a->sig_alg, + &a->signature, a->acinfo, + NULL, r, NULL, NULL); +} + int NETSCAPE_SPKI_verify(NETSCAPE_SPKI *a, EVP_PKEY *r) { return ASN1_item_verify(ASN1_ITEM_rptr(NETSCAPE_SPKAC), @@ -99,11 +116,13 @@ static ASN1_VALUE *simple_get_asn1(const char *url, BIO *bio, BIO *rbio, int timeout, const ASN1_ITEM *it) { #ifndef OPENSSL_NO_HTTP + size_t max_resp_len = (it == ASN1_ITEM_rptr(X509_CRL)) ? + OSSL_HTTP_DEFAULT_MAX_CRL_LEN : OSSL_HTTP_DEFAULT_MAX_RESP_LEN; BIO *mem = OSSL_HTTP_get(url, NULL /* proxy */, NULL /* no_proxy */, bio, rbio, NULL /* cb */, NULL /* arg */, 1024 /* buf_size */, NULL /* headers */, NULL /* expected_ct */, 1 /* expect_asn1 */, - OSSL_HTTP_DEFAULT_MAX_RESP_LEN, timeout); + max_resp_len, timeout); ASN1_VALUE *res = ASN1_item_d2i_bio(it, mem, NULL); BIO_free(mem); @@ -173,6 +192,21 @@ X509_CRL *X509_CRL_load_http(const char *url, BIO *bio, BIO *rbio, int timeout) ASN1_ITEM_rptr(X509_CRL)); } +int X509_ACERT_sign(X509_ACERT *x, EVP_PKEY *pkey, const EVP_MD *md) +{ + return ASN1_item_sign_ex(ASN1_ITEM_rptr(X509_ACERT_INFO), &x->sig_alg, + &x->acinfo->signature, + &x->signature, x->acinfo, NULL, + pkey, md, NULL, NULL); +} + +int X509_ACERT_sign_ctx(X509_ACERT *x, EVP_MD_CTX *ctx) +{ + return ASN1_item_sign_ctx(ASN1_ITEM_rptr(X509_ACERT_INFO), + &x->sig_alg, &x->acinfo->signature, &x->signature, + &x->acinfo, ctx); +} + int NETSCAPE_SPKI_sign(NETSCAPE_SPKI *x, EVP_PKEY *pkey, const EVP_MD *md) { return @@ -824,3 +858,25 @@ EVP_PKEY *d2i_PUBKEY_bio(BIO *bp, EVP_PKEY **a) { return ASN1_d2i_bio_of(EVP_PKEY, EVP_PKEY_new, d2i_PUBKEY, bp, a); } + +#ifndef OPENSSL_NO_STDIO +X509_ACERT *d2i_X509_ACERT_fp(FILE *fp, X509_ACERT **acert) +{ + return ASN1_item_d2i_fp(ASN1_ITEM_rptr(X509_ACERT), fp, acert); +} + +int i2d_X509_ACERT_fp(FILE *fp, const X509_ACERT *acert) +{ + return ASN1_item_i2d_fp(ASN1_ITEM_rptr(X509_ACERT), fp, acert); +} +#endif + +X509_ACERT *d2i_X509_ACERT_bio(BIO *bp, X509_ACERT **acert) +{ + return ASN1_item_d2i_bio(ASN1_ITEM_rptr(X509_ACERT), bp, acert); +} + +int i2d_X509_ACERT_bio(BIO *bp, const X509_ACERT *acert) +{ + return ASN1_item_i2d_bio(ASN1_ITEM_rptr(X509_ACERT), bp, acert); +} diff --git a/crypto/x509/x_attrib.c b/crypto/x509/x_attrib.c index 5c7e622d1a..310bef2580 100644 --- a/crypto/x509/x_attrib.c +++ b/crypto/x509/x_attrib.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,6 +13,7 @@ #include #include #include "x509_local.h" +#include /*- * X509_ATTRIBUTE: this has the following form: @@ -56,3 +57,200 @@ X509_ATTRIBUTE *X509_ATTRIBUTE_create(int nid, int atrtype, void *value) ASN1_TYPE_free(val); return NULL; } + +static int print_hex(BIO *out, unsigned char *buf, int len) +{ + int result = 1; + char *hexbuf; + + if (len == 0) + return 1; + + hexbuf = OPENSSL_buf2hexstr(buf, len); + if (hexbuf == NULL) + return 0; + result = BIO_puts(out, hexbuf) > 0; + + OPENSSL_free(hexbuf); + return result; +} + +static int print_oid(BIO *out, const ASN1_OBJECT *oid) { + const char *ln; + char objbuf[80]; + int rc; + + if (OBJ_obj2txt(objbuf, sizeof(objbuf), oid, 1) <= 0) + return 0; + ln = OBJ_nid2ln(OBJ_obj2nid(oid)); + rc = (ln != NULL) + ? BIO_printf(out, "%s (%s)", objbuf, ln) + : BIO_printf(out, "%s", objbuf); + return (rc >= 0); +} + +int ossl_print_attribute_value(BIO *out, + int obj_nid, + const ASN1_TYPE *av, + int indent) +{ + ASN1_STRING *str; + unsigned char *value; + X509_NAME *xn = NULL; + int64_t int_val; + int ret = 1; + + switch (av->type) { + case V_ASN1_BOOLEAN: + if (av->value.boolean) { + return BIO_printf(out, "%*sTRUE", indent, "") >= 4; + } else { + return BIO_printf(out, "%*sFALSE", indent, "") >= 5; + } + + case V_ASN1_INTEGER: + case V_ASN1_ENUMERATED: + if (BIO_printf(out, "%*s", indent, "") < 0) + return 0; + if (ASN1_ENUMERATED_get_int64(&int_val, av->value.integer) > 0) { + return BIO_printf(out, "%lld", (long long int)int_val) > 0; + } + str = av->value.integer; + return print_hex(out, str->data, str->length); + + case V_ASN1_BIT_STRING: + if (BIO_printf(out, "%*s", indent, "") < 0) + return 0; + return print_hex(out, av->value.bit_string->data, + av->value.bit_string->length); + + case V_ASN1_OCTET_STRING: + case V_ASN1_VIDEOTEXSTRING: + if (BIO_printf(out, "%*s", indent, "") < 0) + return 0; + return print_hex(out, av->value.octet_string->data, + av->value.octet_string->length); + + case V_ASN1_NULL: + return BIO_printf(out, "%*sNULL", indent, "") >= 4; + + case V_ASN1_OBJECT: + if (BIO_printf(out, "%*s", indent, "") < 0) + return 0; + return print_oid(out, av->value.object); + + /* + * ObjectDescriptor is an IMPLICIT GraphicString, but GeneralString is a + * superset supported by OpenSSL, so we will use that anywhere a + * GraphicString is needed here. + */ + case V_ASN1_GENERALSTRING: + case V_ASN1_GRAPHICSTRING: + case V_ASN1_OBJECT_DESCRIPTOR: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.generalstring->length, + av->value.generalstring->data) >= 0; + + /* EXTERNAL would go here. */ + /* EMBEDDED PDV would go here. */ + + case V_ASN1_UTF8STRING: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.utf8string->length, + av->value.utf8string->data) >= 0; + + case V_ASN1_REAL: + return BIO_printf(out, "%*sREAL", indent, "") >= 4; + + /* RELATIVE-OID would go here. */ + /* TIME would go here. */ + + case V_ASN1_SEQUENCE: + switch (obj_nid) { + case NID_undef: /* Unrecognized OID. */ + break; + /* Attribute types with DN syntax. */ + case NID_member: + case NID_roleOccupant: + case NID_seeAlso: + case NID_manager: + case NID_documentAuthor: + case NID_secretary: + case NID_associatedName: + case NID_dITRedirect: + case NID_owner: + /* + * d2i_ functions increment the ppin pointer. See doc/man3/d2i_X509.pod. + * This preserves the original pointer. We don't want to corrupt this + * value. + */ + value = av->value.sequence->data; + xn = d2i_X509_NAME(NULL, + (const unsigned char **)&value, + av->value.sequence->length); + if (xn == NULL) { + BIO_puts(out, "(COULD NOT DECODE DISTINGUISHED NAME)\n"); + return 0; + } + if (X509_NAME_print_ex(out, xn, indent, XN_FLAG_SEP_CPLUS_SPC) <= 0) + ret = 0; + X509_NAME_free(xn); + return ret; + + default: + break; + } + return ASN1_parse_dump(out, av->value.sequence->data, + av->value.sequence->length, indent, 1) > 0; + + case V_ASN1_SET: + return ASN1_parse_dump(out, av->value.set->data, + av->value.set->length, indent, 1) > 0; + + /* + * UTCTime ::= [UNIVERSAL 23] IMPLICIT VisibleString + * GeneralizedTime ::= [UNIVERSAL 24] IMPLICIT VisibleString + * VisibleString is a superset for NumericString, so it will work for that. + */ + case V_ASN1_VISIBLESTRING: + case V_ASN1_UTCTIME: + case V_ASN1_GENERALIZEDTIME: + case V_ASN1_NUMERICSTRING: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.visiblestring->length, + av->value.visiblestring->data) >= 0; + + case V_ASN1_PRINTABLESTRING: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.printablestring->length, + av->value.printablestring->data) >= 0; + + case V_ASN1_T61STRING: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.t61string->length, + av->value.t61string->data) >= 0; + + case V_ASN1_IA5STRING: + return BIO_printf(out, "%*s%.*s", indent, "", + av->value.ia5string->length, + av->value.ia5string->data) >= 0; + + /* UniversalString would go here. */ + /* CHARACTER STRING would go here. */ + /* BMPString would go here. */ + /* DATE would go here. */ + /* TIME-OF-DAY would go here. */ + /* DATE-TIME would go here. */ + /* DURATION would go here. */ + /* OID-IRI would go here. */ + /* RELATIVE-OID-IRI would go here. */ + + /* Would it be appropriate to just hexdump? */ + default: + return BIO_printf(out, + "%*s", + indent, + "", + av->type) >= 0; + } +} diff --git a/crypto/x509/x_exten.c b/crypto/x509/x_exten.c index 4e63b50caa..f4be4dd0d6 100644 --- a/crypto/x509/x_exten.c +++ b/crypto/x509/x_exten.c @@ -1,5 +1,5 @@ /* - * Copyright 2000-2016 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2000-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -15,7 +15,7 @@ ASN1_SEQUENCE(X509_EXTENSION) = { ASN1_SIMPLE(X509_EXTENSION, object, ASN1_OBJECT), - ASN1_OPT(X509_EXTENSION, critical, ASN1_BOOLEAN), + ASN1_OPT(X509_EXTENSION, critical, ASN1_FBOOLEAN), ASN1_EMBED(X509_EXTENSION, value, ASN1_OCTET_STRING) } ASN1_SEQUENCE_END(X509_EXTENSION) diff --git a/crypto/x509/x_ietfatt.c b/crypto/x509/x_ietfatt.c new file mode 100644 index 0000000000..dd1c0ab347 --- /dev/null +++ b/crypto/x509/x_ietfatt.c @@ -0,0 +1,241 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include + +/*- + * Definition of IetfAttrSyntax from RFC 5755 4.4 + * + * IetfAttrSyntax ::= SEQUENCE { + * policyAuthority [0] GeneralNames OPTIONAL, + * values SEQUENCE OF CHOICE { + * octets OCTET STRING, + * oid OBJECT IDENTIFIER, + * string UTF8String + * } + * } + * + * Section 4.4.2 states that all values in the sequence MUST use the + * same choice of value (octet, oid or string). + */ + +struct OSSL_IETF_ATTR_SYNTAX_VALUE_st { + int type; + union { + ASN1_OCTET_STRING *octets; + ASN1_OBJECT *oid; + ASN1_UTF8STRING *string; + } u; +}; + +struct OSSL_IETF_ATTR_SYNTAX_st { + GENERAL_NAMES *policyAuthority; + int type; + STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *values; +}; + +ASN1_CHOICE(OSSL_IETF_ATTR_SYNTAX_VALUE) = { + ASN1_SIMPLE(OSSL_IETF_ATTR_SYNTAX_VALUE, u.octets, ASN1_OCTET_STRING), + ASN1_SIMPLE(OSSL_IETF_ATTR_SYNTAX_VALUE, u.oid, ASN1_OBJECT), + ASN1_SIMPLE(OSSL_IETF_ATTR_SYNTAX_VALUE, u.string, ASN1_UTF8STRING), +} ASN1_CHOICE_END(OSSL_IETF_ATTR_SYNTAX_VALUE) + +ASN1_SEQUENCE(OSSL_IETF_ATTR_SYNTAX) = { + ASN1_IMP_SEQUENCE_OF_OPT(OSSL_IETF_ATTR_SYNTAX, policyAuthority, GENERAL_NAME, 0), + ASN1_SEQUENCE_OF(OSSL_IETF_ATTR_SYNTAX, values, OSSL_IETF_ATTR_SYNTAX_VALUE), +} ASN1_SEQUENCE_END(OSSL_IETF_ATTR_SYNTAX) + +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX) +IMPLEMENT_ASN1_ALLOC_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX_VALUE) + +OSSL_IETF_ATTR_SYNTAX *d2i_OSSL_IETF_ATTR_SYNTAX (OSSL_IETF_ATTR_SYNTAX **a, + const unsigned char **in, + long len) +{ + OSSL_IETF_ATTR_SYNTAX *ias; + int i; + + ias = (OSSL_IETF_ATTR_SYNTAX *) ASN1_item_d2i((ASN1_VALUE **)a, in, len, + OSSL_IETF_ATTR_SYNTAX_it()); + if (ias == NULL) + return ias; + + for (i = 0; i < sk_OSSL_IETF_ATTR_SYNTAX_VALUE_num(ias->values); i++) + { + OSSL_IETF_ATTR_SYNTAX_VALUE *val; + + val = sk_OSSL_IETF_ATTR_SYNTAX_VALUE_value(ias->values, i); + if (i == 0) + ias->type = val->type; + else if (val->type != ias->type) + goto invalid_types; + } + + return ias; + +invalid_types: + OSSL_IETF_ATTR_SYNTAX_free(ias); + if (a) + *a = NULL; + ERR_raise(ERR_LIB_X509V3, ERR_R_PASSED_INVALID_ARGUMENT); + return NULL; +} + +int i2d_OSSL_IETF_ATTR_SYNTAX (const OSSL_IETF_ATTR_SYNTAX *a, + unsigned char **out) +{ + return ASN1_item_i2d((const ASN1_VALUE *)a, out, OSSL_IETF_ATTR_SYNTAX_it()); +} + +int OSSL_IETF_ATTR_SYNTAX_get_value_num(const OSSL_IETF_ATTR_SYNTAX *a) +{ + if (a->values == NULL) + return 0; + + return sk_OSSL_IETF_ATTR_SYNTAX_VALUE_num(a->values); +} + +const GENERAL_NAMES * +OSSL_IETF_ATTR_SYNTAX_get0_policyAuthority(const OSSL_IETF_ATTR_SYNTAX *a) +{ + return a->policyAuthority; +} + +void OSSL_IETF_ATTR_SYNTAX_set0_policyAuthority(OSSL_IETF_ATTR_SYNTAX *a, + GENERAL_NAMES *names) +{ + GENERAL_NAMES_free(a->policyAuthority); + a->policyAuthority = names; +} + +void *OSSL_IETF_ATTR_SYNTAX_get0_value(const OSSL_IETF_ATTR_SYNTAX *a, + int ind, int *type) +{ + OSSL_IETF_ATTR_SYNTAX_VALUE *val; + + val = sk_OSSL_IETF_ATTR_SYNTAX_VALUE_value(a->values, ind); + if (val == NULL) + return NULL; + + if (type != NULL) + *type = val->type; + + switch (val->type) { + case OSSL_IETFAS_OCTETS: + return val->u.octets; + case OSSL_IETFAS_OID: + return val->u.oid; + case OSSL_IETFAS_STRING: + return val->u.string; + } + + return NULL; +} + +int OSSL_IETF_ATTR_SYNTAX_add1_value(OSSL_IETF_ATTR_SYNTAX *a, int type, + void *data) +{ + OSSL_IETF_ATTR_SYNTAX_VALUE *val; + + if (data == NULL) + return 0; + + if (a->values == NULL) { + if ((a->values = sk_OSSL_IETF_ATTR_SYNTAX_VALUE_new_null()) == NULL) + goto err; + a->type = type; + } + + if (type != a->type) { + ERR_raise(ERR_LIB_X509V3, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + + if ((val = OSSL_IETF_ATTR_SYNTAX_VALUE_new()) == NULL) + goto err; + + val->type = type; + switch (type) { + case OSSL_IETFAS_OCTETS: + val->u.octets = data; + break; + case OSSL_IETFAS_OID: + val->u.oid = data; + break; + case OSSL_IETFAS_STRING: + val->u.string = data; + break; + default: + OSSL_IETF_ATTR_SYNTAX_VALUE_free(val); + ERR_raise(ERR_LIB_X509V3, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + + if (sk_OSSL_IETF_ATTR_SYNTAX_VALUE_push(a->values, val) <= 0) { + OSSL_IETF_ATTR_SYNTAX_VALUE_free(val); + return 0; + } + + return 1; + +err: + ERR_raise(ERR_LIB_X509V3, ERR_R_CRYPTO_LIB); + return 0; +} + +int OSSL_IETF_ATTR_SYNTAX_print(BIO *bp, OSSL_IETF_ATTR_SYNTAX *a, int indent) +{ + int i; + + if (a->policyAuthority != NULL) { + for (i = 0; i < sk_GENERAL_NAME_num(a->policyAuthority); i++) { + if (BIO_printf(bp, "%*s", indent, "") <= 0) + goto err; + + if (GENERAL_NAME_print(bp, sk_GENERAL_NAME_value(a->policyAuthority, + i)) <= 0) + goto err; + + if (BIO_printf(bp, "\n") <= 0) + goto err; + } + } + + for (i = 0; i < OSSL_IETF_ATTR_SYNTAX_get_value_num(a); i++) { + char oidstr[80]; + int ietf_type; + void *attr_value = OSSL_IETF_ATTR_SYNTAX_get0_value(a, i, &ietf_type); + + if (attr_value == NULL) + goto err; + + if (BIO_printf(bp, "%*s", indent, "") <= 0) + goto err; + + switch (ietf_type) { + case OSSL_IETFAS_OID: + OBJ_obj2txt(oidstr, sizeof(oidstr), attr_value, 0); + BIO_printf(bp, "%.*s", (int) sizeof(oidstr), oidstr); + break; + case OSSL_IETFAS_OCTETS: + case OSSL_IETFAS_STRING: + ASN1_STRING_print(bp, attr_value); + break; + } + } + if (BIO_printf(bp, "\n") <= 0) + goto err; + + return 1; + +err: + return 0; +} diff --git a/crypto/x509/x_pubkey.c b/crypto/x509/x_pubkey.c index 004c7bdfeb..53639b2bfa 100644 --- a/crypto/x509/x_pubkey.c +++ b/crypto/x509/x_pubkey.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -1004,7 +1004,7 @@ int ossl_i2d_X448_PUBKEY(const ECX_KEY *a, unsigned char **pp) return ret; } -# endif /* OPENSSL_NO_ECX */ +# endif /* OPENSSL_NO_ECX */ #endif void X509_PUBKEY_set0_public_key(X509_PUBKEY *pub, diff --git a/import_openssl.sh b/import_openssl.sh index a8faedc157..47cf51dfa7 100755 --- a/import_openssl.sh +++ b/import_openssl.sh @@ -263,6 +263,7 @@ function generate_build_config_headers() { make include/openssl/asn1.h include/openssl/asn1t.h include/openssl/bio.h include/openssl/cmp.h include/openssl/cms.h include/openssl/conf.h include/openssl/configuration.h include/openssl/crmf.h include/openssl/crypto.h include/openssl/ct.h include/openssl/err.h include/openssl/ess.h make include/openssl/fipskey.h include/openssl/ocsp.h include/openssl/opensslv.h include/openssl/pkcs12.h include/openssl/pkcs7.h include/openssl/safestack.h include/openssl/srp.h include/openssl/ssl.h include/openssl/ui.h include/openssl/x509.h include/openssl/x509_vfy.h include/openssl/x509v3.h make include/openssl/core_names.h include/internal/param_names.h crypto/params_idx.c + make include/openssl/comp.h include/openssl/x509_acert.h rm -f apps/CA.pl.bak openssl/opensslconf.h.bak mv -f include/crypto/bn_conf.h include/crypto/bn_conf-$outname.h diff --git a/include/crypto/asn1.h b/include/crypto/asn1.h index 36af1d7689..8461c1be8d 100644 --- a/include/crypto/asn1.h +++ b/include/crypto/asn1.h @@ -1,5 +1,5 @@ /* - * Copyright 2015-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -92,7 +92,7 @@ DEFINE_STACK_OF_CONST(EVP_PKEY_ASN1_METHOD) extern const EVP_PKEY_ASN1_METHOD ossl_dh_asn1_meth; extern const EVP_PKEY_ASN1_METHOD ossl_dhx_asn1_meth; -extern const EVP_PKEY_ASN1_METHOD ossl_dsa_asn1_meths[5]; +extern const EVP_PKEY_ASN1_METHOD ossl_dsa_asn1_meths[4]; extern const EVP_PKEY_ASN1_METHOD ossl_eckey_asn1_meth; extern const EVP_PKEY_ASN1_METHOD ossl_ecx25519_asn1_meth; extern const EVP_PKEY_ASN1_METHOD ossl_ecx448_asn1_meth; @@ -147,7 +147,6 @@ EVP_PKEY *ossl_d2i_PrivateKey_legacy(int keytype, EVP_PKEY **a, OSSL_LIB_CTX *libctx, const char *propq); X509_ALGOR *ossl_X509_ALGOR_from_nid(int nid, int ptype, void *pval); -time_t ossl_asn1_string_to_time_t(const char *asn1_string); void ossl_asn1_string_set_bits_left(ASN1_STRING *str, unsigned int num); #endif /* ndef OSSL_CRYPTO_ASN1_H */ diff --git a/include/crypto/bn.h b/include/crypto/bn.h index 302f031c2f..47d9b44f87 100644 --- a/include/crypto/bn.h +++ b/include/crypto/bn.h @@ -135,3 +135,9 @@ int s390x_crt(BIGNUM *r, const BIGNUM *i, const BIGNUM *p, const BIGNUM *q, const BIGNUM *dmp, const BIGNUM *dmq, const BIGNUM *iqmp); #endif + +int ossl_bn_mont_ctx_set(BN_MONT_CTX *ctx, const BIGNUM *modulus, int ri, + const unsigned char *rr, size_t rrlen, + uint32_t nlo, uint32_t nhi); + +int ossl_bn_mont_ctx_eq(const BN_MONT_CTX *m1, const BN_MONT_CTX *m2); diff --git a/include/crypto/cmac.h b/include/crypto/cmac.h new file mode 100644 index 0000000000..df55b68f8b --- /dev/null +++ b/include/crypto/cmac.h @@ -0,0 +1,22 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OSSL_CRYPTO_CMAC_H +# define OSSL_CRYPTO_CMAC_H +# pragma once + +# include +# include +# include + +int ossl_cmac_init(CMAC_CTX *ctx, const void *key, size_t keylen, + const EVP_CIPHER *cipher, ENGINE *impl, + const OSSL_PARAM param[]); + +#endif /* OSSL_CRYPTO_CMAC_H */ diff --git a/include/crypto/context.h b/include/crypto/context.h index 7369a730fb..1c181933e0 100644 --- a/include/crypto/context.h +++ b/include/crypto/context.h @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -20,6 +20,7 @@ void *ossl_bio_core_globals_new(OSSL_LIB_CTX *); void *ossl_child_prov_ctx_new(OSSL_LIB_CTX *); void *ossl_prov_drbg_nonce_ctx_new(OSSL_LIB_CTX *); void *ossl_self_test_set_callback_new(OSSL_LIB_CTX *); +void *ossl_indicator_set_callback_new(OSSL_LIB_CTX *); void *ossl_rand_crng_ctx_new(OSSL_LIB_CTX *); int ossl_thread_register_fips(OSSL_LIB_CTX *); void *ossl_thread_event_ctx_new(OSSL_LIB_CTX *); @@ -38,6 +39,7 @@ void ossl_prov_conf_ctx_free(void *); void ossl_bio_core_globals_free(void *); void ossl_child_prov_ctx_free(void *); void ossl_prov_drbg_nonce_ctx_free(void *); +void ossl_indicator_set_callback_free(void *cb); void ossl_self_test_set_callback_free(void *); void ossl_rand_crng_ctx_free(void *); void ossl_thread_event_ctx_free(void *); diff --git a/include/crypto/cryptoerr.h b/include/crypto/cryptoerr.h index 1b6192e3f0..d7df9a2c02 100644 --- a/include/crypto/cryptoerr.h +++ b/include/crypto/cryptoerr.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 2020-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy diff --git a/include/crypto/ecx.h b/include/crypto/ecx.h index f35b875fb6..0e8828e546 100644 --- a/include/crypto/ecx.h +++ b/include/crypto/ecx.h @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -108,6 +108,8 @@ ossl_ed25519_verify(const uint8_t *tbs, size_t tbs_len, const uint8_t *context, size_t context_len, OSSL_LIB_CTX *libctx, const char *propq); int +ossl_ed25519_pubkey_verify(const uint8_t *pub, size_t pub_len); +int ossl_ed448_public_from_private(OSSL_LIB_CTX *ctx, uint8_t out_public_key[57], const uint8_t private_key[57], const char *propq); int @@ -124,6 +126,9 @@ ossl_ed448_verify(OSSL_LIB_CTX *ctx, const uint8_t *context, size_t context_len, const uint8_t phflag, const char *propq); +int +ossl_ed448_pubkey_verify(const uint8_t *pub, size_t pub_len); + int ossl_x448(uint8_t out_shared_key[56], const uint8_t private_key[56], const uint8_t peer_public_value[56]); diff --git a/include/crypto/evp.h b/include/crypto/evp.h index 50ad737fc8..72d9995e8f 100644 --- a/include/crypto/evp.h +++ b/include/crypto/evp.h @@ -396,13 +396,12 @@ static int cname##_ecb_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, const uns #define BLOCK_CIPHER_func_cbc(cname, cprefix, kstruct, ksched) \ static int cname##_cbc_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, const unsigned char *in, size_t inl) \ {\ - while(inl>=EVP_MAXCHUNK) \ - {\ + while(inl>=EVP_MAXCHUNK) {\ cprefix##_cbc_encrypt(in, out, (long)EVP_MAXCHUNK, &EVP_C_DATA(kstruct,ctx)->ksched, ctx->iv, EVP_CIPHER_CTX_is_encrypting(ctx));\ inl-=EVP_MAXCHUNK;\ in +=EVP_MAXCHUNK;\ out+=EVP_MAXCHUNK;\ - }\ + }\ if (inl)\ cprefix##_cbc_encrypt(in, out, (long)inl, &EVP_C_DATA(kstruct,ctx)->ksched, ctx->iv, EVP_CIPHER_CTX_is_encrypting(ctx));\ return 1;\ @@ -414,8 +413,7 @@ static int cname##_cfb##cbits##_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out, size_t chunk = EVP_MAXCHUNK;\ if (cbits == 1) chunk >>= 3;\ if (inl < chunk) chunk = inl;\ - while (inl && inl >= chunk)\ - {\ + while (inl && inl >= chunk) {\ int num = EVP_CIPHER_CTX_get_num(ctx);\ cprefix##_cfb##cbits##_encrypt(in, out, (long) \ ((cbits == 1) \ @@ -726,32 +724,27 @@ struct evp_pkey_st { int security_bits; int size; } cache; -} /* EVP_PKEY */ ; +}; /* EVP_PKEY */ -#define EVP_PKEY_CTX_IS_SIGNATURE_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_SIGN \ - || (ctx)->operation == EVP_PKEY_OP_SIGNCTX \ - || (ctx)->operation == EVP_PKEY_OP_VERIFY \ - || (ctx)->operation == EVP_PKEY_OP_VERIFYCTX \ - || (ctx)->operation == EVP_PKEY_OP_VERIFYRECOVER) +/* The EVP_PKEY_OP_TYPE_ macros are found in include/openssl/evp.h */ -#define EVP_PKEY_CTX_IS_DERIVE_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_DERIVE) +# define EVP_PKEY_CTX_IS_SIGNATURE_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_SIG) != 0) -#define EVP_PKEY_CTX_IS_ASYM_CIPHER_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_ENCRYPT \ - || (ctx)->operation == EVP_PKEY_OP_DECRYPT) +# define EVP_PKEY_CTX_IS_DERIVE_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_DERIVE) != 0) -#define EVP_PKEY_CTX_IS_GEN_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_PARAMGEN \ - || (ctx)->operation == EVP_PKEY_OP_KEYGEN) +# define EVP_PKEY_CTX_IS_ASYM_CIPHER_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_CRYPT) != 0) -#define EVP_PKEY_CTX_IS_FROMDATA_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_FROMDATA) +# define EVP_PKEY_CTX_IS_GEN_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_GEN) != 0) -#define EVP_PKEY_CTX_IS_KEM_OP(ctx) \ - ((ctx)->operation == EVP_PKEY_OP_ENCAPSULATE \ - || (ctx)->operation == EVP_PKEY_OP_DECAPSULATE) +# define EVP_PKEY_CTX_IS_FROMDATA_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_DATA) != 0) + +# define EVP_PKEY_CTX_IS_KEM_OP(ctx) \ + (((ctx)->operation & EVP_PKEY_OP_TYPE_KEM) != 0) void openssl_add_all_ciphers_int(void); void openssl_add_all_digests_int(void); @@ -825,6 +818,8 @@ int evp_keymgmt_gen_set_template(const EVP_KEYMGMT *keymgmt, void *genctx, void *templ); int evp_keymgmt_gen_set_params(const EVP_KEYMGMT *keymgmt, void *genctx, const OSSL_PARAM params[]); +int evp_keymgmt_gen_get_params(const EVP_KEYMGMT *keymgmt, + void *genctx, OSSL_PARAM params[]); void *evp_keymgmt_gen(const EVP_KEYMGMT *keymgmt, void *genctx, OSSL_CALLBACK *cb, void *cbarg); void evp_keymgmt_gen_cleanup(const EVP_KEYMGMT *keymgmt, void *genctx); @@ -969,4 +964,7 @@ int evp_pkey_decrypt_alloc(EVP_PKEY_CTX *ctx, unsigned char **outp, size_t *outlenp, size_t expected_outlen, const unsigned char *in, size_t inlen); +int ossl_md2hmacnid(int mdnid); +int ossl_hmac2mdnid(int hmac_nid); + #endif /* OSSL_CRYPTO_EVP_H */ diff --git a/include/crypto/riscv_arch.def b/include/crypto/riscv_arch.def index 70b0647ae2..32147d0939 100644 --- a/include/crypto/riscv_arch.def +++ b/include/crypto/riscv_arch.def @@ -1,5 +1,5 @@ /* - * Copyright 2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,37 +16,45 @@ * second argument as the index in the array where the capability will be stored * and third argument as the index of the bit to be used to encode the * capability. - * RISCV_DEFINE_CAP(EXTENSION NAME, array index, bit index) */ + * + * The fourth and the fifth arguments are copied from linux header asm/hwprobe.h. + * Directly coping values instead of macro names comes from the fact + * that an old version may lack definition of some macro. + * When there is no hwprobe key/value pair for a capability, the key is set to -1 + * and the value is set to 0, as when the hwprobe syscall returns a key of -1, + * the value is set to 0 and the corresponding capability would not be enabled. + * + * RISCV_DEFINE_CAP(EXTENSION NAME, array index, bit index, hwprobe key, hwprobe value) */ -RISCV_DEFINE_CAP(ZBA, 0, 0) -RISCV_DEFINE_CAP(ZBB, 0, 1) -RISCV_DEFINE_CAP(ZBC, 0, 2) -RISCV_DEFINE_CAP(ZBS, 0, 3) -RISCV_DEFINE_CAP(ZBKB, 0, 4) -RISCV_DEFINE_CAP(ZBKC, 0, 5) -RISCV_DEFINE_CAP(ZBKX, 0, 6) -RISCV_DEFINE_CAP(ZKND, 0, 7) -RISCV_DEFINE_CAP(ZKNE, 0, 8) -RISCV_DEFINE_CAP(ZKNH, 0, 9) -RISCV_DEFINE_CAP(ZKSED, 0, 10) -RISCV_DEFINE_CAP(ZKSH, 0, 11) -RISCV_DEFINE_CAP(ZKR, 0, 12) -RISCV_DEFINE_CAP(ZKT, 0, 13) -RISCV_DEFINE_CAP(V, 0, 14) -RISCV_DEFINE_CAP(ZVBB, 0, 15) -RISCV_DEFINE_CAP(ZVBC, 0, 16) -RISCV_DEFINE_CAP(ZVKB, 0, 17) -RISCV_DEFINE_CAP(ZVKG, 0, 18) -RISCV_DEFINE_CAP(ZVKNED, 0, 19) -RISCV_DEFINE_CAP(ZVKNHA, 0, 20) -RISCV_DEFINE_CAP(ZVKNHB, 0, 21) -RISCV_DEFINE_CAP(ZVKSED, 0, 22) -RISCV_DEFINE_CAP(ZVKSH, 0, 23) +RISCV_DEFINE_CAP(ZBA, 0, 0, 4, (1 << 3)) +RISCV_DEFINE_CAP(ZBB, 0, 1, 4, (1 << 4)) +RISCV_DEFINE_CAP(ZBC, 0, 2, 4, (1 << 7)) +RISCV_DEFINE_CAP(ZBS, 0, 3, 4, (1 << 5)) +RISCV_DEFINE_CAP(ZBKB, 0, 4, 4, (1 << 8)) +RISCV_DEFINE_CAP(ZBKC, 0, 5, 4, (1 << 9)) +RISCV_DEFINE_CAP(ZBKX, 0, 6, 4, (1 << 10)) +RISCV_DEFINE_CAP(ZKND, 0, 7, 4, (1 << 11)) +RISCV_DEFINE_CAP(ZKNE, 0, 8, 4, (1 << 12)) +RISCV_DEFINE_CAP(ZKNH, 0, 9, 4, (1 << 13)) +RISCV_DEFINE_CAP(ZKSED, 0, 10, 4, (1 << 14)) +RISCV_DEFINE_CAP(ZKSH, 0, 11, 4, (1 << 15)) +RISCV_DEFINE_CAP(ZKR, 0, 12, -1, 0) +RISCV_DEFINE_CAP(ZKT, 0, 13, 4, (1 << 16)) +RISCV_DEFINE_CAP(V, 0, 14, 4, (1 << 2)) +RISCV_DEFINE_CAP(ZVBB, 0, 15, 4, (1 << 17)) +RISCV_DEFINE_CAP(ZVBC, 0, 16, 4, (1 << 18)) +RISCV_DEFINE_CAP(ZVKB, 0, 17, 4, (1 << 19)) +RISCV_DEFINE_CAP(ZVKG, 0, 18, 4, (1 << 20)) +RISCV_DEFINE_CAP(ZVKNED, 0, 19, 4, (1 << 21)) +RISCV_DEFINE_CAP(ZVKNHA, 0, 20, 4, (1 << 22)) +RISCV_DEFINE_CAP(ZVKNHB, 0, 21, 4, (1 << 23)) +RISCV_DEFINE_CAP(ZVKSED, 0, 22, 4, (1 << 24)) +RISCV_DEFINE_CAP(ZVKSH, 0, 23, 4, (1 << 25)) /* * In the future ... - * RISCV_DEFINE_CAP(ZFOO, 0, 31) - * RISCV_DEFINE_CAP(ZBAR, 1, 0) + * RISCV_DEFINE_CAP(ZFOO, 0, 31, ..., ...) + * RISCV_DEFINE_CAP(ZBAR, 1, 0, ..., ...) * ... and so on. */ diff --git a/include/crypto/riscv_arch.h b/include/crypto/riscv_arch.h index 6950137f45..4b3573f5a3 100644 --- a/include/crypto/riscv_arch.h +++ b/include/crypto/riscv_arch.h @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,19 +13,28 @@ # include # include -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) +1 +# if defined(OPENSSL_SYS_LINUX) && !defined(FIPS_MODULE) +# if __has_include() +# define OSSL_RISCV_HWPROBE +# endif +# endif + +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) +1 extern uint32_t OPENSSL_riscvcap_P[ (( # include "riscv_arch.def" ) + sizeof(uint32_t) - 1) / sizeof(uint32_t) ]; # ifdef OPENSSL_RISCVCAP_IMPL -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) +1 +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) +1 uint32_t OPENSSL_riscvcap_P[ (( # include "riscv_arch.def" ) + sizeof(uint32_t) - 1) / sizeof(uint32_t) ]; # endif -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) \ +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) \ static inline int RISCV_HAS_##NAME(void) \ { \ return (OPENSSL_riscvcap_P[INDEX] & (1 << BIT_INDEX)) != 0; \ @@ -36,26 +45,50 @@ struct RISCV_capability_s { const char *name; size_t index; size_t bit_offset; +# ifdef OSSL_RISCV_HWPROBE + int32_t hwprobe_key; + uint64_t hwprobe_value; +# endif }; -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) +1 +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + OSSL_RISCV_HWPROBE_KEY, OSSL_RISCV_HWPROBE_VALUE) +1 extern const struct RISCV_capability_s RISCV_capabilities[ # include "riscv_arch.def" ]; # ifdef OPENSSL_RISCVCAP_IMPL -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) \ +# ifdef OSSL_RISCV_HWPROBE +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) \ + { #NAME, INDEX, BIT_INDEX, HWPROBE_KEY, HWPROBE_VALUE }, +# else +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) \ { #NAME, INDEX, BIT_INDEX }, +# endif const struct RISCV_capability_s RISCV_capabilities[] = { # include "riscv_arch.def" }; # endif -# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX) +1 +# define RISCV_DEFINE_CAP(NAME, INDEX, BIT_INDEX, \ + HWPROBE_KEY, HWPROBE_VALUE) +1 static const size_t kRISCVNumCaps = # include "riscv_arch.def" ; +# ifdef OSSL_RISCV_HWPROBE +/* + * Content is an array of { hwprobe_key, 0 } where + * hwprobe_key is copied from asm/hwprobe.h. + * It should be updated along with riscv_arch.def. + */ +# define OSSL_RISCV_HWPROBE_PAIR_COUNT 1 +# define OSSL_RISCV_HWPROBE_PAIR_CONTENT \ + { 4, 0 }, +# endif + /* Extension combination tests. */ #define RISCV_HAS_ZBB_AND_ZBC() (RISCV_HAS_ZBB() && RISCV_HAS_ZBC()) #define RISCV_HAS_ZBKB_AND_ZKND_AND_ZKNE() (RISCV_HAS_ZBKB() && RISCV_HAS_ZKND() && RISCV_HAS_ZKNE()) diff --git a/include/crypto/rsa.h b/include/crypto/rsa.h index 592efdb7fc..dcb465cbca 100644 --- a/include/crypto/rsa.h +++ b/include/crypto/rsa.h @@ -46,6 +46,14 @@ int ossl_rsa_pss_params_30_maskgenhashalg(const RSA_PSS_PARAMS_30 *rsa_pss_param int ossl_rsa_pss_params_30_saltlen(const RSA_PSS_PARAMS_30 *rsa_pss_params); int ossl_rsa_pss_params_30_trailerfield(const RSA_PSS_PARAMS_30 *rsa_pss_params); +int ossl_rsa_verify_PKCS1_PSS_mgf1(RSA *rsa, const unsigned char *mHash, + const EVP_MD *Hash, const EVP_MD *mgf1Hash, + const unsigned char *EM, int *sLenOut); +int ossl_rsa_padding_add_PKCS1_PSS_mgf1(RSA *rsa, unsigned char *EM, + const unsigned char *mHash, + const EVP_MD *Hash, const EVP_MD *mgf1Hash, + int *sLenOut); + const char *ossl_rsa_mgf_nid2name(int mgf); int ossl_rsa_oaeppss_md2nid(const EVP_MD *md); const char *ossl_rsa_oaeppss_nid2name(int md); @@ -127,6 +135,7 @@ void ossl_rsa_acvp_test_free(RSA_ACVP_TEST *t); # else # define RSA_ACVP_TEST void # endif +int ossl_rsa_check_factors(RSA *r); RSA *evp_pkey_get1_RSA_PSS(EVP_PKEY *pkey); #endif diff --git a/include/crypto/x509.h b/include/crypto/x509.h index 18eb2f7c63..338e58b491 100644 --- a/include/crypto/x509.h +++ b/include/crypto/x509.h @@ -373,7 +373,7 @@ int x509v3_add_len_value_uchar(const char *name, const unsigned char *value, size_t vallen, STACK_OF(CONF_VALUE) **extlist); /* Attribute addition functions not checking for duplicate attributes */ STACK_OF(X509_ATTRIBUTE) *ossl_x509at_add1_attr(STACK_OF(X509_ATTRIBUTE) **x, - X509_ATTRIBUTE *attr); + const X509_ATTRIBUTE *attr); STACK_OF(X509_ATTRIBUTE) *ossl_x509at_add1_attr_by_OBJ(STACK_OF(X509_ATTRIBUTE) **x, const ASN1_OBJECT *obj, int type, @@ -388,4 +388,10 @@ STACK_OF(X509_ATTRIBUTE) *ossl_x509at_add1_attr_by_txt(STACK_OF(X509_ATTRIBUTE) int type, const unsigned char *bytes, int len); + +int ossl_print_attribute_value(BIO *out, + int obj_nid, + const ASN1_TYPE *av, + int indent); + #endif /* OSSL_CRYPTO_X509_H */ diff --git a/include/crypto/x509_acert.h b/include/crypto/x509_acert.h new file mode 100644 index 0000000000..79cb07ba36 --- /dev/null +++ b/include/crypto/x509_acert.h @@ -0,0 +1,70 @@ +/* + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OSSL_CRYPTO_X509_ACERT_H +# define OSSL_CRYPTO_X509_ACERT_H +# pragma once + +# include + +#define OSSL_ODI_TYPE_PUBLIC_KEY 0 +#define OSSL_ODI_TYPE_PUBLIC_KEY_CERT 1 +#define OSSL_ODI_TYPE_OTHER 2 + +struct ossl_object_digest_info_st { + ASN1_ENUMERATED digestedObjectType; + ASN1_OBJECT *otherObjectTypeID; + X509_ALGOR digestAlgorithm; + ASN1_BIT_STRING objectDigest; +}; + +struct ossl_issuer_serial_st { + STACK_OF(GENERAL_NAME) *issuer; + ASN1_INTEGER serial; + ASN1_BIT_STRING *issuerUID; +}; + +struct X509_acert_issuer_v2form_st { + STACK_OF(GENERAL_NAME) *issuerName; + OSSL_ISSUER_SERIAL *baseCertificateId; + OSSL_OBJECT_DIGEST_INFO *objectDigestInfo; +}; + +typedef struct X509_acert_issuer_st { + int type; + union { + STACK_OF(GENERAL_NAME) *v1Form; + X509_ACERT_ISSUER_V2FORM *v2Form; + } u; +} X509_ACERT_ISSUER; + +typedef struct X509_holder_st { + OSSL_ISSUER_SERIAL *baseCertificateID; + STACK_OF(GENERAL_NAME) *entityName; + OSSL_OBJECT_DIGEST_INFO *objectDigestInfo; +} X509_HOLDER; + +struct X509_acert_info_st { + ASN1_INTEGER version; /* default of v2 */ + X509_HOLDER holder; + X509_ACERT_ISSUER issuer; + X509_ALGOR signature; + ASN1_INTEGER serialNumber; + X509_VAL validityPeriod; + STACK_OF(X509_ATTRIBUTE) *attributes; + ASN1_BIT_STRING *issuerUID; + X509_EXTENSIONS *extensions; +}; + +struct X509_acert_st { + X509_ACERT_INFO *acinfo; + X509_ALGOR sig_alg; + ASN1_BIT_STRING signature; +}; +#endif diff --git a/include/internal/common.h b/include/internal/common.h index b176a27494..0c0415b777 100644 --- a/include/internal/common.h +++ b/include/internal/common.h @@ -228,4 +228,9 @@ static ossl_inline int ossl_is_absolute_path(const char *path) return path[0] == '/'; } +const char *ossl_get_openssldir(void); +const char *ossl_get_enginesdir(void); +const char *ossl_get_modulesdir(void); +const char *ossl_get_wininstallcontext(void); + #endif diff --git a/include/internal/comp.h b/include/internal/comp.h index c48c29d562..6960427542 100644 --- a/include/internal/comp.h +++ b/include/internal/comp.h @@ -1,14 +1,24 @@ /* - * Copyright 2016-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy * in the file LICENSE in the source distribution or at * https://www.openssl.org/source/license.html */ +#ifndef _INTERNAL_COMP_H +#define _INTERNAL_COMP_H #include void ossl_comp_zlib_cleanup(void); void ossl_comp_brotli_cleanup(void); void ossl_comp_zstd_cleanup(void); + +struct ssl_comp_st { + int id; + const char *name; + COMP_METHOD *method; +}; + +#endif diff --git a/include/internal/constant_time.h b/include/internal/constant_time.h index 2b49afe1ea..0dfca0b106 100644 --- a/include/internal/constant_time.h +++ b/include/internal/constant_time.h @@ -141,6 +141,17 @@ static ossl_inline uint64_t constant_time_lt_64(uint64_t a, uint64_t b) } #ifdef BN_ULONG +static ossl_inline BN_ULONG value_barrier_bn(BN_ULONG a) +{ +#if !defined(OPENSSL_NO_ASM) && defined(__GNUC__) + BN_ULONG r; + __asm__("" : "=r"(r) : "0"(a)); +#else + volatile BN_ULONG r = a; +#endif + return r; +} + static ossl_inline BN_ULONG constant_time_msb_bn(BN_ULONG a) { return 0 - (a >> (sizeof(a) * 8 - 1)); @@ -161,6 +172,13 @@ static ossl_inline BN_ULONG constant_time_eq_bn(BN_ULONG a, { return constant_time_is_zero_bn(a ^ b); } + +static ossl_inline BN_ULONG constant_time_select_bn(BN_ULONG mask, + BN_ULONG a, + BN_ULONG b) +{ + return (value_barrier_bn(mask) & a) | (value_barrier_bn(~mask) & b); +} #endif static ossl_inline unsigned int constant_time_ge(unsigned int a, diff --git a/include/internal/crmf.h b/include/internal/crmf.h new file mode 100644 index 0000000000..9e37320d83 --- /dev/null +++ b/include/internal/crmf.h @@ -0,0 +1,51 @@ +/* + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ +#ifndef OSSL_CRYPTO_CRMF_H +# define OSSL_CRYPTO_CRMF_H +# pragma once + +# include + +struct ossl_crmf_attributetypeandvalue_st { + ASN1_OBJECT *type; + union { + /* NID_id_regCtrl_regToken */ + ASN1_UTF8STRING *regToken; + + /* NID_id_regCtrl_authenticator */ + ASN1_UTF8STRING *authenticator; + + /* NID_id_regCtrl_pkiPublicationInfo */ + OSSL_CRMF_PKIPUBLICATIONINFO *pkiPublicationInfo; + + /* NID_id_regCtrl_oldCertID */ + OSSL_CRMF_CERTID *oldCertID; + + /* NID_id_regCtrl_protocolEncrKey */ + X509_PUBKEY *protocolEncrKey; + + /* NID_id_regCtrl_algId */ + X509_ALGOR *algId; + + /* NID_id_regCtrl_rsaKeyLen */ + ASN1_INTEGER *rsaKeyLen; + + /* NID_id_regInfo_utf8Pairs */ + ASN1_UTF8STRING *utf8Pairs; + + /* NID_id_regInfo_certReq */ + OSSL_CRMF_CERTREQUEST *certReq; + + ASN1_TYPE *other; + } value; +} /* OSSL_CRMF_ATTRIBUTETYPEANDVALUE */; +DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) + +#endif /* OSSL_CRYPTO_CRMF_H */ diff --git a/include/internal/cryptlib.h b/include/internal/cryptlib.h index a4fa4ce8d0..3227f9fcf9 100644 --- a/include/internal/cryptlib.h +++ b/include/internal/cryptlib.h @@ -86,7 +86,6 @@ typedef struct ossl_ex_data_global_st { EX_CALLBACKS ex_data[CRYPTO_EX_INDEX__COUNT]; } OSSL_EX_DATA_GLOBAL; - /* OSSL_LIB_CTX */ # define OSSL_LIB_CTX_PROVIDER_STORE_RUN_ONCE_INDEX 0 @@ -101,7 +100,7 @@ typedef struct ossl_ex_data_global_st { # define OSSL_LIB_CTX_NAMEMAP_INDEX 4 # define OSSL_LIB_CTX_DRBG_INDEX 5 # define OSSL_LIB_CTX_DRBG_NONCE_INDEX 6 -# define OSSL_LIB_CTX_RAND_CRNGT_INDEX 7 +/* slot 7 unused, was CRNG test data and can be reused */ # ifdef FIPS_MODULE # define OSSL_LIB_CTX_THREAD_EVENT_HANDLER_INDEX 8 # endif @@ -117,7 +116,9 @@ typedef struct ossl_ex_data_global_st { # define OSSL_LIB_CTX_CHILD_PROVIDER_INDEX 18 # define OSSL_LIB_CTX_THREAD_INDEX 19 # define OSSL_LIB_CTX_DECODER_CACHE_INDEX 20 -# define OSSL_LIB_CTX_MAX_INDEXES 20 +# define OSSL_LIB_CTX_COMP_METHODS 21 +# define OSSL_LIB_CTX_INDICATOR_CB_INDEX 22 +# define OSSL_LIB_CTX_MAX_INDEXES 22 OSSL_LIB_CTX *ossl_lib_ctx_get_concrete(OSSL_LIB_CTX *ctx); int ossl_lib_ctx_is_default(OSSL_LIB_CTX *ctx); @@ -161,4 +162,13 @@ char *ossl_buf2hexstr_sep(const unsigned char *buf, long buflen, char sep); unsigned char *ossl_hexstr2buf_sep(const char *str, long *buflen, const char sep); +/** + * Writes |n| value in hex format into |buf|, + * and returns the number of bytes written + */ +size_t ossl_to_hex(char *buf, uint8_t n); + +STACK_OF(SSL_COMP) *ossl_load_builtin_compressions(void); +void ossl_free_compression_methods_int(STACK_OF(SSL_COMP) *methods); + #endif diff --git a/include/internal/event_queue.h b/include/internal/event_queue.h deleted file mode 100644 index bda1ee6ad4..0000000000 --- a/include/internal/event_queue.h +++ /dev/null @@ -1,163 +0,0 @@ -/* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. - * - * Licensed under the Apache License 2.0 (the "License"). You may not use - * this file except in compliance with the License. You can obtain a copy - * in the file LICENSE in the source distribution or at - * https://www.openssl.org/source/license.html - */ - -#ifndef OSSL_INTERNAL_EVENT_QUEUE_H -# define OSSL_INTERNAL_EVENT_QUEUE_H -# pragma once - -# include "internal/priority_queue.h" -# include "internal/time.h" - -/* - * Opaque type holding an event. - */ -typedef struct ossl_event_st OSSL_EVENT; - -DEFINE_PRIORITY_QUEUE_OF(OSSL_EVENT); - -/* - * Public type representing an event queue, the underlying structure being - * opaque. - */ -typedef struct ossl_event_queue_st OSSL_EVENT_QUEUE; - -/* - * Public type representing a event queue entry. - * It is (internally) public so that it can be embedded into other structures, - * it should otherwise be treated as opaque. - */ -struct ossl_event_st { - uint32_t type; /* What type of event this is */ - uint32_t priority; /* What priority this event has */ - OSSL_TIME when; /* When the event is scheduled to happen */ - void *ctx; /* User argument passed to call backs */ - void *payload; /* Event specific data of unknown kind */ - size_t payload_size; /* Length (in bytes) of event specific data */ - - /* These fields are for internal use only */ - PRIORITY_QUEUE_OF(OSSL_EVENT) *queue; /* Queue containing this event */ - size_t ref; /* ID for this event */ - unsigned int flag_dynamic : 1; /* Malloced or not? */ -}; - -/* - * Utility function to populate an event structure and add it to the queue - */ -int ossl_event_queue_add(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event, - uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size); - -/* - * Utility functions to extract event fields - */ -static ossl_unused ossl_inline -uint32_t ossl_event_get_type(const OSSL_EVENT *event) -{ - return event->type; -} - -static ossl_unused ossl_inline -uint32_t ossl_event_get_priority(const OSSL_EVENT *event) -{ - return event->priority; -} - -static ossl_unused ossl_inline -OSSL_TIME ossl_event_get_when(const OSSL_EVENT *event) -{ - return event->when; -} - -static ossl_unused ossl_inline -void *ossl_event_get0_ctx(const OSSL_EVENT *event) -{ - return event->ctx; -} - -static ossl_unused ossl_inline -void *ossl_event_get0_payload(const OSSL_EVENT *event, size_t *length) -{ - if (length != NULL) - *length = event->payload_size; - return event->payload; -} - -/* - * Create and free a queue. - */ -OSSL_EVENT_QUEUE *ossl_event_queue_new(void); -void ossl_event_queue_free(OSSL_EVENT_QUEUE *queue); - -/* - * Schedule a new event into an event queue. - * - * The event parameters are taken from the function arguments. - * - * The function returns NULL on failure and the added event on success. - */ -OSSL_EVENT *ossl_event_queue_add_new(OSSL_EVENT_QUEUE *queue, - uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size) -; - -/* - * Schedule an event into an event queue. - * - * The event parameters are taken from the function arguments. - * - * The function returns 0 on failure and 1 on success. - */ -int ossl_event_queue_add(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event, - uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size); - -/* - * Delete an event from the queue. - * This will cause the early deletion function to be called if it is non-NULL. - * A pointer to the event structure is returned. - */ -int ossl_event_queue_remove(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event); - -/* - * Free a dynamic event. - * Is a NOP for a static event. - */ -void ossl_event_free(OSSL_EVENT *event); - -/* - * Return the time until the next event for the specified event, if the event's - * time is past, zero is returned. Once activated, the event reference becomes - * invalid and this function becomes undefined. - */ -OSSL_TIME ossl_event_time_until(const OSSL_EVENT *event); - -/* - * Return the time until the next event in the queue. - * If the next event is in the past, zero is returned. - */ -OSSL_TIME ossl_event_queue_time_until_next(const OSSL_EVENT_QUEUE *queue); - -/* - * Postpone an event to trigger at the specified time. - * If the event has triggered, this function's behaviour is undefined. - */ -int ossl_event_queue_postpone_until(OSSL_EVENT_QUEUE *queue, - OSSL_EVENT *event, - OSSL_TIME when); - -/* - * Return the next event to process. - */ -int ossl_event_queue_get1_next_event(OSSL_EVENT_QUEUE *queue, - OSSL_EVENT **event); - -#endif diff --git a/include/internal/hashtable.h b/include/internal/hashtable.h new file mode 100644 index 0000000000..5ca1efbe22 --- /dev/null +++ b/include/internal/hashtable.h @@ -0,0 +1,335 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OPENSSL_HASHTABLE_H +# define OPENSSL_HASHTABLE_H +# pragma once + +#include +#include +#include +#include +#include "crypto/context.h" + +typedef struct ht_internal_st HT; + +/* + * Represents a key to a hashtable + */ +typedef struct ht_key_header_st { + size_t keysize; + uint8_t *keybuf; +} HT_KEY; + +/* + * Represents a value in the hash table + */ +typedef struct ht_value_st { + void *value; + uintptr_t *type_id; + HT_KEY key; +} HT_VALUE; + +/* + * Represents a list of values filtered from a hash table + */ +typedef struct ht_value_list_st { + size_t list_len; + HT_VALUE **list; +} HT_VALUE_LIST; + +/* + * Hashtable configuration + */ +typedef struct ht_config_st { + OSSL_LIB_CTX *ctx; + void (*ht_free_fn)(HT_VALUE *obj); + uint64_t (*ht_hash_fn)(uint8_t *key, size_t keylen); + size_t init_neighborhoods; + uint32_t collision_check; + uint32_t lockless_reads; +} HT_CONFIG; + +/* + * Hashtable key rules + * Any struct can be used to formulate a hash table key, as long as the + * following rules + * 1) The first element of the struct defining the key must be an HT_KEY + * 2) All struct elements must have a compile time defined length + * 3) Pointers can be used, but the value of the pointer, rather than + * the contents of the address it points to will be used to compute + * the hash + * The key definition macros will assist with enforcing these rules + */ + +/* + * Starts the definition of a hash table key + */ +#define HT_START_KEY_DEFN(keyname) \ +typedef struct keyname##_st { \ + HT_KEY key_header; \ + struct { + +/* + * Ends a hash table key definitions + */ +#define HT_END_KEY_DEFN(keyname) \ + } keyfields; \ +} keyname; + +/* + * Defines a field in a hash table key + */ +#define HT_DEF_KEY_FIELD(name, type) type name; + +/* + * convenience macro to define a static char + * array field in a hash table key + */ +#define HT_DEF_KEY_FIELD_CHAR_ARRAY(name, size) \ + HT_DEF_KEY_FIELD(name[size], char) + +/* + * Defines a uint8_t (blob) field in a hash table key + */ +#define HT_DEF_KEY_FIELD_UINT8T_ARRAY(name, size) \ + HT_DEF_KEY_FIELD(name[size], uint8_t) + +/* + * Initializes a key + */ +#define HT_INIT_KEY(key) do { \ +memset((key), 0, sizeof(*(key))); \ +(key)->key_header.keysize = (sizeof(*(key)) - sizeof(HT_KEY)); \ +(key)->key_header.keybuf = (((uint8_t *)key) + sizeof(HT_KEY)); \ +} while(0) + +/* + * Resets a hash table key to a known state + */ +#define HT_KEY_RESET(key) memset((key)->key_header.keybuf, 0, (key)->key_header.keysize) + +/* + * Sets a scalar field in a hash table key + */ +#define HT_SET_KEY_FIELD(key, member, value) (key)->keyfields.member = value; + +/* + * Sets a string field in a hash table key, preserving + * null terminator + */ +#define HT_SET_KEY_STRING(key, member, value) do { \ + if ((value) != NULL) \ + strncpy((key)->keyfields.member, value, sizeof((key)->keyfields.member) - 1); \ +} while(0) + +/* + * This is the same as HT_SET_KEY_STRING, except that it uses + * ossl_ht_strcase to make the value being passed case insensitive + * This is useful for instances in which we want upper and lower case + * key value to hash to the same entry + */ +#define HT_SET_KEY_STRING_CASE(key, member, value) do { \ + ossl_ht_strcase((key)->keyfields.member, value, sizeof((key)->keyfields.member) -1); \ +} while(0) + +/* + * Sets a uint8_t (blob) field in a hash table key + */ +#define HT_SET_KEY_BLOB(key, member, value, len) do { \ + if (value != NULL) \ + memcpy((key)->keyfields.member, value, len); \ +} while(0) + +/* + * Converts a defined key type to an HT_KEY + */ +#define TO_HT_KEY(key) &(key)->key_header + +/* + * Converts an HT_KEY back to its defined + * type + */ +#define FROM_HT_KEY(key, type) (type)(key) + +/* + * Implements the following type safe operations for a hash table + * ossl_ht_NAME_TYPE_insert - insert a value to a hash table of type TYPE + * ossl_ht_NAME_TYPE_get - gets a value of a specific type from the hash table + * ossl_ht_NAME_TYPE_from_value - converts an HT_VALUE to its type + * ossl_ht_NAME_TYPE_to_value - converts a TYPE to an HT_VALUE + * ossl_ht_NAME_TYPE_type - boolean to detect if a value is of TYPE + */ +#define IMPLEMENT_HT_VALUE_TYPE_FNS(vtype, name, pfx) \ +static uintptr_t name##_##vtype##_id = 0; \ +pfx ossl_unused int ossl_ht_##name##_##vtype##_insert(HT *h, HT_KEY *key, \ + vtype *data, \ + vtype **olddata) { \ + HT_VALUE inval; \ + HT_VALUE *oval = NULL; \ + int rc; \ + \ + inval.value = data; \ + inval.type_id = &name##_##vtype##_id; \ + rc = ossl_ht_insert(h, key, &inval, olddata == NULL ? NULL : &oval); \ + if (oval != NULL) \ + *olddata = (vtype *)oval->value; \ + return rc; \ +} \ + \ +pfx ossl_unused vtype *ossl_ht_##name##_##vtype##_from_value(HT_VALUE *v) \ +{ \ + uintptr_t *expect_type = &name##_##vtype##_id; \ + if (v == NULL) \ + return NULL; \ + if (v->type_id != expect_type) \ + return NULL; \ + return (vtype *)v->value; \ +} \ + \ +pfx ossl_unused vtype *ossl_unused ossl_ht_##name##_##vtype##_get(HT *h, \ + HT_KEY *key, \ + HT_VALUE **v)\ +{ \ + HT_VALUE *vv; \ + vv = ossl_ht_get(h, key); \ + if (vv == NULL) \ + return NULL; \ + *v = ossl_rcu_deref(&vv); \ + return ossl_ht_##name##_##vtype##_from_value(*v); \ +} \ + \ +pfx ossl_unused HT_VALUE *ossl_ht_##name##_##vtype##_to_value(vtype *data, \ + HT_VALUE *v) \ +{ \ + v->type_id = &name##_##vtype##_id; \ + v->value = data; \ + return v; \ +} \ + \ +pfx ossl_unused int ossl_ht_##name##_##vtype##_type(HT_VALUE *h) \ +{ \ + return h->type_id == &name##_##vtype##_id; \ +} + +#define DECLARE_HT_VALUE_TYPE_FNS(vtype, name) \ +int ossl_ht_##name##_##vtype##_insert(HT *h, HT_KEY *key, vtype *data, \ + vtype **olddata); \ +vtype *ossl_ht_##name##_##vtype##_from_value(HT_VALUE *v); \ +vtype *ossl_unused ossl_ht_##name##_##vtype##_get(HT *h, \ + HT_KEY *key, \ + HT_VALUE **v); \ +HT_VALUE *ossl_ht_##name##_##vtype##_to_value(vtype *data, HT_VALUE *v); \ +int ossl_ht_##name##_##vtype##_type(HT_VALUE *h); \ + +/* + * Helper function to construct case insensitive keys + */ +static void ossl_unused ossl_ht_strcase(char *tgt, const char *src, int len) +{ + int i; +#if defined(CHARSET_EBCDIC) && !defined(CHARSET_EBCDIC_TEST) + const long int case_adjust = ~0x40; +#else + const long int case_adjust = ~0x20; +#endif + + if (src == NULL) + return; + + for (i = 0; src[i] != '\0' && i < len; i++) + tgt[i] = case_adjust & src[i]; +} + +/* + * Create a new hashtable + */ +HT *ossl_ht_new(const HT_CONFIG *conf); + +/* + * Frees a hash table, potentially freeing all elements + */ +void ossl_ht_free(HT *htable); + +/* + * Lock the table for reading + */ +void ossl_ht_read_lock(HT *htable); + +/* + * Lock the table for writing + */ +void ossl_ht_write_lock(HT *htable); + +/* + * Read unlock + */ +void ossl_ht_read_unlock(HT *htable); + +/* + * Write unlock + */ +void ossl_ht_write_unlock (HT *htable); + +/* + * Empties a hash table, potentially freeing all elements + */ +int ossl_ht_flush(HT *htable); + +/* + * Inserts an element to a hash table, optionally returning + * replaced data to caller + * Returns 1 if the insert was successful, 0 on error + */ +int ossl_ht_insert(HT *htable, HT_KEY *key, HT_VALUE *data, + HT_VALUE **olddata); + +/* + * Deletes a value from a hash table, based on key + * Returns 1 if the key was removed, 0 if they key was not found + */ +int ossl_ht_delete(HT *htable, HT_KEY *key); + +/* + * Returns number of elements in the hash table + */ +size_t ossl_ht_count(HT *htable); + +/* + * Iterates over each element in the table. + * aborts the loop when cb returns 0 + * Contents of elements in the list may be modified during + * this traversal, assuming proper thread safety is observed while doing + * so (holding the table write lock is sufficient). However, elements of the + * table may not be inserted or removed while iterating. + */ +void ossl_ht_foreach_until(HT *htable, int (*cb)(HT_VALUE *obj, void *arg), + void *arg); +/* + * Returns a list of elements in a hash table based on + * filter function return value. Returns NULL on error, + * or an HT_VALUE_LIST object on success. Note it is possible + * That a list will be returned with 0 entries, if none were found. + * The zero length list must still be freed via ossl_ht_value_list_free + */ +HT_VALUE_LIST *ossl_ht_filter(HT *htable, size_t max_len, + int (*filter)(HT_VALUE *obj, void *arg), + void *arg); +/* + * Frees the list returned from ossl_ht_filter + */ +void ossl_ht_value_list_free(HT_VALUE_LIST *list); + +/* + * Fetches a value from the hash table, based + * on key. Returns NULL if the element was not found. + */ +HT_VALUE *ossl_ht_get(HT *htable, HT_KEY *key); + +#endif diff --git a/include/internal/list.h b/include/internal/list.h index 902047641f..8d68a3e71b 100644 --- a/include/internal/list.h +++ b/include/internal/list.h @@ -1,5 +1,5 @@ /* - * Copyright 2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -20,33 +20,33 @@ # define OSSL_LIST_DBG(x) x; # endif -# define LIST_FOREACH_FROM(p, name, init) \ +# define OSSL_LIST_FOREACH_FROM(p, name, init) \ for ((p) = (init); \ (p) != NULL; \ (p) = ossl_list_##name##_next(p)) -# define LIST_FOREACH(p, name, l) \ - LIST_FOREACH_FROM(p, name, ossl_list_##name##_head(l)) +# define OSSL_LIST_FOREACH(p, name, l) \ + OSSL_LIST_FOREACH_FROM(p, name, ossl_list_##name##_head(l)) -# define LIST_FOREACH_REV_FROM(p, name, init) \ +# define OSSL_LIST_FOREACH_REV_FROM(p, name, init) \ for ((p) = (init); \ (p) != NULL; \ (p) = ossl_list_##name##_prev(p)) -# define LIST_FOREACH_REV(p, name, l) \ - LIST_FOREACH_FROM(p, name, ossl_list_##name##_tail(l)) +# define OSSL_LIST_FOREACH_REV(p, name, l) \ + OSSL_LIST_FOREACH_FROM(p, name, ossl_list_##name##_tail(l)) -# define LIST_FOREACH_DELSAFE_FROM(p, pn, name, init) \ +# define OSSL_LIST_FOREACH_DELSAFE_FROM(p, pn, name, init) \ for ((p) = (init); \ (p) != NULL && (((pn) = ossl_list_##name##_next(p)), 1); \ (p) = (pn)) -#define LIST_FOREACH_DELSAFE(p, pn, name, l) \ - LIST_FOREACH_DELSAFE_FROM(p, pn, name, ossl_list_##name##_head(l)) +#define OSSL_LIST_FOREACH_DELSAFE(p, pn, name, l) \ + OSSL_LIST_FOREACH_DELSAFE_FROM(p, pn, name, ossl_list_##name##_head(l)) -# define LIST_FOREACH_REV_DELSAFE_FROM(p, pn, name, init) \ +# define OSSL_LIST_FOREACH_REV_DELSAFE_FROM(p, pn, name, init) \ for ((p) = (init); \ (p) != NULL && (((pn) = ossl_list_##name##_prev(p)), 1); \ (p) = (pn)) -# define LIST_FOREACH_REV_DELSAFE(p, pn, name, l) \ - LIST_FOREACH_REV_DELSAFE_FROM(p, pn, name, ossl_list_##name##_tail(l)) +# define OSSL_LIST_FOREACH_REV_DELSAFE(p, pn, name, l) \ + OSSL_LIST_FOREACH_REV_DELSAFE_FROM(p, pn, name, ossl_list_##name##_tail(l)) /* Define a list structure */ # define OSSL_LIST(name) OSSL_LIST_ ## name diff --git a/include/internal/namemap.h b/include/internal/namemap.h index 6c42a9cd7c..a3a3414869 100644 --- a/include/internal/namemap.h +++ b/include/internal/namemap.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,7 +13,7 @@ typedef struct ossl_namemap_st OSSL_NAMEMAP; OSSL_NAMEMAP *ossl_namemap_stored(OSSL_LIB_CTX *libctx); -OSSL_NAMEMAP *ossl_namemap_new(void); +OSSL_NAMEMAP *ossl_namemap_new(OSSL_LIB_CTX *libctx); void ossl_namemap_free(OSSL_NAMEMAP *namemap); int ossl_namemap_empty(OSSL_NAMEMAP *namemap); diff --git a/include/internal/packet.h b/include/internal/packet.h index 7abc6b8b1b..6fcd345ce2 100644 --- a/include/internal/packet.h +++ b/include/internal/packet.h @@ -1,5 +1,5 @@ /* - * Copyright 2015-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -627,7 +627,7 @@ __owur static ossl_inline int PACKET_get_length_prefixed_3(PACKET *pkt, return 1; } -/* Writeable packets */ +/* Writable packets */ typedef struct wpacket_sub WPACKET_SUB; struct wpacket_sub { diff --git a/include/internal/param_names.h b/include/internal/param_names.h index 2ef29db4fa..292d377f2c 100644 --- a/include/internal/param_names.h +++ b/include/internal/param_names.h @@ -14,364 +14,433 @@ int ossl_param_find_pidx(const char *s); /* Parameter name definitions - generated by util/perl/OpenSSL/paramnames.pm */ -#define NUM_PIDX 291 +#define NUM_PIDX 329 -#define PIDX_ALG_PARAM_CIPHER 0 -#define PIDX_ALG_PARAM_DIGEST 1 -#define PIDX_ALG_PARAM_ENGINE 2 -#define PIDX_ALG_PARAM_MAC 3 -#define PIDX_ALG_PARAM_PROPERTIES 4 +#define PIDX_ALG_PARAM_ALGORITHM_ID 0 +#define PIDX_ALG_PARAM_ALGORITHM_ID_PARAMS 1 +#define PIDX_ALG_PARAM_CIPHER 2 +#define PIDX_ALG_PARAM_DIGEST 3 +#define PIDX_ALG_PARAM_ENGINE 4 +#define PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR 5 +#define PIDX_ALG_PARAM_MAC 6 +#define PIDX_ALG_PARAM_PROPERTIES 7 #define PIDX_ASYM_CIPHER_PARAM_DIGEST PIDX_PKEY_PARAM_DIGEST #define PIDX_ASYM_CIPHER_PARAM_ENGINE PIDX_PKEY_PARAM_ENGINE -#define PIDX_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION 5 +#define PIDX_ASYM_CIPHER_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_ASYM_CIPHER_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_ASYM_CIPHER_PARAM_FIPS_RSA_PKCS15_PAD_DISABLED PIDX_PROV_PARAM_RSA_PKCS15_PAD_DISABLED +#define PIDX_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION 8 #define PIDX_ASYM_CIPHER_PARAM_MGF1_DIGEST PIDX_PKEY_PARAM_MGF1_DIGEST #define PIDX_ASYM_CIPHER_PARAM_MGF1_DIGEST_PROPS PIDX_PKEY_PARAM_MGF1_PROPERTIES #define PIDX_ASYM_CIPHER_PARAM_OAEP_DIGEST PIDX_ALG_PARAM_DIGEST -#define PIDX_ASYM_CIPHER_PARAM_OAEP_DIGEST_PROPS 6 -#define PIDX_ASYM_CIPHER_PARAM_OAEP_LABEL 7 +#define PIDX_ASYM_CIPHER_PARAM_OAEP_DIGEST_PROPS 9 +#define PIDX_ASYM_CIPHER_PARAM_OAEP_LABEL 10 #define PIDX_ASYM_CIPHER_PARAM_PAD_MODE PIDX_PKEY_PARAM_PAD_MODE #define PIDX_ASYM_CIPHER_PARAM_PROPERTIES PIDX_PKEY_PARAM_PROPERTIES -#define PIDX_ASYM_CIPHER_PARAM_TLS_CLIENT_VERSION 8 -#define PIDX_ASYM_CIPHER_PARAM_TLS_NEGOTIATED_VERSION 9 -#define PIDX_CAPABILITY_TLS_GROUP_ALG 10 -#define PIDX_CAPABILITY_TLS_GROUP_ID 11 -#define PIDX_CAPABILITY_TLS_GROUP_IS_KEM 12 -#define PIDX_CAPABILITY_TLS_GROUP_MAX_DTLS 13 -#define PIDX_CAPABILITY_TLS_GROUP_MAX_TLS 14 -#define PIDX_CAPABILITY_TLS_GROUP_MIN_DTLS 15 -#define PIDX_CAPABILITY_TLS_GROUP_MIN_TLS 16 -#define PIDX_CAPABILITY_TLS_GROUP_NAME 17 -#define PIDX_CAPABILITY_TLS_GROUP_NAME_INTERNAL 18 -#define PIDX_CAPABILITY_TLS_GROUP_SECURITY_BITS 19 -#define PIDX_CAPABILITY_TLS_SIGALG_CODE_POINT 20 -#define PIDX_CAPABILITY_TLS_SIGALG_HASH_NAME 21 -#define PIDX_CAPABILITY_TLS_SIGALG_HASH_OID 22 -#define PIDX_CAPABILITY_TLS_SIGALG_IANA_NAME 23 -#define PIDX_CAPABILITY_TLS_SIGALG_KEYTYPE 24 -#define PIDX_CAPABILITY_TLS_SIGALG_KEYTYPE_OID 25 -#define PIDX_CAPABILITY_TLS_SIGALG_MAX_TLS 14 -#define PIDX_CAPABILITY_TLS_SIGALG_MIN_TLS 16 -#define PIDX_CAPABILITY_TLS_SIGALG_NAME 26 -#define PIDX_CAPABILITY_TLS_SIGALG_OID 27 -#define PIDX_CAPABILITY_TLS_SIGALG_SECURITY_BITS 28 -#define PIDX_CAPABILITY_TLS_SIGALG_SIG_NAME 29 -#define PIDX_CAPABILITY_TLS_SIGALG_SIG_OID 30 -#define PIDX_CIPHER_PARAM_AEAD 31 +#define PIDX_ASYM_CIPHER_PARAM_TLS_CLIENT_VERSION 11 +#define PIDX_ASYM_CIPHER_PARAM_TLS_NEGOTIATED_VERSION 12 +#define PIDX_CAPABILITY_TLS_GROUP_ALG 13 +#define PIDX_CAPABILITY_TLS_GROUP_ID 14 +#define PIDX_CAPABILITY_TLS_GROUP_IS_KEM 15 +#define PIDX_CAPABILITY_TLS_GROUP_MAX_DTLS 16 +#define PIDX_CAPABILITY_TLS_GROUP_MAX_TLS 17 +#define PIDX_CAPABILITY_TLS_GROUP_MIN_DTLS 18 +#define PIDX_CAPABILITY_TLS_GROUP_MIN_TLS 19 +#define PIDX_CAPABILITY_TLS_GROUP_NAME 20 +#define PIDX_CAPABILITY_TLS_GROUP_NAME_INTERNAL 21 +#define PIDX_CAPABILITY_TLS_GROUP_SECURITY_BITS 22 +#define PIDX_CAPABILITY_TLS_SIGALG_CODE_POINT 23 +#define PIDX_CAPABILITY_TLS_SIGALG_HASH_NAME 24 +#define PIDX_CAPABILITY_TLS_SIGALG_HASH_OID 25 +#define PIDX_CAPABILITY_TLS_SIGALG_IANA_NAME 26 +#define PIDX_CAPABILITY_TLS_SIGALG_KEYTYPE 27 +#define PIDX_CAPABILITY_TLS_SIGALG_KEYTYPE_OID 28 +#define PIDX_CAPABILITY_TLS_SIGALG_MAX_TLS 17 +#define PIDX_CAPABILITY_TLS_SIGALG_MIN_TLS 19 +#define PIDX_CAPABILITY_TLS_SIGALG_NAME 29 +#define PIDX_CAPABILITY_TLS_SIGALG_OID 30 +#define PIDX_CAPABILITY_TLS_SIGALG_SECURITY_BITS 31 +#define PIDX_CAPABILITY_TLS_SIGALG_SIG_NAME 32 +#define PIDX_CAPABILITY_TLS_SIGALG_SIG_OID 33 +#define PIDX_CIPHER_PARAM_AEAD 34 #define PIDX_CIPHER_PARAM_AEAD_IVLEN PIDX_CIPHER_PARAM_IVLEN -#define PIDX_CIPHER_PARAM_AEAD_MAC_KEY 32 -#define PIDX_CIPHER_PARAM_AEAD_TAG 33 -#define PIDX_CIPHER_PARAM_AEAD_TAGLEN 34 -#define PIDX_CIPHER_PARAM_AEAD_TLS1_AAD 35 -#define PIDX_CIPHER_PARAM_AEAD_TLS1_AAD_PAD 36 -#define PIDX_CIPHER_PARAM_AEAD_TLS1_GET_IV_GEN 37 -#define PIDX_CIPHER_PARAM_AEAD_TLS1_IV_FIXED 38 -#define PIDX_CIPHER_PARAM_AEAD_TLS1_SET_IV_INV 39 -#define PIDX_CIPHER_PARAM_ALGORITHM_ID_PARAMS 40 -#define PIDX_CIPHER_PARAM_BLOCK_SIZE 41 -#define PIDX_CIPHER_PARAM_CTS 42 -#define PIDX_CIPHER_PARAM_CTS_MODE 43 -#define PIDX_CIPHER_PARAM_CUSTOM_IV 44 -#define PIDX_CIPHER_PARAM_HAS_RAND_KEY 45 -#define PIDX_CIPHER_PARAM_IV 46 -#define PIDX_CIPHER_PARAM_IVLEN 47 -#define PIDX_CIPHER_PARAM_KEYLEN 48 -#define PIDX_CIPHER_PARAM_MODE 49 -#define PIDX_CIPHER_PARAM_NUM 50 -#define PIDX_CIPHER_PARAM_PADDING 51 -#define PIDX_CIPHER_PARAM_RANDOM_KEY 52 -#define PIDX_CIPHER_PARAM_RC2_KEYBITS 53 -#define PIDX_CIPHER_PARAM_ROUNDS 54 -#define PIDX_CIPHER_PARAM_SPEED 55 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK 56 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_AAD 57 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_AAD_PACKLEN 58 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC 59 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC_IN 60 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC_LEN 61 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_INTERLEAVE 62 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_MAX_BUFSIZE 63 -#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_MAX_SEND_FRAGMENT 64 -#define PIDX_CIPHER_PARAM_TLS_MAC 65 -#define PIDX_CIPHER_PARAM_TLS_MAC_SIZE 66 -#define PIDX_CIPHER_PARAM_TLS_VERSION 67 -#define PIDX_CIPHER_PARAM_UPDATED_IV 68 -#define PIDX_CIPHER_PARAM_USE_BITS 69 -#define PIDX_CIPHER_PARAM_XTS_STANDARD 70 +#define PIDX_CIPHER_PARAM_AEAD_IV_GENERATED 35 +#define PIDX_CIPHER_PARAM_AEAD_MAC_KEY 36 +#define PIDX_CIPHER_PARAM_AEAD_TAG 37 +#define PIDX_CIPHER_PARAM_AEAD_TAGLEN 38 +#define PIDX_CIPHER_PARAM_AEAD_TLS1_AAD 39 +#define PIDX_CIPHER_PARAM_AEAD_TLS1_AAD_PAD 40 +#define PIDX_CIPHER_PARAM_AEAD_TLS1_GET_IV_GEN 41 +#define PIDX_CIPHER_PARAM_AEAD_TLS1_IV_FIXED 42 +#define PIDX_CIPHER_PARAM_AEAD_TLS1_SET_IV_INV 43 +#define PIDX_CIPHER_PARAM_ALGORITHM_ID PIDX_ALG_PARAM_ALGORITHM_ID +#define PIDX_CIPHER_PARAM_ALGORITHM_ID_PARAMS PIDX_ALG_PARAM_ALGORITHM_ID_PARAMS +#define PIDX_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD 44 +#define PIDX_CIPHER_PARAM_BLOCK_SIZE 45 +#define PIDX_CIPHER_PARAM_CTS 46 +#define PIDX_CIPHER_PARAM_CTS_MODE 47 +#define PIDX_CIPHER_PARAM_CUSTOM_IV 48 +#define PIDX_CIPHER_PARAM_DECRYPT_ONLY 49 +#define PIDX_CIPHER_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_CIPHER_PARAM_FIPS_ENCRYPT_CHECK 50 +#define PIDX_CIPHER_PARAM_HAS_RAND_KEY 51 +#define PIDX_CIPHER_PARAM_IV 52 +#define PIDX_CIPHER_PARAM_IVLEN 53 +#define PIDX_CIPHER_PARAM_KEYLEN 54 +#define PIDX_CIPHER_PARAM_MODE 55 +#define PIDX_CIPHER_PARAM_NUM 56 +#define PIDX_CIPHER_PARAM_PADDING 57 +#define PIDX_CIPHER_PARAM_RANDOM_KEY 58 +#define PIDX_CIPHER_PARAM_RC2_KEYBITS 59 +#define PIDX_CIPHER_PARAM_ROUNDS 60 +#define PIDX_CIPHER_PARAM_SPEED 61 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK 62 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_AAD 63 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_AAD_PACKLEN 64 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC 65 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC_IN 66 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_ENC_LEN 67 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_INTERLEAVE 68 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_MAX_BUFSIZE 69 +#define PIDX_CIPHER_PARAM_TLS1_MULTIBLOCK_MAX_SEND_FRAGMENT 70 +#define PIDX_CIPHER_PARAM_TLS_MAC 71 +#define PIDX_CIPHER_PARAM_TLS_MAC_SIZE 72 +#define PIDX_CIPHER_PARAM_TLS_VERSION 73 +#define PIDX_CIPHER_PARAM_UPDATED_IV 74 +#define PIDX_CIPHER_PARAM_USE_BITS 75 +#define PIDX_CIPHER_PARAM_XTS_STANDARD 76 #define PIDX_DECODER_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_DIGEST_PARAM_ALGID_ABSENT 71 -#define PIDX_DIGEST_PARAM_BLOCK_SIZE 41 -#define PIDX_DIGEST_PARAM_MICALG 72 -#define PIDX_DIGEST_PARAM_PAD_TYPE 73 -#define PIDX_DIGEST_PARAM_SIZE 74 -#define PIDX_DIGEST_PARAM_SSL3_MS 75 -#define PIDX_DIGEST_PARAM_XOF 76 -#define PIDX_DIGEST_PARAM_XOFLEN 77 +#define PIDX_DIGEST_PARAM_ALGID_ABSENT 77 +#define PIDX_DIGEST_PARAM_BLOCK_SIZE 45 +#define PIDX_DIGEST_PARAM_MICALG 78 +#define PIDX_DIGEST_PARAM_PAD_TYPE 79 +#define PIDX_DIGEST_PARAM_SIZE 80 +#define PIDX_DIGEST_PARAM_SSL3_MS 81 +#define PIDX_DIGEST_PARAM_XOF 82 +#define PIDX_DIGEST_PARAM_XOFLEN 83 #define PIDX_DRBG_PARAM_CIPHER PIDX_ALG_PARAM_CIPHER #define PIDX_DRBG_PARAM_DIGEST PIDX_ALG_PARAM_DIGEST -#define PIDX_DRBG_PARAM_ENTROPY_REQUIRED 78 +#define PIDX_DRBG_PARAM_ENTROPY_REQUIRED 84 +#define PIDX_DRBG_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_DRBG_PARAM_FIPS_DIGEST_CHECK PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK #define PIDX_DRBG_PARAM_MAC PIDX_ALG_PARAM_MAC -#define PIDX_DRBG_PARAM_MAX_ADINLEN 79 -#define PIDX_DRBG_PARAM_MAX_ENTROPYLEN 80 -#define PIDX_DRBG_PARAM_MAX_LENGTH 81 -#define PIDX_DRBG_PARAM_MAX_NONCELEN 82 -#define PIDX_DRBG_PARAM_MAX_PERSLEN 83 -#define PIDX_DRBG_PARAM_MIN_ENTROPYLEN 84 -#define PIDX_DRBG_PARAM_MIN_LENGTH 85 -#define PIDX_DRBG_PARAM_MIN_NONCELEN 86 -#define PIDX_DRBG_PARAM_PREDICTION_RESISTANCE 87 +#define PIDX_DRBG_PARAM_MAX_ADINLEN 85 +#define PIDX_DRBG_PARAM_MAX_ENTROPYLEN 86 +#define PIDX_DRBG_PARAM_MAX_LENGTH 87 +#define PIDX_DRBG_PARAM_MAX_NONCELEN 88 +#define PIDX_DRBG_PARAM_MAX_PERSLEN 89 +#define PIDX_DRBG_PARAM_MIN_ENTROPYLEN 90 +#define PIDX_DRBG_PARAM_MIN_LENGTH 91 +#define PIDX_DRBG_PARAM_MIN_NONCELEN 92 +#define PIDX_DRBG_PARAM_PREDICTION_RESISTANCE 93 #define PIDX_DRBG_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_DRBG_PARAM_RANDOM_DATA 88 -#define PIDX_DRBG_PARAM_RESEED_COUNTER 89 -#define PIDX_DRBG_PARAM_RESEED_REQUESTS 90 -#define PIDX_DRBG_PARAM_RESEED_TIME 91 -#define PIDX_DRBG_PARAM_RESEED_TIME_INTERVAL 92 -#define PIDX_DRBG_PARAM_SIZE 74 -#define PIDX_DRBG_PARAM_USE_DF 93 +#define PIDX_DRBG_PARAM_RANDOM_DATA 94 +#define PIDX_DRBG_PARAM_RESEED_COUNTER 95 +#define PIDX_DRBG_PARAM_RESEED_REQUESTS 96 +#define PIDX_DRBG_PARAM_RESEED_TIME 97 +#define PIDX_DRBG_PARAM_RESEED_TIME_INTERVAL 98 +#define PIDX_DRBG_PARAM_SIZE 80 +#define PIDX_DRBG_PARAM_USE_DF 99 #define PIDX_ENCODER_PARAM_CIPHER PIDX_ALG_PARAM_CIPHER -#define PIDX_ENCODER_PARAM_ENCRYPT_LEVEL 94 +#define PIDX_ENCODER_PARAM_ENCRYPT_LEVEL 100 #define PIDX_ENCODER_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_ENCODER_PARAM_SAVE_PARAMETERS 95 -#define PIDX_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE 96 -#define PIDX_EXCHANGE_PARAM_KDF_DIGEST 97 -#define PIDX_EXCHANGE_PARAM_KDF_DIGEST_PROPS 98 -#define PIDX_EXCHANGE_PARAM_KDF_OUTLEN 99 -#define PIDX_EXCHANGE_PARAM_KDF_TYPE 100 -#define PIDX_EXCHANGE_PARAM_KDF_UKM 101 -#define PIDX_EXCHANGE_PARAM_PAD 102 -#define PIDX_GEN_PARAM_ITERATION 103 -#define PIDX_GEN_PARAM_POTENTIAL 104 -#define PIDX_KDF_PARAM_ARGON2_AD 105 -#define PIDX_KDF_PARAM_ARGON2_LANES 106 -#define PIDX_KDF_PARAM_ARGON2_MEMCOST 107 -#define PIDX_KDF_PARAM_ARGON2_VERSION 108 -#define PIDX_KDF_PARAM_CEK_ALG 109 +#define PIDX_ENCODER_PARAM_SAVE_PARAMETERS 101 +#define PIDX_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE 102 +#define PIDX_EXCHANGE_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_EXCHANGE_PARAM_FIPS_DIGEST_CHECK PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK +#define PIDX_EXCHANGE_PARAM_FIPS_ECDH_COFACTOR_CHECK PIDX_PROV_PARAM_ECDH_COFACTOR_CHECK +#define PIDX_EXCHANGE_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_EXCHANGE_PARAM_KDF_DIGEST 103 +#define PIDX_EXCHANGE_PARAM_KDF_DIGEST_PROPS 104 +#define PIDX_EXCHANGE_PARAM_KDF_OUTLEN 105 +#define PIDX_EXCHANGE_PARAM_KDF_TYPE 106 +#define PIDX_EXCHANGE_PARAM_KDF_UKM 107 +#define PIDX_EXCHANGE_PARAM_PAD 108 +#define PIDX_GEN_PARAM_ITERATION 109 +#define PIDX_GEN_PARAM_POTENTIAL 110 +#define PIDX_KDF_PARAM_ARGON2_AD 111 +#define PIDX_KDF_PARAM_ARGON2_LANES 112 +#define PIDX_KDF_PARAM_ARGON2_MEMCOST 113 +#define PIDX_KDF_PARAM_ARGON2_VERSION 114 +#define PIDX_KDF_PARAM_CEK_ALG 115 #define PIDX_KDF_PARAM_CIPHER PIDX_ALG_PARAM_CIPHER -#define PIDX_KDF_PARAM_CONSTANT 110 -#define PIDX_KDF_PARAM_DATA 111 +#define PIDX_KDF_PARAM_CONSTANT 116 +#define PIDX_KDF_PARAM_DATA 117 #define PIDX_KDF_PARAM_DIGEST PIDX_ALG_PARAM_DIGEST -#define PIDX_KDF_PARAM_EARLY_CLEAN 112 -#define PIDX_KDF_PARAM_HMACDRBG_ENTROPY 113 -#define PIDX_KDF_PARAM_HMACDRBG_NONCE 114 -#define PIDX_KDF_PARAM_INFO 115 -#define PIDX_KDF_PARAM_ITER 116 -#define PIDX_KDF_PARAM_KBKDF_R 117 -#define PIDX_KDF_PARAM_KBKDF_USE_L 118 -#define PIDX_KDF_PARAM_KBKDF_USE_SEPARATOR 119 -#define PIDX_KDF_PARAM_KEY 120 -#define PIDX_KDF_PARAM_LABEL 121 +#define PIDX_KDF_PARAM_EARLY_CLEAN 118 +#define PIDX_KDF_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_KDF_PARAM_FIPS_DIGEST_CHECK PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK +#define PIDX_KDF_PARAM_FIPS_EMS_CHECK 119 +#define PIDX_KDF_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_KDF_PARAM_HMACDRBG_ENTROPY 120 +#define PIDX_KDF_PARAM_HMACDRBG_NONCE 121 +#define PIDX_KDF_PARAM_INFO 122 +#define PIDX_KDF_PARAM_ITER 123 +#define PIDX_KDF_PARAM_KBKDF_R 124 +#define PIDX_KDF_PARAM_KBKDF_USE_L 125 +#define PIDX_KDF_PARAM_KBKDF_USE_SEPARATOR 126 +#define PIDX_KDF_PARAM_KEY 127 +#define PIDX_KDF_PARAM_LABEL 128 #define PIDX_KDF_PARAM_MAC PIDX_ALG_PARAM_MAC -#define PIDX_KDF_PARAM_MAC_SIZE 122 -#define PIDX_KDF_PARAM_MODE 49 -#define PIDX_KDF_PARAM_PASSWORD 123 -#define PIDX_KDF_PARAM_PKCS12_ID 124 -#define PIDX_KDF_PARAM_PKCS5 125 -#define PIDX_KDF_PARAM_PREFIX 126 +#define PIDX_KDF_PARAM_MAC_SIZE 129 +#define PIDX_KDF_PARAM_MODE 55 +#define PIDX_KDF_PARAM_PASSWORD 130 +#define PIDX_KDF_PARAM_PKCS12_ID 131 +#define PIDX_KDF_PARAM_PKCS5 132 +#define PIDX_KDF_PARAM_PREFIX 133 #define PIDX_KDF_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_KDF_PARAM_SALT 127 -#define PIDX_KDF_PARAM_SCRYPT_MAXMEM 128 -#define PIDX_KDF_PARAM_SCRYPT_N 129 -#define PIDX_KDF_PARAM_SCRYPT_P 130 -#define PIDX_KDF_PARAM_SCRYPT_R 117 -#define PIDX_KDF_PARAM_SECRET 131 -#define PIDX_KDF_PARAM_SEED 132 -#define PIDX_KDF_PARAM_SIZE 74 -#define PIDX_KDF_PARAM_SSHKDF_SESSION_ID 133 -#define PIDX_KDF_PARAM_SSHKDF_TYPE 134 -#define PIDX_KDF_PARAM_SSHKDF_XCGHASH 135 -#define PIDX_KDF_PARAM_THREADS 136 -#define PIDX_KDF_PARAM_UKM 137 -#define PIDX_KDF_PARAM_X942_ACVPINFO 138 -#define PIDX_KDF_PARAM_X942_PARTYUINFO 139 -#define PIDX_KDF_PARAM_X942_PARTYVINFO 140 -#define PIDX_KDF_PARAM_X942_SUPP_PRIVINFO 141 -#define PIDX_KDF_PARAM_X942_SUPP_PUBINFO 142 -#define PIDX_KDF_PARAM_X942_USE_KEYBITS 143 -#define PIDX_KEM_PARAM_IKME 144 -#define PIDX_KEM_PARAM_OPERATION 145 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_BLOCK_PADDING 146 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MAX_EARLY_DATA 147 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MAX_FRAG_LEN 148 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MODE 49 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_OPTIONS 149 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_READ_AHEAD 150 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_STREAM_MAC 151 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_TLSTREE 152 -#define PIDX_LIBSSL_RECORD_LAYER_PARAM_USE_ETM 153 -#define PIDX_LIBSSL_RECORD_LAYER_READ_BUFFER_LEN 154 -#define PIDX_MAC_PARAM_BLOCK_SIZE 155 +#define PIDX_KDF_PARAM_SALT 134 +#define PIDX_KDF_PARAM_SCRYPT_MAXMEM 135 +#define PIDX_KDF_PARAM_SCRYPT_N 136 +#define PIDX_KDF_PARAM_SCRYPT_P 137 +#define PIDX_KDF_PARAM_SCRYPT_R 124 +#define PIDX_KDF_PARAM_SECRET 138 +#define PIDX_KDF_PARAM_SEED 139 +#define PIDX_KDF_PARAM_SIZE 80 +#define PIDX_KDF_PARAM_SSHKDF_SESSION_ID 140 +#define PIDX_KDF_PARAM_SSHKDF_TYPE 141 +#define PIDX_KDF_PARAM_SSHKDF_XCGHASH 142 +#define PIDX_KDF_PARAM_THREADS 143 +#define PIDX_KDF_PARAM_UKM 144 +#define PIDX_KDF_PARAM_X942_ACVPINFO 145 +#define PIDX_KDF_PARAM_X942_PARTYUINFO 146 +#define PIDX_KDF_PARAM_X942_PARTYVINFO 147 +#define PIDX_KDF_PARAM_X942_SUPP_PRIVINFO 148 +#define PIDX_KDF_PARAM_X942_SUPP_PUBINFO 149 +#define PIDX_KDF_PARAM_X942_USE_KEYBITS 150 +#define PIDX_KEM_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_KEM_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_KEM_PARAM_IKME 151 +#define PIDX_KEM_PARAM_OPERATION 152 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_BLOCK_PADDING 153 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_HS_PADDING 154 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MAX_EARLY_DATA 155 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MAX_FRAG_LEN 156 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_MODE 55 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_OPTIONS 157 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_READ_AHEAD 158 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_STREAM_MAC 159 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_TLSTREE 160 +#define PIDX_LIBSSL_RECORD_LAYER_PARAM_USE_ETM 161 +#define PIDX_LIBSSL_RECORD_LAYER_READ_BUFFER_LEN 162 +#define PIDX_MAC_PARAM_BLOCK_SIZE 163 #define PIDX_MAC_PARAM_CIPHER PIDX_ALG_PARAM_CIPHER -#define PIDX_MAC_PARAM_CUSTOM 156 -#define PIDX_MAC_PARAM_C_ROUNDS 157 +#define PIDX_MAC_PARAM_CUSTOM 164 +#define PIDX_MAC_PARAM_C_ROUNDS 165 #define PIDX_MAC_PARAM_DIGEST PIDX_ALG_PARAM_DIGEST -#define PIDX_MAC_PARAM_DIGEST_NOINIT 158 -#define PIDX_MAC_PARAM_DIGEST_ONESHOT 159 -#define PIDX_MAC_PARAM_D_ROUNDS 160 -#define PIDX_MAC_PARAM_IV 46 -#define PIDX_MAC_PARAM_KEY 120 +#define PIDX_MAC_PARAM_DIGEST_NOINIT 166 +#define PIDX_MAC_PARAM_DIGEST_ONESHOT 167 +#define PIDX_MAC_PARAM_D_ROUNDS 168 +#define PIDX_MAC_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_MAC_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_MAC_PARAM_FIPS_NO_SHORT_MAC PIDX_PROV_PARAM_NO_SHORT_MAC +#define PIDX_MAC_PARAM_IV 52 +#define PIDX_MAC_PARAM_KEY 127 #define PIDX_MAC_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_MAC_PARAM_SALT 127 -#define PIDX_MAC_PARAM_SIZE 74 -#define PIDX_MAC_PARAM_TLS_DATA_SIZE 161 -#define PIDX_MAC_PARAM_XOF 76 -#define PIDX_OBJECT_PARAM_DATA 111 -#define PIDX_OBJECT_PARAM_DATA_STRUCTURE 162 -#define PIDX_OBJECT_PARAM_DATA_TYPE 163 -#define PIDX_OBJECT_PARAM_DESC 164 -#define PIDX_OBJECT_PARAM_REFERENCE 165 -#define PIDX_OBJECT_PARAM_TYPE 134 -#define PIDX_PASSPHRASE_PARAM_INFO 115 -#define PIDX_PKEY_PARAM_BITS 166 +#define PIDX_MAC_PARAM_SALT 134 +#define PIDX_MAC_PARAM_SIZE 80 +#define PIDX_MAC_PARAM_TLS_DATA_SIZE 169 +#define PIDX_MAC_PARAM_XOF 82 +#define PIDX_OBJECT_PARAM_DATA 117 +#define PIDX_OBJECT_PARAM_DATA_STRUCTURE 170 +#define PIDX_OBJECT_PARAM_DATA_TYPE 171 +#define PIDX_OBJECT_PARAM_DESC 172 +#define PIDX_OBJECT_PARAM_REFERENCE 173 +#define PIDX_OBJECT_PARAM_TYPE 141 +#define PIDX_PASSPHRASE_PARAM_INFO 122 +#define PIDX_PKEY_PARAM_ALGORITHM_ID PIDX_ALG_PARAM_ALGORITHM_ID +#define PIDX_PKEY_PARAM_ALGORITHM_ID_PARAMS PIDX_ALG_PARAM_ALGORITHM_ID_PARAMS +#define PIDX_PKEY_PARAM_BITS 174 #define PIDX_PKEY_PARAM_CIPHER PIDX_ALG_PARAM_CIPHER -#define PIDX_PKEY_PARAM_DEFAULT_DIGEST 167 -#define PIDX_PKEY_PARAM_DHKEM_IKM 168 -#define PIDX_PKEY_PARAM_DH_GENERATOR 169 -#define PIDX_PKEY_PARAM_DH_PRIV_LEN 170 +#define PIDX_PKEY_PARAM_DEFAULT_DIGEST 175 +#define PIDX_PKEY_PARAM_DHKEM_IKM 176 +#define PIDX_PKEY_PARAM_DH_GENERATOR 177 +#define PIDX_PKEY_PARAM_DH_PRIV_LEN 178 #define PIDX_PKEY_PARAM_DIGEST PIDX_ALG_PARAM_DIGEST -#define PIDX_PKEY_PARAM_DIGEST_SIZE 171 -#define PIDX_PKEY_PARAM_DIST_ID 172 -#define PIDX_PKEY_PARAM_EC_A 173 -#define PIDX_PKEY_PARAM_EC_B 174 -#define PIDX_PKEY_PARAM_EC_CHAR2_M 175 -#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K1 176 -#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K2 177 -#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K3 178 -#define PIDX_PKEY_PARAM_EC_CHAR2_TP_BASIS 179 -#define PIDX_PKEY_PARAM_EC_CHAR2_TYPE 180 -#define PIDX_PKEY_PARAM_EC_COFACTOR 181 -#define PIDX_PKEY_PARAM_EC_DECODED_FROM_EXPLICIT_PARAMS 182 -#define PIDX_PKEY_PARAM_EC_ENCODING 183 -#define PIDX_PKEY_PARAM_EC_FIELD_TYPE 184 -#define PIDX_PKEY_PARAM_EC_GENERATOR 185 -#define PIDX_PKEY_PARAM_EC_GROUP_CHECK_TYPE 186 -#define PIDX_PKEY_PARAM_EC_INCLUDE_PUBLIC 187 -#define PIDX_PKEY_PARAM_EC_ORDER 188 -#define PIDX_PKEY_PARAM_EC_P 130 -#define PIDX_PKEY_PARAM_EC_POINT_CONVERSION_FORMAT 189 -#define PIDX_PKEY_PARAM_EC_PUB_X 190 -#define PIDX_PKEY_PARAM_EC_PUB_Y 191 -#define PIDX_PKEY_PARAM_EC_SEED 132 -#define PIDX_PKEY_PARAM_ENCODED_PUBLIC_KEY 192 +#define PIDX_PKEY_PARAM_DIGEST_SIZE 179 +#define PIDX_PKEY_PARAM_DIST_ID 180 +#define PIDX_PKEY_PARAM_EC_A 181 +#define PIDX_PKEY_PARAM_EC_B 182 +#define PIDX_PKEY_PARAM_EC_CHAR2_M 183 +#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K1 184 +#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K2 185 +#define PIDX_PKEY_PARAM_EC_CHAR2_PP_K3 186 +#define PIDX_PKEY_PARAM_EC_CHAR2_TP_BASIS 187 +#define PIDX_PKEY_PARAM_EC_CHAR2_TYPE 188 +#define PIDX_PKEY_PARAM_EC_COFACTOR 189 +#define PIDX_PKEY_PARAM_EC_DECODED_FROM_EXPLICIT_PARAMS 190 +#define PIDX_PKEY_PARAM_EC_ENCODING 191 +#define PIDX_PKEY_PARAM_EC_FIELD_TYPE 192 +#define PIDX_PKEY_PARAM_EC_GENERATOR 193 +#define PIDX_PKEY_PARAM_EC_GROUP_CHECK_TYPE 194 +#define PIDX_PKEY_PARAM_EC_INCLUDE_PUBLIC 195 +#define PIDX_PKEY_PARAM_EC_ORDER 196 +#define PIDX_PKEY_PARAM_EC_P 137 +#define PIDX_PKEY_PARAM_EC_POINT_CONVERSION_FORMAT 197 +#define PIDX_PKEY_PARAM_EC_PUB_X 198 +#define PIDX_PKEY_PARAM_EC_PUB_Y 199 +#define PIDX_PKEY_PARAM_EC_SEED 139 +#define PIDX_PKEY_PARAM_ENCODED_PUBLIC_KEY 200 #define PIDX_PKEY_PARAM_ENGINE PIDX_ALG_PARAM_ENGINE -#define PIDX_PKEY_PARAM_FFC_COFACTOR 193 +#define PIDX_PKEY_PARAM_FFC_COFACTOR 201 #define PIDX_PKEY_PARAM_FFC_DIGEST PIDX_PKEY_PARAM_DIGEST #define PIDX_PKEY_PARAM_FFC_DIGEST_PROPS PIDX_PKEY_PARAM_PROPERTIES -#define PIDX_PKEY_PARAM_FFC_G 194 -#define PIDX_PKEY_PARAM_FFC_GINDEX 195 -#define PIDX_PKEY_PARAM_FFC_H 196 -#define PIDX_PKEY_PARAM_FFC_P 130 -#define PIDX_PKEY_PARAM_FFC_PBITS 197 -#define PIDX_PKEY_PARAM_FFC_PCOUNTER 198 -#define PIDX_PKEY_PARAM_FFC_Q 199 -#define PIDX_PKEY_PARAM_FFC_QBITS 200 -#define PIDX_PKEY_PARAM_FFC_SEED 132 -#define PIDX_PKEY_PARAM_FFC_TYPE 134 -#define PIDX_PKEY_PARAM_FFC_VALIDATE_G 201 -#define PIDX_PKEY_PARAM_FFC_VALIDATE_LEGACY 202 -#define PIDX_PKEY_PARAM_FFC_VALIDATE_PQ 203 -#define PIDX_PKEY_PARAM_GROUP_NAME 204 -#define PIDX_PKEY_PARAM_IMPLICIT_REJECTION 5 -#define PIDX_PKEY_PARAM_MANDATORY_DIGEST 205 -#define PIDX_PKEY_PARAM_MASKGENFUNC 206 -#define PIDX_PKEY_PARAM_MAX_SIZE 207 -#define PIDX_PKEY_PARAM_MGF1_DIGEST 208 -#define PIDX_PKEY_PARAM_MGF1_PROPERTIES 209 -#define PIDX_PKEY_PARAM_PAD_MODE 210 -#define PIDX_PKEY_PARAM_PRIV_KEY 211 +#define PIDX_PKEY_PARAM_FFC_G 202 +#define PIDX_PKEY_PARAM_FFC_GINDEX 203 +#define PIDX_PKEY_PARAM_FFC_H 204 +#define PIDX_PKEY_PARAM_FFC_P 137 +#define PIDX_PKEY_PARAM_FFC_PBITS 205 +#define PIDX_PKEY_PARAM_FFC_PCOUNTER 206 +#define PIDX_PKEY_PARAM_FFC_Q 207 +#define PIDX_PKEY_PARAM_FFC_QBITS 208 +#define PIDX_PKEY_PARAM_FFC_SEED 139 +#define PIDX_PKEY_PARAM_FFC_TYPE 141 +#define PIDX_PKEY_PARAM_FFC_VALIDATE_G 209 +#define PIDX_PKEY_PARAM_FFC_VALIDATE_LEGACY 210 +#define PIDX_PKEY_PARAM_FFC_VALIDATE_PQ 211 +#define PIDX_PKEY_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK 212 +#define PIDX_PKEY_PARAM_FIPS_KEY_CHECK 213 +#define PIDX_PKEY_PARAM_FIPS_SIGN_CHECK 214 +#define PIDX_PKEY_PARAM_GROUP_NAME 215 +#define PIDX_PKEY_PARAM_IMPLICIT_REJECTION 8 +#define PIDX_PKEY_PARAM_MANDATORY_DIGEST 216 +#define PIDX_PKEY_PARAM_MASKGENFUNC 217 +#define PIDX_PKEY_PARAM_MAX_SIZE 218 +#define PIDX_PKEY_PARAM_MGF1_DIGEST 219 +#define PIDX_PKEY_PARAM_MGF1_PROPERTIES 220 +#define PIDX_PKEY_PARAM_PAD_MODE 221 +#define PIDX_PKEY_PARAM_PRIV_KEY 222 #define PIDX_PKEY_PARAM_PROPERTIES PIDX_ALG_PARAM_PROPERTIES -#define PIDX_PKEY_PARAM_PUB_KEY 212 +#define PIDX_PKEY_PARAM_PUB_KEY 223 #define PIDX_PKEY_PARAM_RSA_BITS PIDX_PKEY_PARAM_BITS -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT 213 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT1 214 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT2 215 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT3 216 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT4 217 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT5 218 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT6 219 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT7 220 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT8 221 -#define PIDX_PKEY_PARAM_RSA_COEFFICIENT9 222 -#define PIDX_PKEY_PARAM_RSA_D 223 -#define PIDX_PKEY_PARAM_RSA_DERIVE_FROM_PQ 224 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT 224 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT1 225 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT2 226 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT3 227 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT4 228 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT5 229 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT6 230 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT7 231 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT8 232 +#define PIDX_PKEY_PARAM_RSA_COEFFICIENT9 233 +#define PIDX_PKEY_PARAM_RSA_D 234 +#define PIDX_PKEY_PARAM_RSA_DERIVE_FROM_PQ 235 #define PIDX_PKEY_PARAM_RSA_DIGEST PIDX_PKEY_PARAM_DIGEST #define PIDX_PKEY_PARAM_RSA_DIGEST_PROPS PIDX_PKEY_PARAM_PROPERTIES -#define PIDX_PKEY_PARAM_RSA_E 225 -#define PIDX_PKEY_PARAM_RSA_EXPONENT 226 -#define PIDX_PKEY_PARAM_RSA_EXPONENT1 227 -#define PIDX_PKEY_PARAM_RSA_EXPONENT10 228 -#define PIDX_PKEY_PARAM_RSA_EXPONENT2 229 -#define PIDX_PKEY_PARAM_RSA_EXPONENT3 230 -#define PIDX_PKEY_PARAM_RSA_EXPONENT4 231 -#define PIDX_PKEY_PARAM_RSA_EXPONENT5 232 -#define PIDX_PKEY_PARAM_RSA_EXPONENT6 233 -#define PIDX_PKEY_PARAM_RSA_EXPONENT7 234 -#define PIDX_PKEY_PARAM_RSA_EXPONENT8 235 -#define PIDX_PKEY_PARAM_RSA_EXPONENT9 236 -#define PIDX_PKEY_PARAM_RSA_FACTOR 237 -#define PIDX_PKEY_PARAM_RSA_FACTOR1 238 -#define PIDX_PKEY_PARAM_RSA_FACTOR10 239 -#define PIDX_PKEY_PARAM_RSA_FACTOR2 240 -#define PIDX_PKEY_PARAM_RSA_FACTOR3 241 -#define PIDX_PKEY_PARAM_RSA_FACTOR4 242 -#define PIDX_PKEY_PARAM_RSA_FACTOR5 243 -#define PIDX_PKEY_PARAM_RSA_FACTOR6 244 -#define PIDX_PKEY_PARAM_RSA_FACTOR7 245 -#define PIDX_PKEY_PARAM_RSA_FACTOR8 246 -#define PIDX_PKEY_PARAM_RSA_FACTOR9 247 +#define PIDX_PKEY_PARAM_RSA_E 236 +#define PIDX_PKEY_PARAM_RSA_EXPONENT 237 +#define PIDX_PKEY_PARAM_RSA_EXPONENT1 238 +#define PIDX_PKEY_PARAM_RSA_EXPONENT10 239 +#define PIDX_PKEY_PARAM_RSA_EXPONENT2 240 +#define PIDX_PKEY_PARAM_RSA_EXPONENT3 241 +#define PIDX_PKEY_PARAM_RSA_EXPONENT4 242 +#define PIDX_PKEY_PARAM_RSA_EXPONENT5 243 +#define PIDX_PKEY_PARAM_RSA_EXPONENT6 244 +#define PIDX_PKEY_PARAM_RSA_EXPONENT7 245 +#define PIDX_PKEY_PARAM_RSA_EXPONENT8 246 +#define PIDX_PKEY_PARAM_RSA_EXPONENT9 247 +#define PIDX_PKEY_PARAM_RSA_FACTOR 248 +#define PIDX_PKEY_PARAM_RSA_FACTOR1 249 +#define PIDX_PKEY_PARAM_RSA_FACTOR10 250 +#define PIDX_PKEY_PARAM_RSA_FACTOR2 251 +#define PIDX_PKEY_PARAM_RSA_FACTOR3 252 +#define PIDX_PKEY_PARAM_RSA_FACTOR4 253 +#define PIDX_PKEY_PARAM_RSA_FACTOR5 254 +#define PIDX_PKEY_PARAM_RSA_FACTOR6 255 +#define PIDX_PKEY_PARAM_RSA_FACTOR7 256 +#define PIDX_PKEY_PARAM_RSA_FACTOR8 257 +#define PIDX_PKEY_PARAM_RSA_FACTOR9 258 #define PIDX_PKEY_PARAM_RSA_MASKGENFUNC PIDX_PKEY_PARAM_MASKGENFUNC #define PIDX_PKEY_PARAM_RSA_MGF1_DIGEST PIDX_PKEY_PARAM_MGF1_DIGEST -#define PIDX_PKEY_PARAM_RSA_N 129 -#define PIDX_PKEY_PARAM_RSA_PRIMES 248 -#define PIDX_PKEY_PARAM_RSA_PSS_SALTLEN 249 -#define PIDX_PKEY_PARAM_RSA_TEST_P1 250 -#define PIDX_PKEY_PARAM_RSA_TEST_P2 251 -#define PIDX_PKEY_PARAM_RSA_TEST_Q1 252 -#define PIDX_PKEY_PARAM_RSA_TEST_Q2 253 -#define PIDX_PKEY_PARAM_RSA_TEST_XP 254 -#define PIDX_PKEY_PARAM_RSA_TEST_XP1 255 -#define PIDX_PKEY_PARAM_RSA_TEST_XP2 256 -#define PIDX_PKEY_PARAM_RSA_TEST_XQ 257 -#define PIDX_PKEY_PARAM_RSA_TEST_XQ1 258 -#define PIDX_PKEY_PARAM_RSA_TEST_XQ2 259 -#define PIDX_PKEY_PARAM_SECURITY_BITS 260 +#define PIDX_PKEY_PARAM_RSA_N 136 +#define PIDX_PKEY_PARAM_RSA_PRIMES 259 +#define PIDX_PKEY_PARAM_RSA_PSS_SALTLEN 260 +#define PIDX_PKEY_PARAM_RSA_TEST_P1 261 +#define PIDX_PKEY_PARAM_RSA_TEST_P2 262 +#define PIDX_PKEY_PARAM_RSA_TEST_Q1 263 +#define PIDX_PKEY_PARAM_RSA_TEST_Q2 264 +#define PIDX_PKEY_PARAM_RSA_TEST_XP 265 +#define PIDX_PKEY_PARAM_RSA_TEST_XP1 266 +#define PIDX_PKEY_PARAM_RSA_TEST_XP2 267 +#define PIDX_PKEY_PARAM_RSA_TEST_XQ 268 +#define PIDX_PKEY_PARAM_RSA_TEST_XQ1 269 +#define PIDX_PKEY_PARAM_RSA_TEST_XQ2 270 +#define PIDX_PKEY_PARAM_SECURITY_BITS 271 #define PIDX_PKEY_PARAM_USE_COFACTOR_ECDH PIDX_PKEY_PARAM_USE_COFACTOR_FLAG -#define PIDX_PKEY_PARAM_USE_COFACTOR_FLAG 261 -#define PIDX_PROV_PARAM_BUILDINFO 262 -#define PIDX_PROV_PARAM_CORE_MODULE_FILENAME 263 -#define PIDX_PROV_PARAM_CORE_PROV_NAME 264 -#define PIDX_PROV_PARAM_CORE_VERSION 265 -#define PIDX_PROV_PARAM_DRBG_TRUNC_DIGEST 266 -#define PIDX_PROV_PARAM_NAME 267 -#define PIDX_PROV_PARAM_SECURITY_CHECKS 268 -#define PIDX_PROV_PARAM_SELF_TEST_DESC 269 -#define PIDX_PROV_PARAM_SELF_TEST_PHASE 270 -#define PIDX_PROV_PARAM_SELF_TEST_TYPE 271 -#define PIDX_PROV_PARAM_STATUS 272 -#define PIDX_PROV_PARAM_TLS1_PRF_EMS_CHECK 273 -#define PIDX_PROV_PARAM_VERSION 108 -#define PIDX_RAND_PARAM_GENERATE 274 -#define PIDX_RAND_PARAM_MAX_REQUEST 275 -#define PIDX_RAND_PARAM_STATE 276 -#define PIDX_RAND_PARAM_STRENGTH 277 -#define PIDX_RAND_PARAM_TEST_ENTROPY 278 -#define PIDX_RAND_PARAM_TEST_NONCE 279 -#define PIDX_SIGNATURE_PARAM_ALGORITHM_ID 280 -#define PIDX_SIGNATURE_PARAM_CONTEXT_STRING 281 +#define PIDX_PKEY_PARAM_USE_COFACTOR_FLAG 272 +#define PIDX_PROV_PARAM_BUILDINFO 273 +#define PIDX_PROV_PARAM_CORE_MODULE_FILENAME 274 +#define PIDX_PROV_PARAM_CORE_PROV_NAME 275 +#define PIDX_PROV_PARAM_CORE_VERSION 276 +#define PIDX_PROV_PARAM_DRBG_TRUNC_DIGEST 277 +#define PIDX_PROV_PARAM_DSA_SIGN_DISABLED 278 +#define PIDX_PROV_PARAM_ECDH_COFACTOR_CHECK 279 +#define PIDX_PROV_PARAM_HKDF_DIGEST_CHECK 280 +#define PIDX_PROV_PARAM_HKDF_KEY_CHECK 281 +#define PIDX_PROV_PARAM_HMAC_KEY_CHECK 282 +#define PIDX_PROV_PARAM_KBKDF_KEY_CHECK 283 +#define PIDX_PROV_PARAM_KMAC_KEY_CHECK 284 +#define PIDX_PROV_PARAM_NAME 285 +#define PIDX_PROV_PARAM_NO_SHORT_MAC 286 +#define PIDX_PROV_PARAM_PBKDF2_LOWER_BOUND_CHECK 287 +#define PIDX_PROV_PARAM_RSA_PKCS15_PAD_DISABLED 288 +#define PIDX_PROV_PARAM_RSA_PSS_SALTLEN_CHECK 289 +#define PIDX_PROV_PARAM_RSA_SIGN_X931_PAD_DISABLED 290 +#define PIDX_PROV_PARAM_SECURITY_CHECKS 291 +#define PIDX_PROV_PARAM_SELF_TEST_DESC 292 +#define PIDX_PROV_PARAM_SELF_TEST_PHASE 293 +#define PIDX_PROV_PARAM_SELF_TEST_TYPE 294 +#define PIDX_PROV_PARAM_SIGNATURE_DIGEST_CHECK 295 +#define PIDX_PROV_PARAM_SSHKDF_DIGEST_CHECK 296 +#define PIDX_PROV_PARAM_SSHKDF_KEY_CHECK 297 +#define PIDX_PROV_PARAM_SSKDF_DIGEST_CHECK 298 +#define PIDX_PROV_PARAM_SSKDF_KEY_CHECK 299 +#define PIDX_PROV_PARAM_STATUS 300 +#define PIDX_PROV_PARAM_TDES_ENCRYPT_DISABLED 301 +#define PIDX_PROV_PARAM_TLS13_KDF_DIGEST_CHECK 302 +#define PIDX_PROV_PARAM_TLS13_KDF_KEY_CHECK 303 +#define PIDX_PROV_PARAM_TLS1_PRF_DIGEST_CHECK 304 +#define PIDX_PROV_PARAM_TLS1_PRF_EMS_CHECK 305 +#define PIDX_PROV_PARAM_TLS1_PRF_KEY_CHECK 306 +#define PIDX_PROV_PARAM_VERSION 114 +#define PIDX_PROV_PARAM_X942KDF_KEY_CHECK 307 +#define PIDX_PROV_PARAM_X963KDF_DIGEST_CHECK 308 +#define PIDX_PROV_PARAM_X963KDF_KEY_CHECK 309 +#define PIDX_RAND_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_RAND_PARAM_GENERATE 310 +#define PIDX_RAND_PARAM_MAX_REQUEST 311 +#define PIDX_RAND_PARAM_STATE 312 +#define PIDX_RAND_PARAM_STRENGTH 313 +#define PIDX_RAND_PARAM_TEST_ENTROPY 314 +#define PIDX_RAND_PARAM_TEST_NONCE 315 +#define PIDX_SIGNATURE_PARAM_ALGORITHM_ID PIDX_PKEY_PARAM_ALGORITHM_ID +#define PIDX_SIGNATURE_PARAM_ALGORITHM_ID_PARAMS PIDX_PKEY_PARAM_ALGORITHM_ID_PARAMS +#define PIDX_SIGNATURE_PARAM_CONTEXT_STRING 316 #define PIDX_SIGNATURE_PARAM_DIGEST PIDX_PKEY_PARAM_DIGEST #define PIDX_SIGNATURE_PARAM_DIGEST_SIZE PIDX_PKEY_PARAM_DIGEST_SIZE -#define PIDX_SIGNATURE_PARAM_INSTANCE 282 -#define PIDX_SIGNATURE_PARAM_KAT 283 +#define PIDX_SIGNATURE_PARAM_FIPS_APPROVED_INDICATOR PIDX_ALG_PARAM_FIPS_APPROVED_INDICATOR +#define PIDX_SIGNATURE_PARAM_FIPS_DIGEST_CHECK PIDX_PKEY_PARAM_FIPS_DIGEST_CHECK +#define PIDX_SIGNATURE_PARAM_FIPS_KEY_CHECK PIDX_PKEY_PARAM_FIPS_KEY_CHECK +#define PIDX_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK 289 +#define PIDX_SIGNATURE_PARAM_FIPS_SIGN_CHECK PIDX_PKEY_PARAM_FIPS_SIGN_CHECK +#define PIDX_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK 317 +#define PIDX_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE 318 +#define PIDX_SIGNATURE_PARAM_INSTANCE 319 +#define PIDX_SIGNATURE_PARAM_KAT 320 #define PIDX_SIGNATURE_PARAM_MGF1_DIGEST PIDX_PKEY_PARAM_MGF1_DIGEST #define PIDX_SIGNATURE_PARAM_MGF1_PROPERTIES PIDX_PKEY_PARAM_MGF1_PROPERTIES -#define PIDX_SIGNATURE_PARAM_NONCE_TYPE 284 +#define PIDX_SIGNATURE_PARAM_NONCE_TYPE 321 #define PIDX_SIGNATURE_PARAM_PAD_MODE PIDX_PKEY_PARAM_PAD_MODE #define PIDX_SIGNATURE_PARAM_PROPERTIES PIDX_PKEY_PARAM_PROPERTIES -#define PIDX_SIGNATURE_PARAM_PSS_SALTLEN 249 -#define PIDX_STORE_PARAM_ALIAS 285 -#define PIDX_STORE_PARAM_DIGEST 1 -#define PIDX_STORE_PARAM_EXPECT 286 -#define PIDX_STORE_PARAM_FINGERPRINT 287 -#define PIDX_STORE_PARAM_INPUT_TYPE 288 -#define PIDX_STORE_PARAM_ISSUER 267 -#define PIDX_STORE_PARAM_PROPERTIES 4 -#define PIDX_STORE_PARAM_SERIAL 289 -#define PIDX_STORE_PARAM_SUBJECT 290 +#define PIDX_SIGNATURE_PARAM_PSS_SALTLEN 260 +#define PIDX_SIGNATURE_PARAM_SIGNATURE 322 +#define PIDX_STORE_PARAM_ALIAS 323 +#define PIDX_STORE_PARAM_DIGEST 3 +#define PIDX_STORE_PARAM_EXPECT 324 +#define PIDX_STORE_PARAM_FINGERPRINT 325 +#define PIDX_STORE_PARAM_INPUT_TYPE 326 +#define PIDX_STORE_PARAM_ISSUER 285 +#define PIDX_STORE_PARAM_PROPERTIES 7 +#define PIDX_STORE_PARAM_SERIAL 327 +#define PIDX_STORE_PARAM_SUBJECT 328 diff --git a/include/internal/quic_ackm.h b/include/internal/quic_ackm.h index 69b862d9c5..c271dfca2e 100644 --- a/include/internal/quic_ackm.h +++ b/include/internal/quic_ackm.h @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -115,7 +115,7 @@ struct ossl_ackm_tx_pkt_st { void (*on_discarded)(void *arg); void *cb_arg; - /* + /* * (Internal use fields; must be zero-initialized.) * * Keep a TX history list, anext is used to manifest diff --git a/include/internal/refcount.h b/include/internal/refcount.h index 0bab061228..5ff45ac980 100644 --- a/include/internal/refcount.h +++ b/include/internal/refcount.h @@ -199,7 +199,7 @@ typedef struct { # ifdef OPENSSL_THREADS -static ossl_unused ossl_inline int CRYPTO_UP_REF(CRYPTO_REF_COUNT *refcnt, +static ossl_unused ossl_inline int CRYPTO_UP_REF(CRYPTO_REF_COUNT *refcnt, int *ret) { return CRYPTO_atomic_add(&refcnt->val, 1, ret, refcnt->lock); @@ -237,7 +237,7 @@ static ossl_unused ossl_inline void CRYPTO_FREE_REF(CRYPTO_REF_COUNT *refcnt) # else /* OPENSSL_THREADS */ -static ossl_unused ossl_inline int CRYPTO_UP_REF(CRYPTO_REF_COUNT *refcnt, +static ossl_unused ossl_inline int CRYPTO_UP_REF(CRYPTO_REF_COUNT *refcnt, int *ret) { refcnt->val++; diff --git a/include/internal/sha3.h b/include/internal/sha3.h index 332916aa54..aebdd6eb8f 100644 --- a/include/internal/sha3.h +++ b/include/internal/sha3.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -26,8 +26,7 @@ typedef size_t (sha3_absorb_fn)(void *vctx, const void *in, size_t inlen); typedef int (sha3_final_fn)(void *vctx, unsigned char *out, size_t outlen); typedef int (sha3_squeeze_fn)(void *vctx, unsigned char *out, size_t outlen); -typedef struct prov_sha3_meth_st -{ +typedef struct prov_sha3_meth_st { sha3_absorb_fn *absorb; sha3_final_fn *final; sha3_squeeze_fn *squeeze; @@ -51,8 +50,8 @@ struct keccak_st { void ossl_sha3_reset(KECCAK1600_CTX *ctx); int ossl_sha3_init(KECCAK1600_CTX *ctx, unsigned char pad, size_t bitlen); -int ossl_keccak_kmac_init(KECCAK1600_CTX *ctx, unsigned char pad, - size_t bitlen); +int ossl_keccak_init(KECCAK1600_CTX *ctx, unsigned char pad, + size_t typelen, size_t mdlen); int ossl_sha3_update(KECCAK1600_CTX *ctx, const void *_inp, size_t len); int ossl_sha3_final(KECCAK1600_CTX *ctx, unsigned char *out, size_t outlen); int ossl_sha3_squeeze(KECCAK1600_CTX *ctx, unsigned char *out, size_t outlen); diff --git a/include/internal/to_hex.h b/include/internal/to_hex.h new file mode 100644 index 0000000000..e37e9f0b43 --- /dev/null +++ b/include/internal/to_hex.h @@ -0,0 +1,27 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OSSL_INTERNAL_TO_HEX_H +# define OSSL_INTERNAL_TO_HEX_H +# pragma once + +static ossl_inline size_t to_hex(char *buf, uint8_t n, const char hexdig[17]) +{ + *buf++ = hexdig[(n >> 4) & 0xf]; + *buf = hexdig[n & 0xf]; + return 2; +} + +static ossl_inline size_t ossl_to_lowerhex(char *buf, uint8_t n) +{ + static const char hexdig[] = "0123456789abcdef"; + + return to_hex(buf, n, hexdig); +} +#endif diff --git a/include/openssl/cmp.h b/include/openssl/cmp.h index 80d9709f1a..05aed3029d 100644 --- a/include/openssl/cmp.h +++ b/include/openssl/cmp.h @@ -275,6 +275,46 @@ SKM_DEFINE_STACK_OF_INTERNAL(OSSL_CMP_ITAV, OSSL_CMP_ITAV, OSSL_CMP_ITAV) #define sk_OSSL_CMP_ITAV_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_CMP_ITAV) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_CMP_ITAV_sk_type(sk), ossl_check_OSSL_CMP_ITAV_copyfunc_type(copyfunc), ossl_check_OSSL_CMP_ITAV_freefunc_type(freefunc))) #define sk_OSSL_CMP_ITAV_set_cmp_func(sk, cmp) ((sk_OSSL_CMP_ITAV_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_CMP_ITAV_sk_type(sk), ossl_check_OSSL_CMP_ITAV_compfunc_type(cmp))) + +typedef struct ossl_cmp_crlstatus_st OSSL_CMP_CRLSTATUS; +SKM_DEFINE_STACK_OF_INTERNAL(OSSL_CMP_CRLSTATUS, OSSL_CMP_CRLSTATUS, OSSL_CMP_CRLSTATUS) +#define sk_OSSL_CMP_CRLSTATUS_num(sk) OPENSSL_sk_num(ossl_check_const_OSSL_CMP_CRLSTATUS_sk_type(sk)) +#define sk_OSSL_CMP_CRLSTATUS_value(sk, idx) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_value(ossl_check_const_OSSL_CMP_CRLSTATUS_sk_type(sk), (idx))) +#define sk_OSSL_CMP_CRLSTATUS_new(cmp) ((STACK_OF(OSSL_CMP_CRLSTATUS) *)OPENSSL_sk_new(ossl_check_OSSL_CMP_CRLSTATUS_compfunc_type(cmp))) +#define sk_OSSL_CMP_CRLSTATUS_new_null() ((STACK_OF(OSSL_CMP_CRLSTATUS) *)OPENSSL_sk_new_null()) +#define sk_OSSL_CMP_CRLSTATUS_new_reserve(cmp, n) ((STACK_OF(OSSL_CMP_CRLSTATUS) *)OPENSSL_sk_new_reserve(ossl_check_OSSL_CMP_CRLSTATUS_compfunc_type(cmp), (n))) +#define sk_OSSL_CMP_CRLSTATUS_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), (n)) +#define sk_OSSL_CMP_CRLSTATUS_free(sk) OPENSSL_sk_free(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk)) +#define sk_OSSL_CMP_CRLSTATUS_zero(sk) OPENSSL_sk_zero(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk)) +#define sk_OSSL_CMP_CRLSTATUS_delete(sk, i) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_delete(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), (i))) +#define sk_OSSL_CMP_CRLSTATUS_delete_ptr(sk, ptr) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_delete_ptr(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr))) +#define sk_OSSL_CMP_CRLSTATUS_push(sk, ptr) OPENSSL_sk_push(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr)) +#define sk_OSSL_CMP_CRLSTATUS_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr)) +#define sk_OSSL_CMP_CRLSTATUS_pop(sk) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_pop(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk))) +#define sk_OSSL_CMP_CRLSTATUS_shift(sk) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_shift(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk))) +#define sk_OSSL_CMP_CRLSTATUS_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk),ossl_check_OSSL_CMP_CRLSTATUS_freefunc_type(freefunc)) +#define sk_OSSL_CMP_CRLSTATUS_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr), (idx)) +#define sk_OSSL_CMP_CRLSTATUS_set(sk, idx, ptr) ((OSSL_CMP_CRLSTATUS *)OPENSSL_sk_set(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), (idx), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr))) +#define sk_OSSL_CMP_CRLSTATUS_find(sk, ptr) OPENSSL_sk_find(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr)) +#define sk_OSSL_CMP_CRLSTATUS_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr)) +#define sk_OSSL_CMP_CRLSTATUS_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_type(ptr), pnum) +#define sk_OSSL_CMP_CRLSTATUS_sort(sk) OPENSSL_sk_sort(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk)) +#define sk_OSSL_CMP_CRLSTATUS_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_OSSL_CMP_CRLSTATUS_sk_type(sk)) +#define sk_OSSL_CMP_CRLSTATUS_dup(sk) ((STACK_OF(OSSL_CMP_CRLSTATUS) *)OPENSSL_sk_dup(ossl_check_const_OSSL_CMP_CRLSTATUS_sk_type(sk))) +#define sk_OSSL_CMP_CRLSTATUS_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_CMP_CRLSTATUS) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_copyfunc_type(copyfunc), ossl_check_OSSL_CMP_CRLSTATUS_freefunc_type(freefunc))) +#define sk_OSSL_CMP_CRLSTATUS_set_cmp_func(sk, cmp) ((sk_OSSL_CMP_CRLSTATUS_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_CMP_CRLSTATUS_sk_type(sk), ossl_check_OSSL_CMP_CRLSTATUS_compfunc_type(cmp))) + + +typedef OSSL_CRMF_ATTRIBUTETYPEANDVALUE OSSL_CMP_ATAV; +# define OSSL_CMP_ATAV_free OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free +typedef STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) OSSL_CMP_ATAVS; +DECLARE_ASN1_FUNCTIONS(OSSL_CMP_ATAVS) +# define stack_st_OSSL_CMP_ATAV stack_st_OSSL_CRMF_ATTRIBUTETYPEANDVALUE +# define sk_OSSL_CMP_ATAV_num sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_num +# define sk_OSSL_CMP_ATAV_value sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_value +# define sk_OSSL_CMP_ATAV_push sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_push +# define sk_OSSL_CMP_ATAV_pop_free sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_pop_free + typedef struct ossl_cmp_revrepcontent_st OSSL_CMP_REVREPCONTENT; typedef struct ossl_cmp_pkisi_st OSSL_CMP_PKISI; DECLARE_ASN1_FUNCTIONS(OSSL_CMP_PKISI) @@ -376,7 +416,7 @@ void OSSL_CMP_ITAV_set0(OSSL_CMP_ITAV *itav, ASN1_OBJECT *type, ASN1_TYPE *value); ASN1_OBJECT *OSSL_CMP_ITAV_get0_type(const OSSL_CMP_ITAV *itav); ASN1_TYPE *OSSL_CMP_ITAV_get0_value(const OSSL_CMP_ITAV *itav); -int OSSL_CMP_ITAV_push0_stack_item(STACK_OF(OSSL_CMP_ITAV) **itav_sk_p, +int OSSL_CMP_ITAV_push0_stack_item(STACK_OF(OSSL_CMP_ITAV) **sk_p, OSSL_CMP_ITAV *itav); void OSSL_CMP_ITAV_free(OSSL_CMP_ITAV *itav); @@ -397,6 +437,39 @@ int OSSL_CMP_ITAV_get0_rootCaKeyUpdate(const OSSL_CMP_ITAV *itav, X509 **newWithOld, X509 **oldWithNew); +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_create(const X509_CRL *crl, + const X509 *cert, int only_DN); +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_new1(const DIST_POINT_NAME *dpn, + const GENERAL_NAMES *issuer, + const ASN1_TIME *thisUpdate); +int OSSL_CMP_CRLSTATUS_get0(const OSSL_CMP_CRLSTATUS *crlstatus, + DIST_POINT_NAME **dpn, GENERAL_NAMES **issuer, + ASN1_TIME **thisUpdate); +void OSSL_CMP_CRLSTATUS_free(OSSL_CMP_CRLSTATUS *crlstatus); +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_crlStatusList(STACK_OF(OSSL_CMP_CRLSTATUS) *crlStatusList); +int OSSL_CMP_ITAV_get0_crlStatusList(const OSSL_CMP_ITAV *itav, + STACK_OF(OSSL_CMP_CRLSTATUS) **out); +OSSL_CMP_ITAV *OSSL_CMP_ITAV_new_crls(const X509_CRL *crls); +int OSSL_CMP_ITAV_get0_crls(const OSSL_CMP_ITAV *it, STACK_OF(X509_CRL) **out); +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_certReqTemplate(OSSL_CRMF_CERTTEMPLATE *certTemplate, + OSSL_CMP_ATAVS *keySpec); +int OSSL_CMP_ITAV_get1_certReqTemplate(const OSSL_CMP_ITAV *itav, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec); + +OSSL_CMP_ATAV *OSSL_CMP_ATAV_create(ASN1_OBJECT *type, ASN1_TYPE *value); +void OSSL_CMP_ATAV_set0(OSSL_CMP_ATAV *itav, ASN1_OBJECT *type, + ASN1_TYPE *value); +ASN1_OBJECT *OSSL_CMP_ATAV_get0_type(const OSSL_CMP_ATAV *itav); +ASN1_TYPE *OSSL_CMP_ATAV_get0_value(const OSSL_CMP_ATAV *itav); +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_algId(const X509_ALGOR *alg); +X509_ALGOR *OSSL_CMP_ATAV_get0_algId(const OSSL_CMP_ATAV *atav); +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_rsaKeyLen(int len); +int OSSL_CMP_ATAV_get_rsaKeyLen(const OSSL_CMP_ATAV *atav); +int OSSL_CMP_ATAV_push1(OSSL_CMP_ATAVS **sk_p, const OSSL_CMP_ATAV *atav); + void OSSL_CMP_MSG_free(OSSL_CMP_MSG *msg); /* from cmp_ctx.c */ @@ -640,6 +713,12 @@ int OSSL_CMP_get1_caCerts(OSSL_CMP_CTX *ctx, STACK_OF(X509) **out); int OSSL_CMP_get1_rootCaKeyUpdate(OSSL_CMP_CTX *ctx, const X509 *oldWithOld, X509 **newWithNew, X509 **newWithOld, X509 **oldWithNew); +int OSSL_CMP_get1_crlUpdate(OSSL_CMP_CTX *ctx, const X509 *crlcert, + const X509_CRL *last_crl, + X509_CRL **crl); +int OSSL_CMP_get1_certReqTemplate(OSSL_CMP_CTX *ctx, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec); # ifdef __cplusplus } diff --git a/include/openssl/cmp.h.in b/include/openssl/cmp.h.in index ad9eb3429d..d659331fa3 100644 --- a/include/openssl/cmp.h.in +++ b/include/openssl/cmp.h.in @@ -228,6 +228,22 @@ DECLARE_ASN1_DUP_FUNCTION(OSSL_CMP_ITAV) {- generate_stack_macros("OSSL_CMP_ITAV"); -} + +typedef struct ossl_cmp_crlstatus_st OSSL_CMP_CRLSTATUS; +{- + generate_stack_macros("OSSL_CMP_CRLSTATUS"); +-} + +typedef OSSL_CRMF_ATTRIBUTETYPEANDVALUE OSSL_CMP_ATAV; +# define OSSL_CMP_ATAV_free OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free +typedef STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) OSSL_CMP_ATAVS; +DECLARE_ASN1_FUNCTIONS(OSSL_CMP_ATAVS) +# define stack_st_OSSL_CMP_ATAV stack_st_OSSL_CRMF_ATTRIBUTETYPEANDVALUE +# define sk_OSSL_CMP_ATAV_num sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_num +# define sk_OSSL_CMP_ATAV_value sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_value +# define sk_OSSL_CMP_ATAV_push sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_push +# define sk_OSSL_CMP_ATAV_pop_free sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_pop_free + typedef struct ossl_cmp_revrepcontent_st OSSL_CMP_REVREPCONTENT; typedef struct ossl_cmp_pkisi_st OSSL_CMP_PKISI; DECLARE_ASN1_FUNCTIONS(OSSL_CMP_PKISI) @@ -257,7 +273,7 @@ void OSSL_CMP_ITAV_set0(OSSL_CMP_ITAV *itav, ASN1_OBJECT *type, ASN1_TYPE *value); ASN1_OBJECT *OSSL_CMP_ITAV_get0_type(const OSSL_CMP_ITAV *itav); ASN1_TYPE *OSSL_CMP_ITAV_get0_value(const OSSL_CMP_ITAV *itav); -int OSSL_CMP_ITAV_push0_stack_item(STACK_OF(OSSL_CMP_ITAV) **itav_sk_p, +int OSSL_CMP_ITAV_push0_stack_item(STACK_OF(OSSL_CMP_ITAV) **sk_p, OSSL_CMP_ITAV *itav); void OSSL_CMP_ITAV_free(OSSL_CMP_ITAV *itav); @@ -278,6 +294,39 @@ int OSSL_CMP_ITAV_get0_rootCaKeyUpdate(const OSSL_CMP_ITAV *itav, X509 **newWithOld, X509 **oldWithNew); +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_create(const X509_CRL *crl, + const X509 *cert, int only_DN); +OSSL_CMP_CRLSTATUS *OSSL_CMP_CRLSTATUS_new1(const DIST_POINT_NAME *dpn, + const GENERAL_NAMES *issuer, + const ASN1_TIME *thisUpdate); +int OSSL_CMP_CRLSTATUS_get0(const OSSL_CMP_CRLSTATUS *crlstatus, + DIST_POINT_NAME **dpn, GENERAL_NAMES **issuer, + ASN1_TIME **thisUpdate); +void OSSL_CMP_CRLSTATUS_free(OSSL_CMP_CRLSTATUS *crlstatus); +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_crlStatusList(STACK_OF(OSSL_CMP_CRLSTATUS) *crlStatusList); +int OSSL_CMP_ITAV_get0_crlStatusList(const OSSL_CMP_ITAV *itav, + STACK_OF(OSSL_CMP_CRLSTATUS) **out); +OSSL_CMP_ITAV *OSSL_CMP_ITAV_new_crls(const X509_CRL *crls); +int OSSL_CMP_ITAV_get0_crls(const OSSL_CMP_ITAV *it, STACK_OF(X509_CRL) **out); +OSSL_CMP_ITAV +*OSSL_CMP_ITAV_new0_certReqTemplate(OSSL_CRMF_CERTTEMPLATE *certTemplate, + OSSL_CMP_ATAVS *keySpec); +int OSSL_CMP_ITAV_get1_certReqTemplate(const OSSL_CMP_ITAV *itav, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec); + +OSSL_CMP_ATAV *OSSL_CMP_ATAV_create(ASN1_OBJECT *type, ASN1_TYPE *value); +void OSSL_CMP_ATAV_set0(OSSL_CMP_ATAV *itav, ASN1_OBJECT *type, + ASN1_TYPE *value); +ASN1_OBJECT *OSSL_CMP_ATAV_get0_type(const OSSL_CMP_ATAV *itav); +ASN1_TYPE *OSSL_CMP_ATAV_get0_value(const OSSL_CMP_ATAV *itav); +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_algId(const X509_ALGOR *alg); +X509_ALGOR *OSSL_CMP_ATAV_get0_algId(const OSSL_CMP_ATAV *atav); +OSSL_CMP_ATAV *OSSL_CMP_ATAV_new_rsaKeyLen(int len); +int OSSL_CMP_ATAV_get_rsaKeyLen(const OSSL_CMP_ATAV *atav); +int OSSL_CMP_ATAV_push1(OSSL_CMP_ATAVS **sk_p, const OSSL_CMP_ATAV *atav); + void OSSL_CMP_MSG_free(OSSL_CMP_MSG *msg); /* from cmp_ctx.c */ @@ -521,6 +570,12 @@ int OSSL_CMP_get1_caCerts(OSSL_CMP_CTX *ctx, STACK_OF(X509) **out); int OSSL_CMP_get1_rootCaKeyUpdate(OSSL_CMP_CTX *ctx, const X509 *oldWithOld, X509 **newWithNew, X509 **newWithOld, X509 **oldWithNew); +int OSSL_CMP_get1_crlUpdate(OSSL_CMP_CTX *ctx, const X509 *crlcert, + const X509_CRL *last_crl, + X509_CRL **crl); +int OSSL_CMP_get1_certReqTemplate(OSSL_CMP_CTX *ctx, + OSSL_CRMF_CERTTEMPLATE **certTemplate, + OSSL_CMP_ATAVS **keySpec); # ifdef __cplusplus } diff --git a/include/openssl/cmperr.h b/include/openssl/cmperr.h index 0d876e501c..d196924f74 100644 --- a/include/openssl/cmperr.h +++ b/include/openssl/cmperr.h @@ -60,9 +60,13 @@ # define CMP_R_FAILED_EXTRACTING_PUBKEY 141 # define CMP_R_FAILURE_OBTAINING_RANDOM 110 # define CMP_R_FAIL_INFO_OUT_OF_RANGE 129 +# define CMP_R_GENERATE_CERTREQTEMPLATE 197 +# define CMP_R_GENERATE_CRLSTATUS 198 # define CMP_R_GETTING_GENP 192 +# define CMP_R_GET_ITAV 199 # define CMP_R_INVALID_ARGS 100 # define CMP_R_INVALID_GENP 193 +# define CMP_R_INVALID_KEYSPEC 202 # define CMP_R_INVALID_OPTION 174 # define CMP_R_INVALID_ROOTCAKEYUPDATE 195 # define CMP_R_MISSING_CERTID 165 @@ -100,6 +104,7 @@ # define CMP_R_TRANSFER_ERROR 159 # define CMP_R_UNCLEAN_CTX 191 # define CMP_R_UNEXPECTED_CERTPROFILE 196 +# define CMP_R_UNEXPECTED_CRLSTATUSLIST 201 # define CMP_R_UNEXPECTED_PKIBODY 133 # define CMP_R_UNEXPECTED_PKISTATUS 185 # define CMP_R_UNEXPECTED_POLLREQ 105 @@ -107,6 +112,7 @@ # define CMP_R_UNEXPECTED_SENDER 106 # define CMP_R_UNKNOWN_ALGORITHM_ID 134 # define CMP_R_UNKNOWN_CERT_TYPE 135 +# define CMP_R_UNKNOWN_CRL_ISSUER 200 # define CMP_R_UNKNOWN_PKISTATUS 186 # define CMP_R_UNSUPPORTED_ALGORITHM 136 # define CMP_R_UNSUPPORTED_KEY_TYPE 137 diff --git a/include/openssl/comp.h b/include/openssl/comp.h index f81ba0f39c..90e39511fe 100644 --- a/include/openssl/comp.h +++ b/include/openssl/comp.h @@ -1,5 +1,5 @@ /* - * Copyright 2015-2018 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -7,6 +7,8 @@ * https://www.openssl.org/source/license.html */ + + #ifndef OPENSSL_COMP_H # define OPENSSL_COMP_H # pragma once @@ -18,7 +20,6 @@ # include -# ifndef OPENSSL_NO_COMP # include # include # ifdef __cplusplus @@ -27,6 +28,8 @@ extern "C" { +# ifndef OPENSSL_NO_COMP + COMP_CTX *COMP_CTX_new(COMP_METHOD *meth); const COMP_METHOD *COMP_CTX_get_method(const COMP_CTX *ctx); int COMP_CTX_get_type(const COMP_CTX* comp); @@ -46,19 +49,50 @@ COMP_METHOD *COMP_brotli_oneshot(void); COMP_METHOD *COMP_zstd(void); COMP_METHOD *COMP_zstd_oneshot(void); -#ifndef OPENSSL_NO_DEPRECATED_1_1_0 -# define COMP_zlib_cleanup() while(0) continue -#endif +# ifndef OPENSSL_NO_DEPRECATED_1_1_0 +# define COMP_zlib_cleanup() while(0) continue +# endif -# ifdef OPENSSL_BIO_H +# ifdef OPENSSL_BIO_H const BIO_METHOD *BIO_f_zlib(void); const BIO_METHOD *BIO_f_brotli(void); const BIO_METHOD *BIO_f_zstd(void); +# endif + # endif +typedef struct ssl_comp_st SSL_COMP; + +SKM_DEFINE_STACK_OF_INTERNAL(SSL_COMP, SSL_COMP, SSL_COMP) +#define sk_SSL_COMP_num(sk) OPENSSL_sk_num(ossl_check_const_SSL_COMP_sk_type(sk)) +#define sk_SSL_COMP_value(sk, idx) ((SSL_COMP *)OPENSSL_sk_value(ossl_check_const_SSL_COMP_sk_type(sk), (idx))) +#define sk_SSL_COMP_new(cmp) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new(ossl_check_SSL_COMP_compfunc_type(cmp))) +#define sk_SSL_COMP_new_null() ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new_null()) +#define sk_SSL_COMP_new_reserve(cmp, n) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new_reserve(ossl_check_SSL_COMP_compfunc_type(cmp), (n))) +#define sk_SSL_COMP_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_SSL_COMP_sk_type(sk), (n)) +#define sk_SSL_COMP_free(sk) OPENSSL_sk_free(ossl_check_SSL_COMP_sk_type(sk)) +#define sk_SSL_COMP_zero(sk) OPENSSL_sk_zero(ossl_check_SSL_COMP_sk_type(sk)) +#define sk_SSL_COMP_delete(sk, i) ((SSL_COMP *)OPENSSL_sk_delete(ossl_check_SSL_COMP_sk_type(sk), (i))) +#define sk_SSL_COMP_delete_ptr(sk, ptr) ((SSL_COMP *)OPENSSL_sk_delete_ptr(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr))) +#define sk_SSL_COMP_push(sk, ptr) OPENSSL_sk_push(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) +#define sk_SSL_COMP_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) +#define sk_SSL_COMP_pop(sk) ((SSL_COMP *)OPENSSL_sk_pop(ossl_check_SSL_COMP_sk_type(sk))) +#define sk_SSL_COMP_shift(sk) ((SSL_COMP *)OPENSSL_sk_shift(ossl_check_SSL_COMP_sk_type(sk))) +#define sk_SSL_COMP_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_SSL_COMP_sk_type(sk),ossl_check_SSL_COMP_freefunc_type(freefunc)) +#define sk_SSL_COMP_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr), (idx)) +#define sk_SSL_COMP_set(sk, idx, ptr) ((SSL_COMP *)OPENSSL_sk_set(ossl_check_SSL_COMP_sk_type(sk), (idx), ossl_check_SSL_COMP_type(ptr))) +#define sk_SSL_COMP_find(sk, ptr) OPENSSL_sk_find(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) +#define sk_SSL_COMP_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) +#define sk_SSL_COMP_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr), pnum) +#define sk_SSL_COMP_sort(sk) OPENSSL_sk_sort(ossl_check_SSL_COMP_sk_type(sk)) +#define sk_SSL_COMP_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_SSL_COMP_sk_type(sk)) +#define sk_SSL_COMP_dup(sk) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_dup(ossl_check_const_SSL_COMP_sk_type(sk))) +#define sk_SSL_COMP_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_deep_copy(ossl_check_const_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_copyfunc_type(copyfunc), ossl_check_SSL_COMP_freefunc_type(freefunc))) +#define sk_SSL_COMP_set_cmp_func(sk, cmp) ((sk_SSL_COMP_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_compfunc_type(cmp))) + -# ifdef __cplusplus + +# ifdef __cplusplus } -# endif # endif #endif diff --git a/include/openssl/comp.h.in b/include/openssl/comp.h.in new file mode 100644 index 0000000000..bd1efdc568 --- /dev/null +++ b/include/openssl/comp.h.in @@ -0,0 +1,76 @@ +/* + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +{- +use OpenSSL::stackhash qw(generate_stack_macros); +-} + +#ifndef OPENSSL_COMP_H +# define OPENSSL_COMP_H +# pragma once + +# include +# ifndef OPENSSL_NO_DEPRECATED_3_0 +# define HEADER_COMP_H +# endif + +# include + +# include +# include +# ifdef __cplusplus +extern "C" { +# endif + + + +# ifndef OPENSSL_NO_COMP + +COMP_CTX *COMP_CTX_new(COMP_METHOD *meth); +const COMP_METHOD *COMP_CTX_get_method(const COMP_CTX *ctx); +int COMP_CTX_get_type(const COMP_CTX* comp); +int COMP_get_type(const COMP_METHOD *meth); +const char *COMP_get_name(const COMP_METHOD *meth); +void COMP_CTX_free(COMP_CTX *ctx); + +int COMP_compress_block(COMP_CTX *ctx, unsigned char *out, int olen, + unsigned char *in, int ilen); +int COMP_expand_block(COMP_CTX *ctx, unsigned char *out, int olen, + unsigned char *in, int ilen); + +COMP_METHOD *COMP_zlib(void); +COMP_METHOD *COMP_zlib_oneshot(void); +COMP_METHOD *COMP_brotli(void); +COMP_METHOD *COMP_brotli_oneshot(void); +COMP_METHOD *COMP_zstd(void); +COMP_METHOD *COMP_zstd_oneshot(void); + +# ifndef OPENSSL_NO_DEPRECATED_1_1_0 +# define COMP_zlib_cleanup() while(0) continue +# endif + +# ifdef OPENSSL_BIO_H +const BIO_METHOD *BIO_f_zlib(void); +const BIO_METHOD *BIO_f_brotli(void); +const BIO_METHOD *BIO_f_zstd(void); +# endif + +# endif + +typedef struct ssl_comp_st SSL_COMP; + +{- + generate_stack_macros("SSL_COMP"); +-} + + +# ifdef __cplusplus +} +# endif +#endif diff --git a/include/openssl/configuration-32.h b/include/openssl/configuration-32.h index 1680a4941d..0dba26112c 100644 --- a/include/openssl/configuration-32.h +++ b/include/openssl/configuration-32.h @@ -27,7 +27,7 @@ extern "C" { * OpenSSL was configured with the following options: */ -# define OPENSSL_CONFIGURED_API 30300 +# define OPENSSL_CONFIGURED_API 30400 # ifndef OPENSSL_RAND_SEED_OS # define OPENSSL_RAND_SEED_OS # endif @@ -61,6 +61,9 @@ extern "C" { # ifndef OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # define OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # endif +# ifndef OPENSSL_NO_DEMOS +# define OPENSSL_NO_DEMOS +# endif # ifndef OPENSSL_NO_DEVCRYPTOENG # define OPENSSL_NO_DEVCRYPTOENG # endif @@ -82,6 +85,9 @@ extern "C" { # ifndef OPENSSL_NO_EXTERNAL_TESTS # define OPENSSL_NO_EXTERNAL_TESTS # endif +# ifndef OPENSSL_NO_FIPS_POST +# define OPENSSL_NO_FIPS_POST +# endif # ifndef OPENSSL_NO_FIPS_SECURITYCHECKS # define OPENSSL_NO_FIPS_SECURITYCHECKS # endif @@ -94,9 +100,15 @@ extern "C" { # ifndef OPENSSL_NO_GOST # define OPENSSL_NO_GOST # endif +# ifndef OPENSSL_NO_H3DEMO +# define OPENSSL_NO_H3DEMO +# endif # ifndef OPENSSL_NO_IDEA # define OPENSSL_NO_IDEA # endif +# ifndef OPENSSL_NO_JITTER +# define OPENSSL_NO_JITTER +# endif # ifndef OPENSSL_NO_KTLS # define OPENSSL_NO_KTLS # endif @@ -109,6 +121,9 @@ extern "C" { # ifndef OPENSSL_NO_MSAN # define OPENSSL_NO_MSAN # endif +# ifndef OPENSSL_NO_PIE +# define OPENSSL_NO_PIE +# endif # ifndef OPENSSL_NO_RC5 # define OPENSSL_NO_RC5 # endif diff --git a/include/openssl/configuration-64.h b/include/openssl/configuration-64.h index 602d963cb8..48239b8029 100644 --- a/include/openssl/configuration-64.h +++ b/include/openssl/configuration-64.h @@ -27,7 +27,7 @@ extern "C" { * OpenSSL was configured with the following options: */ -# define OPENSSL_CONFIGURED_API 30300 +# define OPENSSL_CONFIGURED_API 30400 # ifndef OPENSSL_RAND_SEED_OS # define OPENSSL_RAND_SEED_OS # endif @@ -61,6 +61,9 @@ extern "C" { # ifndef OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # define OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # endif +# ifndef OPENSSL_NO_DEMOS +# define OPENSSL_NO_DEMOS +# endif # ifndef OPENSSL_NO_DEVCRYPTOENG # define OPENSSL_NO_DEVCRYPTOENG # endif @@ -82,6 +85,9 @@ extern "C" { # ifndef OPENSSL_NO_EXTERNAL_TESTS # define OPENSSL_NO_EXTERNAL_TESTS # endif +# ifndef OPENSSL_NO_FIPS_POST +# define OPENSSL_NO_FIPS_POST +# endif # ifndef OPENSSL_NO_FIPS_SECURITYCHECKS # define OPENSSL_NO_FIPS_SECURITYCHECKS # endif @@ -94,9 +100,15 @@ extern "C" { # ifndef OPENSSL_NO_GOST # define OPENSSL_NO_GOST # endif +# ifndef OPENSSL_NO_H3DEMO +# define OPENSSL_NO_H3DEMO +# endif # ifndef OPENSSL_NO_IDEA # define OPENSSL_NO_IDEA # endif +# ifndef OPENSSL_NO_JITTER +# define OPENSSL_NO_JITTER +# endif # ifndef OPENSSL_NO_KTLS # define OPENSSL_NO_KTLS # endif @@ -109,6 +121,9 @@ extern "C" { # ifndef OPENSSL_NO_MSAN # define OPENSSL_NO_MSAN # endif +# ifndef OPENSSL_NO_PIE +# define OPENSSL_NO_PIE +# endif # ifndef OPENSSL_NO_RC5 # define OPENSSL_NO_RC5 # endif diff --git a/include/openssl/configuration-static-32.h b/include/openssl/configuration-static-32.h index 2026373651..fe052b1729 100644 --- a/include/openssl/configuration-static-32.h +++ b/include/openssl/configuration-static-32.h @@ -27,7 +27,7 @@ extern "C" { * OpenSSL was configured with the following options: */ -# define OPENSSL_CONFIGURED_API 30300 +# define OPENSSL_CONFIGURED_API 30400 # ifndef OPENSSL_RAND_SEED_OS # define OPENSSL_RAND_SEED_OS # endif @@ -64,6 +64,9 @@ extern "C" { # ifndef OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # define OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # endif +# ifndef OPENSSL_NO_DEMOS +# define OPENSSL_NO_DEMOS +# endif # ifndef OPENSSL_NO_DEVCRYPTOENG # define OPENSSL_NO_DEVCRYPTOENG # endif @@ -88,6 +91,9 @@ extern "C" { # ifndef OPENSSL_NO_EXTERNAL_TESTS # define OPENSSL_NO_EXTERNAL_TESTS # endif +# ifndef OPENSSL_NO_FIPS_POST +# define OPENSSL_NO_FIPS_POST +# endif # ifndef OPENSSL_NO_FIPS_SECURITYCHECKS # define OPENSSL_NO_FIPS_SECURITYCHECKS # endif @@ -100,9 +106,15 @@ extern "C" { # ifndef OPENSSL_NO_GOST # define OPENSSL_NO_GOST # endif +# ifndef OPENSSL_NO_H3DEMO +# define OPENSSL_NO_H3DEMO +# endif # ifndef OPENSSL_NO_IDEA # define OPENSSL_NO_IDEA # endif +# ifndef OPENSSL_NO_JITTER +# define OPENSSL_NO_JITTER +# endif # ifndef OPENSSL_NO_KTLS # define OPENSSL_NO_KTLS # endif @@ -118,6 +130,9 @@ extern "C" { # ifndef OPENSSL_NO_MSAN # define OPENSSL_NO_MSAN # endif +# ifndef OPENSSL_NO_PIE +# define OPENSSL_NO_PIE +# endif # ifndef OPENSSL_NO_RC5 # define OPENSSL_NO_RC5 # endif diff --git a/include/openssl/configuration-static-64.h b/include/openssl/configuration-static-64.h index 6ebdd23533..090f125d32 100644 --- a/include/openssl/configuration-static-64.h +++ b/include/openssl/configuration-static-64.h @@ -27,7 +27,7 @@ extern "C" { * OpenSSL was configured with the following options: */ -# define OPENSSL_CONFIGURED_API 30300 +# define OPENSSL_CONFIGURED_API 30400 # ifndef OPENSSL_RAND_SEED_OS # define OPENSSL_RAND_SEED_OS # endif @@ -64,6 +64,9 @@ extern "C" { # ifndef OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # define OPENSSL_NO_CRYPTO_MDEBUG_BACKTRACE # endif +# ifndef OPENSSL_NO_DEMOS +# define OPENSSL_NO_DEMOS +# endif # ifndef OPENSSL_NO_DEVCRYPTOENG # define OPENSSL_NO_DEVCRYPTOENG # endif @@ -88,6 +91,9 @@ extern "C" { # ifndef OPENSSL_NO_EXTERNAL_TESTS # define OPENSSL_NO_EXTERNAL_TESTS # endif +# ifndef OPENSSL_NO_FIPS_POST +# define OPENSSL_NO_FIPS_POST +# endif # ifndef OPENSSL_NO_FIPS_SECURITYCHECKS # define OPENSSL_NO_FIPS_SECURITYCHECKS # endif @@ -100,9 +106,15 @@ extern "C" { # ifndef OPENSSL_NO_GOST # define OPENSSL_NO_GOST # endif +# ifndef OPENSSL_NO_H3DEMO +# define OPENSSL_NO_H3DEMO +# endif # ifndef OPENSSL_NO_IDEA # define OPENSSL_NO_IDEA # endif +# ifndef OPENSSL_NO_JITTER +# define OPENSSL_NO_JITTER +# endif # ifndef OPENSSL_NO_KTLS # define OPENSSL_NO_KTLS # endif @@ -118,6 +130,9 @@ extern "C" { # ifndef OPENSSL_NO_MSAN # define OPENSSL_NO_MSAN # endif +# ifndef OPENSSL_NO_PIE +# define OPENSSL_NO_PIE +# endif # ifndef OPENSSL_NO_RC5 # define OPENSSL_NO_RC5 # endif diff --git a/include/openssl/core_dispatch.h b/include/openssl/core_dispatch.h index a5bc2cf75d..03838ddd0e 100644 --- a/include/openssl/core_dispatch.h +++ b/include/openssl/core_dispatch.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,6 +13,7 @@ # include # include +# include # ifdef __cplusplus extern "C" { @@ -182,6 +183,9 @@ OSSL_CORE_MAKE_FUNC(int, BIO_ctrl, (OSSL_CORE_BIO *bio, #define OSSL_FUNC_GET_USER_ENTROPY 98 #define OSSL_FUNC_GET_USER_NONCE 99 +#define OSSL_FUNC_INDICATOR_CB 95 +OSSL_CORE_MAKE_FUNC(void, indicator_cb, (OPENSSL_CORE_CTX *ctx, + OSSL_INDICATOR_CALLBACK **cb)) #define OSSL_FUNC_SELF_TEST_CB 100 OSSL_CORE_MAKE_FUNC(void, self_test_cb, (OPENSSL_CORE_CTX *ctx, OSSL_CALLBACK **cb, void **cbarg)) @@ -588,6 +592,9 @@ OSSL_CORE_MAKE_FUNC(void *, keymgmt_new, (void *provctx)) # define OSSL_FUNC_KEYMGMT_GEN_SETTABLE_PARAMS 5 # define OSSL_FUNC_KEYMGMT_GEN 6 # define OSSL_FUNC_KEYMGMT_GEN_CLEANUP 7 +# define OSSL_FUNC_KEYMGMT_GEN_GET_PARAMS 15 +# define OSSL_FUNC_KEYMGMT_GEN_GETTABLE_PARAMS 16 + OSSL_CORE_MAKE_FUNC(void *, keymgmt_gen_init, (void *provctx, int selection, const OSSL_PARAM params[])) OSSL_CORE_MAKE_FUNC(int, keymgmt_gen_set_template, @@ -597,6 +604,10 @@ OSSL_CORE_MAKE_FUNC(int, keymgmt_gen_set_params, OSSL_CORE_MAKE_FUNC(const OSSL_PARAM *, keymgmt_gen_settable_params, (void *genctx, void *provctx)) +OSSL_CORE_MAKE_FUNC(int, keymgmt_gen_get_params, + (void *genctx, OSSL_PARAM params[])) +OSSL_CORE_MAKE_FUNC(const OSSL_PARAM *, keymgmt_gen_gettable_params, + (void *genctx, void *provctx)) OSSL_CORE_MAKE_FUNC(void *, keymgmt_gen, (void *genctx, OSSL_CALLBACK *cb, void *cbarg)) OSSL_CORE_MAKE_FUNC(void, keymgmt_gen_cleanup, (void *genctx)) @@ -730,22 +741,45 @@ OSSL_CORE_MAKE_FUNC(const OSSL_PARAM *, keyexch_gettable_ctx_params, # define OSSL_FUNC_SIGNATURE_GETTABLE_CTX_MD_PARAMS 23 # define OSSL_FUNC_SIGNATURE_SET_CTX_MD_PARAMS 24 # define OSSL_FUNC_SIGNATURE_SETTABLE_CTX_MD_PARAMS 25 +# define OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES 26 +# define OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT 27 +# define OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_UPDATE 28 +# define OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_FINAL 29 +# define OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT 30 +# define OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_UPDATE 31 +# define OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_FINAL 32 OSSL_CORE_MAKE_FUNC(void *, signature_newctx, (void *provctx, - const char *propq)) + const char *propq)) OSSL_CORE_MAKE_FUNC(int, signature_sign_init, (void *ctx, void *provkey, const OSSL_PARAM params[])) OSSL_CORE_MAKE_FUNC(int, signature_sign, (void *ctx, unsigned char *sig, - size_t *siglen, size_t sigsize, - const unsigned char *tbs, - size_t tbslen)) + size_t *siglen, size_t sigsize, + const unsigned char *tbs, + size_t tbslen)) +OSSL_CORE_MAKE_FUNC(int, signature_sign_message_init, + (void *ctx, void *provkey, const OSSL_PARAM params[])) +OSSL_CORE_MAKE_FUNC(int, signature_sign_message_update, + (void *ctx, const unsigned char *in, size_t inlen)) +OSSL_CORE_MAKE_FUNC(int, signature_sign_message_final, + (void *ctx, unsigned char *sig, + size_t *siglen, size_t sigsize)) OSSL_CORE_MAKE_FUNC(int, signature_verify_init, (void *ctx, void *provkey, const OSSL_PARAM params[])) OSSL_CORE_MAKE_FUNC(int, signature_verify, (void *ctx, - const unsigned char *sig, - size_t siglen, - const unsigned char *tbs, - size_t tbslen)) + const unsigned char *sig, + size_t siglen, + const unsigned char *tbs, + size_t tbslen)) +OSSL_CORE_MAKE_FUNC(int, signature_verify_message_init, + (void *ctx, void *provkey, const OSSL_PARAM params[])) +OSSL_CORE_MAKE_FUNC(int, signature_verify_message_update, + (void *ctx, const unsigned char *in, size_t inlen)) +/* + * signature_verify_final requires that the signature to be verified against + * is specified via an OSSL_PARAM. + */ +OSSL_CORE_MAKE_FUNC(int, signature_verify_message_final, (void *ctx)) OSSL_CORE_MAKE_FUNC(int, signature_verify_recover_init, (void *ctx, void *provkey, const OSSL_PARAM params[])) OSSL_CORE_MAKE_FUNC(int, signature_verify_recover, @@ -790,7 +824,7 @@ OSSL_CORE_MAKE_FUNC(int, signature_set_ctx_md_params, (void *ctx, const OSSL_PARAM params[])) OSSL_CORE_MAKE_FUNC(const OSSL_PARAM *, signature_settable_ctx_md_params, (void *ctx)) - +OSSL_CORE_MAKE_FUNC(const char **, signature_query_key_types, (void)) /* Asymmetric Ciphers */ diff --git a/include/openssl/core_names.h b/include/openssl/core_names.h index a61580568f..c4ed2fed4c 100644 --- a/include/openssl/core_names.h +++ b/include/openssl/core_names.h @@ -109,13 +109,19 @@ extern "C" { #define OSSL_KEM_PARAM_OPERATION_DHKEM "DHKEM" /* Parameter name definitions - generated by util/perl/OpenSSL/paramnames.pm */ +# define OSSL_ALG_PARAM_ALGORITHM_ID "algorithm-id" +# define OSSL_ALG_PARAM_ALGORITHM_ID_PARAMS "algorithm-id-params" # define OSSL_ALG_PARAM_CIPHER "cipher" # define OSSL_ALG_PARAM_DIGEST "digest" # define OSSL_ALG_PARAM_ENGINE "engine" +# define OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR "fips-indicator" # define OSSL_ALG_PARAM_MAC "mac" # define OSSL_ALG_PARAM_PROPERTIES "properties" # define OSSL_ASYM_CIPHER_PARAM_DIGEST OSSL_PKEY_PARAM_DIGEST # define OSSL_ASYM_CIPHER_PARAM_ENGINE OSSL_PKEY_PARAM_ENGINE +# define OSSL_ASYM_CIPHER_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_ASYM_CIPHER_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK +# define OSSL_ASYM_CIPHER_PARAM_FIPS_RSA_PKCS15_PAD_DISABLED OSSL_PROV_PARAM_RSA_PKCS15_PAD_DISABLED # define OSSL_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION "implicit-rejection" # define OSSL_ASYM_CIPHER_PARAM_MGF1_DIGEST OSSL_PKEY_PARAM_MGF1_DIGEST # define OSSL_ASYM_CIPHER_PARAM_MGF1_DIGEST_PROPS OSSL_PKEY_PARAM_MGF1_PROPERTIES @@ -151,6 +157,7 @@ extern "C" { # define OSSL_CAPABILITY_TLS_SIGALG_SIG_OID "tls-sigalg-sig-oid" # define OSSL_CIPHER_PARAM_AEAD "aead" # define OSSL_CIPHER_PARAM_AEAD_IVLEN OSSL_CIPHER_PARAM_IVLEN +# define OSSL_CIPHER_PARAM_AEAD_IV_GENERATED "iv-generated" # define OSSL_CIPHER_PARAM_AEAD_MAC_KEY "mackey" # define OSSL_CIPHER_PARAM_AEAD_TAG "tag" # define OSSL_CIPHER_PARAM_AEAD_TAGLEN "taglen" @@ -159,11 +166,16 @@ extern "C" { # define OSSL_CIPHER_PARAM_AEAD_TLS1_GET_IV_GEN "tlsivgen" # define OSSL_CIPHER_PARAM_AEAD_TLS1_IV_FIXED "tlsivfixed" # define OSSL_CIPHER_PARAM_AEAD_TLS1_SET_IV_INV "tlsivinv" -# define OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS "alg_id_param" +# define OSSL_CIPHER_PARAM_ALGORITHM_ID OSSL_ALG_PARAM_ALGORITHM_ID +# define OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS OSSL_ALG_PARAM_ALGORITHM_ID_PARAMS +# define OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD "alg_id_param" # define OSSL_CIPHER_PARAM_BLOCK_SIZE "blocksize" # define OSSL_CIPHER_PARAM_CTS "cts" # define OSSL_CIPHER_PARAM_CTS_MODE "cts_mode" # define OSSL_CIPHER_PARAM_CUSTOM_IV "custom-iv" +# define OSSL_CIPHER_PARAM_DECRYPT_ONLY "decrypt-only" +# define OSSL_CIPHER_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK "encrypt-check" # define OSSL_CIPHER_PARAM_HAS_RAND_KEY "has-randkey" # define OSSL_CIPHER_PARAM_IV "iv" # define OSSL_CIPHER_PARAM_IVLEN "ivlen" @@ -202,6 +214,8 @@ extern "C" { # define OSSL_DRBG_PARAM_CIPHER OSSL_ALG_PARAM_CIPHER # define OSSL_DRBG_PARAM_DIGEST OSSL_ALG_PARAM_DIGEST # define OSSL_DRBG_PARAM_ENTROPY_REQUIRED "entropy_required" +# define OSSL_DRBG_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_DRBG_PARAM_FIPS_DIGEST_CHECK OSSL_PKEY_PARAM_FIPS_DIGEST_CHECK # define OSSL_DRBG_PARAM_MAC OSSL_ALG_PARAM_MAC # define OSSL_DRBG_PARAM_MAX_ADINLEN "max_adinlen" # define OSSL_DRBG_PARAM_MAX_ENTROPYLEN "max_entropylen" @@ -225,6 +239,10 @@ extern "C" { # define OSSL_ENCODER_PARAM_PROPERTIES OSSL_ALG_PARAM_PROPERTIES # define OSSL_ENCODER_PARAM_SAVE_PARAMETERS "save-parameters" # define OSSL_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE "ecdh-cofactor-mode" +# define OSSL_EXCHANGE_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_EXCHANGE_PARAM_FIPS_DIGEST_CHECK OSSL_PKEY_PARAM_FIPS_DIGEST_CHECK +# define OSSL_EXCHANGE_PARAM_FIPS_ECDH_COFACTOR_CHECK OSSL_PROV_PARAM_ECDH_COFACTOR_CHECK +# define OSSL_EXCHANGE_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK # define OSSL_EXCHANGE_PARAM_KDF_DIGEST "kdf-digest" # define OSSL_EXCHANGE_PARAM_KDF_DIGEST_PROPS "kdf-digest-props" # define OSSL_EXCHANGE_PARAM_KDF_OUTLEN "kdf-outlen" @@ -243,6 +261,10 @@ extern "C" { # define OSSL_KDF_PARAM_DATA "data" # define OSSL_KDF_PARAM_DIGEST OSSL_ALG_PARAM_DIGEST # define OSSL_KDF_PARAM_EARLY_CLEAN "early_clean" +# define OSSL_KDF_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_KDF_PARAM_FIPS_DIGEST_CHECK OSSL_PKEY_PARAM_FIPS_DIGEST_CHECK +# define OSSL_KDF_PARAM_FIPS_EMS_CHECK "ems_check" +# define OSSL_KDF_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK # define OSSL_KDF_PARAM_HMACDRBG_ENTROPY "entropy" # define OSSL_KDF_PARAM_HMACDRBG_NONCE "nonce" # define OSSL_KDF_PARAM_INFO "info" @@ -279,9 +301,12 @@ extern "C" { # define OSSL_KDF_PARAM_X942_SUPP_PRIVINFO "supp-privinfo" # define OSSL_KDF_PARAM_X942_SUPP_PUBINFO "supp-pubinfo" # define OSSL_KDF_PARAM_X942_USE_KEYBITS "use-keybits" +# define OSSL_KEM_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_KEM_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK # define OSSL_KEM_PARAM_IKME "ikme" # define OSSL_KEM_PARAM_OPERATION "operation" # define OSSL_LIBSSL_RECORD_LAYER_PARAM_BLOCK_PADDING "block_padding" +# define OSSL_LIBSSL_RECORD_LAYER_PARAM_HS_PADDING "hs_padding" # define OSSL_LIBSSL_RECORD_LAYER_PARAM_MAX_EARLY_DATA "max_early_data" # define OSSL_LIBSSL_RECORD_LAYER_PARAM_MAX_FRAG_LEN "max_frag_len" # define OSSL_LIBSSL_RECORD_LAYER_PARAM_MODE "mode" @@ -299,6 +324,9 @@ extern "C" { # define OSSL_MAC_PARAM_DIGEST_NOINIT "digest-noinit" # define OSSL_MAC_PARAM_DIGEST_ONESHOT "digest-oneshot" # define OSSL_MAC_PARAM_D_ROUNDS "d-rounds" +# define OSSL_MAC_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_MAC_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK +# define OSSL_MAC_PARAM_FIPS_NO_SHORT_MAC OSSL_PROV_PARAM_NO_SHORT_MAC # define OSSL_MAC_PARAM_IV "iv" # define OSSL_MAC_PARAM_KEY "key" # define OSSL_MAC_PARAM_PROPERTIES OSSL_ALG_PARAM_PROPERTIES @@ -313,6 +341,8 @@ extern "C" { # define OSSL_OBJECT_PARAM_REFERENCE "reference" # define OSSL_OBJECT_PARAM_TYPE "type" # define OSSL_PASSPHRASE_PARAM_INFO "info" +# define OSSL_PKEY_PARAM_ALGORITHM_ID OSSL_ALG_PARAM_ALGORITHM_ID +# define OSSL_PKEY_PARAM_ALGORITHM_ID_PARAMS OSSL_ALG_PARAM_ALGORITHM_ID_PARAMS # define OSSL_PKEY_PARAM_BITS "bits" # define OSSL_PKEY_PARAM_CIPHER OSSL_ALG_PARAM_CIPHER # define OSSL_PKEY_PARAM_DEFAULT_DIGEST "default-digest" @@ -361,6 +391,10 @@ extern "C" { # define OSSL_PKEY_PARAM_FFC_VALIDATE_G "validate-g" # define OSSL_PKEY_PARAM_FFC_VALIDATE_LEGACY "validate-legacy" # define OSSL_PKEY_PARAM_FFC_VALIDATE_PQ "validate-pq" +# define OSSL_PKEY_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_PKEY_PARAM_FIPS_DIGEST_CHECK "digest-check" +# define OSSL_PKEY_PARAM_FIPS_KEY_CHECK "key-check" +# define OSSL_PKEY_PARAM_FIPS_SIGN_CHECK "sign-check" # define OSSL_PKEY_PARAM_GROUP_NAME "group" # define OSSL_PKEY_PARAM_IMPLICIT_REJECTION "implicit-rejection" # define OSSL_PKEY_PARAM_MANDATORY_DIGEST "mandatory-digest" @@ -433,24 +467,58 @@ extern "C" { # define OSSL_PROV_PARAM_CORE_PROV_NAME "provider-name" # define OSSL_PROV_PARAM_CORE_VERSION "openssl-version" # define OSSL_PROV_PARAM_DRBG_TRUNC_DIGEST "drbg-no-trunc-md" +# define OSSL_PROV_PARAM_DSA_SIGN_DISABLED "dsa-sign-disabled" +# define OSSL_PROV_PARAM_ECDH_COFACTOR_CHECK "ecdh-cofactor-check" +# define OSSL_PROV_PARAM_HKDF_DIGEST_CHECK "hkdf-digest-check" +# define OSSL_PROV_PARAM_HKDF_KEY_CHECK "hkdf-key-check" +# define OSSL_PROV_PARAM_HMAC_KEY_CHECK "hmac-key-check" +# define OSSL_PROV_PARAM_KBKDF_KEY_CHECK "kbkdf-key-check" +# define OSSL_PROV_PARAM_KMAC_KEY_CHECK "kmac-key-check" # define OSSL_PROV_PARAM_NAME "name" +# define OSSL_PROV_PARAM_NO_SHORT_MAC "no-short-mac" +# define OSSL_PROV_PARAM_PBKDF2_LOWER_BOUND_CHECK "pbkdf2-lower-bound-check" +# define OSSL_PROV_PARAM_RSA_PKCS15_PAD_DISABLED "rsa-pkcs15-pad-disabled" +# define OSSL_PROV_PARAM_RSA_PSS_SALTLEN_CHECK "rsa-pss-saltlen-check" +# define OSSL_PROV_PARAM_RSA_SIGN_X931_PAD_DISABLED "rsa-sign-x931-pad-disabled" # define OSSL_PROV_PARAM_SECURITY_CHECKS "security-checks" # define OSSL_PROV_PARAM_SELF_TEST_DESC "st-desc" # define OSSL_PROV_PARAM_SELF_TEST_PHASE "st-phase" # define OSSL_PROV_PARAM_SELF_TEST_TYPE "st-type" +# define OSSL_PROV_PARAM_SIGNATURE_DIGEST_CHECK "signature-digest-check" +# define OSSL_PROV_PARAM_SSHKDF_DIGEST_CHECK "sshkdf-digest-check" +# define OSSL_PROV_PARAM_SSHKDF_KEY_CHECK "sshkdf-key-check" +# define OSSL_PROV_PARAM_SSKDF_DIGEST_CHECK "sskdf-digest-check" +# define OSSL_PROV_PARAM_SSKDF_KEY_CHECK "sskdf-key-check" # define OSSL_PROV_PARAM_STATUS "status" +# define OSSL_PROV_PARAM_TDES_ENCRYPT_DISABLED "tdes-encrypt-disabled" +# define OSSL_PROV_PARAM_TLS13_KDF_DIGEST_CHECK "tls13-kdf-digest-check" +# define OSSL_PROV_PARAM_TLS13_KDF_KEY_CHECK "tls13-kdf-key-check" +# define OSSL_PROV_PARAM_TLS1_PRF_DIGEST_CHECK "tls1-prf-digest-check" # define OSSL_PROV_PARAM_TLS1_PRF_EMS_CHECK "tls1-prf-ems-check" +# define OSSL_PROV_PARAM_TLS1_PRF_KEY_CHECK "tls1-prf-key-check" # define OSSL_PROV_PARAM_VERSION "version" +# define OSSL_PROV_PARAM_X942KDF_KEY_CHECK "x942kdf-key-check" +# define OSSL_PROV_PARAM_X963KDF_DIGEST_CHECK "x963kdf-digest-check" +# define OSSL_PROV_PARAM_X963KDF_KEY_CHECK "x963kdf-key-check" +# define OSSL_RAND_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR # define OSSL_RAND_PARAM_GENERATE "generate" # define OSSL_RAND_PARAM_MAX_REQUEST "max_request" # define OSSL_RAND_PARAM_STATE "state" # define OSSL_RAND_PARAM_STRENGTH "strength" # define OSSL_RAND_PARAM_TEST_ENTROPY "test_entropy" # define OSSL_RAND_PARAM_TEST_NONCE "test_nonce" -# define OSSL_SIGNATURE_PARAM_ALGORITHM_ID "algorithm-id" +# define OSSL_SIGNATURE_PARAM_ALGORITHM_ID OSSL_PKEY_PARAM_ALGORITHM_ID +# define OSSL_SIGNATURE_PARAM_ALGORITHM_ID_PARAMS OSSL_PKEY_PARAM_ALGORITHM_ID_PARAMS # define OSSL_SIGNATURE_PARAM_CONTEXT_STRING "context-string" # define OSSL_SIGNATURE_PARAM_DIGEST OSSL_PKEY_PARAM_DIGEST # define OSSL_SIGNATURE_PARAM_DIGEST_SIZE OSSL_PKEY_PARAM_DIGEST_SIZE +# define OSSL_SIGNATURE_PARAM_FIPS_APPROVED_INDICATOR OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR +# define OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK OSSL_PKEY_PARAM_FIPS_DIGEST_CHECK +# define OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK OSSL_PKEY_PARAM_FIPS_KEY_CHECK +# define OSSL_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK "rsa-pss-saltlen-check" +# define OSSL_SIGNATURE_PARAM_FIPS_SIGN_CHECK OSSL_PKEY_PARAM_FIPS_SIGN_CHECK +# define OSSL_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK "sign-x931-pad-check" +# define OSSL_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE "verify-message" # define OSSL_SIGNATURE_PARAM_INSTANCE "instance" # define OSSL_SIGNATURE_PARAM_KAT "kat" # define OSSL_SIGNATURE_PARAM_MGF1_DIGEST OSSL_PKEY_PARAM_MGF1_DIGEST @@ -459,6 +527,7 @@ extern "C" { # define OSSL_SIGNATURE_PARAM_PAD_MODE OSSL_PKEY_PARAM_PAD_MODE # define OSSL_SIGNATURE_PARAM_PROPERTIES OSSL_PKEY_PARAM_PROPERTIES # define OSSL_SIGNATURE_PARAM_PSS_SALTLEN "saltlen" +# define OSSL_SIGNATURE_PARAM_SIGNATURE "signature" # define OSSL_STORE_PARAM_ALIAS "alias" # define OSSL_STORE_PARAM_DIGEST "digest" # define OSSL_STORE_PARAM_EXPECT "expect" diff --git a/include/openssl/crmf.h b/include/openssl/crmf.h index 1f901f35f8..a08af28948 100644 --- a/include/openssl/crmf.h +++ b/include/openssl/crmf.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/crmf.h.in * - * Copyright 2007-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -77,6 +77,36 @@ SKM_DEFINE_STACK_OF_INTERNAL(OSSL_CRMF_MSG, OSSL_CRMF_MSG, OSSL_CRMF_MSG) #define sk_OSSL_CRMF_MSG_set_cmp_func(sk, cmp) ((sk_OSSL_CRMF_MSG_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_CRMF_MSG_sk_type(sk), ossl_check_OSSL_CRMF_MSG_compfunc_type(cmp))) typedef struct ossl_crmf_attributetypeandvalue_st OSSL_CRMF_ATTRIBUTETYPEANDVALUE; +void OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free(OSSL_CRMF_ATTRIBUTETYPEANDVALUE *v); +DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +SKM_DEFINE_STACK_OF_INTERNAL(OSSL_CRMF_ATTRIBUTETYPEANDVALUE, OSSL_CRMF_ATTRIBUTETYPEANDVALUE, OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_num(sk) OPENSSL_sk_num(ossl_check_const_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_value(sk, idx) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_value(ossl_check_const_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), (idx))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new(cmp) ((STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) *)OPENSSL_sk_new(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_compfunc_type(cmp))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new_null() ((STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) *)OPENSSL_sk_new_null()) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_new_reserve(cmp, n) ((STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) *)OPENSSL_sk_new_reserve(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_compfunc_type(cmp), (n))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), (n)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free(sk) OPENSSL_sk_free(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_zero(sk) OPENSSL_sk_zero(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_delete(sk, i) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_delete(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), (i))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_delete_ptr(sk, ptr) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_delete_ptr(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_push(sk, ptr) OPENSSL_sk_push(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_pop(sk) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_pop(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_shift(sk) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_shift(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk),ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_freefunc_type(freefunc)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr), (idx)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_set(sk, idx, ptr) ((OSSL_CRMF_ATTRIBUTETYPEANDVALUE *)OPENSSL_sk_set(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), (idx), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_find(sk, ptr) OPENSSL_sk_find(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_type(ptr), pnum) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sort(sk) OPENSSL_sk_sort(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk)) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_dup(sk) ((STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) *)OPENSSL_sk_dup(ossl_check_const_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_copyfunc_type(copyfunc), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_freefunc_type(freefunc))) +#define sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_set_cmp_func(sk, cmp) ((sk_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_sk_type(sk), ossl_check_OSSL_CRMF_ATTRIBUTETYPEANDVALUE_compfunc_type(cmp))) + + typedef struct ossl_crmf_pbmparameter_st OSSL_CRMF_PBMPARAMETER; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_PBMPARAMETER) typedef struct ossl_crmf_poposigningkey_st OSSL_CRMF_POPOSIGNINGKEY; @@ -118,6 +148,7 @@ typedef struct ossl_crmf_singlepubinfo_st OSSL_CRMF_SINGLEPUBINFO; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_SINGLEPUBINFO) typedef struct ossl_crmf_certtemplate_st OSSL_CRMF_CERTTEMPLATE; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_CERTTEMPLATE) +DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_CERTTEMPLATE) typedef STACK_OF(OSSL_CRMF_MSG) OSSL_CRMF_MSGS; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_MSGS) diff --git a/include/openssl/crmf.h.in b/include/openssl/crmf.h.in index 43411fa42f..17dc4d9103 100644 --- a/include/openssl/crmf.h.in +++ b/include/openssl/crmf.h.in @@ -1,7 +1,7 @@ /*- * {- join("\n * ", @autowarntext) -} * - * Copyright 2007-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2007-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright Nokia 2007-2019 * Copyright Siemens AG 2015-2019 * @@ -54,6 +54,12 @@ DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_MSG) generate_stack_macros("OSSL_CRMF_MSG"); -} typedef struct ossl_crmf_attributetypeandvalue_st OSSL_CRMF_ATTRIBUTETYPEANDVALUE; +void OSSL_CRMF_ATTRIBUTETYPEANDVALUE_free(OSSL_CRMF_ATTRIBUTETYPEANDVALUE *v); +DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_ATTRIBUTETYPEANDVALUE) +{- + generate_stack_macros("OSSL_CRMF_ATTRIBUTETYPEANDVALUE"); +-} + typedef struct ossl_crmf_pbmparameter_st OSSL_CRMF_PBMPARAMETER; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_PBMPARAMETER) typedef struct ossl_crmf_poposigningkey_st OSSL_CRMF_POPOSIGNINGKEY; @@ -71,6 +77,7 @@ typedef struct ossl_crmf_singlepubinfo_st OSSL_CRMF_SINGLEPUBINFO; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_SINGLEPUBINFO) typedef struct ossl_crmf_certtemplate_st OSSL_CRMF_CERTTEMPLATE; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_CERTTEMPLATE) +DECLARE_ASN1_DUP_FUNCTION(OSSL_CRMF_CERTTEMPLATE) typedef STACK_OF(OSSL_CRMF_MSG) OSSL_CRMF_MSGS; DECLARE_ASN1_FUNCTIONS(OSSL_CRMF_MSGS) diff --git a/include/openssl/crypto.h b/include/openssl/crypto.h index 55e00dccdc..3afe76b014 100644 --- a/include/openssl/crypto.h +++ b/include/openssl/crypto.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/crypto.h.in * - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -85,10 +85,15 @@ int CRYPTO_THREAD_unlock(CRYPTO_RWLOCK *lock); void CRYPTO_THREAD_lock_free(CRYPTO_RWLOCK *lock); int CRYPTO_atomic_add(int *val, int amount, int *ret, CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_add64(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_and(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock); int CRYPTO_atomic_or(uint64_t *val, uint64_t op, uint64_t *ret, CRYPTO_RWLOCK *lock); int CRYPTO_atomic_load(uint64_t *val, uint64_t *ret, CRYPTO_RWLOCK *lock); int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_store(uint64_t *dst, uint64_t val, CRYPTO_RWLOCK *lock); /* No longer needed, so this is a no-op */ #define OPENSSL_malloc_init() while(0) continue @@ -97,6 +102,9 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); CRYPTO_malloc(num, OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_zalloc(num) \ CRYPTO_zalloc(num, OPENSSL_FILE, OPENSSL_LINE) +# define OPENSSL_aligned_alloc(num, alignment, freeptr) \ + CRYPTO_aligned_alloc(num, alignment, freeptr, \ + OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_realloc(addr, num) \ CRYPTO_realloc(addr, num, OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_clear_realloc(addr, old_num, num) \ @@ -125,6 +133,7 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); size_t OPENSSL_strlcpy(char *dst, const char *src, size_t siz); size_t OPENSSL_strlcat(char *dst, const char *src, size_t siz); size_t OPENSSL_strnlen(const char *str, size_t maxlen); +int OPENSSL_strtoul(const char *str, char **endptr, int base, unsigned long *num); int OPENSSL_buf2hexstr_ex(char *str, size_t str_n, size_t *strlength, const unsigned char *buf, size_t buflen, const char sep); @@ -161,6 +170,7 @@ const char *OpenSSL_version(int type); # define OPENSSL_FULL_VERSION_STRING 7 # define OPENSSL_MODULES_DIR 8 # define OPENSSL_CPU_INFO 9 +# define OPENSSL_WINCTX 10 const char *OPENSSL_info(int type); /* @@ -175,6 +185,7 @@ const char *OPENSSL_info(int type); # define OPENSSL_INFO_LIST_SEPARATOR 1006 # define OPENSSL_INFO_SEED_SOURCE 1007 # define OPENSSL_INFO_CPU_SETTINGS 1008 +# define OPENSSL_INFO_WINDOWS_CONTEXT 1009 int OPENSSL_issetugid(void); @@ -344,6 +355,9 @@ void CRYPTO_get_mem_functions(CRYPTO_malloc_fn *malloc_fn, OSSL_CRYPTO_ALLOC void *CRYPTO_malloc(size_t num, const char *file, int line); OSSL_CRYPTO_ALLOC void *CRYPTO_zalloc(size_t num, const char *file, int line); +OSSL_CRYPTO_ALLOC void *CRYPTO_aligned_alloc(size_t num, size_t align, + void **freeptr, const char *file, + int line); OSSL_CRYPTO_ALLOC void *CRYPTO_memdup(const void *str, size_t siz, const char *file, int line); OSSL_CRYPTO_ALLOC char *CRYPTO_strdup(const char *str, const char *file, int line); OSSL_CRYPTO_ALLOC char *CRYPTO_strndup(const char *str, size_t s, const char *file, int line); @@ -552,9 +566,14 @@ int OSSL_LIB_CTX_load_config(OSSL_LIB_CTX *ctx, const char *config_file); void OSSL_LIB_CTX_free(OSSL_LIB_CTX *); OSSL_LIB_CTX *OSSL_LIB_CTX_get0_global_default(void); OSSL_LIB_CTX *OSSL_LIB_CTX_set0_default(OSSL_LIB_CTX *libctx); +int OSSL_LIB_CTX_get_conf_diagnostics(OSSL_LIB_CTX *ctx); +void OSSL_LIB_CTX_set_conf_diagnostics(OSSL_LIB_CTX *ctx, int value); void OSSL_sleep(uint64_t millis); + +void *OSSL_LIB_CTX_get_data(OSSL_LIB_CTX *ctx, int index); + # ifdef __cplusplus } # endif diff --git a/include/openssl/crypto.h.in b/include/openssl/crypto.h.in index b2d691b90f..101719ab5b 100644 --- a/include/openssl/crypto.h.in +++ b/include/openssl/crypto.h.in @@ -1,7 +1,7 @@ /* * {- join("\n * ", @autowarntext) -} * - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -86,10 +86,15 @@ int CRYPTO_THREAD_unlock(CRYPTO_RWLOCK *lock); void CRYPTO_THREAD_lock_free(CRYPTO_RWLOCK *lock); int CRYPTO_atomic_add(int *val, int amount, int *ret, CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_add64(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_and(uint64_t *val, uint64_t op, uint64_t *ret, + CRYPTO_RWLOCK *lock); int CRYPTO_atomic_or(uint64_t *val, uint64_t op, uint64_t *ret, CRYPTO_RWLOCK *lock); int CRYPTO_atomic_load(uint64_t *val, uint64_t *ret, CRYPTO_RWLOCK *lock); int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); +int CRYPTO_atomic_store(uint64_t *dst, uint64_t val, CRYPTO_RWLOCK *lock); /* No longer needed, so this is a no-op */ #define OPENSSL_malloc_init() while(0) continue @@ -98,6 +103,9 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); CRYPTO_malloc(num, OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_zalloc(num) \ CRYPTO_zalloc(num, OPENSSL_FILE, OPENSSL_LINE) +# define OPENSSL_aligned_alloc(num, alignment, freeptr) \ + CRYPTO_aligned_alloc(num, alignment, freeptr, \ + OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_realloc(addr, num) \ CRYPTO_realloc(addr, num, OPENSSL_FILE, OPENSSL_LINE) # define OPENSSL_clear_realloc(addr, old_num, num) \ @@ -126,6 +134,7 @@ int CRYPTO_atomic_load_int(int *val, int *ret, CRYPTO_RWLOCK *lock); size_t OPENSSL_strlcpy(char *dst, const char *src, size_t siz); size_t OPENSSL_strlcat(char *dst, const char *src, size_t siz); size_t OPENSSL_strnlen(const char *str, size_t maxlen); +int OPENSSL_strtoul(const char *str, char **endptr, int base, unsigned long *num); int OPENSSL_buf2hexstr_ex(char *str, size_t str_n, size_t *strlength, const unsigned char *buf, size_t buflen, const char sep); @@ -162,6 +171,7 @@ const char *OpenSSL_version(int type); # define OPENSSL_FULL_VERSION_STRING 7 # define OPENSSL_MODULES_DIR 8 # define OPENSSL_CPU_INFO 9 +# define OPENSSL_WINCTX 10 const char *OPENSSL_info(int type); /* @@ -176,6 +186,7 @@ const char *OPENSSL_info(int type); # define OPENSSL_INFO_LIST_SEPARATOR 1006 # define OPENSSL_INFO_SEED_SOURCE 1007 # define OPENSSL_INFO_CPU_SETTINGS 1008 +# define OPENSSL_INFO_WINDOWS_CONTEXT 1009 int OPENSSL_issetugid(void); @@ -321,6 +332,9 @@ void CRYPTO_get_mem_functions(CRYPTO_malloc_fn *malloc_fn, OSSL_CRYPTO_ALLOC void *CRYPTO_malloc(size_t num, const char *file, int line); OSSL_CRYPTO_ALLOC void *CRYPTO_zalloc(size_t num, const char *file, int line); +OSSL_CRYPTO_ALLOC void *CRYPTO_aligned_alloc(size_t num, size_t align, + void **freeptr, const char *file, + int line); OSSL_CRYPTO_ALLOC void *CRYPTO_memdup(const void *str, size_t siz, const char *file, int line); OSSL_CRYPTO_ALLOC char *CRYPTO_strdup(const char *str, const char *file, int line); OSSL_CRYPTO_ALLOC char *CRYPTO_strndup(const char *str, size_t s, const char *file, int line); @@ -529,9 +543,14 @@ int OSSL_LIB_CTX_load_config(OSSL_LIB_CTX *ctx, const char *config_file); void OSSL_LIB_CTX_free(OSSL_LIB_CTX *); OSSL_LIB_CTX *OSSL_LIB_CTX_get0_global_default(void); OSSL_LIB_CTX *OSSL_LIB_CTX_set0_default(OSSL_LIB_CTX *libctx); +int OSSL_LIB_CTX_get_conf_diagnostics(OSSL_LIB_CTX *ctx); +void OSSL_LIB_CTX_set_conf_diagnostics(OSSL_LIB_CTX *ctx, int value); void OSSL_sleep(uint64_t millis); + +void *OSSL_LIB_CTX_get_data(OSSL_LIB_CTX *ctx, int index); + # ifdef __cplusplus } # endif diff --git a/include/openssl/cryptoerr.h b/include/openssl/cryptoerr.h index e84b12df6d..7fa79cf385 100644 --- a/include/openssl/cryptoerr.h +++ b/include/openssl/cryptoerr.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -47,6 +47,7 @@ # define CRYPTO_R_SECURE_MALLOC_FAILURE 111 # define CRYPTO_R_STRING_TOO_LONG 112 # define CRYPTO_R_TOO_MANY_BYTES 113 +# define CRYPTO_R_TOO_MANY_NAMES 132 # define CRYPTO_R_TOO_MANY_RECORDS 114 # define CRYPTO_R_TOO_SMALL_BUFFER 116 # define CRYPTO_R_UNKNOWN_NAME_IN_RANDOM_SECTION 120 diff --git a/include/openssl/e_os2.h b/include/openssl/e_os2.h index f1e17958ab..b8c6107915 100644 --- a/include/openssl/e_os2.h +++ b/include/openssl/e_os2.h @@ -200,6 +200,7 @@ extern "C" { # endif # ifndef ossl_ssize_t +# include # define ossl_ssize_t ssize_t # if defined(SSIZE_MAX) # define OSSL_SSIZE_MAX SSIZE_MAX @@ -288,7 +289,7 @@ typedef uint64_t ossl_uintmax_t; # endif # if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 201112L && \ - !defined(__cplusplus) + !defined(__cplusplus) # define ossl_noreturn _Noreturn # elif defined(__GNUC__) && __GNUC__ >= 2 # define ossl_noreturn __attribute__((noreturn)) diff --git a/include/openssl/evp.h b/include/openssl/evp.h index f70b9d744d..5466327087 100644 --- a/include/openssl/evp.h +++ b/include/openssl/evp.h @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -552,6 +552,7 @@ int EVP_MD_get_block_size(const EVP_MD *md); # define EVP_MD_block_size EVP_MD_get_block_size unsigned long EVP_MD_get_flags(const EVP_MD *md); # define EVP_MD_flags EVP_MD_get_flags +int EVP_MD_xof(const EVP_MD *md); const EVP_MD *EVP_MD_CTX_get0_md(const EVP_MD_CTX *ctx); EVP_MD *EVP_MD_CTX_get1_md(EVP_MD_CTX *ctx); @@ -566,9 +567,11 @@ void EVP_MD_CTX_set_update_fn(EVP_MD_CTX *ctx, int (*update) (EVP_MD_CTX *ctx, const void *data, size_t count)); # endif +int EVP_MD_CTX_get_size_ex(const EVP_MD_CTX *ctx); + # define EVP_MD_CTX_get0_name(e) EVP_MD_get0_name(EVP_MD_CTX_get0_md(e)) -# define EVP_MD_CTX_get_size(e) EVP_MD_get_size(EVP_MD_CTX_get0_md(e)) -# define EVP_MD_CTX_size EVP_MD_CTX_get_size +# define EVP_MD_CTX_get_size(e) EVP_MD_CTX_get_size_ex(e) +# define EVP_MD_CTX_size EVP_MD_CTX_get_size_ex # define EVP_MD_CTX_get_block_size(e) EVP_MD_get_block_size(EVP_MD_CTX_get0_md(e)) # define EVP_MD_CTX_block_size EVP_MD_CTX_get_block_size # define EVP_MD_CTX_get_type(e) EVP_MD_get_type(EVP_MD_CTX_get0_md(e)) @@ -895,6 +898,10 @@ const OSSL_PARAM *EVP_CIPHER_gettable_ctx_params(const EVP_CIPHER *cipher); const OSSL_PARAM *EVP_CIPHER_CTX_settable_params(EVP_CIPHER_CTX *ctx); const OSSL_PARAM *EVP_CIPHER_CTX_gettable_params(EVP_CIPHER_CTX *ctx); +int EVP_CIPHER_CTX_set_algor_params(EVP_CIPHER_CTX *ctx, const X509_ALGOR *alg); +int EVP_CIPHER_CTX_get_algor_params(EVP_CIPHER_CTX *ctx, X509_ALGOR *alg); +int EVP_CIPHER_CTX_get_algor(EVP_CIPHER_CTX *ctx, X509_ALGOR **alg); + const BIO_METHOD *BIO_f_md(void); const BIO_METHOD *BIO_f_base64(void); const BIO_METHOD *BIO_f_cipher(void); @@ -1690,33 +1697,47 @@ int EVP_PKEY_CTX_set_kem_op(EVP_PKEY_CTX *ctx, const char *op); const char *EVP_PKEY_get0_type_name(const EVP_PKEY *key); # define EVP_PKEY_OP_UNDEFINED 0 -# define EVP_PKEY_OP_PARAMGEN (1<<1) -# define EVP_PKEY_OP_KEYGEN (1<<2) -# define EVP_PKEY_OP_FROMDATA (1<<3) -# define EVP_PKEY_OP_SIGN (1<<4) -# define EVP_PKEY_OP_VERIFY (1<<5) -# define EVP_PKEY_OP_VERIFYRECOVER (1<<6) -# define EVP_PKEY_OP_SIGNCTX (1<<7) -# define EVP_PKEY_OP_VERIFYCTX (1<<8) -# define EVP_PKEY_OP_ENCRYPT (1<<9) -# define EVP_PKEY_OP_DECRYPT (1<<10) -# define EVP_PKEY_OP_DERIVE (1<<11) -# define EVP_PKEY_OP_ENCAPSULATE (1<<12) -# define EVP_PKEY_OP_DECAPSULATE (1<<13) - -# define EVP_PKEY_OP_TYPE_SIG \ - (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_VERIFY | EVP_PKEY_OP_VERIFYRECOVER \ - | EVP_PKEY_OP_SIGNCTX | EVP_PKEY_OP_VERIFYCTX) - -# define EVP_PKEY_OP_TYPE_CRYPT \ - (EVP_PKEY_OP_ENCRYPT | EVP_PKEY_OP_DECRYPT) - -# define EVP_PKEY_OP_TYPE_NOGEN \ - (EVP_PKEY_OP_TYPE_SIG | EVP_PKEY_OP_TYPE_CRYPT | EVP_PKEY_OP_DERIVE) - -# define EVP_PKEY_OP_TYPE_GEN \ - (EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN) - +# define EVP_PKEY_OP_PARAMGEN (1 << 1) +# define EVP_PKEY_OP_KEYGEN (1 << 2) +# define EVP_PKEY_OP_FROMDATA (1 << 3) +# define EVP_PKEY_OP_SIGN (1 << 4) +# define EVP_PKEY_OP_VERIFY (1 << 5) +# define EVP_PKEY_OP_VERIFYRECOVER (1 << 6) +# define EVP_PKEY_OP_SIGNCTX (1 << 7) +# define EVP_PKEY_OP_VERIFYCTX (1 << 8) +# define EVP_PKEY_OP_ENCRYPT (1 << 9) +# define EVP_PKEY_OP_DECRYPT (1 << 10) +# define EVP_PKEY_OP_DERIVE (1 << 11) +# define EVP_PKEY_OP_ENCAPSULATE (1 << 12) +# define EVP_PKEY_OP_DECAPSULATE (1 << 13) +# define EVP_PKEY_OP_SIGNMSG (1 << 14) +# define EVP_PKEY_OP_VERIFYMSG (1 << 15) +/* Update the following when adding new EVP_PKEY_OPs */ +# define EVP_PKEY_OP_ALL ((1 << 16) - 1) + +# define EVP_PKEY_OP_TYPE_SIG \ + (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG \ + | EVP_PKEY_OP_VERIFY | EVP_PKEY_OP_VERIFYMSG \ + | EVP_PKEY_OP_VERIFYRECOVER \ + | EVP_PKEY_OP_SIGNCTX | EVP_PKEY_OP_VERIFYCTX) + +# define EVP_PKEY_OP_TYPE_CRYPT \ + (EVP_PKEY_OP_ENCRYPT | EVP_PKEY_OP_DECRYPT) + +# define EVP_PKEY_OP_TYPE_DERIVE \ + (EVP_PKEY_OP_DERIVE) + +# define EVP_PKEY_OP_TYPE_DATA \ + (EVP_PKEY_OP_FROMDATA) + +# define EVP_PKEY_OP_TYPE_KEM \ + (EVP_PKEY_OP_ENCAPSULATE | EVP_PKEY_OP_DECAPSULATE) + +# define EVP_PKEY_OP_TYPE_GEN \ + (EVP_PKEY_OP_PARAMGEN | EVP_PKEY_OP_KEYGEN) + +# define EVP_PKEY_OP_TYPE_NOGEN \ + (EVP_PKEY_OP_ALL & ~EVP_PKEY_OP_TYPE_GEN) int EVP_PKEY_CTX_set_mac_key(EVP_PKEY_CTX *ctx, const unsigned char *key, int keylen); @@ -1780,6 +1801,7 @@ int EVP_KEYMGMT_names_do_all(const EVP_KEYMGMT *keymgmt, const OSSL_PARAM *EVP_KEYMGMT_gettable_params(const EVP_KEYMGMT *keymgmt); const OSSL_PARAM *EVP_KEYMGMT_settable_params(const EVP_KEYMGMT *keymgmt); const OSSL_PARAM *EVP_KEYMGMT_gen_settable_params(const EVP_KEYMGMT *keymgmt); +const OSSL_PARAM *EVP_KEYMGMT_gen_gettable_params(const EVP_KEYMGMT *keymgmt); EVP_PKEY_CTX *EVP_PKEY_CTX_new(EVP_PKEY *pkey, ENGINE *e); EVP_PKEY_CTX *EVP_PKEY_CTX_new_id(int id, ENGINE *e); @@ -1796,6 +1818,11 @@ int EVP_PKEY_CTX_get_params(EVP_PKEY_CTX *ctx, OSSL_PARAM *params); const OSSL_PARAM *EVP_PKEY_CTX_gettable_params(const EVP_PKEY_CTX *ctx); int EVP_PKEY_CTX_set_params(EVP_PKEY_CTX *ctx, const OSSL_PARAM *params); const OSSL_PARAM *EVP_PKEY_CTX_settable_params(const EVP_PKEY_CTX *ctx); + +int EVP_PKEY_CTX_set_algor_params(EVP_PKEY_CTX *ctx, const X509_ALGOR *alg); +int EVP_PKEY_CTX_get_algor_params(EVP_PKEY_CTX *ctx, X509_ALGOR *alg); +int EVP_PKEY_CTX_get_algor(EVP_PKEY_CTX *ctx, X509_ALGOR **alg); + int EVP_PKEY_CTX_ctrl(EVP_PKEY_CTX *ctx, int keytype, int optype, int cmd, int p1, void *p2); int EVP_PKEY_CTX_ctrl_str(EVP_PKEY_CTX *ctx, const char *type, @@ -1846,6 +1873,9 @@ EVP_PKEY *EVP_PKEY_CTX_get0_peerkey(EVP_PKEY_CTX *ctx); void EVP_PKEY_CTX_set_app_data(EVP_PKEY_CTX *ctx, void *data); void *EVP_PKEY_CTX_get_app_data(EVP_PKEY_CTX *ctx); +int EVP_PKEY_CTX_set_signature(EVP_PKEY_CTX *pctx, + const unsigned char *sig, size_t siglen); + void EVP_SIGNATURE_free(EVP_SIGNATURE *signature); int EVP_SIGNATURE_up_ref(EVP_SIGNATURE *signature); OSSL_PROVIDER *EVP_SIGNATURE_get0_provider(const EVP_SIGNATURE *signature); @@ -1899,17 +1929,35 @@ const OSSL_PARAM *EVP_KEM_settable_ctx_params(const EVP_KEM *kem); int EVP_PKEY_sign_init(EVP_PKEY_CTX *ctx); int EVP_PKEY_sign_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]); +int EVP_PKEY_sign_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]); int EVP_PKEY_sign(EVP_PKEY_CTX *ctx, unsigned char *sig, size_t *siglen, const unsigned char *tbs, size_t tbslen); +int EVP_PKEY_sign_message_init(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]); +int EVP_PKEY_sign_message_update(EVP_PKEY_CTX *ctx, + const unsigned char *in, size_t inlen); +int EVP_PKEY_sign_message_final(EVP_PKEY_CTX *ctx, + unsigned char *sig, size_t *siglen); int EVP_PKEY_verify_init(EVP_PKEY_CTX *ctx); int EVP_PKEY_verify_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]); +int EVP_PKEY_verify_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]); int EVP_PKEY_verify(EVP_PKEY_CTX *ctx, const unsigned char *sig, size_t siglen, const unsigned char *tbs, size_t tbslen); +int EVP_PKEY_verify_message_init(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, const OSSL_PARAM params[]); +int EVP_PKEY_verify_message_update(EVP_PKEY_CTX *ctx, + const unsigned char *in, size_t inlen); +int EVP_PKEY_verify_message_final(EVP_PKEY_CTX *ctx); int EVP_PKEY_verify_recover_init(EVP_PKEY_CTX *ctx); int EVP_PKEY_verify_recover_init_ex(EVP_PKEY_CTX *ctx, const OSSL_PARAM params[]); +int EVP_PKEY_verify_recover_init_ex2(EVP_PKEY_CTX *ctx, + EVP_SIGNATURE *algo, + const OSSL_PARAM params[]); int EVP_PKEY_verify_recover(EVP_PKEY_CTX *ctx, unsigned char *rout, size_t *routlen, const unsigned char *sig, size_t siglen); diff --git a/include/openssl/evperr.h b/include/openssl/evperr.h index 11f3faa459..0a991f735a 100644 --- a/include/openssl/evperr.h +++ b/include/openssl/evperr.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -54,6 +54,7 @@ # define EVP_R_EXPECTING_A_SIPHASH_KEY 175 # define EVP_R_FINAL_ERROR 188 # define EVP_R_GENERATE_ERROR 214 +# define EVP_R_GETTING_ALGORITHMIDENTIFIER_NOT_SUPPORTED 229 # define EVP_R_GET_RAW_KEY_FAILED 182 # define EVP_R_ILLEGAL_SCRYPT_PARAMETERS 171 # define EVP_R_INACCESSIBLE_DOMAIN_PARAMETERS 204 @@ -94,6 +95,7 @@ # define EVP_R_ONLY_ONESHOT_SUPPORTED 177 # define EVP_R_OPERATION_NOT_INITIALIZED 151 # define EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE 150 +# define EVP_R_OPERATION_NOT_SUPPORTED_FOR_THIS_SIGNATURE_TYPE 226 # define EVP_R_OUTPUT_WOULD_OVERFLOW 202 # define EVP_R_PARAMETER_TOO_LARGE 187 # define EVP_R_PARTIALLY_OVERLAPPING 162 @@ -104,6 +106,7 @@ # define EVP_R_PUBLIC_KEY_NOT_RSA 106 # define EVP_R_SETTING_XOF_FAILED 227 # define EVP_R_SET_DEFAULT_PROPERTY_FAILURE 209 +# define EVP_R_SIGNATURE_TYPE_AND_KEY_TYPE_INCOMPATIBLE 228 # define EVP_R_TOO_MANY_RECORDS 183 # define EVP_R_UNABLE_TO_ENABLE_LOCKING 212 # define EVP_R_UNABLE_TO_GET_MAXIMUM_REQUEST_SIZE 215 diff --git a/include/openssl/fips_names.h b/include/openssl/fips_names.h index 5c77f6d691..fa481fc611 100644 --- a/include/openssl/fips_names.h +++ b/include/openssl/fips_names.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,27 +17,18 @@ extern "C" { /* * Parameter names that the FIPS Provider defines + * All parameters are of type: OSSL_PARAM_UTF8_STRING */ -/* - * The calculated MAC of the module file (Used for FIPS Self Testing) - * Type: OSSL_PARAM_UTF8_STRING - */ +/* The following 4 Parameters are used for FIPS Self Testing */ + +/* The calculated MAC of the module file */ # define OSSL_PROV_FIPS_PARAM_MODULE_MAC "module-mac" -/* - * A version number for the fips install process (Used for FIPS Self Testing) - * Type: OSSL_PARAM_UTF8_STRING - */ +/* The Version number for the fips install process */ # define OSSL_PROV_FIPS_PARAM_INSTALL_VERSION "install-version" -/* - * The calculated MAC of the install status indicator (Used for FIPS Self Testing) - * Type: OSSL_PARAM_UTF8_STRING - */ +/* The calculated MAC of the install status indicator */ # define OSSL_PROV_FIPS_PARAM_INSTALL_MAC "install-mac" -/* - * The install status indicator (Used for FIPS Self Testing) - * Type: OSSL_PARAM_UTF8_STRING - */ +/* The install status indicator */ # define OSSL_PROV_FIPS_PARAM_INSTALL_STATUS "install-status" /* @@ -47,28 +38,10 @@ extern "C" { */ # define OSSL_PROV_FIPS_PARAM_CONDITIONAL_ERRORS "conditional-errors" -/* - * A boolean that determines if the runtime FIPS security checks are performed. - * This is enabled by default. - * Type: OSSL_PARAM_UTF8_STRING - */ -# define OSSL_PROV_FIPS_PARAM_SECURITY_CHECKS "security-checks" - -/* - * A boolean that determines if the runtime FIPS check for TLS1_PRF EMS is performed. - * This is disabled by default. - * Type: OSSL_PARAM_UTF8_STRING - */ -# define OSSL_PROV_FIPS_PARAM_TLS1_PRF_EMS_CHECK "tls1-prf-ems-check" - -/* - * A boolean that determines if truncated digests can be used with Hash and HMAC - * DRBGs. FIPS 140-3 IG D.R disallows such use for efficiency rather than - * security reasons. - * This is disabled by default. - * Type: OSSL_PARAM_UTF8_STRING - */ -# define OSSL_PROV_FIPS_PARAM_DRBG_TRUNC_DIGEST "drbg-no-trunc-md" +/* The following are provided for backwards compatibility */ +# define OSSL_PROV_FIPS_PARAM_SECURITY_CHECKS OSSL_PROV_PARAM_SECURITY_CHECKS +# define OSSL_PROV_FIPS_PARAM_TLS1_PRF_EMS_CHECK OSSL_PROV_PARAM_TLS1_PRF_EMS_CHECK +# define OSSL_PROV_FIPS_PARAM_DRBG_TRUNC_DIGEST OSSL_PROV_PARAM_DRBG_TRUNC_DIGEST # ifdef __cplusplus } diff --git a/include/openssl/fipskey.h b/include/openssl/fipskey.h index 42ba014b31..620812bf0a 100644 --- a/include/openssl/fipskey.h +++ b/include/openssl/fipskey.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/fipskey.h.in * - * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -29,6 +29,11 @@ extern "C" { */ #define FIPS_KEY_STRING "f4556650ac31d35461610bac4ed81b1a181b2d8a43ea2854cbae22ca74560813" +/* + * The FIPS provider vendor name, as a string. + */ +#define FIPS_VENDOR "OpenSSL non-compliant FIPS Provider" + # ifdef __cplusplus } # endif diff --git a/include/openssl/fipskey.h.in b/include/openssl/fipskey.h.in index 56b947e852..c53012a862 100644 --- a/include/openssl/fipskey.h.in +++ b/include/openssl/fipskey.h.in @@ -1,7 +1,7 @@ /* * {- join("\n * ", @autowarntext) -} * - * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -28,6 +28,11 @@ extern "C" { */ #define FIPS_KEY_STRING "{- $config{FIPSKEY} -}" +/* + * The FIPS provider vendor name, as a string. + */ +#define FIPS_VENDOR "{- $config{FIPS_VENDOR} -}" + # ifdef __cplusplus } # endif diff --git a/include/openssl/http.h b/include/openssl/http.h index 8f4e9da30b..339b567dcd 100644 --- a/include/openssl/http.h +++ b/include/openssl/http.h @@ -35,9 +35,10 @@ extern "C" { # ifndef OPENSSL_NO_HTTP -#define OSSL_HTTP_DEFAULT_MAX_LINE_LEN (4 * 1024) -#define OSSL_HTTP_DEFAULT_MAX_RESP_LEN (100 * 1024) -#define OSSL_HTTP_DEFAULT_MAX_RESP_HDR_LINES 256 +# define OSSL_HTTP_DEFAULT_MAX_LINE_LEN (4 * 1024) +# define OSSL_HTTP_DEFAULT_MAX_RESP_LEN (100 * 1024) +# define OSSL_HTTP_DEFAULT_MAX_CRL_LEN (32 * 1024 * 1024) +# define OSSL_HTTP_DEFAULT_MAX_RESP_HDR_LINES 256 /* Low-level HTTP API */ diff --git a/include/openssl/indicator.h b/include/openssl/indicator.h new file mode 100644 index 0000000000..3ea0122188 --- /dev/null +++ b/include/openssl/indicator.h @@ -0,0 +1,31 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifndef OPENSSL_INDICATOR_H +# define OPENSSL_INDICATOR_H +# pragma once + +# ifdef __cplusplus +extern "C" { +# endif + +#include + +typedef int (OSSL_INDICATOR_CALLBACK)(const char *type, const char *desc, + const OSSL_PARAM params[]); + +void OSSL_INDICATOR_set_callback(OSSL_LIB_CTX *libctx, + OSSL_INDICATOR_CALLBACK *cb); +void OSSL_INDICATOR_get_callback(OSSL_LIB_CTX *libctx, + OSSL_INDICATOR_CALLBACK **cb); + +# ifdef __cplusplus +} +# endif +#endif /* OPENSSL_INDICATOR_H */ diff --git a/include/openssl/macros.h b/include/openssl/macros.h index e9ef938747..8330c758da 100644 --- a/include/openssl/macros.h +++ b/include/openssl/macros.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -169,6 +169,7 @@ * 'no-deprecated'. */ +# undef OPENSSL_NO_DEPRECATED_3_4 # undef OPENSSL_NO_DEPRECATED_3_1 # undef OPENSSL_NO_DEPRECATED_3_0 # undef OPENSSL_NO_DEPRECATED_1_1_1 @@ -178,6 +179,17 @@ # undef OPENSSL_NO_DEPRECATED_1_0_0 # undef OPENSSL_NO_DEPRECATED_0_9_8 +# if OPENSSL_API_LEVEL >= 30400 +# ifndef OPENSSL_NO_DEPRECATED +# define OSSL_DEPRECATEDIN_3_4 OSSL_DEPRECATED(3.4) +# define OSSL_DEPRECATEDIN_3_4_FOR(msg) OSSL_DEPRECATED_FOR(3.4, msg) +# else +# define OPENSSL_NO_DEPRECATED_3_4 +# endif +# else +# define OSSL_DEPRECATEDIN_3_4 +# define OSSL_DEPRECATEDIN_3_4_FOR(msg) +# endif # if OPENSSL_API_LEVEL >= 30100 # ifndef OPENSSL_NO_DEPRECATED # define OSSL_DEPRECATEDIN_3_1 OSSL_DEPRECATED(3.1) diff --git a/include/openssl/obj_mac.h b/include/openssl/obj_mac.h index 1b7d9240a9..ea603c2416 100644 --- a/include/openssl/obj_mac.h +++ b/include/openssl/obj_mac.h @@ -1583,9 +1583,13 @@ #define NID_qcStatements 286 #define OBJ_qcStatements OBJ_id_pe,3L -#define SN_ac_auditEntity "ac-auditEntity" -#define NID_ac_auditEntity 287 -#define OBJ_ac_auditEntity OBJ_id_pe,4L +#define SN_ac_auditIdentity "ac-auditIdentity" +#define LN_ac_auditIdentity "X509v3 Audit Identity" +#define NID_ac_auditIdentity 287 +#define OBJ_ac_auditIdentity OBJ_id_pe,4L + +#define NID_ac_auditEntity 1323 +#define OBJ_ac_auditEntity OBJ_ac_auditIdentity #define SN_ac_targeting "ac-targeting" #define NID_ac_targeting 288 @@ -2022,6 +2026,11 @@ #define NID_id_on_permanentIdentifier 858 #define OBJ_id_on_permanentIdentifier OBJ_id_on,3L +#define SN_id_on_hardwareModuleName "id-on-hardwareModuleName" +#define LN_id_on_hardwareModuleName "Hardware Module Name" +#define NID_id_on_hardwareModuleName 1321 +#define OBJ_id_on_hardwareModuleName OBJ_id_on,4L + #define SN_XmppAddr "id-on-xmppAddr" #define LN_XmppAddr "XmppAddr" #define NID_XmppAddr 1209 @@ -3019,6 +3028,11 @@ #define NID_dcObject 390 #define OBJ_dcObject OBJ_Enterprises,1466L,344L +#define SN_id_kp_wisun_fan_device "id-kp-wisun-fan-device" +#define LN_id_kp_wisun_fan_device "Wi-SUN Alliance Field Area Network (FAN)" +#define NID_id_kp_wisun_fan_device 1322 +#define OBJ_id_kp_wisun_fan_device OBJ_Enterprises,45605L,1L + #define SN_mime_mhs "mime-mhs" #define LN_mime_mhs "MIME MHS" #define NID_mime_mhs 504 diff --git a/include/openssl/objects.h b/include/openssl/objects.h index 9ea91c27c8..cc9f3c51b0 100644 --- a/include/openssl/objects.h +++ b/include/openssl/objects.h @@ -1,5 +1,5 @@ /* - * Copyright 1995-2019 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -176,6 +176,7 @@ int OBJ_find_sigid_by_algs(int *psignid, int dig_nid, int pkey_nid); int OBJ_add_sigid(int signid, int dig_id, int pkey_id); void OBJ_sigid_free(void); +#define SN_ac_auditEntity SN_ac_auditIdentity # ifdef __cplusplus } diff --git a/include/openssl/opensslv.h b/include/openssl/opensslv.h index f62a43cfae..0b48437901 100644 --- a/include/openssl/opensslv.h +++ b/include/openssl/opensslv.h @@ -28,8 +28,8 @@ extern "C" { * These macros express version number MAJOR.MINOR.PATCH exactly */ # define OPENSSL_VERSION_MAJOR 3 -# define OPENSSL_VERSION_MINOR 3 -# define OPENSSL_VERSION_PATCH 2 +# define OPENSSL_VERSION_MINOR 4 +# define OPENSSL_VERSION_PATCH 0 /* * Additional version information @@ -74,21 +74,21 @@ extern "C" { * longer variant with OPENSSL_VERSION_PRE_RELEASE_STR and * OPENSSL_VERSION_BUILD_METADATA_STR appended. */ -# define OPENSSL_VERSION_STR "3.3.2" -# define OPENSSL_FULL_VERSION_STR "3.3.2" +# define OPENSSL_VERSION_STR "3.4.0" +# define OPENSSL_FULL_VERSION_STR "3.4.0" /* * SECTION 3: ADDITIONAL METADATA * * These strings are defined separately to allow them to be parsable. */ -# define OPENSSL_RELEASE_DATE "3 Sep 2024" +# define OPENSSL_RELEASE_DATE "22 Oct 2024" /* * SECTION 4: BACKWARD COMPATIBILITY */ -# define OPENSSL_VERSION_TEXT "OpenSSL 3.3.2 3 Sep 2024" +# define OPENSSL_VERSION_TEXT "OpenSSL 3.4.0 22 Oct 2024" /* Synthesize OPENSSL_VERSION_NUMBER with the layout 0xMNN00PPSL */ # ifdef OPENSSL_VERSION_PRE_RELEASE diff --git a/include/openssl/pem.h b/include/openssl/pem.h index 0446c77019..6b7b66a2be 100644 --- a/include/openssl/pem.h +++ b/include/openssl/pem.h @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -58,6 +58,7 @@ extern "C" { # define PEM_STRING_PARAMETERS "PARAMETERS" # define PEM_STRING_CMS "CMS" # define PEM_STRING_SM2PARAMETERS "SM2 PARAMETERS" +# define PEM_STRING_ACERT "ATTRIBUTE CERTIFICATE" # define PEM_TYPE_ENCRYPTED 10 # define PEM_TYPE_MIC_ONLY 20 diff --git a/include/openssl/pkcs12.h b/include/openssl/pkcs12.h index b08b0bc214..0809645dad 100644 --- a/include/openssl/pkcs12.h +++ b/include/openssl/pkcs12.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/pkcs12.h.in * - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -292,6 +292,9 @@ int PKCS12_verify_mac(PKCS12 *p12, const char *pass, int passlen); int PKCS12_set_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char *salt, int saltlen, int iter, const EVP_MD *md_type); +int PKCS12_set_pbmac1_pbkdf2(PKCS12 *p12, const char *pass, int passlen, + unsigned char *salt, int saltlen, int iter, + const EVP_MD *md_type, const char *prf_md_name); int PKCS12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, const EVP_MD *md_type); unsigned char *OPENSSL_asc2uni(const char *asc, int asclen, diff --git a/include/openssl/pkcs12.h.in b/include/openssl/pkcs12.h.in index 35759d4dea..097afba368 100644 --- a/include/openssl/pkcs12.h.in +++ b/include/openssl/pkcs12.h.in @@ -1,7 +1,7 @@ /* * {- join("\n * ", @autowarntext) -} * - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -269,6 +269,9 @@ int PKCS12_verify_mac(PKCS12 *p12, const char *pass, int passlen); int PKCS12_set_mac(PKCS12 *p12, const char *pass, int passlen, unsigned char *salt, int saltlen, int iter, const EVP_MD *md_type); +int PKCS12_set_pbmac1_pbkdf2(PKCS12 *p12, const char *pass, int passlen, + unsigned char *salt, int saltlen, int iter, + const EVP_MD *md_type, const char *prf_md_name); int PKCS12_setup_mac(PKCS12 *p12, int iter, unsigned char *salt, int saltlen, const EVP_MD *md_type); unsigned char *OPENSSL_asc2uni(const char *asc, int asclen, diff --git a/include/openssl/proverr.h b/include/openssl/proverr.h index d9ef56815c..d10b653152 100644 --- a/include/openssl/proverr.h +++ b/include/openssl/proverr.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -30,9 +30,11 @@ # define PROV_R_BAD_TLS_CLIENT_VERSION 161 # define PROV_R_BN_ERROR 160 # define PROV_R_CIPHER_OPERATION_FAILED 102 +# define PROV_R_COFACTOR_REQUIRED 236 # define PROV_R_DERIVATION_FUNCTION_INIT_FAILED 205 # define PROV_R_DIGEST_NOT_ALLOWED 174 # define PROV_R_EMS_NOT_ENABLED 233 +# define PROV_R_ENTROPY_SOURCE_FAILED_CONTINUOUS_TESTS 244 # define PROV_R_ENTROPY_SOURCE_STRENGTH_TOO_WEAK 186 # define PROV_R_ERROR_INSTANTIATING_DRBG 188 # define PROV_R_ERROR_RETRIEVING_ENTROPY 189 @@ -44,12 +46,14 @@ # define PROV_R_FAILED_TO_GET_PARAMETER 103 # define PROV_R_FAILED_TO_SET_PARAMETER 104 # define PROV_R_FAILED_TO_SIGN 175 +# define PROV_R_FINAL_CALL_OUT_OF_ORDER 237 # define PROV_R_FIPS_MODULE_CONDITIONAL_ERROR 227 # define PROV_R_FIPS_MODULE_ENTERING_ERROR_STATE 224 # define PROV_R_FIPS_MODULE_IN_ERROR_STATE 225 # define PROV_R_GENERATE_ERROR 191 # define PROV_R_ILLEGAL_OR_UNSUPPORTED_PADDING_MODE 165 # define PROV_R_INDICATOR_INTEGRITY_FAILURE 210 +# define PROV_R_INIT_CALL_OUT_OF_ORDER 238 # define PROV_R_INSUFFICIENT_DRBG_STRENGTH 181 # define PROV_R_INVALID_AAD 108 # define PROV_R_INVALID_AEAD 231 @@ -61,6 +65,7 @@ # define PROV_R_INVALID_DIGEST 122 # define PROV_R_INVALID_DIGEST_LENGTH 166 # define PROV_R_INVALID_DIGEST_SIZE 218 +# define PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION 243 # define PROV_R_INVALID_INPUT_LENGTH 230 # define PROV_R_INVALID_ITERATION_COUNT 123 # define PROV_R_INVALID_IV_LENGTH 109 @@ -73,6 +78,7 @@ # define PROV_R_INVALID_MODE 125 # define PROV_R_INVALID_OUTPUT_LENGTH 217 # define PROV_R_INVALID_PADDING_MODE 168 +# define PROV_R_INVALID_PREHASHED_DIGEST_LENGTH 241 # define PROV_R_INVALID_PUBINFO 198 # define PROV_R_INVALID_SALT_LENGTH 112 # define PROV_R_INVALID_SEED_LENGTH 154 @@ -110,8 +116,10 @@ # define PROV_R_NOT_PARAMETERS 226 # define PROV_R_NOT_SUPPORTED 136 # define PROV_R_NOT_XOF_OR_INVALID_LENGTH 113 +# define PROV_R_NO_INSTANCE_ALLOWED 242 # define PROV_R_NO_KEY_SET 114 # define PROV_R_NO_PARAMETERS_SET 177 +# define PROV_R_ONESHOT_CALL_OUT_OF_ORDER 239 # define PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE 178 # define PROV_R_OUTPUT_BUFFER_TOO_SMALL 106 # define PROV_R_PARENT_CANNOT_GENERATE_RANDOM_NUMBERS 228 @@ -142,6 +150,7 @@ # define PROV_R_UNSUPPORTED_KEY_SIZE 153 # define PROV_R_UNSUPPORTED_MAC_TYPE 137 # define PROV_R_UNSUPPORTED_NUMBER_OF_ROUNDS 152 +# define PROV_R_UPDATE_CALL_OUT_OF_ORDER 240 # define PROV_R_URI_AUTHORITY_UNSUPPORTED 223 # define PROV_R_VALUE_ERROR 138 # define PROV_R_WRONG_FINAL_BLOCK_LENGTH 107 diff --git a/include/openssl/self_test.h b/include/openssl/self_test.h index 17822049ac..98652f9abd 100644 --- a/include/openssl/self_test.h +++ b/include/openssl/self_test.h @@ -44,6 +44,7 @@ extern "C" { /* Test event sub categories */ # define OSSL_SELF_TEST_DESC_NONE "None" # define OSSL_SELF_TEST_DESC_INTEGRITY_HMAC "HMAC" +# define OSSL_SELF_TEST_DESC_PCT_RSA "RSA" # define OSSL_SELF_TEST_DESC_PCT_RSA_PKCS1 "RSA" # define OSSL_SELF_TEST_DESC_PCT_ECDSA "ECDSA" # define OSSL_SELF_TEST_DESC_PCT_EDDSA "EDDSA" @@ -59,6 +60,7 @@ extern "C" { # define OSSL_SELF_TEST_DESC_SIGN_DSA "DSA" # define OSSL_SELF_TEST_DESC_SIGN_RSA "RSA" # define OSSL_SELF_TEST_DESC_SIGN_ECDSA "ECDSA" +# define OSSL_SELF_TEST_DESC_SIGN_EDDSA "EDDSA" # define OSSL_SELF_TEST_DESC_DRBG_CTR "CTR" # define OSSL_SELF_TEST_DESC_DRBG_HASH "HASH" # define OSSL_SELF_TEST_DESC_DRBG_HMAC "HMAC" diff --git a/include/openssl/ssl.h b/include/openssl/ssl.h index 6815f846cc..8687308a4e 100644 --- a/include/openssl/ssl.h +++ b/include/openssl/ssl.h @@ -235,10 +235,8 @@ typedef struct ssl_cipher_st SSL_CIPHER; typedef struct ssl_session_st SSL_SESSION; typedef struct tls_sigalgs_st TLS_SIGALGS; typedef struct ssl_conf_ctx_st SSL_CONF_CTX; -typedef struct ssl_comp_st SSL_COMP; STACK_OF(SSL_CIPHER); -STACK_OF(SSL_COMP); /* SRTP protection profiles for use with the use_srtp extension (RFC 5764)*/ typedef struct srtp_protection_profile_st { @@ -1023,32 +1021,6 @@ SKM_DEFINE_STACK_OF_INTERNAL(SSL_CIPHER, const SSL_CIPHER, SSL_CIPHER) #define sk_SSL_CIPHER_dup(sk) ((STACK_OF(SSL_CIPHER) *)OPENSSL_sk_dup(ossl_check_const_SSL_CIPHER_sk_type(sk))) #define sk_SSL_CIPHER_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(SSL_CIPHER) *)OPENSSL_sk_deep_copy(ossl_check_const_SSL_CIPHER_sk_type(sk), ossl_check_SSL_CIPHER_copyfunc_type(copyfunc), ossl_check_SSL_CIPHER_freefunc_type(freefunc))) #define sk_SSL_CIPHER_set_cmp_func(sk, cmp) ((sk_SSL_CIPHER_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_SSL_CIPHER_sk_type(sk), ossl_check_SSL_CIPHER_compfunc_type(cmp))) -SKM_DEFINE_STACK_OF_INTERNAL(SSL_COMP, SSL_COMP, SSL_COMP) -#define sk_SSL_COMP_num(sk) OPENSSL_sk_num(ossl_check_const_SSL_COMP_sk_type(sk)) -#define sk_SSL_COMP_value(sk, idx) ((SSL_COMP *)OPENSSL_sk_value(ossl_check_const_SSL_COMP_sk_type(sk), (idx))) -#define sk_SSL_COMP_new(cmp) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new(ossl_check_SSL_COMP_compfunc_type(cmp))) -#define sk_SSL_COMP_new_null() ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new_null()) -#define sk_SSL_COMP_new_reserve(cmp, n) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_new_reserve(ossl_check_SSL_COMP_compfunc_type(cmp), (n))) -#define sk_SSL_COMP_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_SSL_COMP_sk_type(sk), (n)) -#define sk_SSL_COMP_free(sk) OPENSSL_sk_free(ossl_check_SSL_COMP_sk_type(sk)) -#define sk_SSL_COMP_zero(sk) OPENSSL_sk_zero(ossl_check_SSL_COMP_sk_type(sk)) -#define sk_SSL_COMP_delete(sk, i) ((SSL_COMP *)OPENSSL_sk_delete(ossl_check_SSL_COMP_sk_type(sk), (i))) -#define sk_SSL_COMP_delete_ptr(sk, ptr) ((SSL_COMP *)OPENSSL_sk_delete_ptr(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr))) -#define sk_SSL_COMP_push(sk, ptr) OPENSSL_sk_push(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) -#define sk_SSL_COMP_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) -#define sk_SSL_COMP_pop(sk) ((SSL_COMP *)OPENSSL_sk_pop(ossl_check_SSL_COMP_sk_type(sk))) -#define sk_SSL_COMP_shift(sk) ((SSL_COMP *)OPENSSL_sk_shift(ossl_check_SSL_COMP_sk_type(sk))) -#define sk_SSL_COMP_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_SSL_COMP_sk_type(sk),ossl_check_SSL_COMP_freefunc_type(freefunc)) -#define sk_SSL_COMP_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr), (idx)) -#define sk_SSL_COMP_set(sk, idx, ptr) ((SSL_COMP *)OPENSSL_sk_set(ossl_check_SSL_COMP_sk_type(sk), (idx), ossl_check_SSL_COMP_type(ptr))) -#define sk_SSL_COMP_find(sk, ptr) OPENSSL_sk_find(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) -#define sk_SSL_COMP_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr)) -#define sk_SSL_COMP_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_type(ptr), pnum) -#define sk_SSL_COMP_sort(sk) OPENSSL_sk_sort(ossl_check_SSL_COMP_sk_type(sk)) -#define sk_SSL_COMP_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_SSL_COMP_sk_type(sk)) -#define sk_SSL_COMP_dup(sk) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_dup(ossl_check_const_SSL_COMP_sk_type(sk))) -#define sk_SSL_COMP_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(SSL_COMP) *)OPENSSL_sk_deep_copy(ossl_check_const_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_copyfunc_type(copyfunc), ossl_check_SSL_COMP_freefunc_type(freefunc))) -#define sk_SSL_COMP_set_cmp_func(sk, cmp) ((sk_SSL_COMP_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_SSL_COMP_sk_type(sk), ossl_check_SSL_COMP_compfunc_type(cmp))) /* compatibility */ @@ -1644,7 +1616,11 @@ void SSL_CTX_set1_cert_store(SSL_CTX *, X509_STORE *); __owur int SSL_want(const SSL *s); __owur int SSL_clear(SSL *s); +#ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_CTX_flush_sessions_ex()") void SSL_CTX_flush_sessions(SSL_CTX *ctx, long tm); +#endif +void SSL_CTX_flush_sessions_ex(SSL_CTX *ctx, time_t tm); __owur const SSL_CIPHER *SSL_get_current_cipher(const SSL *s); __owur const SSL_CIPHER *SSL_get_pending_cipher(const SSL *s); @@ -1756,8 +1732,13 @@ __owur const char *SSL_state_string(const SSL *s); __owur const char *SSL_rstate_string(const SSL *s); __owur const char *SSL_state_string_long(const SSL *s); __owur const char *SSL_rstate_string_long(const SSL *s); + +#ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_SESSION_get_time_ex()") __owur long SSL_SESSION_get_time(const SSL_SESSION *s); +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_SESSION_set_time_ex()") __owur long SSL_SESSION_set_time(SSL_SESSION *s, long t); +#endif __owur long SSL_SESSION_get_timeout(const SSL_SESSION *s); __owur long SSL_SESSION_set_timeout(SSL_SESSION *s, long t); __owur int SSL_SESSION_get_protocol_version(const SSL_SESSION *s); @@ -2329,6 +2310,8 @@ void SSL_CTX_set_record_padding_callback(SSL_CTX *ctx, void SSL_CTX_set_record_padding_callback_arg(SSL_CTX *ctx, void *arg); void *SSL_CTX_get_record_padding_callback_arg(const SSL_CTX *ctx); int SSL_CTX_set_block_padding(SSL_CTX *ctx, size_t block_size); +int SSL_CTX_set_block_padding_ex(SSL_CTX *ctx, size_t app_block_size, + size_t hs_block_size); int SSL_set_record_padding_callback(SSL *ssl, size_t (*cb) (SSL *ssl, int type, @@ -2336,7 +2319,8 @@ int SSL_set_record_padding_callback(SSL *ssl, void SSL_set_record_padding_callback_arg(SSL *ssl, void *arg); void *SSL_get_record_padding_callback_arg(const SSL *ssl); int SSL_set_block_padding(SSL *ssl, size_t block_size); - +int SSL_set_block_padding_ex(SSL *ssl, size_t app_block_size, + size_t hs_block_size); int SSL_set_num_tickets(SSL *s, size_t num_tickets); size_t SSL_get_num_tickets(const SSL *s); int SSL_CTX_set_num_tickets(SSL_CTX *ctx, size_t num_tickets); diff --git a/include/openssl/ssl.h.in b/include/openssl/ssl.h.in index 442d5cbc3c..4bab2ac767 100644 --- a/include/openssl/ssl.h.in +++ b/include/openssl/ssl.h.in @@ -236,10 +236,8 @@ typedef struct ssl_cipher_st SSL_CIPHER; typedef struct ssl_session_st SSL_SESSION; typedef struct tls_sigalgs_st TLS_SIGALGS; typedef struct ssl_conf_ctx_st SSL_CONF_CTX; -typedef struct ssl_comp_st SSL_COMP; STACK_OF(SSL_CIPHER); -STACK_OF(SSL_COMP); /* SRTP protection profiles for use with the use_srtp extension (RFC 5764)*/ typedef struct srtp_protection_profile_st { @@ -975,8 +973,7 @@ extern "C" { * in VisualStudio 2015 */ {- - generate_const_stack_macros("SSL_CIPHER") - .generate_stack_macros("SSL_COMP"); + generate_const_stack_macros("SSL_CIPHER"); -} /* compatibility */ @@ -1572,7 +1569,11 @@ void SSL_CTX_set1_cert_store(SSL_CTX *, X509_STORE *); __owur int SSL_want(const SSL *s); __owur int SSL_clear(SSL *s); +#ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_CTX_flush_sessions_ex()") void SSL_CTX_flush_sessions(SSL_CTX *ctx, long tm); +#endif +void SSL_CTX_flush_sessions_ex(SSL_CTX *ctx, time_t tm); __owur const SSL_CIPHER *SSL_get_current_cipher(const SSL *s); __owur const SSL_CIPHER *SSL_get_pending_cipher(const SSL *s); @@ -1684,8 +1685,13 @@ __owur const char *SSL_state_string(const SSL *s); __owur const char *SSL_rstate_string(const SSL *s); __owur const char *SSL_state_string_long(const SSL *s); __owur const char *SSL_rstate_string_long(const SSL *s); + +#ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_SESSION_get_time_ex()") __owur long SSL_SESSION_get_time(const SSL_SESSION *s); +OSSL_DEPRECATEDIN_3_4_FOR("not Y2038-safe, replace with SSL_SESSION_set_time_ex()") __owur long SSL_SESSION_set_time(SSL_SESSION *s, long t); +#endif __owur long SSL_SESSION_get_timeout(const SSL_SESSION *s); __owur long SSL_SESSION_set_timeout(SSL_SESSION *s, long t); __owur int SSL_SESSION_get_protocol_version(const SSL_SESSION *s); @@ -2257,6 +2263,8 @@ void SSL_CTX_set_record_padding_callback(SSL_CTX *ctx, void SSL_CTX_set_record_padding_callback_arg(SSL_CTX *ctx, void *arg); void *SSL_CTX_get_record_padding_callback_arg(const SSL_CTX *ctx); int SSL_CTX_set_block_padding(SSL_CTX *ctx, size_t block_size); +int SSL_CTX_set_block_padding_ex(SSL_CTX *ctx, size_t app_block_size, + size_t hs_block_size); int SSL_set_record_padding_callback(SSL *ssl, size_t (*cb) (SSL *ssl, int type, @@ -2264,7 +2272,8 @@ int SSL_set_record_padding_callback(SSL *ssl, void SSL_set_record_padding_callback_arg(SSL *ssl, void *arg); void *SSL_get_record_padding_callback_arg(const SSL *ssl); int SSL_set_block_padding(SSL *ssl, size_t block_size); - +int SSL_set_block_padding_ex(SSL *ssl, size_t app_block_size, + size_t hs_block_size); int SSL_set_num_tickets(SSL *s, size_t num_tickets); size_t SSL_get_num_tickets(const SSL *s); int SSL_CTX_set_num_tickets(SSL_CTX *ctx, size_t num_tickets); diff --git a/include/openssl/sslerr.h b/include/openssl/sslerr.h index ec35df64e5..d6ae547876 100644 --- a/include/openssl/sslerr.h +++ b/include/openssl/sslerr.h @@ -117,6 +117,7 @@ # define SSL_R_EMPTY_SRTP_PROTECTION_PROFILE_LIST 354 # define SSL_R_ENCRYPTED_LENGTH_TOO_LONG 150 # define SSL_R_ERROR_IN_RECEIVED_CIPHER_LIST 151 +# define SSL_R_ERROR_IN_SYSTEM_DEFAULT_CONFIG 419 # define SSL_R_ERROR_SETTING_TLSA_BASE_DOMAIN 204 # define SSL_R_EXCEEDS_MAX_FRAGMENT_SIZE 194 # define SSL_R_EXCESSIVE_MESSAGE_SIZE 152 @@ -178,6 +179,7 @@ # define SSL_R_MISSING_SIGNING_CERT 221 # define SSL_R_MISSING_SRP_PARAM 358 # define SSL_R_MISSING_SUPPORTED_GROUPS_EXTENSION 209 +# define SSL_R_MISSING_SUPPORTED_VERSIONS_EXTENSION 420 # define SSL_R_MISSING_TMP_DH_KEY 171 # define SSL_R_MISSING_TMP_ECDH_KEY 311 # define SSL_R_MIXED_HANDSHAKE_AND_NON_HANDSHAKE_DATA 293 diff --git a/include/openssl/tls1.h b/include/openssl/tls1.h index 5329338efa..8e9b110bb3 100644 --- a/include/openssl/tls1.h +++ b/include/openssl/tls1.h @@ -282,6 +282,8 @@ int SSL_get_sigalgs(SSL *s, int idx, int *psign, int *phash, int *psignandhash, unsigned char *rsig, unsigned char *rhash); +char *SSL_get1_builtin_sigalgs(OSSL_LIB_CTX *libctx); + int SSL_get_shared_sigalgs(SSL *s, int idx, int *psign, int *phash, int *psignandhash, unsigned char *rsig, unsigned char *rhash); @@ -624,6 +626,10 @@ int SSL_CTX_set_tlsext_ticket_key_evp_cb # define TLS1_3_CK_AES_128_CCM_SHA256 0x03001304 # define TLS1_3_CK_AES_128_CCM_8_SHA256 0x03001305 +/* Integrity-only ciphersuites from RFC 9150 */ +# define TLS1_3_CK_SHA256_SHA256 0x0300C0B4 +# define TLS1_3_CK_SHA384_SHA384 0x0300C0B5 + /* Aria ciphersuites from RFC6209 */ # define TLS1_CK_RSA_WITH_ARIA_128_GCM_SHA256 0x0300C050 # define TLS1_CK_RSA_WITH_ARIA_256_GCM_SHA384 0x0300C051 @@ -701,6 +707,8 @@ int SSL_CTX_set_tlsext_ticket_key_evp_cb # define TLS1_3_RFC_AES_128_GCM_SHA256 "TLS_AES_128_GCM_SHA256" # define TLS1_3_RFC_AES_256_GCM_SHA384 "TLS_AES_256_GCM_SHA384" # define TLS1_3_RFC_CHACHA20_POLY1305_SHA256 "TLS_CHACHA20_POLY1305_SHA256" +# define TLS1_3_RFC_SHA256_SHA256 "TLS_SHA256_SHA256" +# define TLS1_3_RFC_SHA384_SHA384 "TLS_SHA384_SHA384" # define TLS1_3_RFC_AES_128_CCM_SHA256 "TLS_AES_128_CCM_SHA256" # define TLS1_3_RFC_AES_128_CCM_8_SHA256 "TLS_AES_128_CCM_8_SHA256" # define TLS1_RFC_ECDHE_ECDSA_WITH_NULL_SHA "TLS_ECDHE_ECDSA_WITH_NULL_SHA" diff --git a/include/openssl/ts.h b/include/openssl/ts.h index b09b646dff..31c78b55a4 100644 --- a/include/openssl/ts.h +++ b/include/openssl/ts.h @@ -1,5 +1,5 @@ /* - * Copyright 2006-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2006-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -418,14 +418,31 @@ void TS_VERIFY_CTX_free(TS_VERIFY_CTX *ctx); void TS_VERIFY_CTX_cleanup(TS_VERIFY_CTX *ctx); int TS_VERIFY_CTX_set_flags(TS_VERIFY_CTX *ctx, int f); int TS_VERIFY_CTX_add_flags(TS_VERIFY_CTX *ctx, int f); +# ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("Unclear semantics, replace with TS_VERIFY_CTX_set0_data().") BIO *TS_VERIFY_CTX_set_data(TS_VERIFY_CTX *ctx, BIO *b); +# endif +int TS_VERIFY_CTX_set0_data(TS_VERIFY_CTX *ctx, BIO *b); +# ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("Unclear semantics, replace with TS_VERIFY_CTX_set0_imprint().") unsigned char *TS_VERIFY_CTX_set_imprint(TS_VERIFY_CTX *ctx, unsigned char *hexstr, long len); +# endif +int TS_VERIFY_CTX_set0_imprint(TS_VERIFY_CTX *ctx, + unsigned char *hexstr, long len); +# ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("Unclear semantics, replace with TS_VERIFY_CTX_set0_store().") X509_STORE *TS_VERIFY_CTX_set_store(TS_VERIFY_CTX *ctx, X509_STORE *s); +# endif +int TS_VERIFY_CTX_set0_store(TS_VERIFY_CTX *ctx, X509_STORE *s); # ifndef OPENSSL_NO_DEPRECATED_3_0 # define TS_VERIFY_CTS_set_certs(ctx, cert) TS_VERIFY_CTX_set_certs(ctx,cert) # endif +# ifndef OPENSSL_NO_DEPRECATED_3_4 +OSSL_DEPRECATEDIN_3_4_FOR("Unclear semantics, replace with TS_VERIFY_CTX_set0_certs().") STACK_OF(X509) *TS_VERIFY_CTX_set_certs(TS_VERIFY_CTX *ctx, STACK_OF(X509) *certs); +# endif +int TS_VERIFY_CTX_set0_certs(TS_VERIFY_CTX *ctx, STACK_OF(X509) *certs); /*- * If ctx is NULL, it allocates and returns a new object, otherwise diff --git a/include/openssl/types.h b/include/openssl/types.h index c28028681f..e05a350f1d 100644 --- a/include/openssl/types.h +++ b/include/openssl/types.h @@ -1,5 +1,5 @@ /* - * Copyright 2001-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2001-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -33,6 +33,12 @@ extern "C" { # include # include +# if OPENSSL_VERSION_MAJOR >= 4 +# define OSSL_FUTURE_CONST const +# else +# define OSSL_FUTURE_CONST +# endif + typedef struct ossl_provider_st OSSL_PROVIDER; /* Provider Object */ # ifdef NO_ASN1_TYPEDEFS diff --git a/include/openssl/x509.h b/include/openssl/x509.h index ac1326330b..21eadba220 100644 --- a/include/openssl/x509.h +++ b/include/openssl/x509.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/x509.h.in * - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -165,16 +165,24 @@ SKM_DEFINE_STACK_OF_INTERNAL(X509_CRL, X509_CRL, X509_CRL) # define X509_FILETYPE_ASN1 2 # define X509_FILETYPE_DEFAULT 3 -# define X509v3_KU_DIGITAL_SIGNATURE 0x0080 -# define X509v3_KU_NON_REPUDIATION 0x0040 -# define X509v3_KU_KEY_ENCIPHERMENT 0x0020 -# define X509v3_KU_DATA_ENCIPHERMENT 0x0010 -# define X509v3_KU_KEY_AGREEMENT 0x0008 -# define X509v3_KU_KEY_CERT_SIGN 0x0004 -# define X509v3_KU_CRL_SIGN 0x0002 -# define X509v3_KU_ENCIPHER_ONLY 0x0001 -# define X509v3_KU_DECIPHER_ONLY 0x8000 -# define X509v3_KU_UNDEF 0xffff +/*- + * : + * The KeyUsage BITSTRING is treated as a little-endian integer, hence bit `0` + * is 0x80, while bit `7` is 0x01 (the LSB of the integer value), bit `8` is + * then the MSB of the second octet, or 0x8000. + */ +# define X509v3_KU_DIGITAL_SIGNATURE 0x0080 /* (0) */ +# define X509v3_KU_NON_REPUDIATION 0x0040 /* (1) */ +# define X509v3_KU_KEY_ENCIPHERMENT 0x0020 /* (2) */ +# define X509v3_KU_DATA_ENCIPHERMENT 0x0010 /* (3) */ +# define X509v3_KU_KEY_AGREEMENT 0x0008 /* (4) */ +# define X509v3_KU_KEY_CERT_SIGN 0x0004 /* (5) */ +# define X509v3_KU_CRL_SIGN 0x0002 /* (6) */ +# define X509v3_KU_ENCIPHER_ONLY 0x0001 /* (7) */ +# define X509v3_KU_DECIPHER_ONLY 0x8000 /* (8) */ +# ifndef OPENSSL_NO_DEPRECATED_3_4 +# define X509v3_KU_UNDEF 0xffff /* vestigial, not used */ +# endif struct X509_algor_st { ASN1_OBJECT *algorithm; @@ -465,7 +473,12 @@ typedef struct PBKDF2PARAM_st { X509_ALGOR *prf; } PBKDF2PARAM; -#ifndef OPENSSL_NO_SCRYPT +typedef struct { + X509_ALGOR *keyDerivationFunc; + X509_ALGOR *messageAuthScheme; +} PBMAC1PARAM; + +# ifndef OPENSSL_NO_SCRYPT typedef struct SCRYPT_PARAMS_st { ASN1_OCTET_STRING *salt; ASN1_INTEGER *costParameter; @@ -473,7 +486,7 @@ typedef struct SCRYPT_PARAMS_st { ASN1_INTEGER *parallelizationParameter; ASN1_INTEGER *keyLength; } SCRYPT_PARAMS; -#endif +# endif #ifdef __cplusplus } @@ -896,7 +909,7 @@ X509_PUBKEY *X509_REQ_get_X509_PUBKEY(X509_REQ *req); int X509_REQ_extension_nid(int nid); int *X509_REQ_get_extension_nids(void); void X509_REQ_set_extension_nids(int *nids); -STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req); +STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(OSSL_FUTURE_CONST X509_REQ *req); int X509_REQ_add_extensions_nid(X509_REQ *req, const STACK_OF(X509_EXTENSION) *exts, int nid); int X509_REQ_add_extensions(X509_REQ *req, const STACK_OF(X509_EXTENSION) *ext); @@ -1085,6 +1098,9 @@ X509_EXTENSION *X509v3_get_ext(const STACK_OF(X509_EXTENSION) *x, int loc); X509_EXTENSION *X509v3_delete_ext(STACK_OF(X509_EXTENSION) *x, int loc); STACK_OF(X509_EXTENSION) *X509v3_add_ext(STACK_OF(X509_EXTENSION) **x, X509_EXTENSION *ex, int loc); +STACK_OF(X509_EXTENSION) + *X509v3_add_extensions(STACK_OF(X509_EXTENSION) **target, + const STACK_OF(X509_EXTENSION) *exts); int X509_get_ext_count(const X509 *x); int X509_get_ext_by_NID(const X509 *x, int nid, int lastpos); @@ -1206,9 +1222,10 @@ X509 *X509_find_by_subject(STACK_OF(X509) *sk, const X509_NAME *name); DECLARE_ASN1_FUNCTIONS(PBEPARAM) DECLARE_ASN1_FUNCTIONS(PBE2PARAM) DECLARE_ASN1_FUNCTIONS(PBKDF2PARAM) -#ifndef OPENSSL_NO_SCRYPT +DECLARE_ASN1_FUNCTIONS(PBMAC1PARAM) +# ifndef OPENSSL_NO_SCRYPT DECLARE_ASN1_FUNCTIONS(SCRYPT_PARAMS) -#endif +# endif int PKCS5_pbe_set0_algor(X509_ALGOR *algor, int alg, int iter, const unsigned char *salt, int saltlen); @@ -1245,6 +1262,7 @@ X509_ALGOR *PKCS5_pbkdf2_set_ex(int iter, unsigned char *salt, int saltlen, int prf_nid, int keylen, OSSL_LIB_CTX *libctx); +PBKDF2PARAM *PBMAC1_get1_pbkdf2_param(const X509_ALGOR *macalg); /* PKCS#8 utilities */ DECLARE_ASN1_FUNCTIONS(PKCS8_PRIV_KEY_INFO) diff --git a/include/openssl/x509.h.in b/include/openssl/x509.h.in index 7210391305..2100790a2f 100644 --- a/include/openssl/x509.h.in +++ b/include/openssl/x509.h.in @@ -1,7 +1,7 @@ /* * {- join("\n * ", @autowarntext) -} * - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -67,16 +67,24 @@ extern "C" { # define X509_FILETYPE_ASN1 2 # define X509_FILETYPE_DEFAULT 3 -# define X509v3_KU_DIGITAL_SIGNATURE 0x0080 -# define X509v3_KU_NON_REPUDIATION 0x0040 -# define X509v3_KU_KEY_ENCIPHERMENT 0x0020 -# define X509v3_KU_DATA_ENCIPHERMENT 0x0010 -# define X509v3_KU_KEY_AGREEMENT 0x0008 -# define X509v3_KU_KEY_CERT_SIGN 0x0004 -# define X509v3_KU_CRL_SIGN 0x0002 -# define X509v3_KU_ENCIPHER_ONLY 0x0001 -# define X509v3_KU_DECIPHER_ONLY 0x8000 -# define X509v3_KU_UNDEF 0xffff +/*- + * : + * The KeyUsage BITSTRING is treated as a little-endian integer, hence bit `0` + * is 0x80, while bit `7` is 0x01 (the LSB of the integer value), bit `8` is + * then the MSB of the second octet, or 0x8000. + */ +# define X509v3_KU_DIGITAL_SIGNATURE 0x0080 /* (0) */ +# define X509v3_KU_NON_REPUDIATION 0x0040 /* (1) */ +# define X509v3_KU_KEY_ENCIPHERMENT 0x0020 /* (2) */ +# define X509v3_KU_DATA_ENCIPHERMENT 0x0010 /* (3) */ +# define X509v3_KU_KEY_AGREEMENT 0x0008 /* (4) */ +# define X509v3_KU_KEY_CERT_SIGN 0x0004 /* (5) */ +# define X509v3_KU_CRL_SIGN 0x0002 /* (6) */ +# define X509v3_KU_ENCIPHER_ONLY 0x0001 /* (7) */ +# define X509v3_KU_DECIPHER_ONLY 0x8000 /* (8) */ +# ifndef OPENSSL_NO_DEPRECATED_3_4 +# define X509v3_KU_UNDEF 0xffff /* vestigial, not used */ +# endif struct X509_algor_st { ASN1_OBJECT *algorithm; @@ -271,7 +279,12 @@ typedef struct PBKDF2PARAM_st { X509_ALGOR *prf; } PBKDF2PARAM; -#ifndef OPENSSL_NO_SCRYPT +typedef struct { + X509_ALGOR *keyDerivationFunc; + X509_ALGOR *messageAuthScheme; +} PBMAC1PARAM; + +# ifndef OPENSSL_NO_SCRYPT typedef struct SCRYPT_PARAMS_st { ASN1_OCTET_STRING *salt; ASN1_INTEGER *costParameter; @@ -279,7 +292,7 @@ typedef struct SCRYPT_PARAMS_st { ASN1_INTEGER *parallelizationParameter; ASN1_INTEGER *keyLength; } SCRYPT_PARAMS; -#endif +# endif #ifdef __cplusplus } @@ -702,7 +715,7 @@ X509_PUBKEY *X509_REQ_get_X509_PUBKEY(X509_REQ *req); int X509_REQ_extension_nid(int nid); int *X509_REQ_get_extension_nids(void); void X509_REQ_set_extension_nids(int *nids); -STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(X509_REQ *req); +STACK_OF(X509_EXTENSION) *X509_REQ_get_extensions(OSSL_FUTURE_CONST X509_REQ *req); int X509_REQ_add_extensions_nid(X509_REQ *req, const STACK_OF(X509_EXTENSION) *exts, int nid); int X509_REQ_add_extensions(X509_REQ *req, const STACK_OF(X509_EXTENSION) *ext); @@ -891,6 +904,9 @@ X509_EXTENSION *X509v3_get_ext(const STACK_OF(X509_EXTENSION) *x, int loc); X509_EXTENSION *X509v3_delete_ext(STACK_OF(X509_EXTENSION) *x, int loc); STACK_OF(X509_EXTENSION) *X509v3_add_ext(STACK_OF(X509_EXTENSION) **x, X509_EXTENSION *ex, int loc); +STACK_OF(X509_EXTENSION) + *X509v3_add_extensions(STACK_OF(X509_EXTENSION) **target, + const STACK_OF(X509_EXTENSION) *exts); int X509_get_ext_count(const X509 *x); int X509_get_ext_by_NID(const X509 *x, int nid, int lastpos); @@ -1012,9 +1028,10 @@ X509 *X509_find_by_subject(STACK_OF(X509) *sk, const X509_NAME *name); DECLARE_ASN1_FUNCTIONS(PBEPARAM) DECLARE_ASN1_FUNCTIONS(PBE2PARAM) DECLARE_ASN1_FUNCTIONS(PBKDF2PARAM) -#ifndef OPENSSL_NO_SCRYPT +DECLARE_ASN1_FUNCTIONS(PBMAC1PARAM) +# ifndef OPENSSL_NO_SCRYPT DECLARE_ASN1_FUNCTIONS(SCRYPT_PARAMS) -#endif +# endif int PKCS5_pbe_set0_algor(X509_ALGOR *algor, int alg, int iter, const unsigned char *salt, int saltlen); @@ -1051,6 +1068,7 @@ X509_ALGOR *PKCS5_pbkdf2_set_ex(int iter, unsigned char *salt, int saltlen, int prf_nid, int keylen, OSSL_LIB_CTX *libctx); +PBKDF2PARAM *PBMAC1_get1_pbkdf2_param(const X509_ALGOR *macalg); /* PKCS#8 utilities */ DECLARE_ASN1_FUNCTIONS(PKCS8_PRIV_KEY_INFO) diff --git a/include/openssl/x509_acert.h b/include/openssl/x509_acert.h new file mode 100644 index 0000000000..d7c3dc70d8 --- /dev/null +++ b/include/openssl/x509_acert.h @@ -0,0 +1,263 @@ +/* + * WARNING: do not edit! + * Generated by Makefile from include/openssl/x509_acert.h.in + * + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + + + +#ifndef OPENSSL_X509_ACERT_H +# define OPENSSL_X509_ACERT_H +# pragma once + +# include +# include +# include + +typedef struct X509_acert_st X509_ACERT; +typedef struct X509_acert_info_st X509_ACERT_INFO; +typedef struct ossl_object_digest_info_st OSSL_OBJECT_DIGEST_INFO; +typedef struct ossl_issuer_serial_st OSSL_ISSUER_SERIAL; +typedef struct X509_acert_issuer_v2form_st X509_ACERT_ISSUER_V2FORM; + +DECLARE_ASN1_FUNCTIONS(X509_ACERT) +DECLARE_ASN1_DUP_FUNCTION(X509_ACERT) +DECLARE_ASN1_ITEM(X509_ACERT_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(X509_ACERT_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_OBJECT_DIGEST_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_ISSUER_SERIAL) +DECLARE_ASN1_ALLOC_FUNCTIONS(X509_ACERT_ISSUER_V2FORM) + +# ifndef OPENSSL_NO_STDIO +X509_ACERT *d2i_X509_ACERT_fp(FILE *fp, X509_ACERT **acert); +int i2d_X509_ACERT_fp(FILE *fp, const X509_ACERT *acert); +# endif + +DECLARE_PEM_rw(X509_ACERT, X509_ACERT) + +X509_ACERT *d2i_X509_ACERT_bio(BIO *bp, X509_ACERT **acert); +int i2d_X509_ACERT_bio(BIO *bp, const X509_ACERT *acert); + +int X509_ACERT_sign(X509_ACERT *x, EVP_PKEY *pkey, const EVP_MD *md); +int X509_ACERT_sign_ctx(X509_ACERT *x, EVP_MD_CTX *ctx); +int X509_ACERT_verify(X509_ACERT *a, EVP_PKEY *r); + +# define X509_ACERT_VERSION_2 1 + +const GENERAL_NAMES *X509_ACERT_get0_holder_entityName(const X509_ACERT *x); +const OSSL_ISSUER_SERIAL *X509_ACERT_get0_holder_baseCertId(const X509_ACERT *x); +const OSSL_OBJECT_DIGEST_INFO * X509_ACERT_get0_holder_digest(const X509_ACERT *x); +const X509_NAME *X509_ACERT_get0_issuerName(const X509_ACERT *x); +long X509_ACERT_get_version(const X509_ACERT *x); +void X509_ACERT_get0_signature(const X509_ACERT *x, + const ASN1_BIT_STRING **psig, + const X509_ALGOR **palg); +int X509_ACERT_get_signature_nid(const X509_ACERT *x); +const X509_ALGOR *X509_ACERT_get0_info_sigalg(const X509_ACERT *x); +const ASN1_INTEGER *X509_ACERT_get0_serialNumber(const X509_ACERT *x); +const ASN1_TIME *X509_ACERT_get0_notBefore(const X509_ACERT *x); +const ASN1_TIME *X509_ACERT_get0_notAfter(const X509_ACERT *x); +const ASN1_BIT_STRING *X509_ACERT_get0_issuerUID(const X509_ACERT *x); + +int X509_ACERT_print(BIO *bp, X509_ACERT *x); +int X509_ACERT_print_ex(BIO *bp, X509_ACERT *x, unsigned long nmflags, + unsigned long cflag); + +int X509_ACERT_get_attr_count(const X509_ACERT *x); +int X509_ACERT_get_attr_by_NID(const X509_ACERT *x, int nid, int lastpos); +int X509_ACERT_get_attr_by_OBJ(const X509_ACERT *x, const ASN1_OBJECT *obj, + int lastpos); +X509_ATTRIBUTE *X509_ACERT_get_attr(const X509_ACERT *x, int loc); +X509_ATTRIBUTE *X509_ACERT_delete_attr(X509_ACERT *x, int loc); + +void *X509_ACERT_get_ext_d2i(const X509_ACERT *x, int nid, int *crit, int *idx); +int X509_ACERT_add1_ext_i2d(X509_ACERT *x, int nid, void *value, int crit, + unsigned long flags); +const STACK_OF(X509_EXTENSION) *X509_ACERT_get0_extensions(const X509_ACERT *x); + +# define OSSL_OBJECT_DIGEST_INFO_PUBLIC_KEY 0 +# define OSSL_OBJECT_DIGEST_INFO_PUBLIC_KEY_CERT 1 +# define OSSL_OBJECT_DIGEST_INFO_OTHER 2 /* must not be used in RFC 5755 profile */ +int X509_ACERT_set_version(X509_ACERT *x, long version); +void X509_ACERT_set0_holder_entityName(X509_ACERT *x, GENERAL_NAMES *name); +void X509_ACERT_set0_holder_baseCertId(X509_ACERT *x, OSSL_ISSUER_SERIAL *isss); +void X509_ACERT_set0_holder_digest(X509_ACERT *x, + OSSL_OBJECT_DIGEST_INFO *dinfo); + +int X509_ACERT_add1_attr(X509_ACERT *x, X509_ATTRIBUTE *attr); +int X509_ACERT_add1_attr_by_OBJ(X509_ACERT *x, const ASN1_OBJECT *obj, + int type, const void *bytes, int len); +int X509_ACERT_add1_attr_by_NID(X509_ACERT *x, int nid, int type, + const void *bytes, int len); +int X509_ACERT_add1_attr_by_txt(X509_ACERT *x, const char *attrname, int type, + const unsigned char *bytes, int len); +int X509_ACERT_add_attr_nconf(CONF *conf, const char *section, + X509_ACERT *acert); + +int X509_ACERT_set1_issuerName(X509_ACERT *x, const X509_NAME *name); +int X509_ACERT_set1_serialNumber(X509_ACERT *x, const ASN1_INTEGER *serial); +int X509_ACERT_set1_notBefore(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time); +int X509_ACERT_set1_notAfter(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time); + +void OSSL_OBJECT_DIGEST_INFO_get0_digest(const OSSL_OBJECT_DIGEST_INFO *o, + int *digestedObjectType, + const X509_ALGOR **digestAlgorithm, + const ASN1_BIT_STRING **digest); + +int OSSL_OBJECT_DIGEST_INFO_set1_digest(OSSL_OBJECT_DIGEST_INFO *o, + int digestedObjectType, + X509_ALGOR *digestAlgorithm, + ASN1_BIT_STRING *digest); + +const X509_NAME *OSSL_ISSUER_SERIAL_get0_issuer(const OSSL_ISSUER_SERIAL *isss); +const ASN1_INTEGER *OSSL_ISSUER_SERIAL_get0_serial(const OSSL_ISSUER_SERIAL *isss); +const ASN1_BIT_STRING *OSSL_ISSUER_SERIAL_get0_issuerUID(const OSSL_ISSUER_SERIAL *isss); + +int OSSL_ISSUER_SERIAL_set1_issuer(OSSL_ISSUER_SERIAL *isss, + const X509_NAME *issuer); +int OSSL_ISSUER_SERIAL_set1_serial(OSSL_ISSUER_SERIAL *isss, + const ASN1_INTEGER *serial); +int OSSL_ISSUER_SERIAL_set1_issuerUID(OSSL_ISSUER_SERIAL *isss, + const ASN1_BIT_STRING *uid); + +# define OSSL_IETFAS_OCTETS 0 +# define OSSL_IETFAS_OID 1 +# define OSSL_IETFAS_STRING 2 + +typedef struct OSSL_IETF_ATTR_SYNTAX_VALUE_st OSSL_IETF_ATTR_SYNTAX_VALUE; +typedef struct OSSL_IETF_ATTR_SYNTAX_st OSSL_IETF_ATTR_SYNTAX; +SKM_DEFINE_STACK_OF_INTERNAL(OSSL_IETF_ATTR_SYNTAX_VALUE, OSSL_IETF_ATTR_SYNTAX_VALUE, OSSL_IETF_ATTR_SYNTAX_VALUE) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_num(sk) OPENSSL_sk_num(ossl_check_const_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_value(sk, idx) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_value(ossl_check_const_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), (idx))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_new(cmp) ((STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *)OPENSSL_sk_new(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_compfunc_type(cmp))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_new_null() ((STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *)OPENSSL_sk_new_null()) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_new_reserve(cmp, n) ((STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *)OPENSSL_sk_new_reserve(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_compfunc_type(cmp), (n))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), (n)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_free(sk) OPENSSL_sk_free(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_zero(sk) OPENSSL_sk_zero(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_delete(sk, i) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_delete(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), (i))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_delete_ptr(sk, ptr) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_delete_ptr(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_push(sk, ptr) OPENSSL_sk_push(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_pop(sk) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_pop(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_shift(sk) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_shift(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk),ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_freefunc_type(freefunc)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr), (idx)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_set(sk, idx, ptr) ((OSSL_IETF_ATTR_SYNTAX_VALUE *)OPENSSL_sk_set(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), (idx), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_find(sk, ptr) OPENSSL_sk_find(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_type(ptr), pnum) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_sort(sk) OPENSSL_sk_sort(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk)) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_dup(sk) ((STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *)OPENSSL_sk_dup(ossl_check_const_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_IETF_ATTR_SYNTAX_VALUE) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_copyfunc_type(copyfunc), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_freefunc_type(freefunc))) +#define sk_OSSL_IETF_ATTR_SYNTAX_VALUE_set_cmp_func(sk, cmp) ((sk_OSSL_IETF_ATTR_SYNTAX_VALUE_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_sk_type(sk), ossl_check_OSSL_IETF_ATTR_SYNTAX_VALUE_compfunc_type(cmp))) + + +DECLARE_ASN1_ITEM(OSSL_IETF_ATTR_SYNTAX_VALUE) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX_VALUE) +DECLARE_ASN1_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX) + +const GENERAL_NAMES * +OSSL_IETF_ATTR_SYNTAX_get0_policyAuthority(const OSSL_IETF_ATTR_SYNTAX *a); +void OSSL_IETF_ATTR_SYNTAX_set0_policyAuthority(OSSL_IETF_ATTR_SYNTAX *a, + GENERAL_NAMES *names); + +int OSSL_IETF_ATTR_SYNTAX_get_value_num(const OSSL_IETF_ATTR_SYNTAX *a); +void *OSSL_IETF_ATTR_SYNTAX_get0_value(const OSSL_IETF_ATTR_SYNTAX *a, + int ind, int *type); +int OSSL_IETF_ATTR_SYNTAX_add1_value(OSSL_IETF_ATTR_SYNTAX *a, int type, + void *data); +int OSSL_IETF_ATTR_SYNTAX_print(BIO *bp, OSSL_IETF_ATTR_SYNTAX *a, int indent); + +struct TARGET_CERT_st { + OSSL_ISSUER_SERIAL *targetCertificate; + GENERAL_NAME *targetName; + OSSL_OBJECT_DIGEST_INFO *certDigestInfo; +}; + +typedef struct TARGET_CERT_st OSSL_TARGET_CERT; + +# define OSSL_TGT_TARGET_NAME 0 +# define OSSL_TGT_TARGET_GROUP 1 +# define OSSL_TGT_TARGET_CERT 2 + +typedef struct TARGET_st { + int type; + union { + GENERAL_NAME *targetName; + GENERAL_NAME *targetGroup; + OSSL_TARGET_CERT *targetCert; + } choice; +} OSSL_TARGET; + +typedef STACK_OF(OSSL_TARGET) OSSL_TARGETS; +typedef STACK_OF(OSSL_TARGETS) OSSL_TARGETING_INFORMATION; + +SKM_DEFINE_STACK_OF_INTERNAL(OSSL_TARGET, OSSL_TARGET, OSSL_TARGET) +#define sk_OSSL_TARGET_num(sk) OPENSSL_sk_num(ossl_check_const_OSSL_TARGET_sk_type(sk)) +#define sk_OSSL_TARGET_value(sk, idx) ((OSSL_TARGET *)OPENSSL_sk_value(ossl_check_const_OSSL_TARGET_sk_type(sk), (idx))) +#define sk_OSSL_TARGET_new(cmp) ((STACK_OF(OSSL_TARGET) *)OPENSSL_sk_new(ossl_check_OSSL_TARGET_compfunc_type(cmp))) +#define sk_OSSL_TARGET_new_null() ((STACK_OF(OSSL_TARGET) *)OPENSSL_sk_new_null()) +#define sk_OSSL_TARGET_new_reserve(cmp, n) ((STACK_OF(OSSL_TARGET) *)OPENSSL_sk_new_reserve(ossl_check_OSSL_TARGET_compfunc_type(cmp), (n))) +#define sk_OSSL_TARGET_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_OSSL_TARGET_sk_type(sk), (n)) +#define sk_OSSL_TARGET_free(sk) OPENSSL_sk_free(ossl_check_OSSL_TARGET_sk_type(sk)) +#define sk_OSSL_TARGET_zero(sk) OPENSSL_sk_zero(ossl_check_OSSL_TARGET_sk_type(sk)) +#define sk_OSSL_TARGET_delete(sk, i) ((OSSL_TARGET *)OPENSSL_sk_delete(ossl_check_OSSL_TARGET_sk_type(sk), (i))) +#define sk_OSSL_TARGET_delete_ptr(sk, ptr) ((OSSL_TARGET *)OPENSSL_sk_delete_ptr(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr))) +#define sk_OSSL_TARGET_push(sk, ptr) OPENSSL_sk_push(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr)) +#define sk_OSSL_TARGET_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr)) +#define sk_OSSL_TARGET_pop(sk) ((OSSL_TARGET *)OPENSSL_sk_pop(ossl_check_OSSL_TARGET_sk_type(sk))) +#define sk_OSSL_TARGET_shift(sk) ((OSSL_TARGET *)OPENSSL_sk_shift(ossl_check_OSSL_TARGET_sk_type(sk))) +#define sk_OSSL_TARGET_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_OSSL_TARGET_sk_type(sk),ossl_check_OSSL_TARGET_freefunc_type(freefunc)) +#define sk_OSSL_TARGET_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr), (idx)) +#define sk_OSSL_TARGET_set(sk, idx, ptr) ((OSSL_TARGET *)OPENSSL_sk_set(ossl_check_OSSL_TARGET_sk_type(sk), (idx), ossl_check_OSSL_TARGET_type(ptr))) +#define sk_OSSL_TARGET_find(sk, ptr) OPENSSL_sk_find(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr)) +#define sk_OSSL_TARGET_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr)) +#define sk_OSSL_TARGET_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_type(ptr), pnum) +#define sk_OSSL_TARGET_sort(sk) OPENSSL_sk_sort(ossl_check_OSSL_TARGET_sk_type(sk)) +#define sk_OSSL_TARGET_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_OSSL_TARGET_sk_type(sk)) +#define sk_OSSL_TARGET_dup(sk) ((STACK_OF(OSSL_TARGET) *)OPENSSL_sk_dup(ossl_check_const_OSSL_TARGET_sk_type(sk))) +#define sk_OSSL_TARGET_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_TARGET) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_copyfunc_type(copyfunc), ossl_check_OSSL_TARGET_freefunc_type(freefunc))) +#define sk_OSSL_TARGET_set_cmp_func(sk, cmp) ((sk_OSSL_TARGET_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_TARGET_sk_type(sk), ossl_check_OSSL_TARGET_compfunc_type(cmp))) + + +SKM_DEFINE_STACK_OF_INTERNAL(OSSL_TARGETS, OSSL_TARGETS, OSSL_TARGETS) +#define sk_OSSL_TARGETS_num(sk) OPENSSL_sk_num(ossl_check_const_OSSL_TARGETS_sk_type(sk)) +#define sk_OSSL_TARGETS_value(sk, idx) ((OSSL_TARGETS *)OPENSSL_sk_value(ossl_check_const_OSSL_TARGETS_sk_type(sk), (idx))) +#define sk_OSSL_TARGETS_new(cmp) ((STACK_OF(OSSL_TARGETS) *)OPENSSL_sk_new(ossl_check_OSSL_TARGETS_compfunc_type(cmp))) +#define sk_OSSL_TARGETS_new_null() ((STACK_OF(OSSL_TARGETS) *)OPENSSL_sk_new_null()) +#define sk_OSSL_TARGETS_new_reserve(cmp, n) ((STACK_OF(OSSL_TARGETS) *)OPENSSL_sk_new_reserve(ossl_check_OSSL_TARGETS_compfunc_type(cmp), (n))) +#define sk_OSSL_TARGETS_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_OSSL_TARGETS_sk_type(sk), (n)) +#define sk_OSSL_TARGETS_free(sk) OPENSSL_sk_free(ossl_check_OSSL_TARGETS_sk_type(sk)) +#define sk_OSSL_TARGETS_zero(sk) OPENSSL_sk_zero(ossl_check_OSSL_TARGETS_sk_type(sk)) +#define sk_OSSL_TARGETS_delete(sk, i) ((OSSL_TARGETS *)OPENSSL_sk_delete(ossl_check_OSSL_TARGETS_sk_type(sk), (i))) +#define sk_OSSL_TARGETS_delete_ptr(sk, ptr) ((OSSL_TARGETS *)OPENSSL_sk_delete_ptr(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr))) +#define sk_OSSL_TARGETS_push(sk, ptr) OPENSSL_sk_push(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr)) +#define sk_OSSL_TARGETS_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr)) +#define sk_OSSL_TARGETS_pop(sk) ((OSSL_TARGETS *)OPENSSL_sk_pop(ossl_check_OSSL_TARGETS_sk_type(sk))) +#define sk_OSSL_TARGETS_shift(sk) ((OSSL_TARGETS *)OPENSSL_sk_shift(ossl_check_OSSL_TARGETS_sk_type(sk))) +#define sk_OSSL_TARGETS_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_OSSL_TARGETS_sk_type(sk),ossl_check_OSSL_TARGETS_freefunc_type(freefunc)) +#define sk_OSSL_TARGETS_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr), (idx)) +#define sk_OSSL_TARGETS_set(sk, idx, ptr) ((OSSL_TARGETS *)OPENSSL_sk_set(ossl_check_OSSL_TARGETS_sk_type(sk), (idx), ossl_check_OSSL_TARGETS_type(ptr))) +#define sk_OSSL_TARGETS_find(sk, ptr) OPENSSL_sk_find(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr)) +#define sk_OSSL_TARGETS_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr)) +#define sk_OSSL_TARGETS_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_type(ptr), pnum) +#define sk_OSSL_TARGETS_sort(sk) OPENSSL_sk_sort(ossl_check_OSSL_TARGETS_sk_type(sk)) +#define sk_OSSL_TARGETS_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_OSSL_TARGETS_sk_type(sk)) +#define sk_OSSL_TARGETS_dup(sk) ((STACK_OF(OSSL_TARGETS) *)OPENSSL_sk_dup(ossl_check_const_OSSL_TARGETS_sk_type(sk))) +#define sk_OSSL_TARGETS_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(OSSL_TARGETS) *)OPENSSL_sk_deep_copy(ossl_check_const_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_copyfunc_type(copyfunc), ossl_check_OSSL_TARGETS_freefunc_type(freefunc))) +#define sk_OSSL_TARGETS_set_cmp_func(sk, cmp) ((sk_OSSL_TARGETS_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_OSSL_TARGETS_sk_type(sk), ossl_check_OSSL_TARGETS_compfunc_type(cmp))) + + +DECLARE_ASN1_FUNCTIONS(OSSL_TARGET) +DECLARE_ASN1_FUNCTIONS(OSSL_TARGETS) +DECLARE_ASN1_FUNCTIONS(OSSL_TARGETING_INFORMATION) + +#endif diff --git a/include/openssl/x509_acert.h.in b/include/openssl/x509_acert.h.in new file mode 100644 index 0000000000..76570d4954 --- /dev/null +++ b/include/openssl/x509_acert.h.in @@ -0,0 +1,192 @@ +/* + * {- join("\n * ", @autowarntext) -} + * + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +{- +use OpenSSL::stackhash qw(generate_stack_macros); +-} + +#ifndef OPENSSL_X509_ACERT_H +# define OPENSSL_X509_ACERT_H +# pragma once + +# include +# include +# include + +typedef struct X509_acert_st X509_ACERT; +typedef struct X509_acert_info_st X509_ACERT_INFO; +typedef struct ossl_object_digest_info_st OSSL_OBJECT_DIGEST_INFO; +typedef struct ossl_issuer_serial_st OSSL_ISSUER_SERIAL; +typedef struct X509_acert_issuer_v2form_st X509_ACERT_ISSUER_V2FORM; + +DECLARE_ASN1_FUNCTIONS(X509_ACERT) +DECLARE_ASN1_DUP_FUNCTION(X509_ACERT) +DECLARE_ASN1_ITEM(X509_ACERT_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(X509_ACERT_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_OBJECT_DIGEST_INFO) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_ISSUER_SERIAL) +DECLARE_ASN1_ALLOC_FUNCTIONS(X509_ACERT_ISSUER_V2FORM) + +# ifndef OPENSSL_NO_STDIO +X509_ACERT *d2i_X509_ACERT_fp(FILE *fp, X509_ACERT **acert); +int i2d_X509_ACERT_fp(FILE *fp, const X509_ACERT *acert); +# endif + +DECLARE_PEM_rw(X509_ACERT, X509_ACERT) + +X509_ACERT *d2i_X509_ACERT_bio(BIO *bp, X509_ACERT **acert); +int i2d_X509_ACERT_bio(BIO *bp, const X509_ACERT *acert); + +int X509_ACERT_sign(X509_ACERT *x, EVP_PKEY *pkey, const EVP_MD *md); +int X509_ACERT_sign_ctx(X509_ACERT *x, EVP_MD_CTX *ctx); +int X509_ACERT_verify(X509_ACERT *a, EVP_PKEY *r); + +# define X509_ACERT_VERSION_2 1 + +const GENERAL_NAMES *X509_ACERT_get0_holder_entityName(const X509_ACERT *x); +const OSSL_ISSUER_SERIAL *X509_ACERT_get0_holder_baseCertId(const X509_ACERT *x); +const OSSL_OBJECT_DIGEST_INFO * X509_ACERT_get0_holder_digest(const X509_ACERT *x); +const X509_NAME *X509_ACERT_get0_issuerName(const X509_ACERT *x); +long X509_ACERT_get_version(const X509_ACERT *x); +void X509_ACERT_get0_signature(const X509_ACERT *x, + const ASN1_BIT_STRING **psig, + const X509_ALGOR **palg); +int X509_ACERT_get_signature_nid(const X509_ACERT *x); +const X509_ALGOR *X509_ACERT_get0_info_sigalg(const X509_ACERT *x); +const ASN1_INTEGER *X509_ACERT_get0_serialNumber(const X509_ACERT *x); +const ASN1_TIME *X509_ACERT_get0_notBefore(const X509_ACERT *x); +const ASN1_TIME *X509_ACERT_get0_notAfter(const X509_ACERT *x); +const ASN1_BIT_STRING *X509_ACERT_get0_issuerUID(const X509_ACERT *x); + +int X509_ACERT_print(BIO *bp, X509_ACERT *x); +int X509_ACERT_print_ex(BIO *bp, X509_ACERT *x, unsigned long nmflags, + unsigned long cflag); + +int X509_ACERT_get_attr_count(const X509_ACERT *x); +int X509_ACERT_get_attr_by_NID(const X509_ACERT *x, int nid, int lastpos); +int X509_ACERT_get_attr_by_OBJ(const X509_ACERT *x, const ASN1_OBJECT *obj, + int lastpos); +X509_ATTRIBUTE *X509_ACERT_get_attr(const X509_ACERT *x, int loc); +X509_ATTRIBUTE *X509_ACERT_delete_attr(X509_ACERT *x, int loc); + +void *X509_ACERT_get_ext_d2i(const X509_ACERT *x, int nid, int *crit, int *idx); +int X509_ACERT_add1_ext_i2d(X509_ACERT *x, int nid, void *value, int crit, + unsigned long flags); +const STACK_OF(X509_EXTENSION) *X509_ACERT_get0_extensions(const X509_ACERT *x); + +# define OSSL_OBJECT_DIGEST_INFO_PUBLIC_KEY 0 +# define OSSL_OBJECT_DIGEST_INFO_PUBLIC_KEY_CERT 1 +# define OSSL_OBJECT_DIGEST_INFO_OTHER 2 /* must not be used in RFC 5755 profile */ +int X509_ACERT_set_version(X509_ACERT *x, long version); +void X509_ACERT_set0_holder_entityName(X509_ACERT *x, GENERAL_NAMES *name); +void X509_ACERT_set0_holder_baseCertId(X509_ACERT *x, OSSL_ISSUER_SERIAL *isss); +void X509_ACERT_set0_holder_digest(X509_ACERT *x, + OSSL_OBJECT_DIGEST_INFO *dinfo); + +int X509_ACERT_add1_attr(X509_ACERT *x, X509_ATTRIBUTE *attr); +int X509_ACERT_add1_attr_by_OBJ(X509_ACERT *x, const ASN1_OBJECT *obj, + int type, const void *bytes, int len); +int X509_ACERT_add1_attr_by_NID(X509_ACERT *x, int nid, int type, + const void *bytes, int len); +int X509_ACERT_add1_attr_by_txt(X509_ACERT *x, const char *attrname, int type, + const unsigned char *bytes, int len); +int X509_ACERT_add_attr_nconf(CONF *conf, const char *section, + X509_ACERT *acert); + +int X509_ACERT_set1_issuerName(X509_ACERT *x, const X509_NAME *name); +int X509_ACERT_set1_serialNumber(X509_ACERT *x, const ASN1_INTEGER *serial); +int X509_ACERT_set1_notBefore(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time); +int X509_ACERT_set1_notAfter(X509_ACERT *x, const ASN1_GENERALIZEDTIME *time); + +void OSSL_OBJECT_DIGEST_INFO_get0_digest(const OSSL_OBJECT_DIGEST_INFO *o, + int *digestedObjectType, + const X509_ALGOR **digestAlgorithm, + const ASN1_BIT_STRING **digest); + +int OSSL_OBJECT_DIGEST_INFO_set1_digest(OSSL_OBJECT_DIGEST_INFO *o, + int digestedObjectType, + X509_ALGOR *digestAlgorithm, + ASN1_BIT_STRING *digest); + +const X509_NAME *OSSL_ISSUER_SERIAL_get0_issuer(const OSSL_ISSUER_SERIAL *isss); +const ASN1_INTEGER *OSSL_ISSUER_SERIAL_get0_serial(const OSSL_ISSUER_SERIAL *isss); +const ASN1_BIT_STRING *OSSL_ISSUER_SERIAL_get0_issuerUID(const OSSL_ISSUER_SERIAL *isss); + +int OSSL_ISSUER_SERIAL_set1_issuer(OSSL_ISSUER_SERIAL *isss, + const X509_NAME *issuer); +int OSSL_ISSUER_SERIAL_set1_serial(OSSL_ISSUER_SERIAL *isss, + const ASN1_INTEGER *serial); +int OSSL_ISSUER_SERIAL_set1_issuerUID(OSSL_ISSUER_SERIAL *isss, + const ASN1_BIT_STRING *uid); + +# define OSSL_IETFAS_OCTETS 0 +# define OSSL_IETFAS_OID 1 +# define OSSL_IETFAS_STRING 2 + +typedef struct OSSL_IETF_ATTR_SYNTAX_VALUE_st OSSL_IETF_ATTR_SYNTAX_VALUE; +typedef struct OSSL_IETF_ATTR_SYNTAX_st OSSL_IETF_ATTR_SYNTAX; +{- + generate_stack_macros("OSSL_IETF_ATTR_SYNTAX_VALUE"); +-} + +DECLARE_ASN1_ITEM(OSSL_IETF_ATTR_SYNTAX_VALUE) +DECLARE_ASN1_ALLOC_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX_VALUE) +DECLARE_ASN1_FUNCTIONS(OSSL_IETF_ATTR_SYNTAX) + +const GENERAL_NAMES * +OSSL_IETF_ATTR_SYNTAX_get0_policyAuthority(const OSSL_IETF_ATTR_SYNTAX *a); +void OSSL_IETF_ATTR_SYNTAX_set0_policyAuthority(OSSL_IETF_ATTR_SYNTAX *a, + GENERAL_NAMES *names); + +int OSSL_IETF_ATTR_SYNTAX_get_value_num(const OSSL_IETF_ATTR_SYNTAX *a); +void *OSSL_IETF_ATTR_SYNTAX_get0_value(const OSSL_IETF_ATTR_SYNTAX *a, + int ind, int *type); +int OSSL_IETF_ATTR_SYNTAX_add1_value(OSSL_IETF_ATTR_SYNTAX *a, int type, + void *data); +int OSSL_IETF_ATTR_SYNTAX_print(BIO *bp, OSSL_IETF_ATTR_SYNTAX *a, int indent); + +struct TARGET_CERT_st { + OSSL_ISSUER_SERIAL *targetCertificate; + GENERAL_NAME *targetName; + OSSL_OBJECT_DIGEST_INFO *certDigestInfo; +}; + +typedef struct TARGET_CERT_st OSSL_TARGET_CERT; + +# define OSSL_TGT_TARGET_NAME 0 +# define OSSL_TGT_TARGET_GROUP 1 +# define OSSL_TGT_TARGET_CERT 2 + +typedef struct TARGET_st { + int type; + union { + GENERAL_NAME *targetName; + GENERAL_NAME *targetGroup; + OSSL_TARGET_CERT *targetCert; + } choice; +} OSSL_TARGET; + +typedef STACK_OF(OSSL_TARGET) OSSL_TARGETS; +typedef STACK_OF(OSSL_TARGETS) OSSL_TARGETING_INFORMATION; + +{- + generate_stack_macros("OSSL_TARGET"); +-} + +{- + generate_stack_macros("OSSL_TARGETS"); +-} + +DECLARE_ASN1_FUNCTIONS(OSSL_TARGET) +DECLARE_ASN1_FUNCTIONS(OSSL_TARGETS) +DECLARE_ASN1_FUNCTIONS(OSSL_TARGETING_INFORMATION) + +#endif diff --git a/include/openssl/x509err.h b/include/openssl/x509err.h index 71b557a3e6..77b91c8b2c 100644 --- a/include/openssl/x509err.h +++ b/include/openssl/x509err.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -63,6 +63,7 @@ # define X509_R_UNKNOWN_SIGID_ALGS 144 # define X509_R_UNKNOWN_TRUST_ID 120 # define X509_R_UNSUPPORTED_ALGORITHM 111 +# define X509_R_UNSUPPORTED_VERSION 145 # define X509_R_WRONG_LOOKUP_TYPE 112 # define X509_R_WRONG_TYPE 122 diff --git a/include/openssl/x509v3.h b/include/openssl/x509v3.h index e64da7e0c5..09a8521f8b 100644 --- a/include/openssl/x509v3.h +++ b/include/openssl/x509v3.h @@ -2,7 +2,7 @@ * WARNING: do not edit! * Generated by Makefile from include/openssl/x509v3.h.in * - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -149,6 +149,11 @@ typedef struct BASIC_CONSTRAINTS_st { ASN1_INTEGER *pathlen; } BASIC_CONSTRAINTS; +typedef struct OSSL_BASIC_ATTR_CONSTRAINTS_st { + int authority; + ASN1_INTEGER *pathlen; +} OSSL_BASIC_ATTR_CONSTRAINTS; + typedef struct PKEY_USAGE_PERIOD_st { ASN1_GENERALIZEDTIME *notBefore; ASN1_GENERALIZEDTIME *notAfter; @@ -201,6 +206,8 @@ typedef struct ACCESS_DESCRIPTION_st { GENERAL_NAME *location; } ACCESS_DESCRIPTION; +int GENERAL_NAME_set1_X509_NAME(GENERAL_NAME **tgt, const X509_NAME *src); + SKM_DEFINE_STACK_OF_INTERNAL(ACCESS_DESCRIPTION, ACCESS_DESCRIPTION, ACCESS_DESCRIPTION) #define sk_ACCESS_DESCRIPTION_num(sk) OPENSSL_sk_num(ossl_check_const_ACCESS_DESCRIPTION_sk_type(sk)) #define sk_ACCESS_DESCRIPTION_value(sk, idx) ((ACCESS_DESCRIPTION *)OPENSSL_sk_value(ossl_check_const_ACCESS_DESCRIPTION_sk_type(sk), (idx))) @@ -297,6 +304,7 @@ typedef struct DIST_POINT_NAME_st { /* If relativename then this contains the full distribution point name */ X509_NAME *dpname; } DIST_POINT_NAME; +DECLARE_ASN1_DUP_FUNCTION(DIST_POINT_NAME) /* All existing reasons */ # define CRLDP_ALL_REASONS 0x807f @@ -662,15 +670,16 @@ struct ISSUING_DIST_POINT_st { # define EXFLAG_SAN_CRITICAL 0x80000 # define EXFLAG_NO_FINGERPRINT 0x100000 -# define KU_DIGITAL_SIGNATURE 0x0080 -# define KU_NON_REPUDIATION 0x0040 -# define KU_KEY_ENCIPHERMENT 0x0020 -# define KU_DATA_ENCIPHERMENT 0x0010 -# define KU_KEY_AGREEMENT 0x0008 -# define KU_KEY_CERT_SIGN 0x0004 -# define KU_CRL_SIGN 0x0002 -# define KU_ENCIPHER_ONLY 0x0001 -# define KU_DECIPHER_ONLY 0x8000 +/* https://datatracker.ietf.org/doc/html/rfc5280#section-4.2.1.3 */ +# define KU_DIGITAL_SIGNATURE X509v3_KU_DIGITAL_SIGNATURE +# define KU_NON_REPUDIATION X509v3_KU_NON_REPUDIATION +# define KU_KEY_ENCIPHERMENT X509v3_KU_KEY_ENCIPHERMENT +# define KU_DATA_ENCIPHERMENT X509v3_KU_DATA_ENCIPHERMENT +# define KU_KEY_AGREEMENT X509v3_KU_KEY_AGREEMENT +# define KU_KEY_CERT_SIGN X509v3_KU_KEY_CERT_SIGN +# define KU_CRL_SIGN X509v3_KU_CRL_SIGN +# define KU_ENCIPHER_ONLY X509v3_KU_ENCIPHER_ONLY +# define KU_DECIPHER_ONLY X509v3_KU_DECIPHER_ONLY # define NS_SSL_CLIENT 0x80 # define NS_SSL_SERVER 0x40 @@ -771,6 +780,7 @@ SKM_DEFINE_STACK_OF_INTERNAL(X509_PURPOSE, X509_PURPOSE, X509_PURPOSE) # define X509V3_ADD_SILENT 0x10 DECLARE_ASN1_FUNCTIONS(BASIC_CONSTRAINTS) +DECLARE_ASN1_FUNCTIONS(OSSL_BASIC_ATTR_CONSTRAINTS) DECLARE_ASN1_FUNCTIONS(SXNET) DECLARE_ASN1_FUNCTIONS(SXNETID) @@ -1448,6 +1458,42 @@ const ASN1_PRINTABLESTRING *PROFESSION_INFO_get0_registrationNumber( void PROFESSION_INFO_set0_registrationNumber( PROFESSION_INFO *pi, ASN1_PRINTABLESTRING *rn); +int OSSL_GENERAL_NAMES_print(BIO *out, GENERAL_NAMES *gens, int indent); + +typedef STACK_OF(X509_ATTRIBUTE) OSSL_ATTRIBUTES_SYNTAX; +DECLARE_ASN1_FUNCTIONS(OSSL_ATTRIBUTES_SYNTAX) + +typedef STACK_OF(USERNOTICE) OSSL_USER_NOTICE_SYNTAX; +DECLARE_ASN1_FUNCTIONS(OSSL_USER_NOTICE_SYNTAX) + +SKM_DEFINE_STACK_OF_INTERNAL(USERNOTICE, USERNOTICE, USERNOTICE) +#define sk_USERNOTICE_num(sk) OPENSSL_sk_num(ossl_check_const_USERNOTICE_sk_type(sk)) +#define sk_USERNOTICE_value(sk, idx) ((USERNOTICE *)OPENSSL_sk_value(ossl_check_const_USERNOTICE_sk_type(sk), (idx))) +#define sk_USERNOTICE_new(cmp) ((STACK_OF(USERNOTICE) *)OPENSSL_sk_new(ossl_check_USERNOTICE_compfunc_type(cmp))) +#define sk_USERNOTICE_new_null() ((STACK_OF(USERNOTICE) *)OPENSSL_sk_new_null()) +#define sk_USERNOTICE_new_reserve(cmp, n) ((STACK_OF(USERNOTICE) *)OPENSSL_sk_new_reserve(ossl_check_USERNOTICE_compfunc_type(cmp), (n))) +#define sk_USERNOTICE_reserve(sk, n) OPENSSL_sk_reserve(ossl_check_USERNOTICE_sk_type(sk), (n)) +#define sk_USERNOTICE_free(sk) OPENSSL_sk_free(ossl_check_USERNOTICE_sk_type(sk)) +#define sk_USERNOTICE_zero(sk) OPENSSL_sk_zero(ossl_check_USERNOTICE_sk_type(sk)) +#define sk_USERNOTICE_delete(sk, i) ((USERNOTICE *)OPENSSL_sk_delete(ossl_check_USERNOTICE_sk_type(sk), (i))) +#define sk_USERNOTICE_delete_ptr(sk, ptr) ((USERNOTICE *)OPENSSL_sk_delete_ptr(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr))) +#define sk_USERNOTICE_push(sk, ptr) OPENSSL_sk_push(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr)) +#define sk_USERNOTICE_unshift(sk, ptr) OPENSSL_sk_unshift(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr)) +#define sk_USERNOTICE_pop(sk) ((USERNOTICE *)OPENSSL_sk_pop(ossl_check_USERNOTICE_sk_type(sk))) +#define sk_USERNOTICE_shift(sk) ((USERNOTICE *)OPENSSL_sk_shift(ossl_check_USERNOTICE_sk_type(sk))) +#define sk_USERNOTICE_pop_free(sk, freefunc) OPENSSL_sk_pop_free(ossl_check_USERNOTICE_sk_type(sk),ossl_check_USERNOTICE_freefunc_type(freefunc)) +#define sk_USERNOTICE_insert(sk, ptr, idx) OPENSSL_sk_insert(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr), (idx)) +#define sk_USERNOTICE_set(sk, idx, ptr) ((USERNOTICE *)OPENSSL_sk_set(ossl_check_USERNOTICE_sk_type(sk), (idx), ossl_check_USERNOTICE_type(ptr))) +#define sk_USERNOTICE_find(sk, ptr) OPENSSL_sk_find(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr)) +#define sk_USERNOTICE_find_ex(sk, ptr) OPENSSL_sk_find_ex(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr)) +#define sk_USERNOTICE_find_all(sk, ptr, pnum) OPENSSL_sk_find_all(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_type(ptr), pnum) +#define sk_USERNOTICE_sort(sk) OPENSSL_sk_sort(ossl_check_USERNOTICE_sk_type(sk)) +#define sk_USERNOTICE_is_sorted(sk) OPENSSL_sk_is_sorted(ossl_check_const_USERNOTICE_sk_type(sk)) +#define sk_USERNOTICE_dup(sk) ((STACK_OF(USERNOTICE) *)OPENSSL_sk_dup(ossl_check_const_USERNOTICE_sk_type(sk))) +#define sk_USERNOTICE_deep_copy(sk, copyfunc, freefunc) ((STACK_OF(USERNOTICE) *)OPENSSL_sk_deep_copy(ossl_check_const_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_copyfunc_type(copyfunc), ossl_check_USERNOTICE_freefunc_type(freefunc))) +#define sk_USERNOTICE_set_cmp_func(sk, cmp) ((sk_USERNOTICE_compfunc)OPENSSL_sk_set_cmp_func(ossl_check_USERNOTICE_sk_type(sk), ossl_check_USERNOTICE_compfunc_type(cmp))) + + # ifdef __cplusplus } # endif diff --git a/include/openssl/x509v3.h.in b/include/openssl/x509v3.h.in index 569680378d..0f37e1348d 100644 --- a/include/openssl/x509v3.h.in +++ b/include/openssl/x509v3.h.in @@ -1,7 +1,7 @@ /* * {- join("\n * ", @autowarntext) -} * - * Copyright 1999-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1999-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -126,6 +126,11 @@ typedef struct BASIC_CONSTRAINTS_st { ASN1_INTEGER *pathlen; } BASIC_CONSTRAINTS; +typedef struct OSSL_BASIC_ATTR_CONSTRAINTS_st { + int authority; + ASN1_INTEGER *pathlen; +} OSSL_BASIC_ATTR_CONSTRAINTS; + typedef struct PKEY_USAGE_PERIOD_st { ASN1_GENERALIZEDTIME *notBefore; ASN1_GENERALIZEDTIME *notAfter; @@ -178,6 +183,8 @@ typedef struct ACCESS_DESCRIPTION_st { GENERAL_NAME *location; } ACCESS_DESCRIPTION; +int GENERAL_NAME_set1_X509_NAME(GENERAL_NAME **tgt, const X509_NAME *src); + {- generate_stack_macros("ACCESS_DESCRIPTION") .generate_stack_macros("GENERAL_NAME"); @@ -201,6 +208,7 @@ typedef struct DIST_POINT_NAME_st { /* If relativename then this contains the full distribution point name */ X509_NAME *dpname; } DIST_POINT_NAME; +DECLARE_ASN1_DUP_FUNCTION(DIST_POINT_NAME) /* All existing reasons */ # define CRLDP_ALL_REASONS 0x807f @@ -422,15 +430,16 @@ struct ISSUING_DIST_POINT_st { # define EXFLAG_SAN_CRITICAL 0x80000 # define EXFLAG_NO_FINGERPRINT 0x100000 -# define KU_DIGITAL_SIGNATURE 0x0080 -# define KU_NON_REPUDIATION 0x0040 -# define KU_KEY_ENCIPHERMENT 0x0020 -# define KU_DATA_ENCIPHERMENT 0x0010 -# define KU_KEY_AGREEMENT 0x0008 -# define KU_KEY_CERT_SIGN 0x0004 -# define KU_CRL_SIGN 0x0002 -# define KU_ENCIPHER_ONLY 0x0001 -# define KU_DECIPHER_ONLY 0x8000 +/* https://datatracker.ietf.org/doc/html/rfc5280#section-4.2.1.3 */ +# define KU_DIGITAL_SIGNATURE X509v3_KU_DIGITAL_SIGNATURE +# define KU_NON_REPUDIATION X509v3_KU_NON_REPUDIATION +# define KU_KEY_ENCIPHERMENT X509v3_KU_KEY_ENCIPHERMENT +# define KU_DATA_ENCIPHERMENT X509v3_KU_DATA_ENCIPHERMENT +# define KU_KEY_AGREEMENT X509v3_KU_KEY_AGREEMENT +# define KU_KEY_CERT_SIGN X509v3_KU_KEY_CERT_SIGN +# define KU_CRL_SIGN X509v3_KU_CRL_SIGN +# define KU_ENCIPHER_ONLY X509v3_KU_ENCIPHER_ONLY +# define KU_DECIPHER_ONLY X509v3_KU_DECIPHER_ONLY # define NS_SSL_CLIENT 0x80 # define NS_SSL_SERVER 0x40 @@ -507,6 +516,7 @@ typedef struct x509_purpose_st { # define X509V3_ADD_SILENT 0x10 DECLARE_ASN1_FUNCTIONS(BASIC_CONSTRAINTS) +DECLARE_ASN1_FUNCTIONS(OSSL_BASIC_ATTR_CONSTRAINTS) DECLARE_ASN1_FUNCTIONS(SXNET) DECLARE_ASN1_FUNCTIONS(SXNETID) @@ -1015,6 +1025,18 @@ const ASN1_PRINTABLESTRING *PROFESSION_INFO_get0_registrationNumber( void PROFESSION_INFO_set0_registrationNumber( PROFESSION_INFO *pi, ASN1_PRINTABLESTRING *rn); +int OSSL_GENERAL_NAMES_print(BIO *out, GENERAL_NAMES *gens, int indent); + +typedef STACK_OF(X509_ATTRIBUTE) OSSL_ATTRIBUTES_SYNTAX; +DECLARE_ASN1_FUNCTIONS(OSSL_ATTRIBUTES_SYNTAX) + +typedef STACK_OF(USERNOTICE) OSSL_USER_NOTICE_SYNTAX; +DECLARE_ASN1_FUNCTIONS(OSSL_USER_NOTICE_SYNTAX) + +{- + generate_stack_macros("USERNOTICE"); +-} + # ifdef __cplusplus } # endif diff --git a/openssl.cmake b/openssl.cmake index 1f39467256..46a60119d6 100644 --- a/openssl.cmake +++ b/openssl.cmake @@ -162,6 +162,7 @@ set(crypto_srcs crypto/cms/cms_pwri.c crypto/cms/cms_sd.c crypto/cms/cms_smime.c + crypto/comp_methods.c crypto/comp/c_brotli.c crypto/comp/c_zlib.c crypto/comp/c_zstd.c @@ -200,6 +201,7 @@ set(crypto_srcs crypto/ctype.c crypto/cpuid.c crypto/cversion.c + crypto/defaults.c crypto/des/cbc_cksm.c crypto/des/cbc_enc.c crypto/des/cfb64ede.c @@ -420,12 +422,14 @@ set(crypto_srcs crypto/ffc/ffc_params_generate.c crypto/ffc/ffc_params_validate.c crypto/getenv.c + crypto/hashtable/hashtable.c crypto/hmac/hmac.c crypto/hpke/hpke.c crypto/hpke/hpke_util.c crypto/http/http_client.c crypto/http/http_err.c crypto/http/http_lib.c + crypto/indicator_core.c crypto/info.c crypto/init.c crypto/initthread.c @@ -622,6 +626,7 @@ set(crypto_srcs crypto/x509/v3_no_rev_avail.c crypto/x509/v3_single_use.c crypto/x509/v3_soa_id.c + crypto/x509/x509_acert.c crypto/x509/x509_att.c crypto/x509/x509_cmp.c crypto/x509/x509_d2.c @@ -658,9 +663,12 @@ set(crypto_srcs crypto/x509/pcy_map.c crypto/x509/pcy_node.c crypto/x509/pcy_tree.c + crypto/x509/v3_ac_tgt.c crypto/x509/v3_admis.c crypto/x509/v3_akeya.c crypto/x509/v3_akid.c + crypto/x509/v3_audit_id.c + crypto/x509/v3_battcons.c crypto/x509/v3_bcons.c crypto/x509/v3_bitst.c crypto/x509/v3_conf.c @@ -672,6 +680,7 @@ set(crypto_srcs crypto/x509/v3_ia5.c crypto/x509/v3_info.c crypto/x509/v3_int.c + crypto/x509/v3_iobo.c crypto/x509/v3_ist.c crypto/x509/v3_lib.c crypto/x509/v3_ncons.c @@ -683,9 +692,11 @@ set(crypto_srcs crypto/x509/v3_prn.c crypto/x509/v3_purp.c crypto/x509/v3_san.c + crypto/x509/v3_sda.c crypto/x509/v3_skid.c crypto/x509/v3_sxnet.c crypto/x509/v3_tlsf.c + crypto/x509/v3_usernotice.c crypto/x509/v3_utf8.c crypto/x509/v3_utl.c crypto/x509/v3err.c @@ -974,7 +985,6 @@ set(provider_srcs providers/implementations/macs/kmac_prov.c providers/implementations/macs/poly1305_prov.c providers/implementations/macs/siphash_prov.c - providers/implementations/rands/crngt.c providers/implementations/rands/drbg.c providers/implementations/rands/drbg_ctr.c providers/implementations/rands/drbg_hash.c @@ -1015,7 +1025,8 @@ target_include_directories(crypto PUBLIC ${CMAKE_CURRENT_SOURCE_DIR}/openssl/crypto/ec/curve448/ ${CMAKE_CURRENT_SOURCE_DIR}/openssl/providers/common/include/ ${CMAKE_CURRENT_SOURCE_DIR}/openssl/providers/implementations/include/ - ) + ${CMAKE_CURRENT_SOURCE_DIR}/openssl/providers/fips/include/ +) target_include_directories(crypto PRIVATE ${CMAKE_CURRENT_SOURCE_DIR}/openssl/crypto/modes @@ -1109,7 +1120,6 @@ set(ssl_srcs ssl/d1_lib.c ssl/d1_msg.c ssl/d1_srtp.c - ssl/event_queue.c ssl/methods.c ssl/pqueue.c ssl/priority_queue.c diff --git a/openssl.version b/openssl.version index 88be2ab4e6..53cd491306 100644 --- a/openssl.version +++ b/openssl.version @@ -1 +1 @@ -OPENSSL_VERSION=3.3.2 +OPENSSL_VERSION=3.4.0 diff --git a/providers/baseprov.c b/providers/baseprov.c index 6b8de7cb36..7b068f0933 100644 --- a/providers/baseprov.c +++ b/providers/baseprov.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -93,6 +93,9 @@ static const OSSL_ALGORITHM base_store[] = { static const OSSL_ALGORITHM base_rands[] = { { PROV_NAMES_SEED_SRC, "provider=base", ossl_seed_src_functions }, +#ifndef OPENSSL_NO_JITTER + { PROV_NAMES_JITTER, "provider=base", ossl_jitter_functions }, +#endif { NULL, NULL, NULL } }; diff --git a/providers/build.info b/providers/build.info index 3b211bbb2f..06f27df9c6 100644 --- a/providers/build.info +++ b/providers/build.info @@ -46,7 +46,8 @@ LIBS{noinst}=$LIBDEFAULT $LIBCOMMON # providers/implementations/include), which includes crypto/*_platform.h # (present in include), which in turn may include very internal header # files in crypto/, so let's have a common include list for them all. -$COMMON_INCLUDES=../crypto ../include implementations/include common/include +$COMMON_INCLUDES=../crypto ../include implementations/include common/include \ + fips/include INCLUDE[$LIBCOMMON]=$COMMON_INCLUDES INCLUDE[$LIBFIPS]=.. $COMMON_INCLUDES diff --git a/providers/common/capabilities.c b/providers/common/capabilities.c index f7234615e4..550eca1af7 100644 --- a/providers/common/capabilities.c +++ b/providers/common/capabilities.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -189,10 +189,8 @@ static const OSSL_PARAM param_group_list[][10] = { TLS_GROUP_ENTRY("brainpoolP256r1", "brainpoolP256r1", "EC", 25), TLS_GROUP_ENTRY("brainpoolP384r1", "brainpoolP384r1", "EC", 26), TLS_GROUP_ENTRY("brainpoolP512r1", "brainpoolP512r1", "EC", 27), -# endif TLS_GROUP_ENTRY("x25519", "X25519", "X25519", 28), TLS_GROUP_ENTRY("x448", "X448", "X448", 29), -# ifndef FIPS_MODULE TLS_GROUP_ENTRY("brainpoolP256r1tls13", "brainpoolP256r1", "EC", 30), TLS_GROUP_ENTRY("brainpoolP384r1tls13", "brainpoolP384r1", "EC", 31), TLS_GROUP_ENTRY("brainpoolP512r1tls13", "brainpoolP512r1", "EC", 32), diff --git a/providers/common/digest_to_nid.c b/providers/common/digest_to_nid.c index 49af04ad2a..5a0448c009 100644 --- a/providers/common/digest_to_nid.c +++ b/providers/common/digest_to_nid.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -39,6 +39,7 @@ int ossl_digest_md_to_nid(const EVP_MD *md, const OSSL_ITEM *it, size_t it_len) */ int ossl_digest_get_approved_nid(const EVP_MD *md) { + /* TODO: FIPS 180-5 RFC 8692 RFC 8702 allow SHAKE */ static const OSSL_ITEM name_to_nid[] = { { NID_sha1, OSSL_DIGEST_NAME_SHA1 }, { NID_sha224, OSSL_DIGEST_NAME_SHA2_224 }, diff --git a/providers/common/include/prov/proverr.h b/providers/common/include/prov/proverr.h index 69e14465c7..34247ed2f7 100644 --- a/providers/common/include/prov/proverr.h +++ b/providers/common/include/prov/proverr.h @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy diff --git a/providers/common/include/prov/securitycheck.h b/providers/common/include/prov/securitycheck.h index 611c6d531b..29a2b7fbf8 100644 --- a/providers/common/include/prov/securitycheck.h +++ b/providers/common/include/prov/securitycheck.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -8,24 +8,32 @@ */ #include "crypto/types.h" +#include + +#include "fips/fipsindicator.h" /* Functions that are common */ -int ossl_rsa_check_key(OSSL_LIB_CTX *ctx, const RSA *rsa, int operation); -int ossl_ec_check_key(OSSL_LIB_CTX *ctx, const EC_KEY *ec, int protect); -int ossl_dsa_check_key(OSSL_LIB_CTX *ctx, const DSA *dsa, int sign); -int ossl_dh_check_key(OSSL_LIB_CTX *ctx, const DH *dh); +int ossl_rsa_key_op_get_protect(const RSA *rsa, int operation, int *outprotect); +int ossl_rsa_check_key_size(const RSA *rsa, int protect); +int ossl_kdf_check_key_size(size_t keylen); +int ossl_mac_check_key_size(size_t keylen); -int ossl_digest_is_allowed(OSSL_LIB_CTX *ctx, const EVP_MD *md); -/* With security check enabled it can return -1 to indicate disallowed md */ -int ossl_digest_get_approved_nid_with_sha1(OSSL_LIB_CTX *ctx, const EVP_MD *md, - int sha1_allowed); +#ifndef OPENSSL_NO_EC +int ossl_ec_check_curve_allowed(const EC_GROUP *group); +int ossl_ec_check_security_strength(const EC_GROUP *group, int protect); +#endif + +#ifndef OPENSSL_NO_DSA +int ossl_dsa_check_key(const DSA *dsa, int sign); +#endif + +#ifndef OPENSSL_NO_DH +int ossl_dh_check_key(const DH *dh); +#endif -/* Functions that are common */ int ossl_digest_md_to_nid(const EVP_MD *md, const OSSL_ITEM *it, size_t it_len); int ossl_digest_get_approved_nid(const EVP_MD *md); /* Functions that have different implementations for the FIPS_MODULE */ -int ossl_digest_rsa_sign_get_md_nid(OSSL_LIB_CTX *ctx, const EVP_MD *md, - int sha1_allowed); -int ossl_securitycheck_enabled(OSSL_LIB_CTX *libctx); -int ossl_tls1_prf_ems_check_enabled(OSSL_LIB_CTX *libctx); +int ossl_digest_rsa_sign_get_md_nid(const EVP_MD *md); +int ossl_fips_config_securitycheck_enabled(OSSL_LIB_CTX *libctx); diff --git a/providers/common/provider_err.c b/providers/common/provider_err.c index 611ec847cb..df4bab0966 100644 --- a/providers/common/provider_err.c +++ b/providers/common/provider_err.c @@ -1,6 +1,6 @@ /* * Generated by util/mkerr.pl DO NOT EDIT - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,211 +16,228 @@ static const ERR_STRING_DATA PROV_str_reasons[] = { {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ADDITIONAL_INPUT_TOO_LONG), - "additional input too long"}, + "additional input too long"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ALGORITHM_MISMATCH), - "algorithm mismatch"}, + "algorithm mismatch"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ALREADY_INSTANTIATED), - "already instantiated"}, + "already instantiated"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_BAD_DECRYPT), "bad decrypt"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_BAD_ENCODING), "bad encoding"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_BAD_LENGTH), "bad length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_BAD_TLS_CLIENT_VERSION), - "bad tls client version"}, + "bad tls client version"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_BN_ERROR), "bn error"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_CIPHER_OPERATION_FAILED), - "cipher operation failed"}, + "cipher operation failed"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_COFACTOR_REQUIRED), "cofactor required"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_DERIVATION_FUNCTION_INIT_FAILED), - "derivation function init failed"}, + "derivation function init failed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_DIGEST_NOT_ALLOWED), - "digest not allowed"}, + "digest not allowed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_EMS_NOT_ENABLED), "ems not enabled"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ENTROPY_SOURCE_FAILED_CONTINUOUS_TESTS), + "entropy source failed continuous tests"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ENTROPY_SOURCE_STRENGTH_TOO_WEAK), - "entropy source strength too weak"}, + "entropy source strength too weak"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ERROR_INSTANTIATING_DRBG), - "error instantiating drbg"}, + "error instantiating drbg"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ERROR_RETRIEVING_ENTROPY), - "error retrieving entropy"}, + "error retrieving entropy"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ERROR_RETRIEVING_NONCE), - "error retrieving nonce"}, + "error retrieving nonce"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_DURING_DERIVATION), - "failed during derivation"}, + "failed during derivation"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_CREATE_LOCK), - "failed to create lock"}, + "failed to create lock"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_DECRYPT), "failed to decrypt"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_GENERATE_KEY), - "failed to generate key"}, + "failed to generate key"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_GET_PARAMETER), - "failed to get parameter"}, + "failed to get parameter"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_SET_PARAMETER), - "failed to set parameter"}, + "failed to set parameter"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FAILED_TO_SIGN), "failed to sign"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FINAL_CALL_OUT_OF_ORDER), + "final call out of order"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FIPS_MODULE_CONDITIONAL_ERROR), - "fips module conditional error"}, + "fips module conditional error"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FIPS_MODULE_ENTERING_ERROR_STATE), - "fips module entering error state"}, + "fips module entering error state"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_FIPS_MODULE_IN_ERROR_STATE), - "fips module in error state"}, + "fips module in error state"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_GENERATE_ERROR), "generate error"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ILLEGAL_OR_UNSUPPORTED_PADDING_MODE), - "illegal or unsupported padding mode"}, + "illegal or unsupported padding mode"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INDICATOR_INTEGRITY_FAILURE), - "indicator integrity failure"}, + "indicator integrity failure"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INIT_CALL_OUT_OF_ORDER), + "init call out of order"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INSUFFICIENT_DRBG_STRENGTH), - "insufficient drbg strength"}, + "insufficient drbg strength"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_AAD), "invalid aad"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_AEAD), "invalid aead"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_CONFIG_DATA), - "invalid config data"}, + "invalid config data"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_CONSTANT_LENGTH), - "invalid constant length"}, + "invalid constant length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_CURVE), "invalid curve"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_CUSTOM_LENGTH), - "invalid custom length"}, + "invalid custom length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_DATA), "invalid data"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_DIGEST), "invalid digest"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_DIGEST_LENGTH), - "invalid digest length"}, + "invalid digest length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_DIGEST_SIZE), - "invalid digest size"}, + "invalid digest size"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION), + "invalid eddsa instance for attempted operation"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_INPUT_LENGTH), - "invalid input length"}, + "invalid input length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_ITERATION_COUNT), - "invalid iteration count"}, + "invalid iteration count"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_IV_LENGTH), "invalid iv length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KDF), "invalid kdf"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KEY), "invalid key"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_KEY_LENGTH), - "invalid key length"}, + "invalid key length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_MAC), "invalid mac"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_MEMORY_SIZE), - "invalid memory size"}, + "invalid memory size"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_MGF1_MD), "invalid mgf1 md"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_MODE), "invalid mode"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_OUTPUT_LENGTH), - "invalid output length"}, + "invalid output length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_PADDING_MODE), - "invalid padding mode"}, + "invalid padding mode"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_PREHASHED_DIGEST_LENGTH), + "invalid prehashed digest length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_PUBINFO), "invalid pubinfo"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_SALT_LENGTH), - "invalid salt length"}, + "invalid salt length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_SEED_LENGTH), - "invalid seed length"}, + "invalid seed length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_SIGNATURE_SIZE), - "invalid signature size"}, + "invalid signature size"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_STATE), "invalid state"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_TAG), "invalid tag"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_TAG_LENGTH), - "invalid tag length"}, + "invalid tag length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_THREAD_POOL_SIZE), - "invalid thread pool size"}, + "invalid thread pool size"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_UKM_LENGTH), - "invalid ukm length"}, + "invalid ukm length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_INVALID_X931_DIGEST), - "invalid x931 digest"}, + "invalid x931 digest"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_IN_ERROR_STATE), "in error state"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_KEY_SETUP_FAILED), "key setup failed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_KEY_SIZE_TOO_SMALL), - "key size too small"}, + "key size too small"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_LENGTH_TOO_LARGE), "length too large"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISMATCHING_DOMAIN_PARAMETERS), - "mismatching domain parameters"}, + "mismatching domain parameters"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_CEK_ALG), "missing cek alg"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_CIPHER), "missing cipher"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_CONFIG_DATA), - "missing config data"}, + "missing config data"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_CONSTANT), "missing constant"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_KEY), "missing key"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_MAC), "missing mac"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_MESSAGE_DIGEST), - "missing message digest"}, + "missing message digest"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_OID), "missing OID"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_PASS), "missing pass"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_SALT), "missing salt"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_SECRET), "missing secret"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_SEED), "missing seed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_SESSION_ID), - "missing session id"}, + "missing session id"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_TYPE), "missing type"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MISSING_XCGHASH), "missing xcghash"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_MODULE_INTEGRITY_FAILURE), - "module integrity failure"}, + "module integrity failure"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_A_PRIVATE_KEY), "not a private key"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_A_PUBLIC_KEY), "not a public key"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_INSTANTIATED), "not instantiated"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_PARAMETERS), "not parameters"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_SUPPORTED), "not supported"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NOT_XOF_OR_INVALID_LENGTH), - "not xof or invalid length"}, + "not xof or invalid length"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NO_INSTANCE_ALLOWED), + "no instance allowed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NO_KEY_SET), "no key set"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_NO_PARAMETERS_SET), "no parameters set"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_ONESHOT_CALL_OUT_OF_ORDER), + "oneshot call out of order"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE), - "operation not supported for this keytype"}, + "operation not supported for this keytype"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_OUTPUT_BUFFER_TOO_SMALL), - "output buffer too small"}, + "output buffer too small"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PARENT_CANNOT_GENERATE_RANDOM_NUMBERS), - "parent cannot generate random numbers"}, + "parent cannot generate random numbers"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PARENT_CANNOT_SUPPLY_ENTROPY_SEED), - "parent cannot supply entropy seed"}, + "parent cannot supply entropy seed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PARENT_LOCKING_NOT_ENABLED), - "parent locking not enabled"}, + "parent locking not enabled"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PARENT_STRENGTH_TOO_WEAK), - "parent strength too weak"}, + "parent strength too weak"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PATH_MUST_BE_ABSOLUTE), - "path must be absolute"}, + "path must be absolute"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PERSONALISATION_STRING_TOO_LONG), - "personalisation string too long"}, + "personalisation string too long"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_PSS_SALTLEN_TOO_SMALL), - "pss saltlen too small"}, + "pss saltlen too small"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_REQUEST_TOO_LARGE_FOR_DRBG), - "request too large for drbg"}, + "request too large for drbg"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_REQUIRE_CTR_MODE_CIPHER), - "require ctr mode cipher"}, + "require ctr mode cipher"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_RESEED_ERROR), "reseed error"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_SEARCH_ONLY_SUPPORTED_FOR_DIRECTORIES), - "search only supported for directories"}, + "search only supported for directories"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_SEED_SOURCES_MUST_NOT_HAVE_A_PARENT), - "seed sources must not have a parent"}, + "seed sources must not have a parent"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_SELF_TEST_KAT_FAILURE), - "self test kat failure"}, + "self test kat failure"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_SELF_TEST_POST_FAILURE), - "self test post failure"}, + "self test post failure"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_TAG_NOT_NEEDED), "tag not needed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_TAG_NOT_SET), "tag not set"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_TOO_MANY_RECORDS), "too many records"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_FIND_CIPHERS), - "unable to find ciphers"}, + "unable to find ciphers"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_GET_PARENT_STRENGTH), - "unable to get parent strength"}, + "unable to get parent strength"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_GET_PASSPHRASE), - "unable to get passphrase"}, + "unable to get passphrase"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_INITIALISE_CIPHERS), - "unable to initialise ciphers"}, + "unable to initialise ciphers"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_LOAD_SHA256), - "unable to load sha256"}, + "unable to load sha256"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_LOCK_PARENT), - "unable to lock parent"}, + "unable to lock parent"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNABLE_TO_RESEED), "unable to reseed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNSUPPORTED_CEK_ALG), - "unsupported cek alg"}, + "unsupported cek alg"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNSUPPORTED_KEY_SIZE), - "unsupported key size"}, + "unsupported key size"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNSUPPORTED_MAC_TYPE), - "unsupported mac type"}, + "unsupported mac type"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UNSUPPORTED_NUMBER_OF_ROUNDS), - "unsupported number of rounds"}, + "unsupported number of rounds"}, + {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_UPDATE_CALL_OUT_OF_ORDER), + "update call out of order"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_URI_AUTHORITY_UNSUPPORTED), - "uri authority unsupported"}, + "uri authority unsupported"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_VALUE_ERROR), "value error"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_WRONG_FINAL_BLOCK_LENGTH), - "wrong final block length"}, + "wrong final block length"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_WRONG_OUTPUT_BUFFER_SIZE), - "wrong output buffer size"}, + "wrong output buffer size"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_XOF_DIGESTS_NOT_ALLOWED), - "xof digests not allowed"}, + "xof digests not allowed"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_XTS_DATA_UNIT_IS_TOO_LARGE), - "xts data unit is too large"}, + "xts data unit is too large"}, {ERR_PACK(ERR_LIB_PROV, 0, PROV_R_XTS_DUPLICATED_KEYS), - "xts duplicated keys"}, + "xts duplicated keys"}, {0, NULL} }; diff --git a/providers/common/securitycheck.c b/providers/common/securitycheck.c index 0d3acdbe56..8ef8dc2a81 100644 --- a/providers/common/securitycheck.c +++ b/providers/common/securitycheck.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -20,61 +20,90 @@ #include #include "prov/securitycheck.h" +#define OSSL_FIPS_MIN_SECURITY_STRENGTH_BITS 112 + +int ossl_rsa_key_op_get_protect(const RSA *rsa, int operation, int *outprotect) +{ + int protect = 0; + + switch (operation) { + case EVP_PKEY_OP_SIGN: + case EVP_PKEY_OP_SIGNMSG: + protect = 1; + /* fallthrough */ + case EVP_PKEY_OP_VERIFY: + case EVP_PKEY_OP_VERIFYMSG: + break; + case EVP_PKEY_OP_ENCAPSULATE: + case EVP_PKEY_OP_ENCRYPT: + protect = 1; + /* fallthrough */ + case EVP_PKEY_OP_VERIFYRECOVER: + case EVP_PKEY_OP_DECAPSULATE: + case EVP_PKEY_OP_DECRYPT: + if (RSA_test_flags(rsa, + RSA_FLAG_TYPE_MASK) == RSA_FLAG_TYPE_RSASSAPSS) { + ERR_raise_data(ERR_LIB_PROV, + PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE, + "operation: %d", operation); + return 0; + } + break; + default: + ERR_raise_data(ERR_LIB_PROV, ERR_R_INTERNAL_ERROR, + "invalid operation: %d", operation); + return 0; + } + *outprotect = protect; + return 1; +} + /* * FIPS requires a minimum security strength of 112 bits (for encryption or * signing), and for legacy purposes 80 bits (for decryption or verifying). * Set protect = 1 for encryption or signing operations, or 0 otherwise. See * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-131Ar2.pdf. */ -int ossl_rsa_check_key(OSSL_LIB_CTX *ctx, const RSA *rsa, int operation) +int ossl_rsa_check_key_size(const RSA *rsa, int protect) { - int protect = 0; + int sz = RSA_bits(rsa); - switch (operation) { - case EVP_PKEY_OP_SIGN: - protect = 1; - /* fallthrough */ - case EVP_PKEY_OP_VERIFY: - break; - case EVP_PKEY_OP_ENCAPSULATE: - case EVP_PKEY_OP_ENCRYPT: - protect = 1; - /* fallthrough */ - case EVP_PKEY_OP_VERIFYRECOVER: - case EVP_PKEY_OP_DECAPSULATE: - case EVP_PKEY_OP_DECRYPT: - if (RSA_test_flags(rsa, - RSA_FLAG_TYPE_MASK) == RSA_FLAG_TYPE_RSASSAPSS) { - ERR_raise_data(ERR_LIB_PROV, - PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE, - "operation: %d", operation); - return 0; - } - break; - default: - ERR_raise_data(ERR_LIB_PROV, ERR_R_INTERNAL_ERROR, - "invalid operation: %d", operation); - return 0; - } + if (protect ? (sz < 2048) : (sz < 1024)) + return 0; + return 1; +} -#if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) { - int sz = RSA_bits(rsa); +/* + * FIPS requires a minimum security strength of 112 bits for key-derivation key. + * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-131Ar2.pdf. + */ +int ossl_kdf_check_key_size(size_t keylen) +{ + return (keylen * 8) >= OSSL_FIPS_MIN_SECURITY_STRENGTH_BITS; +} - if (protect ? (sz < 2048) : (sz < 1024)) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH, - "operation: %d", operation); - return 0; - } - } -#else - /* make protect used */ - (void)protect; -#endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return 1; +int ossl_mac_check_key_size(size_t keylen) +{ + return ossl_kdf_check_key_size(keylen); } #ifndef OPENSSL_NO_EC + +int ossl_ec_check_curve_allowed(const EC_GROUP *group) +{ + const char *curve_name; + int nid = EC_GROUP_get_curve_name(group); + + /* Explicit curves are not FIPS approved */ + if (nid == NID_undef) + return 0; + /* Only NIST curves are FIPS approved */ + curve_name = EC_curve_nid2nist(nid); + if (curve_name == NULL) + return 0; + return 1; +} + /* * In FIPS mode: * protect should be 1 for any operations that need 112 bits of security @@ -89,56 +118,25 @@ int ossl_rsa_check_key(OSSL_LIB_CTX *ctx, const RSA *rsa, int operation) * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-131Ar2.pdf * "Table 2" */ -int ossl_ec_check_key(OSSL_LIB_CTX *ctx, const EC_KEY *ec, int protect) +int ossl_ec_check_security_strength(const EC_GROUP *group, int protect) { -# if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) { - int nid, strength; - const char *curve_name; - const EC_GROUP *group = EC_KEY_get0_group(ec); - - if (group == NULL) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_CURVE, "No group"); - return 0; - } - nid = EC_GROUP_get_curve_name(group); - if (nid == NID_undef) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_CURVE, - "Explicit curves are not allowed in fips mode"); - return 0; - } - - curve_name = EC_curve_nid2nist(nid); - if (curve_name == NULL) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_CURVE, - "Curve %s is not approved in FIPS mode", curve_name); - return 0; - } - - /* - * For EC the security strength is the (order_bits / 2) - * e.g. P-224 is 112 bits. - */ - strength = EC_GROUP_order_bits(group) / 2; - /* The min security strength allowed for legacy verification is 80 bits */ - if (strength < 80) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_CURVE); - return 0; - } - - /* - * For signing or key agreement only allow curves with at least 112 bits of - * security strength - */ - if (protect && strength < 112) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_CURVE, - "Curve %s cannot be used for signing", curve_name); - return 0; - } - } -# endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ + /* + * For EC the security strength is the (order_bits / 2) + * e.g. P-224 is 112 bits. + */ + int strength = EC_GROUP_order_bits(group) / 2; + /* The min security strength allowed for legacy verification is 80 bits */ + if (strength < 80) + return 0; + /* + * For signing or key agreement only allow curves with at least 112 bits of + * security strength + */ + if (protect && strength < OSSL_FIPS_MIN_SECURITY_STRENGTH_BITS) + return 0; return 1; } + #endif /* OPENSSL_NO_EC */ #ifndef OPENSSL_NO_DSA @@ -147,48 +145,43 @@ int ossl_ec_check_key(OSSL_LIB_CTX *ctx, const EC_KEY *ec, int protect) * https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-131Ar2.pdf * "Table 2" */ -int ossl_dsa_check_key(OSSL_LIB_CTX *ctx, const DSA *dsa, int sign) +int ossl_dsa_check_key(const DSA *dsa, int sign) { -# if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) { - size_t L, N; - const BIGNUM *p, *q; - - if (dsa == NULL) + size_t L, N; + const BIGNUM *p, *q; + + if (dsa == NULL) + return 0; + + p = DSA_get0_p(dsa); + q = DSA_get0_q(dsa); + if (p == NULL || q == NULL) + return 0; + + L = BN_num_bits(p); + N = BN_num_bits(q); + + /* + * For Digital signature verification DSA keys with < 112 bits of + * security strength, are still allowed for legacy + * use. The bounds given in SP 800-131Ar2 - Table 2 are + * (512 <= L < 2048 or 160 <= N < 224). + * + * We are a little stricter and insist that both minimums are met. + * For example a L = 256, N = 160 key *would* be allowed by SP 800-131Ar2 + * but we don't. + */ + if (!sign) { + if (L < 512 || N < 160) return 0; - - p = DSA_get0_p(dsa); - q = DSA_get0_q(dsa); - if (p == NULL || q == NULL) - return 0; - - L = BN_num_bits(p); - N = BN_num_bits(q); - - /* - * For Digital signature verification DSA keys with < 112 bits of - * security strength, are still allowed for legacy - * use. The bounds given in SP 800-131Ar2 - Table 2 are - * (512 <= L < 2048 or 160 <= N < 224). - * - * We are a little stricter and insist that both minimums are met. - * For example a L = 256, N = 160 key *would* be allowed by SP 800-131Ar2 - * but we don't. - */ - if (!sign) { - if (L < 512 || N < 160) - return 0; - if (L < 2048 || N < 224) - return 1; - } - - /* Valid sizes for both sign and verify */ - if (L == 2048 && (N == 224 || N == 256)) /* 112 bits */ + if (L < 2048 || N < 224) return 1; - return (L == 3072 && N == 256); /* 128 bits */ } -# endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return 1; + + /* Valid sizes for both sign and verify */ + if (L == 2048 && (N == 224 || N == 256)) /* 112 bits */ + return 1; + return (L == 3072 && N == 256); /* 128 bits */ } #endif /* OPENSSL_NO_DSA */ @@ -199,58 +192,30 @@ int ossl_dsa_check_key(OSSL_LIB_CTX *ctx, const DSA *dsa, int sign) * "Section 5.5.1.1FFC Domain Parameter Selection/Generation" and * "Appendix D" FFC Safe-prime Groups */ -int ossl_dh_check_key(OSSL_LIB_CTX *ctx, const DH *dh) +int ossl_dh_check_key(const DH *dh) { -# if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) { - size_t L, N; - const BIGNUM *p, *q; + size_t L, N; + const BIGNUM *p, *q; - if (dh == NULL) - return 0; + if (dh == NULL) + return 0; - p = DH_get0_p(dh); - q = DH_get0_q(dh); - if (p == NULL || q == NULL) - return 0; + p = DH_get0_p(dh); + q = DH_get0_q(dh); + if (p == NULL || q == NULL) + return 0; - L = BN_num_bits(p); - if (L < 2048) - return 0; + L = BN_num_bits(p); + if (L < 2048) + return 0; - /* If it is a safe prime group then it is ok */ - if (DH_get_nid(dh)) - return 1; + /* If it is a safe prime group then it is ok */ + if (DH_get_nid(dh)) + return 1; - /* If not then it must be FFC, which only allows certain sizes. */ - N = BN_num_bits(q); + /* If not then it must be FFC, which only allows certain sizes. */ + N = BN_num_bits(q); - return (L == 2048 && (N == 224 || N == 256)); - } -# endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return 1; + return (L == 2048 && (N == 224 || N == 256)); } #endif /* OPENSSL_NO_DH */ - -int ossl_digest_get_approved_nid_with_sha1(OSSL_LIB_CTX *ctx, const EVP_MD *md, - int sha1_allowed) -{ - int mdnid = ossl_digest_get_approved_nid(md); - -# if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) { - if (mdnid == NID_undef || (mdnid == NID_sha1 && !sha1_allowed)) - mdnid = -1; /* disallowed by security checks */ - } -# endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return mdnid; -} - -int ossl_digest_is_allowed(OSSL_LIB_CTX *ctx, const EVP_MD *md) -{ -# if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) - return ossl_digest_get_approved_nid(md) != NID_undef; -# endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return 1; -} diff --git a/providers/common/securitycheck_default.c b/providers/common/securitycheck_default.c index 246323493e..dd71fd91eb 100644 --- a/providers/common/securitycheck_default.c +++ b/providers/common/securitycheck_default.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,19 +17,12 @@ #include "internal/nelem.h" /* Disable the security checks in the default provider */ -int ossl_securitycheck_enabled(OSSL_LIB_CTX *libctx) +int ossl_fips_config_securitycheck_enabled(OSSL_LIB_CTX *libctx) { return 0; } -/* Disable the ems check in the default provider */ -int ossl_tls1_prf_ems_check_enabled(OSSL_LIB_CTX *libctx) -{ - return 0; -} - -int ossl_digest_rsa_sign_get_md_nid(OSSL_LIB_CTX *ctx, const EVP_MD *md, - ossl_unused int sha1_allowed) +int ossl_digest_rsa_sign_get_md_nid(const EVP_MD *md) { int mdnid; @@ -40,9 +33,10 @@ int ossl_digest_rsa_sign_get_md_nid(OSSL_LIB_CTX *ctx, const EVP_MD *md, { NID_md4, OSSL_DIGEST_NAME_MD4 }, { NID_mdc2, OSSL_DIGEST_NAME_MDC2 }, { NID_ripemd160, OSSL_DIGEST_NAME_RIPEMD160 }, + { NID_sm3, OSSL_DIGEST_NAME_SM3 }, }; - mdnid = ossl_digest_get_approved_nid_with_sha1(ctx, md, 1); + mdnid = ossl_digest_get_approved_nid(md); if (mdnid == NID_undef) mdnid = ossl_digest_md_to_nid(md, name_to_nid, OSSL_NELEM(name_to_nid)); return mdnid; diff --git a/providers/common/securitycheck_fips.c b/providers/common/securitycheck_fips.c index d1262d8795..c02fa960c0 100644 --- a/providers/common/securitycheck_fips.c +++ b/providers/common/securitycheck_fips.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -18,28 +18,102 @@ #include #include #include "prov/securitycheck.h" -#include "prov/fipscommon.h" -int ossl_securitycheck_enabled(OSSL_LIB_CTX *libctx) +int ossl_fips_config_securitycheck_enabled(OSSL_LIB_CTX *libctx) { #if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - return FIPS_security_check_enabled(libctx); + return ossl_fips_config_security_checks(libctx); #else return 0; #endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ } -int ossl_tls1_prf_ems_check_enabled(OSSL_LIB_CTX *libctx) +int ossl_digest_rsa_sign_get_md_nid(const EVP_MD *md) { - return FIPS_tls_prf_ems_check(libctx); + return ossl_digest_get_approved_nid(md); } -int ossl_digest_rsa_sign_get_md_nid(OSSL_LIB_CTX *ctx, const EVP_MD *md, - int sha1_allowed) +int ossl_fips_ind_rsa_key_check(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + const RSA *rsa, const char *desc, int protect) { -#if !defined(OPENSSL_NO_FIPS_SECURITYCHECKS) - if (ossl_securitycheck_enabled(ctx)) - return ossl_digest_get_approved_nid_with_sha1(ctx, md, sha1_allowed); -#endif /* OPENSSL_NO_FIPS_SECURITYCHECKS */ - return ossl_digest_get_approved_nid(md); + int key_approved = ossl_rsa_check_key_size(rsa, protect); + + if (!key_approved) { + if (!ossl_FIPS_IND_on_unapproved(ind, id, libctx, desc, "Key size", + ossl_fips_config_securitycheck_enabled)) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH, + "operation: %s", desc); + return 0; + } + } + return 1; +} + +# ifndef OPENSSL_NO_EC +int ossl_fips_ind_ec_key_check(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + const EC_GROUP *group, const char *desc, + int protect) +{ + int curve_allowed, strength_allowed; + + if (group == NULL) + return 0; + + curve_allowed = ossl_ec_check_curve_allowed(group); + strength_allowed = ossl_ec_check_security_strength(group, protect); + + if (!strength_allowed || !curve_allowed) { + if (!ossl_FIPS_IND_on_unapproved(ind, id, libctx, desc, "EC Key", + ossl_fips_config_securitycheck_enabled)) { + if (!curve_allowed) + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_CURVE); + if (!strength_allowed) + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + +int ossl_fips_ind_digest_exch_check(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + const EVP_MD *md, const char *desc) +{ + int nid = ossl_digest_get_approved_nid(md); + int approved = (nid != NID_undef && nid != NID_sha1); + + if (!approved) { + if (!ossl_FIPS_IND_on_unapproved(ind, id, libctx, desc, "Digest", + ossl_fips_config_securitycheck_enabled)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST); + return 0; + } + } + return 1; +} + +int ossl_fips_ind_digest_sign_check(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + int nid, int sha1_allowed, + const char *desc, + OSSL_FIPS_IND_CHECK_CB *config_check_f) +{ + int approved; + + if (nid == NID_undef) + approved = 0; + else + approved = sha1_allowed || nid != NID_sha1; + + if (!approved) { + if (!ossl_FIPS_IND_on_unapproved(ind, id, libctx, desc, "Digest SHA1", + config_check_f)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST); + return 0; + } + } + return 1; } diff --git a/providers/defltprov.c b/providers/defltprov.c index f02e04835d..765ae25a3b 100644 --- a/providers/defltprov.c +++ b/providers/defltprov.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -387,6 +387,9 @@ static const OSSL_ALGORITHM deflt_rands[] = { { PROV_NAMES_HASH_DRBG, "provider=default", ossl_drbg_hash_functions }, { PROV_NAMES_HMAC_DRBG, "provider=default", ossl_drbg_ossl_hmac_functions }, { PROV_NAMES_SEED_SRC, "provider=default", ossl_seed_src_functions }, +#ifndef OPENSSL_NO_JITTER + { PROV_NAMES_JITTER, "provider=default", ossl_jitter_functions }, +#endif { PROV_NAMES_TEST_RAND, "provider=default", ossl_test_rng_functions }, { NULL, NULL, NULL } }; @@ -394,14 +397,52 @@ static const OSSL_ALGORITHM deflt_rands[] = { static const OSSL_ALGORITHM deflt_signature[] = { #ifndef OPENSSL_NO_DSA { PROV_NAMES_DSA, "provider=default", ossl_dsa_signature_functions }, + { PROV_NAMES_DSA_SHA1, "provider=default", ossl_dsa_sha1_signature_functions }, + { PROV_NAMES_DSA_SHA224, "provider=default", ossl_dsa_sha224_signature_functions }, + { PROV_NAMES_DSA_SHA256, "provider=default", ossl_dsa_sha256_signature_functions }, + { PROV_NAMES_DSA_SHA384, "provider=default", ossl_dsa_sha384_signature_functions }, + { PROV_NAMES_DSA_SHA512, "provider=default", ossl_dsa_sha512_signature_functions }, + { PROV_NAMES_DSA_SHA3_224, "provider=default", ossl_dsa_sha3_224_signature_functions }, + { PROV_NAMES_DSA_SHA3_256, "provider=default", ossl_dsa_sha3_256_signature_functions }, + { PROV_NAMES_DSA_SHA3_384, "provider=default", ossl_dsa_sha3_384_signature_functions }, + { PROV_NAMES_DSA_SHA3_512, "provider=default", ossl_dsa_sha3_512_signature_functions }, #endif { PROV_NAMES_RSA, "provider=default", ossl_rsa_signature_functions }, +#if !defined(OPENSSL_NO_RMD160) && !defined(FIPS_MODULE) + { PROV_NAMES_RSA_RIPEMD160, "provider=default", ossl_rsa_ripemd160_signature_functions }, +#endif + { PROV_NAMES_RSA_SHA1, "provider=default", ossl_rsa_sha1_signature_functions }, + { PROV_NAMES_RSA_SHA224, "provider=default", ossl_rsa_sha224_signature_functions }, + { PROV_NAMES_RSA_SHA256, "provider=default", ossl_rsa_sha256_signature_functions }, + { PROV_NAMES_RSA_SHA384, "provider=default", ossl_rsa_sha384_signature_functions }, + { PROV_NAMES_RSA_SHA512, "provider=default", ossl_rsa_sha512_signature_functions }, + { PROV_NAMES_RSA_SHA512_224, "provider=default", ossl_rsa_sha512_224_signature_functions }, + { PROV_NAMES_RSA_SHA512_256, "provider=default", ossl_rsa_sha512_256_signature_functions }, + { PROV_NAMES_RSA_SHA3_224, "provider=default", ossl_rsa_sha3_224_signature_functions }, + { PROV_NAMES_RSA_SHA3_256, "provider=default", ossl_rsa_sha3_256_signature_functions }, + { PROV_NAMES_RSA_SHA3_384, "provider=default", ossl_rsa_sha3_384_signature_functions }, + { PROV_NAMES_RSA_SHA3_512, "provider=default", ossl_rsa_sha3_512_signature_functions }, +#ifndef OPENSSL_NO_SM3 + { PROV_NAMES_RSA_SM3, "provider=default", ossl_rsa_sm3_signature_functions }, +#endif #ifndef OPENSSL_NO_EC # ifndef OPENSSL_NO_ECX { PROV_NAMES_ED25519, "provider=default", ossl_ed25519_signature_functions }, + { PROV_NAMES_ED25519ph, "provider=default", ossl_ed25519ph_signature_functions }, + { PROV_NAMES_ED25519ctx, "provider=default", ossl_ed25519ctx_signature_functions }, { PROV_NAMES_ED448, "provider=default", ossl_ed448_signature_functions }, + { PROV_NAMES_ED448ph, "provider=default", ossl_ed448ph_signature_functions }, # endif { PROV_NAMES_ECDSA, "provider=default", ossl_ecdsa_signature_functions }, + { PROV_NAMES_ECDSA_SHA1, "provider=default", ossl_ecdsa_sha1_signature_functions }, + { PROV_NAMES_ECDSA_SHA224, "provider=default", ossl_ecdsa_sha224_signature_functions }, + { PROV_NAMES_ECDSA_SHA256, "provider=default", ossl_ecdsa_sha256_signature_functions }, + { PROV_NAMES_ECDSA_SHA384, "provider=default", ossl_ecdsa_sha384_signature_functions }, + { PROV_NAMES_ECDSA_SHA512, "provider=default", ossl_ecdsa_sha512_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_224, "provider=default", ossl_ecdsa_sha3_224_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_256, "provider=default", ossl_ecdsa_sha3_256_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_384, "provider=default", ossl_ecdsa_sha3_384_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_512, "provider=default", ossl_ecdsa_sha3_512_signature_functions }, # ifndef OPENSSL_NO_SM2 { PROV_NAMES_SM2, "provider=default", ossl_sm2_signature_functions }, # endif diff --git a/providers/fips-sources.checksums b/providers/fips-sources.checksums index c707a404d0..9ce7e4a9bd 100644 --- a/providers/fips-sources.checksums +++ b/providers/fips-sources.checksums @@ -18,27 +18,27 @@ bcdf6c2c0fc13ae5bd2586b0fb8e72be44f26cb919f4fbd7b2eb5cde90a1ff33 crypto/aes/asm 18283dea4477ab722ec7e4bff000a4a2df89b2a430c42c6fa8ee8099b13c86ee crypto/aes/asm/aes-riscv64.pl d139e5ad69560fd0ffd8aa2e72304e463650cea4c657be7a90e0d1eb782d580a crypto/aes/asm/aes-s390x.pl 133ba35d77002abcd430414749c4e98c4a319630da898e45ff8dbc5800176df1 crypto/aes/asm/aes-sparcv9.pl -c98690249d490d23e6fee84f672f1463ffc029427110a4329244a59e4e4aaed8 crypto/aes/asm/aes-x86_64.pl +da4a62c12d12540302f91ba2933b8a485cc1bacda83cc5b50caeeb7f57556b3b crypto/aes/asm/aes-x86_64.pl 7ec99947b47e56595f0b085b8bda0b3113112f694e78b1f71b63ecd1f0fa2c67 crypto/aes/asm/aesfx-sparcv9.pl ab94a27e533e164bcf09898a6f6019f43609d51a3b374cf75482dcf2914d464e crypto/aes/asm/aesni-mb-x86_64.pl -74939261340a0056eb9333fff1c843c8758b9f93de3d94650cd6d2899c6790d8 crypto/aes/asm/aesni-sha1-x86_64.pl -ce91f0893a2a35fdf4c024ccb0fd8329b30fdbd955f0ae011ab948101ee14951 crypto/aes/asm/aesni-sha256-x86_64.pl +c197aeb5178096bbdc43234f01ce4e44174ba13787b5b77790207a8f144d2550 crypto/aes/asm/aesni-sha1-x86_64.pl +142b4197204839958805b35fa06377f0deb274b02ff365a9d68cc4621e557e71 crypto/aes/asm/aesni-sha256-x86_64.pl 4ff74d4e629a88ef5a9e3d3f5b340fc0a4793d16d7cc7f1b70da62512a856248 crypto/aes/asm/aesni-x86.pl -30103cfe3b29d06b34feff48a927e0fa649e9109d35a3db64b09cfeb15426fa2 crypto/aes/asm/aesni-x86_64.pl +53e61960590f73e364a41d1a26bf09875a24e38697055ec55bb72e5021a9eb4a crypto/aes/asm/aesni-x86_64.pl f3490c936a80e012c49e577ec6e1d4d36df324dfef6264e788e6225e20b5fd52 crypto/aes/asm/aesp8-ppc.pl a5807ed92ec8a16d123061487c385bf1f65e50878cee95c8e8096844454129f8 crypto/aes/asm/aest4-sparcv9.pl 89688a470d0a714b2d83e11b09b110e707e9b5e69c8cb37295d1f0bfc087106a crypto/aes/asm/aesv8-armx.pl a0b578b7d2787c91013547df07dfa73d8d7a420446dd624c66f7c55159817eb2 crypto/aes/asm/bsaes-armv7.pl 270a0cd4c80a0cde53538009037916a330348addfdd87870d41ab40f9ddbc451 crypto/aes/asm/bsaes-armv8.pl -34accd08242a6bf4a751105f89b0c4de2cd7e54320753587815647abff7124de crypto/aes/asm/bsaes-x86_64.pl +c22a4a276257db7c7a44ae8ddae3575f46dfdf65f14893985c73173294946c2a crypto/aes/asm/bsaes-x86_64.pl 068cb6cdf4c737b7f7f9ebf27284599d17f6f5c4a01f0c61c7777323b2f203f5 crypto/aes/asm/vpaes-armv8.pl b4656c09bec06eea0b3fe504d47af847ceb0c90f1fb1cc76f43c1caa0dc17613 crypto/aes/asm/vpaes-loongarch64.pl 516421b1a321b842f879ad69e7b82ae3e1f3efc8288c83bb34d6577996e85787 crypto/aes/asm/vpaes-ppc.pl 3ec24185750a995377516bc2fb2eae8b1c52094c6fff093bff591837fc12d6c3 crypto/aes/asm/vpaes-x86.pl -47bedbe6a04254eede121e71f11a657b1f1940aee1916bbfc04fa9fb8454f9b8 crypto/aes/asm/vpaes-x86_64.pl +0bdd2083d4454e46ec8d8ddd667a304684411f4d2ea9549237ae02260e13f009 crypto/aes/asm/vpaes-x86_64.pl 1c9a2a0e8cee4a1283c74b2e306f46f79890f6d236394de2a80d1994fd411d1d crypto/alphacpuid.pl f2e5fee49c133a63fda341580a898f3266743b4ef15d539ba6abf90a5d660628 crypto/arm64cpuid.pl -4890754d4236be78327f99ab1244ce4593cd1e98750e4a35f8e9374809a1b65e crypto/armcap.c +92a10a1fbac5d0379a33a041d02ebb08e2535894f041b28d9908e4fcecf566da crypto/armcap.c ff7aa344dbcd04767837e1319de718ce85c4b55c065c52435bf5a2a60e65d304 crypto/armv4cpuid.pl 16739d54200fb81ca7835b5814f965022a2ab41589c7787e2697e3ea72d4fafa crypto/asn1_dsa.c 155eff9d747eed808398cfa2af4b276dfc1f9aac8a0f9d801b314ab3f2bf5b56 crypto/bn/asm/alpha-mont.pl @@ -51,17 +51,17 @@ c86664fb974362ee52a454c83c2c4b23fd5b7d64b3c9e23ef1e0dfd130a46ee5 crypto/bn/asm/ b88190d748056e6a64988bf1a3d19efc4c292e3d338a65f4505cf769a2041077 crypto/bn/asm/ia64-mont.pl a511aafbf76647a0c83705d4491c898a5584d300aa449fa6166c8803372946eb crypto/bn/asm/ia64.S fee42cabeeb87cdf0fa0a6ff3698b2fe98a8a47d10a756052df572097161a8b9 crypto/bn/asm/mips-mont.pl -b197a8e1be79b8c21f8d26b34b9a282ca42ec4bcd1f3212fde3889747082a1f7 crypto/bn/asm/mips.pl +b0698029e7011246a72b121f76890f3a48fe45f08ef435585c33faf6e9903e4e crypto/bn/asm/mips.pl 13df09cee06a21669137294f92e5c31b4bf05a8035be6800c1cb4403d7cd8290 crypto/bn/asm/parisc-mont.pl 25c96e545b4981d45557eb14ea5c83aa2d6375ae0df806cb6e6ded2f59ddfed3 crypto/bn/asm/ppc-mont.pl 1c057083546fa1a3bb1b9819dc5110f5a3b11b7bf5a2fb275012323bd7412403 crypto/bn/asm/ppc.pl 04c9b5d2494c06e6f8a47c35274ddf53ae46b65e6abc297bd41e5beb735a3e8e crypto/bn/asm/ppc64-mont-fixed.pl fe9278a2504fb40257637a4718081775c29c4eb81f87a8528e5c85f8d0c6281a crypto/bn/asm/ppc64-mont.pl -191459ad441f1f0bc4bcf31fb2628d2bed3b0bd40e28fc96b5e0e8d8846db791 crypto/bn/asm/rsaz-2k-avx512.pl -fbbb79bbde7db1294d55f41919a29dca46ce44f5105a98abfd107f2ab07caa0a crypto/bn/asm/rsaz-3k-avx512.pl -8db2e45c5bbc01313f31f57d068a54bc6889da8e8e73250a79bf1cb65a468d46 crypto/bn/asm/rsaz-4k-avx512.pl -94b2d5cf0faf2efddeb5fb7c575dabc35c1791715cc9299d59a01d9f96cb2d6f crypto/bn/asm/rsaz-avx2.pl -c19c717d87dd1ba74f138af05c044c05f5d025e26323637f46ba54a8c871a378 crypto/bn/asm/rsaz-x86_64.pl +4bb6bc7c26ba71f79eec2a0008872316e7f8b799f4e089f7815b297fc9457c95 crypto/bn/asm/rsaz-2k-avx512.pl +d8d85a0cc27b84650a1a62cdbabcce7b00543368665f335fa03d9ddf3243fb75 crypto/bn/asm/rsaz-3k-avx512.pl +53e81fa491330f0208dcd940f806f7e573df9bbe54bb3549cc23addaf5e4f452 crypto/bn/asm/rsaz-4k-avx512.pl +d9c8e45377eff220f0eca3e830f042423ed99e92b3c900e7b6e58685f27d69c0 crypto/bn/asm/rsaz-avx2.pl +c1ec44791c60ad2a952bfbdda9246faca29548f62961f3d97a4b27809e905bac crypto/bn/asm/rsaz-x86_64.pl ae26becda9f6d30e9edde8bb89c251a0c40a9a6c879c4cdaec273d8c09af9cd6 crypto/bn/asm/s390x-gf2m.pl 2700337ef133d6688047a1a8e1c671db06016aae777679923ce2b301896762cf crypto/bn/asm/s390x-mont.pl aa02597f3dc09cfbc190aedb75711859ba0f3efff87067ebfba1ec78ebee40d7 crypto/bn/asm/s390x.S @@ -78,28 +78,28 @@ d632edf9b9bab7d2cd2d616512a98d15cf4b3ebba7a8e7b83650d654ceb52ecb crypto/bn/asm/ d444ca73875e97e0ea88b20e4c02f2fcf3850e8b9311e3b67a2d04fe2796d543 crypto/bn/asm/x86_64-gcc.c a5481ca55d94dc7ebdc93173610d38ae2569cea1fe9b5180debe0ab94e455ce1 crypto/bn/asm/x86_64-gf2m.pl d8cc080824a72774cb3343a3d50ddf8f41a5b8321203d4c9a764762b62498b96 crypto/bn/asm/x86_64-mont.pl -03788cb685268e6a50ddfa742ea1fe937570c9b86f2ebc88ee35f3304f67c045 crypto/bn/asm/x86_64-mont5.pl +8b687e927ee9261ac86ef45edc0b46bf1e97cb77694e30f83485b87c20f77cf5 crypto/bn/asm/x86_64-mont5.pl 0ea8185a037a2951bb3d1e590bbbdeac305176d5e618f3e43a04c09733a9de34 crypto/bn/bn_add.c 964c7eecef99ef56997cbb90b6560d41e0e90bb1f87dcc5e2a1bf177851c005f crypto/bn/bn_asm.c 22269bec400abc2d4b38f250134070680075aa320a1a8a2e0c4dcd33fd66cd8c crypto/bn/bn_blind.c 7b761d541e3b7f6a3f2b14a09b2b3836a079a845cf67a54db4853e3fd38277c6 crypto/bn/bn_const.c -7567a675d2b275637209ccced0fd8b47e85bb763065da87809cfc07ce3805124 crypto/bn/bn_conv.c +eee3d2710144b0e860c57e84f5adc6b2bf64fc27cbd202a8ca2630aefed3b84c crypto/bn/bn_conv.c f53d3804456b787be45ace2b33b7a323e5e4fb6cfbe3aa3b6696e3ce0a640baa crypto/bn/bn_ctx.c d94295953ab91469fe2b9da2a542b8ea11ac38551ecde8f8202b7f645c2dea16 crypto/bn/bn_dh.c 74b63a4515894592b7241fb30b91b21510beaa3d397809e3d74bc9a73e879d18 crypto/bn/bn_div.c 0b5da41b6e2d705898b949568d06920509bf16a9a74dd4de39c406b378cd61b2 crypto/bn/bn_exp.c ec2b6e3af6df473a23e7f1a8522f2554cb0eb5d34e3282458c4a66d242278434 crypto/bn/bn_exp2.c -c9f09aff5b6ba70ca966ca0a0f8f07db980487dd53abf04f52b61f37d8dcd2fb crypto/bn/bn_gcd.c -4d18c6a92631955b4b5374ecd31892459060d9c763da89a310feeea8a8b41e5b crypto/bn/bn_gf2m.c +98b2c9a4ffa3063731a10d74318a9f0b808bfa0bb9a5e1c2faca4121a2390d76 crypto/bn/bn_gcd.c +6c5c69c03d5390467aecb5344c7928f62122e47a4e0e2742af9ee1610dd233a1 crypto/bn/bn_gf2m.c 73ee247467879d4ec984c9900dfe7761233c5b889b8762be37c7e8fdd6d1d210 crypto/bn/bn_intern.c 602ed46fbfe12c899dfb7d9d99ff0dbfff96b454fce3cd02817f3e2488dd9192 crypto/bn/bn_kron.c -31e592daf19a9031b89df69fa84c85b5f9b7393c3edbc60b55cd93be469a3bb9 crypto/bn/bn_lib.c +b0b02639e782fe3a5ed41f2248ad485ccc2a2bc1132a1326b8fa204066c2aa12 crypto/bn/bn_lib.c d5beb9fbac2ff5dc3ccbdfa4d1aabca7225c778cff4e3b05b6d6c63e182637f5 crypto/bn/bn_local.h -23c47b51cbdab1a8a8e3f3504fae2ceb36c7c227e264d7f4d4fc11c1e0ecdbaf crypto/bn/bn_mod.c -7ddcb7b9b2b008d6f31783c7697d77dd3188d9f643ca948cf49a805d770c3a14 crypto/bn/bn_mont.c +929c636ccc31899f366717c1adf691d69534c2329aa79bb3edc2ad1935204ecb crypto/bn/bn_mod.c +e1fd447361388b6f1290971543149db346c9e6871ccbf54143c61a5872746bef crypto/bn/bn_mont.c 2da73a76b746a47d8cf8ec8b3e0708c2a34e810abde4b4f1241a49e7f5bb2b60 crypto/bn/bn_mpi.c 76982b18b0803d59b33168b260677e7412970757d3b9513de5c80025290f211d crypto/bn/bn_mul.c -b3677b73ac29aab660c9a549f7af154ca14347fac5cffd43b153a75211f1373f crypto/bn/bn_nist.c +6bf1d67ea493401f7765647828d3f426305fd0686cc89956c9d205922b7ab4db crypto/bn/bn_nist.c 5377e9596c3b9a3153ce75004599dce1f0fef23612d4e086cc936a87d4d5fa99 crypto/bn/bn_prime.c c56ad3073108a0de21c5820a48beae2bccdbf5aa8075ec21738878222eb9adc3 crypto/bn/bn_prime.h 4e1f3e71cdb05d41608224d1837da6f261d5f60a570be1045c10738e1e6646ff crypto/bn/bn_rand.c @@ -111,15 +111,15 @@ b5cc902624b3af2149c9ea91f9d18bea56302144e87dfe49105ec6789b73764b crypto/bn/bn_r 24e62baa56e02f2db6454e10168b7c7fa7638db9221b9acda1803d43f38f36e0 crypto/bn/bn_word.c ec684bfc01a74492150e930fe6d6cc5586be48b9674bbd7a492efa517d04c340 crypto/bn/rsaz_exp.c c4d64da1cdc732ea918fccd6a7bb2746b03365dd26f7ba1e74e08c307ca4c58e crypto/bn/rsaz_exp.h -55266c387202fd4f90bebfe7bb93c550b23b78dc3a90edcc668e5dbf480f916c crypto/bn/rsaz_exp_x2.c +b176c420308bd4a185a28e549016ffba5f72edf9dba4dacec34c9883f3ddae22 crypto/bn/rsaz_exp_x2.c 834db8ff36006e5cb53e09ca6c44290124bd23692f4341ea6563b66fcade4cea crypto/bsearch.c 82117f6a7cfc31fc86ecd9629bd3bf614126b8e8b2c23717a03ff5c1db7c3c5c crypto/buffer/buffer.c d2bfdfd96b182741d2d51f91478ffcc48491b0da44662bc1c32bc506b3eef1ba crypto/c64xpluscpuid.pl -ad82132a10f0d4e13672ebed29fc40905717fd83716d1feb7d9b8d86a2192fb6 crypto/cmac/cmac.c -d46e0b730115110a1022ebdcedaef4ecc2a58ae122d86b306712a9417bf1bd81 crypto/context.c +205f0be0317343b17003f261b427008aad1b31aacc6979c4557fc837e9548b92 crypto/cmac/cmac.c +b2b8884159b74a01af1f4fbb7299cd228072da3a009aa17247f8ce7b705e32f8 crypto/context.c 67c2367871b9350a7f7af5be903d6bcca9ebdbff0e9a9bd9f61b56bef5b76696 crypto/core_algorithm.c f0fd9eb38bf7f196bbb4d26ce8fdf86d0a4f9db219157e66b2c0ffefb4f42005 crypto/core_fetch.c -2f03908edadddc55a61e4cfb4d76751a342f61aad564971df37a6b90c7b2a26f crypto/core_namemap.c +9a281faea39e976046a27fe9fc718171580cafccc53a2aa2c3b793913c6cdb6d crypto/core_namemap.c a7f86c1495a140e5dc2acb737c5ff835691ead833842e0a37bbfc2116530b246 crypto/cpuid.c a6732e22ccb49cf51fc9dbf23f6059774b70ecc3d7e848c5df112a2d3c179027 crypto/cryptlib.c 66dbfc58916709d5a6913777346083247942a8d9458ee9b2bf443f0ea4988d64 crypto/ctype.c @@ -129,7 +129,7 @@ fea3ba4225df97aee90690adf387625b746d8edfdc5af2357ee65151a3d236ac crypto/des/des eeef5722ad56bf1af2ff71681bcc8b8525bc7077e973c98cee920ce9bcc66c81 crypto/des/ecb3_enc.c 04d4cc355200b57f1e7d265a2cebdf094df1eb6e96621b533adddc3d60d31fbe crypto/des/fcrypt_b.c 499513b3ad386fe694c4e04b3c8a9fd4c4e18fc44bb6c4f94d6bf2d9362a3a5a crypto/des/ncbc_enc.c -61926e30dd940616e80936d1c94c5f522daf0d475fb3a40a9e589e78f322901e crypto/des/set_key.c +9549901d6f0f96cd17bd76c2b6cb33fb25641707bfdb8ed34aab250c34f7f4f6 crypto/des/set_key.c 8344811b14d151f6cd40a7bc45c8f4a1106252b119c1d5e6a589a023f39b107d crypto/des/spr.h a54b1b60cf48ca89dfb3f71d299794dd6c2e462c576b0fe583d1448f819c80ea crypto/dh/dh_backend.c 24cf9462da6632c52b726041271f8a43dfb3f74414abe460d9cc9c7fd2fd2d7d crypto/dh/dh_check.c @@ -155,20 +155,20 @@ fa172e62f175a58ffa69c41476fe41d297411f1822af88ce8c9faa125fbad2d1 crypto/ec/asm/ 729729f8233c95138158f4647b33a36cf175e707ce29563db0eedc811f324ec0 crypto/ec/asm/ecp_nistz256-ppc64.pl 78a5b172f7c13ae8ac622439ffb9d99b240dbb4bbda3f5c88d1533ae74a445ad crypto/ec/asm/ecp_nistz256-sparcv9.pl 922725c4761cfa567af6ed9ecab04f2c7729ae2595f2fc0fa46dc67879dc87b0 crypto/ec/asm/ecp_nistz256-x86.pl -19ba01af58788e2873ebc1d5b503a76604bec0b9b6296fa794946e141fc945a4 crypto/ec/asm/ecp_nistz256-x86_64.pl +c429416028457285cef0c24c5d07d4804eccef29b3be4efda37e8194c3fa9eb9 crypto/ec/asm/ecp_nistz256-x86_64.pl e806141073aa3792e2748f6feeee6d3017124b3bc6059a9eca0d53a2f5785346 crypto/ec/asm/x25519-ppc64.pl a397592dc9fdb13016311db6184b4a3a4f2e198aacb03528f770f30ea4966cc4 crypto/ec/asm/x25519-x86_64.pl -5fe1cfb5bb13a1aa838453101f5a9783cd6cdd0c5f904d5372a74750ac43c302 crypto/ec/curve25519.c +d0e81e6185fd589094e06854460cce0d070cc10901ff993c36312fd58420908a crypto/ec/curve25519.c 5daf9f524cd63dd95a2136535b27f2b3d90966562ea5766f4b2d1cd4fccf2502 crypto/ec/curve448/arch_32/f_impl32.c 063dac1e4a9573c47532123e9e03e3532a7473cc3e146521ba9ec6f486ddf3b1 crypto/ec/curve448/arch_64/arch_intrinsics.h 43423b7ee85a5c740c1d81499ee06f4a17732c7731a598e7429d5e402ee77cf4 crypto/ec/curve448/arch_64/f_impl.h 75c8103fddef2b6a1b43245e7b4fa2fc8507aacc61dd8916d1a28e1c28c86623 crypto/ec/curve448/arch_64/f_impl64.c -cba11345e742cd4eedead0505f92062916ece6fa688cdbdf6466fbea12a7b16c crypto/ec/curve448/curve448.c +242421aa2568931f2d175a0cfd1ca3927fddbc31e89187417cce50ad6376a344 crypto/ec/curve448/curve448.c a6c70707c520234ccd111562f012e1abf83c43b20b3b36c339ef1ea0369a9e5f crypto/ec/curve448/curve448_local.h 178fb9863c33174b633c2e7607160b1bedb506d66cc06d53382d87431441f306 crypto/ec/curve448/curve448_tables.c f30e13bba5a136ab9ba5225c98b9b94c2cd73fb3aef60f9dcde3cd471cfa1ca4 crypto/ec/curve448/curve448utils.h 4a45e7828831fbe9f282f933cda54b12cd393ec9bffe5c0ace8e4d1c4d5d6358 crypto/ec/curve448/ed448.h -498fda3e0f2d261ab9729ae4de05ff1b496af4582aa019f507570f852d5a2726 crypto/ec/curve448/eddsa.c +de75ada19d49a0943cc1badf4b258c4d827e6c33921a1a412f9a0e37f2728d0c crypto/ec/curve448/eddsa.c 9f712e7397b10f1dc88a6d18ff38dcda13d09c02775f3682f2b8698715b1095a crypto/ec/curve448/f_generic.c 070daafb9a532ebb8bc0af8b1341254f0cd3e8932a8c8a2dca7baeef6678768b crypto/ec/curve448/field.h 514014f9fa7835056aab1e6df5511fd7de8ecef3cfcada8e0eadec9b727b419c crypto/ec/curve448/point_448.h @@ -177,37 +177,37 @@ f30e13bba5a136ab9ba5225c98b9b94c2cd73fb3aef60f9dcde3cd471cfa1ca4 crypto/ec/curv ae1637d89287c9d22a34bdc0d67f6e01262a2f8dcef9b61369dba8c334f5a80d crypto/ec/ec2_oct.c 9965a95c878438eb94bb0c21876b5a971f47b91f9d22f9c93cf7209a184cd1d1 crypto/ec/ec2_smpl.c a1f22814f501780591da20de5e724895438094824fce440fd026850c46ad8149 crypto/ec/ec_asn1.c -29783240b377e98006d21b13e984545aa296b26070fd74e77f7d75c01d2616f3 crypto/ec/ec_backend.c +805c42cf4deff93ceb8553c9d572f46e08d148a4de3ed8695a6db290b00b92f1 crypto/ec/ec_backend.c 7f19cebad4a94db291464b0d93006a87d15ccec93b94f725052a1037107a96be crypto/ec/ec_check.c -c85f4885f2892dcf074451b137efe0828e486ff5ceadae1fac9b2543fa2114a1 crypto/ec/ec_curve.c +b5d1182daa207e0f27b817801da96af15c8f13a9ceeb04fcc66b45d36f67f6aa crypto/ec/ec_curve.c 8cfd0dcfb5acbf6105691a2d5e2826dba1ff3906707bc9dd6ff9bffcc306468f crypto/ec/ec_cvt.c -f4b1f679ca6da3e54121109d4f40b0c46a2366ef48bbf17d8e769f8baaa35f5f crypto/ec/ec_key.c +993c69bdd164a54e3536f9ff1190e80f70772a626cf4b5623e73634ef39469e8 crypto/ec/ec_key.c 93f35d2e21d49bb6780d200fda8486edd4a7123956337ba535720bb547a47c4a crypto/ec/ec_kmeth.c -1829428993aa5c51c6322d7d800cb13ccd566bf1f9e38d271f618f1a2315c3c5 crypto/ec/ec_lib.c -eb2f08624819f5d5d865b954a1123a833bc18e9024980f5701125f230e6406b1 crypto/ec/ec_local.h +c4ba4261db0565be046b630782b430c3af5e0c9f0cc2c262dd08fc5a6ca8b123 crypto/ec/ec_lib.c +9f86576ca885dd5523879dfdf928c5781bd13d2dbe626a90a785d04184c7a8bc crypto/ec/ec_local.h 7417037d376a99498b3044982d72fbe07bcd2cc5b78f73c3665e87c9202af418 crypto/ec/ec_mult.c -5ad8b7c52f91416c5e93b96e1d19f6c0ba1bb8f99d1e382ac43025e8d060a278 crypto/ec/ec_oct.c +7a777b96560b44bbb9965f099ebc31ee6c8057b9778e854b0f9f3b4125f8dcda crypto/ec/ec_oct.c c7fba2f2c33f67dafa23caef8c3abd12f5336274a9a07d412b83be0366969ee6 crypto/ec/ecdh_kdf.c b86a943ae62145438a7214539ceb3e0de5a30e17a6e59742c6e30991db730ab6 crypto/ec/ecdh_ossl.c -04d29e0b631904012e7c3bd4c908c01159a0bf9731ac84f416fc827fe348e3ee crypto/ec/ecdsa_ossl.c +8515ff7e69bc5387e97de76f3663f49c4901ab942d51b36035cf3f9e9c147406 crypto/ec/ecdsa_ossl.c b6baa42b16e8df69a12e0ab101033100cddc808ec2682ba1574373e6ec86ae93 crypto/ec/ecdsa_sign.c f686cea8c8a3259d95c1e6142813d9da47b6d624c62f26c7e4a16d5607cddb35 crypto/ec/ecdsa_vrf.c 141cfc1459214555b623517a054a9e8d5e4065a11301237b7247be2c6f397a0a crypto/ec/ecp_mont.c 13b30f34aeeb0c98747239bfe91b5f0f14e91b2c1f11db62ebb5950c7219daa0 crypto/ec/ecp_nist.c -b19d2ffc6a21405c125e7831a9c1385acad8eea283f52c6b57ac6c8728233ccf crypto/ec/ecp_nistz256.c +e203f6f7b4de28394627a0fcba1e89f4291fa4f2af2a36692c0030813ec276e8 crypto/ec/ecp_nistz256.c 51cb98e7e9c241e33261589f0d74103238baaa850e333c61ff1da360e127518a crypto/ec/ecp_oct.c 9cf3bacc8a990f6dffe369c28f2f47b192c8d17178185acec601e3fee5b05fac crypto/ec/ecp_smpl.c 43f81968983e9a466b7dc9cffe64302418703f7a66adcbac4b7c4d8cb19c9af5 crypto/ec/ecx_backend.c 5ee19c357c318b2948ff5d9118a626a6207af2b2eade7d8536051d4a522668d3 crypto/ec/ecx_backend.h 72caa2b7d2a54165fb35fea5ec7f5f230a3e9746fa71d56cb345e809bfdaf0a0 crypto/ec/ecx_key.c 64d0ed4018f874f6f88f60eea7b8cc093ebd2495172132603f759445d0bf0edc crypto/evp/asymcipher.c -0e75a058dcbbb62cfe39fec6c4a85385dc1a8fce794e4278ce6cebb29763b82b crypto/evp/dh_support.c -8808a1f9caa06279e36e8e7b24fde97f64a4bc353c96248467a87b87a04fca6e crypto/evp/digest.c +80da494704c8fc54fea36e5de7100a6c2fdcc5f8c50f43ac477df5f56fa57e58 crypto/evp/dh_support.c +cc4ce4f3047faab79b646c96d68c72c61d387a89fc519e32764010cd1b077241 crypto/evp/digest.c 838277f228cd3025cf95a9cd435e5606ad1fb5d207bbb057aa29892e6a657c55 crypto/evp/ec_support.c -2a24523f7aece1a4a32919fad7d2ba3beabe7b12c80c27ccd08ea642c5e0ff32 crypto/evp/evp_enc.c +d985bf30d1cd257a9f352599fc38c35239051e45bce72077e2821fa5acd8aa25 crypto/evp/evp_enc.c 7267c75b7d96f7adb85b4b18734dd5d19e59c80b1f96b2e3e4ce112af7763c5b crypto/evp/evp_fetch.c -2712a8b23eecd5e65afe53cacc7db7e31e17307f450ad6e6ebe005884109767b crypto/evp/evp_lib.c -69801f82d74205bb61ffae86dd07c1308581c3b4d7801a29ea662f8d3b4923fe crypto/evp/evp_local.h +2a2c4dcd880386d5a7ba88d78600c57d74626d569d435628e7d7365e97629d1c crypto/evp/evp_lib.c +8b562a491e79e7638306dac3c737035ebcd288b268ba0c895b402ead739575e7 crypto/evp/evp_local.h eaaf795148c5dd99c4194d076c029c843f3aee0c37afeb0dac43a86fd931ac68 crypto/evp/evp_rand.c 2a128617ec0178e9eeacbe41d75a5530755f41ea524cd124607543cf73456a0c crypto/evp/evp_utils.c a9e940b29f3064e771eeafe9d4d0e6d1f7258cd61a57258faabdbe8121764986 crypto/evp/exchange.c @@ -215,27 +215,28 @@ a9e940b29f3064e771eeafe9d4d0e6d1f7258cd61a57258faabdbe8121764986 crypto/evp/exc 9328c7ea06e0719aaff2d59c959d1b7907b9e6a337f784680e2e289e8c3e4328 crypto/evp/kdf_meth.c c67d90f42c4d2294ecd103bdb02296a13248ead4aebadc3aead0cb964e171d81 crypto/evp/kem.c 55d141a74405415ad21789abcace9557f1d1ef54cf207e99993bf0a801f4b81e crypto/evp/keymgmt_lib.c -e67ff632bc7c6881375f7d86ba777e5cc866beeb719b245447f8cee4da7a1594 crypto/evp/keymgmt_meth.c -41f2e8d9fca78dfce6116e659fdefbdeb590cee567d5f9681eb2c028c0b5c424 crypto/evp/m_sigver.c +955480afeeb054d81ea1a540f124bc7bc20af467cc1ae4db2385a3ddcd3ae2e0 crypto/evp/keymgmt_meth.c +598d4c578a8720026a2dc09d456412c74307ec5cc7b55e4e9d2625f6ffb96c1c crypto/evp/m_sigver.c 2a1207fc3108d1aef4fc10f5d450dc344214f3cfff7a6e9688468c12846d4b64 crypto/evp/mac_lib.c 036307223518ec03a93c9e519cbad9903341bf105642b6b694a791d31a1f232c crypto/evp/mac_meth.c a93bf4ee0562235dab615562e1780c704bdf58aa62457511ae206ab1d0e2c760 crypto/evp/p_lib.c 3b4228b92eebd04616ecc3ee58684095313dd5ffd1b43cf698a7d6c202cb4622 crypto/evp/pmeth_check.c 759573aea2a4cc7b6f763b440e6868bfcfcb7ca94d812fa61ab24a194be2cb36 crypto/evp/pmeth_gn.c -7d9dfc974d15a2b7e2c1c6c54a594f0a14ccdfe5e2e1afe84a3a52130ac8097b crypto/evp/pmeth_lib.c -b16d40bcc50a0f1d23747d48c486ed4d34f11a72ee8110034f22252fc797af3e crypto/evp/signature.c +ab99a6f659635d2887fb46a641d40e9a70a4e68bf8420aeaf848d215a1c7726f crypto/evp/pmeth_lib.c +a90ae9dfbb6d0a01c99c0ca5ef4c11190f25a8c0d4c740df34cd51a3bcc3b2d0 crypto/evp/signature.c 64f7e366e681930ba10267272b87dba223b9744a01c27ba0504a4941802a580d crypto/ex_data.c d986ec74995b05ff65a68df320ab45894ba35d7be4906f8d78ca5fca294a4e6c crypto/ffc/ffc_backend.c a12af33e605315cdddd6d759e70cd9632f0f33682b9aa7103ed1ecd354fc7e55 crypto/ffc/ffc_dh.c 854378f57707e31ad02cca6eec94369f91f327288d3665713e249c12f7b13211 crypto/ffc/ffc_key_generate.c 4e973d956d4ec2087994de8e963be1a512da1441f22e6e7b9cd7ee536e3ff834 crypto/ffc/ffc_key_validate.c -b6bc7a9c2887b459d2a4e202e3ca5d637ad169e023d7353be3d4ef6082fda96b crypto/ffc/ffc_params.c -c9c635805b26d85e8c0c7720592fb04b674cde4339fcd94712a4403e8677cb41 crypto/ffc/ffc_params_generate.c +0eb367c50fb903276a2577c92a4eff210ea1ec176ba29363fd36d21fe0aa7d2f crypto/ffc/ffc_params.c +be43754acce63bfd3caf08118d67af31b6f024c9df23debba7432a220bf293a1 crypto/ffc/ffc_params_generate.c 73dac805abab36cd9df53a421221c71d06a366a4ce479fa788be777f11b47159 crypto/ffc/ffc_params_validate.c -0a4fc92e408b0562cf95c480df93a9907a318a2c92356642903a5d50ed04fd88 crypto/hmac/hmac.c -0395c1b0834f2f4a0ca1756385f4dc1a4ef6fb925b2db3743df7f57256c5166f crypto/hmac/hmac_local.h +5d1af783f1cd14c6c772ca7f6957c90930f05fe1f58abe6172d08847762a7406 crypto/hashtable/hashtable.c +7a9af0b14f1463b36de0689bc434a318adcb7990bb23862bf1d2a0adf510583a crypto/hmac/hmac.c +df7ed80c3c2c0df4bf6a3d5379655d0ba9147d4f4e9f7509672bc9273f163bb8 crypto/hmac/hmac_local.h 0e2d6129504d15ffaf5baa63158ccec0e4b6193a8275333956d8f868ef35127e crypto/ia64cpuid.S -3f123f7de496711fa60c47aeaef96640571dbcb1657b23901307e04c3d712579 crypto/initthread.c +c685813be6ad35b0861ba888670ef54aa2b399d003472698e39426de6e52db59 crypto/initthread.c 8727fbbb867fca990238ba37c17ae67e4b78a02769913425925ee841af5c0b07 crypto/lhash/lhash.c 22261096a117533e78012f5f18586b6a81edb3e09ae8b206b5eb9a0a5c054adc crypto/lhash/lhash_local.h ef9007de207b87aa260ac6fd5f7fe966e6a966bfeb1461b78841cafae0a57259 crypto/loongarch64cpuid.pl @@ -243,10 +244,10 @@ ef9007de207b87aa260ac6fd5f7fe966e6a966bfeb1461b78841cafae0a57259 crypto/loongar f866aafae928db1b439ac950dc90744a2397dfe222672fe68b3798396190c8b0 crypto/mem_clr.c 6906e197c84ae0d828748d47c47d565fd912076c35a65ea304e306fee4a17157 crypto/modes/asm/aes-gcm-armv8-unroll8_64.pl 2c97a18aad5f681876dbd77f0a0ed20d86fc22060592cbda1fc0449fdf329724 crypto/modes/asm/aes-gcm-armv8_64.pl -efba3c8944a19993565989e33d8758f32f18ac484305e5b8f2a40c8734057389 crypto/modes/asm/aes-gcm-avx512.pl +6b98d90b233d87f4d99f54a553b242199cd621f9c09b5cf64923831cd98ba054 crypto/modes/asm/aes-gcm-avx512.pl b878b589b9c74bddac990f9f98fe323d3cbe0dfb5634d92224812d18ecca3f23 crypto/modes/asm/aes-gcm-ppc.pl b7104ee749d555127a08609c7df5056b56d9aee19c90f3c42b42d69cf7caba03 crypto/modes/asm/aes-gcm-riscv64-zvkb-zvkg-zvkned.pl -e482f02932d77d61142548ca4f3c8d5709d88ec14ab84723d82331444c0f57da crypto/modes/asm/aesni-gcm-x86_64.pl +cf349eb3f35090d8114770ce32577bfa34af0f8b25ba47e28584b47a4c8c4552 crypto/modes/asm/aesni-gcm-x86_64.pl 8fdcb4313fa3a6e541a697525856b9527a06ddf4c794f9393e843f86d67f543c crypto/modes/asm/ghash-alpha.pl ace8c376b394439301cecaf468d2a9a8adae21eff1d43191cefbf6765023452d crypto/modes/asm/ghash-armv4.pl c22f4945e7de3bd7bfef73447f09983e40a3e4dd0938244d902a1c44c98a8467 crypto/modes/asm/ghash-c64xplus.pl @@ -258,27 +259,27 @@ b353c76f30ed3bcde79e1280a53acbd7172d1924124c33bf2fd5830396e7ac0f crypto/modes/a 4bb81f297f0c76762116895295fe027fb1b22ddb5b992c216128116afd09db77 crypto/modes/asm/ghash-s390x.pl de97107e0c19ff9dd4069f0761eccb00e0b3ced345e1f119ab3b918dd2f9c5f6 crypto/modes/asm/ghash-sparcv9.pl 26f55a57e77f774d17dfba93d757f78edfa3a03f68a71ffa37ccf3bfc468b1e2 crypto/modes/asm/ghash-x86.pl -2a0d23a644083e46745c7cb1ca79de393af9336a2e8eab7c85ffeb3b7b1a286f crypto/modes/asm/ghash-x86_64.pl +efa4769b6e84ef2b24830226f755b64d3d5f89ff3a9faf78a2007932cc61fc45 crypto/modes/asm/ghash-x86_64.pl b407d9fc6ea65fe1a05edc2d139298d78391f3c165314fa6d56dd375b8e453cd crypto/modes/asm/ghashp8-ppc.pl 3643d2ec821a959ad79bd41b82fe6d56d32264c972b34544ded519029c948f5d crypto/modes/asm/ghashv8-armx.pl 65112dfe63cd59487e7bdb1706b44acfcf48ecede12cc3ae51daa5b661f41f06 crypto/modes/cbc128.c 1611e73dc1e01b5c2201f51756a7405b7673aa0bb872e2957d1ec80c3530486f crypto/modes/ccm128.c d8c2f256532a4b94db6d03aea5cb609cccc938069f644b2fc77c5015648d148d crypto/modes/cfb128.c af1c034152d82b29cb7c938c8516cfd136b62bac0908c1d40eb50790d23b288c crypto/modes/ctr128.c -8973e8554af39f9c5c0b28e59c1fd65ca7e158841f348ceb7b6884bcbf179b81 crypto/modes/gcm128.c +d4ddb087eb4dd54b8e37a414e32d8a2d4e42a7cf2766fc2051e4e31acdf3419c crypto/modes/gcm128.c bdf25257b15eca206be4d950d2dd807ca5f058f91f54edbd7a0d312ed83eef8e crypto/modes/ofb128.c e55a816c356b2d526bc6e40c8b81afa02576e4d44c7d7b6bbe444fb8b01aad41 crypto/modes/wrap128.c 608a04f387be2a509b4d4ad414b7015ab833e56b85020e692e193160f36883a2 crypto/modes/xts128.c fb874ea18e9754dde11ef1c2993818074ff7cd8a74a981598745f7e11317bb91 crypto/modes/xts128gb.c -28f3e418a5b64dc1e2860019155d7a1f275e78eae330b5ca7d909e860d63bac8 crypto/o_str.c +f867b6de6ac34a6aa5e2438f3d74506bfe808d3ed74217a40e61890230b32f5d crypto/o_str.c b0decda3aae1d3e07cf3cbe9153cdde9deafe65fae346cd208951b4d7dec512e crypto/packet.c 05563d44cb345e7859093296f95a3ea5139fcc316e98fcb86c6748ee49363a84 crypto/param_build.c cae7bd4973d36edbdc3bdd8d2c8d157f2c4fcfae00fdf821b67aebb789bc8aa6 crypto/param_build_set.c f6c684b42fd1fade17c46599068a43701fe447c60d789908b3af3519c4fcf084 crypto/params.c bb7b79b5a070050f5e7dfc66b5635f0891bc278e3e24eec3583b769b33bef657 crypto/params_dup.c da23f7014a60e3e37640b9128d57d8350b17fa8cde77b6f14d0d4ca0dee2b437 crypto/params_from_text.c -e3cc1fcbf42ed19a38fb0f84cb41795c94438768f36fda6f371d1f17d7b45740 crypto/params_idx.c -c27b8c1659274be74e2d6e9fd76980df499d1331c0c2d51f41b3ad547ba88d59 crypto/ppccap.c +a9e5ed6e15785156cb99d23c388b4f385e08c488158188528c1c9743f594279b crypto/params_idx.c +9620a96eb5e411f5c96c210fb7975afe6b24635e4c5565be34fb8d10589890e7 crypto/ppccap.c b650e7e96b8faad750842b86905032db51e17880958bb8d9826d02ca8eb60642 crypto/ppccpuid.pl 467c416422ecf61e3b713c5eb259fdbcb4aa73ae8dee61804d0b85cfd3fff4f7 crypto/property/defn_cache.c d48ce9b38720b4d0b118b83322c3344afd11a5ce6b31adf59c6584b5e02e3f6a crypto/property/property.c @@ -289,33 +290,33 @@ a7cefda6a117550e2c76e0f307565ce1e11640b11ba10c80e469a837fd1212a3 crypto/propert 5844196864db30e773fe555a679435614f5d6a6d22442c54fa10dea4c87628bd crypto/provider_core.c d0af10d4091b2032aac1b7db80f8c2e14fa7176592716b25b9437ab6b53c0a89 crypto/provider_local.h 5ba2e1c74ddcd0453d02e32612299d1eef18eff8493a7606c15d0dc3738ad1d9 crypto/provider_predefined.c -d2851ce0930b36e6f1fbc593a756d9a7c8097eb6b0ace163cecd917c8e9637dd crypto/rand/rand_lib.c +1d0941739c0ff41563da1891c8bb11e60acf2c7843fc182092b1cd8b5bd7b219 crypto/rand/rand_lib.c fd03b9bb2c23470fa40880ed3bf9847bb17d50592101a78c0ad7a0f121209788 crypto/rand/rand_local.h 426ba915ca65a770f8264129f8ac47db7aaf06c6ae51517c5d775eacdf91b9f6 crypto/rcu_internal.h d3fe26daee8945c5b5996fd45e96d1d2ddf9d157a87759f1c17699dc85abd2e4 crypto/riscv32cpuid.pl 54405cc169591c013db41171e922fd03c4616d63454e79761dd2912c65845aee crypto/riscv64cpuid.pl -8b2bcf4a6ad1736424f882fe016a74bcce3f3310b5d70c1d284a10dfd793e476 crypto/riscvcap.c +4b5ab38fa0a41cfaf331dafd13a1f6df5b82fcfe1d27c18b419ea20a1f292685 crypto/riscvcap.c f0c8792a99132e0b9c027cfa7370f45594a115934cdc9e8f23bdd64abecaf7fd crypto/rsa/rsa_acvp_test_params.c -4409152474e1093be4d9c7685972d7ebe8c61ffdff11b78de47bd9889741daf8 crypto/rsa/rsa_backend.c +1b828f428f0e78b591378f7b780164c4574620c68f9097de041cbd576f811bf6 crypto/rsa/rsa_backend.c 38a102cd1da1f6ca5a46e6a22f018237964336274385f5c70cbedcaa6997647e crypto/rsa/rsa_chk.c e762c599b17d5c89f4b1c9eb7d0ca1f04a95d815c86a3e72c30b231ce57fb199 crypto/rsa/rsa_crpt.c -1b6109a48d2915310efba016cd7f7fdf40c88f61717e938e71fe41adc270ba46 crypto/rsa/rsa_gen.c -deb8257e5ba1e3cdd46e9289b3be671b31e3744a26a9e37bc77aead5de9f7b50 crypto/rsa/rsa_lib.c +a3d20f27ae3cb41af5b62febd0bb19025e59d401b136306d570cdba103b15542 crypto/rsa/rsa_gen.c +b05eb77c0715e7b77ea4b72955384bcb4f25f0aa1720537541ca993785d3aca7 crypto/rsa/rsa_lib.c 5ae8edaf654645996385fbd420ef73030762fc146bf41deb5294d6d83e257a16 crypto/rsa/rsa_local.h cf0b75cd54b61b9b9a290ef18d0ddce9fb26a029a54eb3f720d9b25188440f00 crypto/rsa/rsa_mp_names.c 5c60f6e05db82e13178d805deb1947b8eee4a905e6e77523d3b288da70a46bb5 crypto/rsa/rsa_none.c -59fca779f9a9d68d40582654ab264000ef1abaf2fbad96424448f8c22db0f2e0 crypto/rsa/rsa_oaep.c -6adc9202558e531f4d78c75920882e916be27395dca386044a91adae5b331c64 crypto/rsa/rsa_ossl.c +cf7e95467a6e6681069ba0c6a0befeb631b499d9b2ab12db0e93967746686f11 crypto/rsa/rsa_oaep.c +752f35ccaea51eaee693c5b08e8e9909a978d8e79f71dda0b33b3ef72554f6e0 crypto/rsa/rsa_ossl.c 54446a41065d85d22ed521285196bf285427a071d32d00d070b2248723c2a914 crypto/rsa/rsa_pk1.c -cdf66a4964152e16b7da5b6631f31bd2d90bf730b5a46c2622d5279abdecabe1 crypto/rsa/rsa_pss.c +b0fbf0b55d2afac9b1a1e871bf8cc6f0a41b34cf695c393d97e716536928931a crypto/rsa/rsa_pss.c bf6d300b7e7e9e512a47c5bd1f8713806ae3033a140d83dfae4a16ad58d11170 crypto/rsa/rsa_schemes.c 58db0509f34d970a2f206d468f718c17513970315d5d5ec92822fe6f4b6523fa crypto/rsa/rsa_sign.c 83529424639f77832d2c189c0134ce514b35a296567ac1a2936a9c4ed6407239 crypto/rsa/rsa_sp800_56b_check.c -74cdef59c442939d53cde124d43a7f170d7934e4db621f899fbea66d051508f1 crypto/rsa/rsa_sp800_56b_gen.c +dc0af42319118811e1fa250f1647634f510f9ffcd720ea5141db4fd090938c46 crypto/rsa/rsa_sp800_56b_gen.c 1c1c2aeeb18bf1d69e8f134315b7e50d8f43d30eb1aa5bf42983eec9136a2fdc crypto/rsa/rsa_x931.c 4bf7f5cbbf7bf0e6c904b8c4988d077842cdd6aed0ad184cbfa4d4b3bfee79af crypto/s390xcap.c -370d98549d4d98e04b60677b319b85904259359bd9401dd5385aa728278e6626 crypto/s390xcpuid.pl -465f850c3d6f2e9410f2e1ee9604b1b5b80f99bae1f6c581161c2f7ebc2c6e41 crypto/self_test_core.c +afe52ea4952a5114e3a475b6c25e692562b68fa7b0af0f089f707679b95b7c4e crypto/s390xcpuid.pl +c865dba12debe9ad4a0f0b8c078b5c3e614c83a851cf9666cd3c4c7a9992f319 crypto/self_test_core.c 79bdaf53182dad94aadc33b0474a25f95e432f3d03565d861410227c2f016ea9 crypto/sha/asm/keccak1600-armv4.pl bdb63514b1a53015f323138060328622f3ee22b4425f24d3f464f7dd54fae701 crypto/sha/asm/keccak1600-armv8.pl 81bfb4484d68a3a3e1d704855f76356090867fe10a75db7707b6f7364e8ee8da crypto/sha/asm/keccak1600-avx2.pl @@ -325,7 +326,7 @@ b7bb35d51d439abbf3810454ccb9bfb5a51e2111eaf389fb95796ad6220a61a0 crypto/sha/asm 09fc831dd39bd90a701e9b16d9e9987cc215252a22e1e0355f5da6c495fca35a crypto/sha/asm/keccak1600-mmx.pl 8437a690f972bbbf873da6485c119fad84f3f47677f53c9411204ff7443cc6c4 crypto/sha/asm/keccak1600-ppc64.pl 07b55370141200b9b765a3e6f118d85bb278838087198cc07c57f0121aba46c4 crypto/sha/asm/keccak1600-s390x.pl -2173ecb1b0d40e181d58818eca4f000518fbe0069baa45985754ff10fa3ba905 crypto/sha/asm/keccak1600-x86_64.pl +04faf495408a1ec2979fb7a584748e58deaa921df7675603dcece72f777ad0ee crypto/sha/asm/keccak1600-x86_64.pl e0a4a1df82716053a3f01ec0b096c735a0e3c4f6c9d9ec6b2006b37aaac64448 crypto/sha/asm/keccak1600p8-ppc.pl 75d832db9bf0e98e7a5c522169060a6dd276c5118cfb297fc3f1111f55cd4007 crypto/sha/asm/sha1-586.pl 8d937771993f04407f5fdcca8ca8565f9f8a4d9c9a8f7bfd4e9f9121dd0450bb crypto/sha/asm/sha1-alpha.pl @@ -333,7 +334,7 @@ e0a4a1df82716053a3f01ec0b096c735a0e3c4f6c9d9ec6b2006b37aaac64448 crypto/sha/asm 083ab18f3753fe886b188328eae183f24a2ef5cfc929dc3a53c24410d91ca052 crypto/sha/asm/sha1-armv8.pl c36f51761e7f59bdd0f61230297fb802542ac5d2d1c6d2b1096ed937131bd583 crypto/sha/asm/sha1-c64xplus.pl 4ab7c9153b085274a579b388ddff97a4ac7e11585e01811ca95b93a3ec786605 crypto/sha/asm/sha1-ia64.pl -7a392c5ef7dc19c39d67c7080e0c5214e7a80572c85c022be7e7d4378a5f740d crypto/sha/asm/sha1-mb-x86_64.pl +48224a83c51bb7728af7ed5c83aa2aae502c1750cf84522d3d18b314f9b06be8 crypto/sha/asm/sha1-mb-x86_64.pl c0fea5a0d32001263c8bcf7fc0757aa68c6a7377f20fef8d28708e1b81de5dec crypto/sha/asm/sha1-mips.pl f11b75a54c5f42aa3a052de8091bfba47d7cac01920b2fe0ddcb637d4c9d0eb9 crypto/sha/asm/sha1-parisc.pl d46ef3fc166271a83144d90985034e2c514bd1020b84ec0fe5427ad593bfeb74 crypto/sha/asm/sha1-ppc.pl @@ -341,11 +342,11 @@ a48c7d9403fe99fbd4daec60e96eb22058da766ab9e606d084a63613962851a2 crypto/sha/asm 0e2951e0574c64ee055ffddf16ceefdec00823107d60362976605f139ad8ae68 crypto/sha/asm/sha1-sparcv9.pl 5da48400d4fae85e205e95a2fa368e7bf525e51e274b1dd680dfb48645426c85 crypto/sha/asm/sha1-sparcv9a.pl 04b73c902d36c28b5a7eab47cb85f743eb9c648ed5936f64f655524a1010a1b5 crypto/sha/asm/sha1-thumb.pl -f36d7ec7464c932230585a754b91f13cea4cde5a381fc9f798d959256d07910e crypto/sha/asm/sha1-x86_64.pl +ddd4825dcacd84f6d731a2bd416a4110df08a03a9e86f2e82215ffea0df1d92c crypto/sha/asm/sha1-x86_64.pl c099059ef107f548ea2c2bab64a4eb8c277070ce6d74c4d32bb9808dc19c5fa3 crypto/sha/asm/sha256-586.pl 8bfdb28ef338f981fffa5957a7867ce2408680d71a4c6e975eeb85970579d6a8 crypto/sha/asm/sha256-armv4.pl c394bb5b0ff05595a9e6848b6602a0f29f73a79fc006593740f3ca645ad9d316 crypto/sha/asm/sha256-c64xplus.pl -f33af8e2e2f57b7b63b8c8b35722d7d11ca6ef1f73fb6c4ccebdd3e86912f4b1 crypto/sha/asm/sha256-mb-x86_64.pl +2c56cb60a8543fc5e5dbc738c4228169e549eb7bfe226a568cca08343d1f1533 crypto/sha/asm/sha256-mb-x86_64.pl 84531dcee8cd2e48c126141cc43345edec1a8f14e182b73425ced281a51cd141 crypto/sha/asm/sha256-riscv64-zvkb-zvknha_or_zvknhb.pl dd82e1311703abb019975fc7b61fb87d67e1ed916dddd065aced051e851114b9 crypto/sha/asm/sha512-586.pl 101659eaade9a3162ecc0257c271b9c05411318fc45b02445ec3ace5f6bf28d0 crypto/sha/asm/sha512-armv4.pl @@ -358,12 +359,12 @@ e8df660671ba61aa2e8f51358baf5d8ca913093e2ee1a40c9cb46d9c2c0851f6 crypto/sha/asm 9806a5caa570eaefc8ce62af470126ef99c01c078af3c22871a9ca1da2006686 crypto/sha/asm/sha512-riscv64-zvkb-zvknhb.pl 193a0ea240264b29dd68a425f604a6da4b18e28838dcf909dd7e711af880f782 crypto/sha/asm/sha512-s390x.pl dcb466a1e5938fb64ecb38b0533602192d61334da864ee8dfdcfa12d3cdfa273 crypto/sha/asm/sha512-sparcv9.pl -bb6503967a58b767a3e73441cfabc77f15c8ac747f377e276d4aa63d05f2c3c4 crypto/sha/asm/sha512-x86_64.pl +71198504332a27988f6e5c9627964a838d0220f69717b0ec60d0b6eeaa14669d crypto/sha/asm/sha512-x86_64.pl 68d2f3b2dccb978ee42640f4fb4d2eae6b74d071017a3eedd9e7cb77762817dc crypto/sha/asm/sha512p8-ppc.pl -c3b9d4507b8e1ce8376f1423a7908333ef23007f646f506036387ac0b792df6d crypto/sha/keccak1600.c +e10cd2ff1fb57f3a3b5a9264878910627de989284ed4f78483e5863285f7f26e crypto/sha/keccak1600.c 306cacd3f86e5cacaca74c58ef862516515e5c0cafaff48636d537fd84f1c2fb crypto/sha/sha1dgst.c 65ca7d67f3e3fc0314ccb179b734530bf1cdbde3d3cf428adc4c402f52e4b394 crypto/sha/sha256.c -6999a480671f1b4c9dd1a802a231815673d30e7a4e0e2de14ef45e896818c9a5 crypto/sha/sha3.c +ac714ce14a0b1fe1c0cb5fea9e0e76a188048649c43f3b3a527945ab8554cba4 crypto/sha/sha3.c aef204d50f96b636576d8a52f8858fb5a4b2eb14bb60ebc14eb533df7a210e33 crypto/sha/sha512.c 6c6f0e6069ac98e407a5810b84deace2d1396d252c584703bcd154d1a015c3ea crypto/sha/sha_local.h 9ef5a01caccc2eb15f72e367d0424737040ac8018479bbbbce3d216c655765c2 crypto/sparccpuid.S @@ -377,19 +378,20 @@ e298c753be277ad9a2ac0132d9897cb4c85607dbb2d11cfefd0c98e0f6a723d9 crypto/thread/ a00e16963e1e2a0126c6a8e62da8a14f98de9736027654c925925dadd0ca3cc1 crypto/thread/arch/thread_win.c 27ec0090f4243c96e4fbe1babfd4320c2a16615ffa368275433217d50a1ef76c crypto/thread/internal.c 67ba8d87fbbb7c9a9e438018e7ecfd1cedd4d00224be05755580d044f5f1317a crypto/threads_lib.c -245ebf04d6814f020b2cf0922e1083704d736d4788998e2d17b0e26a8098a7bf crypto/threads_none.c -6f6916daa171f96c513aca4965b6f94cd2009310a6edbee876475e8c7a99197b crypto/threads_pthread.c -90d223ad2c0cb3c756ac11758c9e3873e77ae862fc9f6cf4101d044587074345 crypto/threads_win.c +8344c928af055f38a0627796aa8dd71db87c5a0fb03f18c7b1ca20e3df22e4ae crypto/threads_none.c +cc4186b419118dc42d0ba044c126c83f328dd60fa084e6e211c8da84c16b1bd6 crypto/threads_pthread.c +e1c801bcf235eca9dd5d960ee098822754b4850910f95b85f223d4e03c965ec6 crypto/threads_win.c 8b45f948303045d8f753858b1b892e3da13bebe1bdac500db91fbb54a0ac07da crypto/time.c af0af59fe2cb8668a96751f343232d7faa3e7a937beb2bda09ed74fe60b9cb5f crypto/x86_64cpuid.pl bbec287bb9bf35379885f8f8998b7fd9e8fc22efee9e1b299109af0f33a7ee16 crypto/x86cpuid.pl 56912aa7bfb1aba71fdb5b590a60593d604ddec007fd7820cdf176ec07d2694d include/crypto/aes_platform.h -68f6c521b1dbfacb99d75cb1ffdbcd1795d6e0157df69c6c6a7c04f85ea715ec include/crypto/asn1.h +44222ee3dbcc71acf0fc40fcb5f700d307eb843b3d456e11d04539d9613e920b include/crypto/asn1.h 8c6f308c1ca774e6127e325c3b80511dbcdc99631f032694d8db53a5c02364ee include/crypto/asn1_dsa.h -bb5c7bfddfa81db40a8b078cbb9eff9ca6c3767232489accbaa5dc0c9a203f2f include/crypto/bn.h +27915b72146dba69906c5727eab174e01c2edc3c74526a57b45d4ddf49b5adb7 include/crypto/bn.h 1c46818354d42bd1b1c4e5fdae9e019814936e775fd8c918ca49959c2a6416df include/crypto/bn_conf.h.in 7a43a4898fcc8446065e6c99249bcc14e475716e8c1d40d50408c0ab179520e6 include/crypto/bn_dh.h -a6957475e4c7ae80c06537c3fd3b63f2368b664da54a96befd0a6fa38de27b4a include/crypto/context.h +76cec717df68b4cbe33cf6fb557c9724ab027a1ab5e06b27eb0294fef2edd75b include/crypto/cmac.h +66d6f120bef9ff1bb33867a1071a315528a616c0ae0c64fa88d70710cccb8b5b include/crypto/context.h e69b2b20fb415e24b970941c84a62b752b5d0175bc68126e467f7cc970495504 include/crypto/cryptlib.h 6c72cfa9e59d276c1debcfd36a0aff277539b43d2272267147fad4165d72747c include/crypto/ctype.h 09a27585de4638577b482ec9102a0e70d843dee6297a2d45e27d888f6de5e27f include/crypto/decoder.h @@ -397,23 +399,23 @@ e69b2b20fb415e24b970941c84a62b752b5d0175bc68126e467f7cc970495504 include/crypto daf508bb7ed5783f1c8c622f0c230e179244dd3f584e1223a19ab95930fbcb4f include/crypto/dh.h 679f6e52d9becdf51fde1649478083d18fa4f5a6ece21eeb1decf70f739f49d5 include/crypto/dsa.h c7aafee54cc3ace0c563f15aa5af2cdce13e2cfc4f9a9a133952825fb7c8faf5 include/crypto/ec.h -2d8cba492193c170d1f759508556188a568cabe5960020b9a889b69838adbfa4 include/crypto/ecx.h -0b55a5801dd3ce5f9ea27c7bc49a4685cc574410d67a9c49e27a217257123981 include/crypto/evp.h +adf369f3c9392e9f2dec5a87f61ac9e48160f4a763dae51d4ad5306c4ca4e226 include/crypto/ecx.h +53d99b70ff09f5105f5e8077741811e32710abb720247a3fdc96d4a0361afb12 include/crypto/evp.h bbe5e52d84e65449a13e42cd2d6adce59b8ed6e73d6950917aa77dc1f3f5dff6 include/crypto/lhash.h 906bc2316e4f4651e5db7a8273ec3bb4bcbfb55f0f484bebdae4f6d0ce033bdf include/crypto/md32_common.h 6e7762e7fb63f56d25b24f70209f4dc834c59a87f74467531ec81646f565dbe3 include/crypto/modes.h 920bc48a4dad3712bdcef188c0ce8e8a8304e0ce332b54843bab366fc5eab472 include/crypto/rand.h 90930fc8788d6e04e57829346e0405293ac7a678c3cef23d0692c742e9586d09 include/crypto/rand_pool.h -cb59783c25ffecb35aaff5548f5d97a26ad463ae491eb3932adb512626f85681 include/crypto/rsa.h +6f16685ffbc97dc2ac1240bfddf4bbac2dd1ad83fff6da91aee6f3f64c6ee8ff include/crypto/rsa.h 32f0149ab1d82fddbdfbbc44e3078b4a4cc6936d35187e0f8d02cc0bc19f2401 include/crypto/security_bits.h 80338f3865b7c74aab343879432a6399507b834e2f55dd0e9ee7a5eeba11242a include/crypto/sha.h 7676b02824b2d68df6bddeb251e9b8a8fa2e35a95dad9a7ebeca53f9ab8d2dad include/crypto/sparse_array.h 7ad02c7de77304c3b298deeb038ab2550cf8b2bce03021994477c6c43dbcf86e include/crypto/types.h 27d13538d9303b1c2f0b2ce9b6d376097ce7661354fbefbde24b7ef07206ea45 include/internal/bio.h -53ec45b4f165adf271b528fc08da0832e2f82d9e13a338cc3ad78e925147c7cc include/internal/common.h -8e984890c7c62cdd6356963f034831831f7167c65096cb4d23bc765d84d2c598 include/internal/constant_time.h +a8cb407a10e50b1168412bd6ed6af9552cac1326d28c35f91152c48edc42dc3f include/internal/common.h +b0c37f3c6d1262ebfe2c15e6aa7e9bee34c81ba4e9dc225f02fa27018a9017bb include/internal/constant_time.h c5bb97f654984130c8b44c09a52395bce0b22985d5dbc9c4d9377d86283f11f8 include/internal/core.h -36e5c3ea8e285d0df80a136d26c05df0de521c017ba0e50873e3bcfdb612bd99 include/internal/cryptlib.h +6f2bd96f2acd0e02575c9cbef55752be16b3c9e53bf8bac0b4d464ffb3332a3f include/internal/cryptlib.h 9571cfd3d5666749084b354a6d65adee443deeb5713a58c098c7b03bc69dbc63 include/internal/deprecated.h dc5afb955d810feb5af9f8d25cd8a92118abef320fee95c07b04f301c4e0d96c include/internal/der.h 8059e715f981fbe02b5731610ed24bb6ae617a55e90b03f4260cbb6ccd71e8de include/internal/deterministic_nonce.h @@ -422,7 +424,8 @@ f144daebef828a5bd4416466257a50f06b894e0ce0adf1601aa381f34f25a9e7 include/intern 45036710f2499cdf6b786a9dce29dfe6d2ae06ea8e3d5cb2a782f64ed85d267e include/internal/e_os.h 70d3e0d5a1bd8db58dcc57bea4d1c3ed816c735fe0e6b2f4b07073712d2dc5ef include/internal/endian.h 4838a68ff626825c261df6a1fd21e156e25d8365af45552f29054d7038a7db3d include/internal/ffc.h -55c4102496ed5ab16de11afe38c328a1396c3b6e2c7e44add4a38855103c19da include/internal/namemap.h +65ebab34df54f19832bbda6b9e71c28b985196bdaef64776d5662c32c0be8a98 include/internal/hashtable.h +f6f30785e3eced1ccdd4b149286ff2b8bbb860eb7e070cbe54c997aa022854da include/internal/namemap.h b02701592960eb4608bb83b297eed90184004828c7fc03ea81568062f347623d include/internal/nelem.h 3363405b2d6afab68f7e13921385ccb648fe7f77522bd0aa5fdf2d7af0b87660 include/internal/numbers.h 66f7c420e531383e8a93c1daccbdc4ab64d11e0ed167af1b7f7be54bd61329aa include/internal/packet.h @@ -435,7 +438,7 @@ d4ac19b28ea61f03383364cfad1e941cac44fc36787d80882c5b76ecc9d34e29 include/intern 95d21e761402fcbf1d3bdb261e425316b07d2790dd190e4eeaa1e21e40ff9a59 include/internal/rcu.h 6771d6b154f3979903c4e53c0249bc0e709ce698966761bc60081428270eafa5 include/internal/refcount.h 5f48b2caa1986f85fc31d1f96621684736c27964291b3718dd35f3a15534fa99 include/internal/safe_math.h -c422f38eca312a2f97a0cc91891185a14f812247dfea8abd66f68540870b0429 include/internal/sha3.h +d11b69bed0965e47c3be0e0f44a812a7eb69ae91d7ca8f148a91d6ef6d255a47 include/internal/sha3.h 494ab5c802716bf38032986674fb094dde927a21752fe395d82e6044d81801d1 include/internal/sizes.h abf03dc8635f2925bdc2299feabe115f8d5d6eaa450b421172ded222872386ba include/internal/ssl3_cbc.h 24f41a1985fa305833c3f58030c494d2563d15fc922cdf3eeb6a7ea8c135a880 include/internal/symhacks.h @@ -444,6 +447,7 @@ abf03dc8635f2925bdc2299feabe115f8d5d6eaa450b421172ded222872386ba include/intern 640cc6a2aae208073a7f495c08b4c5006a69e8ac1c2d9aaaafd56b0e74d5f859 include/internal/thread_once.h 300fd75e47ace860d006db0050683553417701ead2106c4b5bc6a31745099155 include/internal/time.h ef96b731db0e0998c11a297d601f5b37c02525774d532fb4f92160e9069c7dfc include/internal/tlsgroups.h +0b41d6646786c16083fa071b788dd9fec0da1c8f715a7e2ad3a05d77520b162d include/internal/to_hex.h 7d97636320f6ce993ff6ff15741b90323a32fbeea4960fa64be2eb147063a149 include/internal/tsan_assist.h 2b38fb6e65d549aca3b2c76907daf67124f395251c0261dec26faa54da8d6d73 include/openssl/aes.h 47fd81a330f042baf3675f4154c6276ab7a8cf76efaf01288abe41f119ec5588 include/openssl/asn1.h.in @@ -461,10 +465,10 @@ bb45de4eafdd89c14096e9af9b0aee12b09adcee43b9313a3a373294dec99142 include/openss 69d98c5230b1c2a1b70c3e6b244fcfd8460a80ebf548542ea43bb1a57fe6cf57 include/openssl/configuration.h.in 6b3810dac6c9d6f5ee36a10ad6d895a5e4553afdfb9641ce9b7dc5db7eef30b7 include/openssl/conftypes.h 28c6f0ede39c821dcf4abeeb4e41972038ebb3e3c9d0a43ffdf28edb559470e1 include/openssl/core.h -b40a869b35c4ee64bb167b673c8cf435ece3612439f4c4424bea74afa1326922 include/openssl/core_dispatch.h +bf8bc83dfab4652e8c4b0edaa520c6fc61d38bdc4ba8609779a2998bdca4bad5 include/openssl/core_dispatch.h 8b4027cf19ce2a7cbad506cde61552123818b6eae62d5fbdae34e9f68660e6f8 include/openssl/core_names.h.in -371413ef13841f1245a225c8ec1cec463629c42bfc33254f979d2a8672112f9a include/openssl/crypto.h.in -2f9570c2514b4d1b2a86fbdf30ced879e5c52e62f1d3691cb3da37ce4f6a98dd include/openssl/cryptoerr.h +48942627f6cc4b5ffcb59948a20cd09b06827f835c84a7d898c771f70dfb1ee6 include/openssl/crypto.h.in +628e2a9e67412e2903ecb75efb27b262db1f266b805c07ece6b85bf7ffa19dac include/openssl/cryptoerr.h bbc82260cbcadd406091f39b9e3b5ea63146d9a4822623ead16fa12c43ab9fc6 include/openssl/cryptoerr_legacy.h 83af275af84cf88c4e420030a9ea07c38d1887009c8f471874ed1458a4b1cda7 include/openssl/decoder.h 503b45367b035ddf6e54587125c2100ceec324d646e6f3df92c12513185e977c include/openssl/decodererr.h @@ -473,46 +477,53 @@ fa3e6b6c2e6222424b9cd7005e3c5499a2334c831cd5d6a29256ce945be8cb1d include/openss b74a54335bb2f55caacd5c3fd10db3575166fc35077dc5740059243f70e0b179 include/openssl/dherr.h 3cfb7211419c5dcc98b9a20713e2245befa0182a10615edb89a5ce0a0725a787 include/openssl/dsa.h 276d1f6e111ba933bc708e6a0670047cbe0d0b67aabe31807abbbc231de4d8cf include/openssl/dsaerr.h -9dd6f71572098501790b79959f5215ad4458c3e88fd4fd1b1cd00e0788306de7 include/openssl/e_os2.h +25bcf84a034502eaa16354c61bb9a2f2f3d607b2f343bbe7fa1f1e810a353db0 include/openssl/e_os2.h bc9ec2be442a4f49980ba2c63c8f0da701de1f6e23d7db35d781658f833dd7b9 include/openssl/ebcdic.h 49e8a9d226d543ac482cecdc01c83b7ccdfbfca6ad92d690aad75a245148e2ab include/openssl/ec.h 7aa8c5bee779af59d4733f6a50f7f6be39f1eb43409e5b3357440f9a7d0ca115 include/openssl/ecerr.h 61c76ee3f12ed0e42503a56421ca00f1cb9a0f4caa5f9c4421c374bcd45917d7 include/openssl/encoder.h 69dd983f45b8ccd551f084796519446552963a18c52b70470d978b597c81b2dc include/openssl/encodererr.h aa02455482d744418123266f581b9b4310ba678c7d28c10fffc5eec74ce3c8ef include/openssl/err.h.in -61a6fffa77d7482bae2096996ab48b9f399c144083b1629ba2500259f87e35fc include/openssl/evp.h -a5e2027d1154dfae857c34e846a79aa99576bcb261341ec3c2ced73ac28c2aba include/openssl/evperr.h -3085bc5a77ea3776619bf9c748632a3a23f1d8dcad5239ba0f48939f375fb0e8 include/openssl/fips_names.h -b1d41beba560a41383f899a361b786e04f889106fb5960ec831b0af7996c9783 include/openssl/fipskey.h.in +88d16e8c0de59a8f9b9834dfb88c53675e3c43ba22aca43c9886930c18f5375e include/openssl/evp.h +2d19db80d47e09798661791b5808b0f3a1b260d23a2b8b224634ac10475adf0a include/openssl/evperr.h +f37c13a7cc0b05a734efcafb7da321dcc366090c255da8ee532e5f2be2eaa152 include/openssl/fips_names.h +fef2b79b4de2cd74b02f12f1c0515cb2eaca742b8ded67fce722fb417e818e25 include/openssl/fipskey.h.in 47a088c98ad536ea99f2c6a9333e372507cb61b9bdffb930c586ed52f8f261eb include/openssl/hmac.h +1ed24e4fc0c5a6cc97a42fdb05928e7a2ead969388444675419fe73551ad8135 include/openssl/http.h +3644c7094fd5310a103aa9adff947ad9aa87e0a48432471a4ca10b4885d215d3 include/openssl/indicator.h faab8accc9520269dd874126ae164a43526d5784e6280521c7ab3772c02b0a0c include/openssl/kdf.h 625258d115ddc5117eaa2ff126e548e25fb81336abead079e6f2028f4bce4e92 include/openssl/lhash.h.in -1d0727322274c34d622a9955a5c50a6537f872f2740286068758fde24bf607b1 include/openssl/macros.h +6030ed9e4c0096624f18d237a17685855dd4f2281eddd9ae913f4682782a1734 include/openssl/macros.h 9184207c562fd1fa7bd3a4f1fadcb984130561279818f0cdfcf3e9c55be8a7d1 include/openssl/modes.h -46d7f1dfef8bce7c0edf89d8f08d63f35c998bd9de52b864d5ce3e1b661da067 include/openssl/obj_mac.h -157797b450215f973eb10be96a04e58048ab9c131ad29427e80d0e37e230ed98 include/openssl/objects.h +e0114662228e54393bcbaa24f22bca1ebc58bf28b12915b96464420630f6f091 include/openssl/obj_mac.h +cb6bca3913c60a57bac39583eee0f789d49c3d29be3ecde9aecc7f3287117aa5 include/openssl/objects.h d25537af264684dff033dd8ae62b0348f868fcfec4aa51fa8f07bcfa4bd807ad include/openssl/objectserr.h fe6acd42c3e90db31aaafc2236a7d30ebfa53c4c07ea4d8265064c7fcb951970 include/openssl/opensslconf.h 1bf52d136e94f727a96651c1f48ad040482f35dae152519ccd585efd410b92f0 include/openssl/opensslv.h.in 767d9d7d5051c937a3ce8a268c702902fda93eeaa210a94dfde1f45c23277d20 include/openssl/param_build.h 30085f4d1b4934bb25ffe7aa9a30859966318a1b4d4dcea937c426e90e6e1984 include/openssl/params.h +44f178176293c6ce8142890ff9dc2d466364c734e4e811f56bd62010c5403183 include/openssl/pkcs7.h.in +8394828da6fd7a794777320c955d27069bfef694356c25c62b7a9eb47cd55832 include/openssl/pkcs7err.h ed785c451189aa5f7299f9f32a841e7f25b67c4ee937c8de8491a39240f5bd9d include/openssl/prov_ssl.h -08980b1dbc01e2926fc59707d867030fc7a3d37dc625c0e1edf2d31bdf71b2fb include/openssl/proverr.h +51249095a53ad2fa26e5b5a16c4f79cc19ff0a0787d7dd0753e48ff339370331 include/openssl/proverr.h 03bda8974476f0f038a7cfa0cb30f0b8210d55c74c6e7e853fd1564dca3e2b14 include/openssl/provider.h e512ab2e492d968a9bf8b2b048f79ac5dfe11bddf3c00f2eec6e9c6ecc57d330 include/openssl/rand.h 5be9d723cf368b48ab35bda5db1a3e83bda6e9e38218dd0b020be1a5427e7488 include/openssl/randerr.h 2f4f0106e9b2db6636491dbe3ef81b80dbf01aefe6f73d19663423b7fcd54466 include/openssl/rsa.h 2f339ba2f22b8faa406692289a6e51fdbbb04b03f85cf3ca849835e58211ad23 include/openssl/rsaerr.h 6586f2187991731835353de0ffad0b6b57609b495e53d0f32644491ece629eb2 include/openssl/safestack.h.in -f2d37d316a2f80ad83117495ba68af6629a3817b2cc0dd5cdf981e116145483b include/openssl/self_test.h +4ab1e61699d675b514ce0d1635a033be16c89e4d0a58c908f9838c0c7fb9eafa include/openssl/self_test.h a435cb5d87a37c05921afb2d68f581018ec9f62fd9b3194ab651139b24f616d2 include/openssl/sha.h c169a015d7be52b7b99dd41c418a48d97e52ad21687c39c512a83a7c3f3ddb70 include/openssl/stack.h 22d7584ad609e30e818b54dca1dfae8dea38913fffedd25cd540c550372fb9a6 include/openssl/symhacks.h 8acd8147402a816c835b4240e18972072bab41d3fb6ee364fc17e543d6a854f6 include/openssl/thread.h a99dcb756a27eb019c9e3f5c49bd55ca39def82684aea891bac011e9e99f9b8d include/openssl/trace.h -a22bb862d4e1e7bb41b4199f81fc6737dc0a277534b17f9e22b102ea297532c1 include/openssl/types.h +c7ec2154c2e55f1540abee52b8c2af53c9d993045408517d49a3d6a833cf281c include/openssl/types.h +e0308d6ae6a7309a163898079f6e2abd435589066856c92ddcafa2bf04718c1c include/openssl/x509.h.in +7844d00cef77c9be785b3dea17ba8b61cd3ee3db22518bd0928c6ea70771a7bc include/openssl/x509_vfy.h.in +ef9e7c7a2176cf1b3f2d0c52b7cc1f47ad0666fbbd8a9479cbb39b7bf0dfe06b include/openssl/x509err.h c0a9551efccf43f3dd748d4fd8ec897ddaabbc629c00ec1ad76ce983e1195a13 providers/common/bio_prov.c -9da3f65c020cc14b99bfb732b015841b02a25f2d5022f8c0ef0e0d71c3b9f9f8 providers/common/capabilities.c +a50f2219683a7ad44a18936603abcba5e2e588e6c4c4e7d14c6922ae833d719b providers/common/capabilities.c f94b7435d4ec888ec30df1c611afa8b9eedbb59e905a2c7cb17cfc8c4b9b85b8 providers/common/der/der_digests_gen.c.in 424d7b2ece984a0904b80c73e541400c6e2d50a285c397dd323b440a4f2a8d8e providers/common/der/der_dsa_gen.c.in 27ff361a5fbfc97cd41690ab26639708961d0507b60912f55f5919649842c6ae providers/common/der/der_dsa_key.c @@ -534,71 +545,75 @@ c0a020765feb7ededc7e6f20b2b140dca09f347cc72404a5c7971df82b2f9ad0 providers/comm 5b6b7d8d12011c48195b7db8f65bc4bc4a48fb753763a3ce5006dc227b5139d7 providers/common/include/prov/der_ecx.h.in ce605f32413b09d33ce5795de9498a08183895c3347f33344f9ae5d31c29ccac providers/common/include/prov/der_rsa.h.in 6c1fa3f229c6f049c3ac152c4c265f3eb056d94221b82df95a15400649690e93 providers/common/include/prov/der_wrap.h.in -237c3e6f6c23f64414f3e93c08c0bcbfe8ba859efb930df836958ba6be682518 providers/common/include/prov/fipscommon.h 76087f04f4de6414c240f88807659fb2a04af914108f0c5f2515a4cb5482f655 providers/common/include/prov/proverr.h 83a57505d88a6a9cc4f7781c9f7f4af07668e7923502dfd6c5960bb492c1d24e providers/common/include/prov/provider_ctx.h f533a548eee6ec1863ca4afc4eb27766596fdf74c5eaed81817a92d26bbf26f0 providers/common/include/prov/provider_util.h e1ef8b2be828a54312d6561b37751a5b6e9d5ebdb6c3e63589728c3d8adca7dc providers/common/include/prov/providercommon.h -c2b4301a9f835c0b3776ad3afba7121d00cd7ae6387fe11c96269a37da08027c providers/common/include/prov/securitycheck.h +4a6e35be7600e78633324422f019443747a62777eba4987efc50f900c43fda25 providers/common/include/prov/securitycheck.h 737cc1228106e555e9bab24e3c2438982e04e05b0d5b9ee6995d71df16c49143 providers/common/provider_ctx.c -3f5656c405ec57a261df7af940c1512990555361f69488a28d65e16f6b865a1d providers/common/provider_err.c +501c66b2d534c90b7550cf0d67fdd779e772d03cbe8f190aa3440dfe2a8ead71 providers/common/provider_err.c c4032b7cb033b588c6eb0585b8dfbed029d5b112a74ddd134dbcb1d78b0f9684 providers/common/provider_seeding.c 6e833d259d04cdedc007e6cda52fd706527edcf4b4432dbd88cbf45c3f7a4442 providers/common/provider_util.c -5b94312727ca33e4f5c038f4caaae8417bf584cfde22df83d91f3c55c30c81ee providers/common/securitycheck.c -bc4370324c4c8791ea6de8641d255073c6745ee984e18912d535e155d9815244 providers/common/securitycheck_fips.c +bde6107744cf6840a4c350a48265ed000c49b0524fa60b0d68d6d7b33df5fce6 providers/common/securitycheck.c +8ea192553b423e881d85118c70bcb26a40fbdee4e110f230c966939c76f4aa7e providers/common/securitycheck_fips.c abd5997bc33b681a4ab275978b92aebca0806a4a3f0c2f41dacf11b3b6f4e101 providers/fips/fips_entry.c -4182e53ef3923e24c497bda55a3e594c538cb53eaab7659a43e59081640b6e96 providers/fips/fipsprov.c -029fad3c27617c725e516621c2f6c3a0e1dca0fa22f4e89a1a6b9a977c8d935d providers/fips/self_test.c -f822a03138e8b83ccaa910b89d72f31691da6778bf6638181f993ec7ae1167e3 providers/fips/self_test.h -09362a49fda902e2d29617cad7296b11b9d372fc925c6114196a1ffe3ee81b33 providers/fips/self_test_data.inc -47b5e2649e7b37178c2c6236c8503bf87fabfe2b7cc5ecee69a5ed4780decb92 providers/fips/self_test_kats.c -9088379971217bcdc3d599a5b253f5c6d1d2f420f0486e3e279c70156ba995ba providers/implementations/asymciphers/rsa_enc.c +d8cb05784ae8533a7d9569d4fbaaea4175b63a7c9f4fb0f254215224069dea6b providers/fips/fipsindicator.c +761d9bad1b2dc31e295edb4b9f61618acfda7977c4d728870b6a0f3fe1febaa5 providers/fips/fipsprov.c +7be8349d3b557b6d9d5f87d318253a73d21123628a08f50726502abf0e3d8a44 providers/fips/include/fips/fipsindicator.h +ef204adc49776214dbb299265bc4f2c40b48848cbea4c25b8029f2b46a5c9797 providers/fips/include/fips_indicator_params.inc +f2581d7b4e105f2bb6d30908f3c2d9959313be08cec6dbeb49030c125a7676d3 providers/fips/include/fips_selftest_params.inc +669f76f742bcaaf28846b057bfab97da7c162d69da244de71b7c743bf16e430f providers/fips/include/fipscommon.h +3a638ccab5de977b3279ba04798737fc7565930648635a62132669d6843a2bf7 providers/fips/self_test.c +5c2c6c2f69e2eb01b88fa35630f27948e00dd2c2fd351735c74f34ccb2005cbe providers/fips/self_test.h +178d3ae7f5798e8bce87bd9483b3cac88be3121373c5493184a87008702ed835 providers/fips/self_test_data.inc +dae7df69ed3bc7ea7c95b8b3260c507d25c2573829f8a1cd139abe5ffaf54f9d providers/fips/self_test_kats.c +4e39248b595074aaa9a7b4b072eb2ef07afc6cf3d5d18c053b938abbf17f9a81 providers/implementations/asymciphers/rsa_enc.c c2f1b12c64fc369dfc3b9bc9e76a76de7280e6429adaee55d332eb1971ad1879 providers/implementations/ciphers/cipher_aes.c 6ba7d817081cf0d87ba7bfb38cd9d70e41505480bb8bc796ef896f68d4514ea6 providers/implementations/ciphers/cipher_aes.h -20494fb9eb9f0578a3a574e0c6406108cfb28d7895a1891d57b3238420ec4f7b providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c +c4325a839ed5c719c6888f7939516f32a9802b9065b5372f23f8efb46d0d5071 providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c 7668e5c1cac474ad7b0f28aa78ca885edf44815fe4a606a6cd328b3c02fac25a providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.h 26e0f28523b416ba4067e471061f5a11fd76f5dc8bfe57ce37a137cf5667630b providers/implementations/ciphers/cipher_aes_cbc_hmac_sha1_hw.c 6d2ab2e059ef38fad342d4c65eebd533c08a2092bb174ff3566c6604e175c5a4 providers/implementations/ciphers/cipher_aes_cbc_hmac_sha256_hw.c -f37c3cf9e2e6fcfcbed941f3670b790fe09990349db72eb065bef51705d46e96 providers/implementations/ciphers/cipher_aes_ccm.c +1b6d31811a6729f0c75c7c7ccfb7d3a75ab6001605b229593187918a592da789 providers/implementations/ciphers/cipher_aes_ccm.c 00f36bf48e522dbb5ec71df0ec13e387955fa3672e6ff90e8a412ae95c4a642f providers/implementations/ciphers/cipher_aes_ccm.h 4812d59ab6e1380f38e0c7cc0d7995eb6a2abf1438cedf233b939a17c4111482 providers/implementations/ciphers/cipher_aes_ccm_hw.c 302b3819ff9fdfed750185421616b248b0e1233d75b45a065490fe4762b42f55 providers/implementations/ciphers/cipher_aes_ccm_hw_aesni.inc a8eaca99a71521ff8ac4ffcf08315e59220f7e0b7f505ecddad04fadd021ec14 providers/implementations/ciphers/cipher_aes_cts.inc -7e886ecc088b5903aa082eac72a4c46f9064392bdf5723a592368ecebfeb71c0 providers/implementations/ciphers/cipher_aes_gcm.c +14de031ae6a95653f7d819bfdb2abaf873f884b8313901bee4c2ec3ffc286712 providers/implementations/ciphers/cipher_aes_gcm.c 79f5a732820d2512a7f4fc2a99ece7e6e2523a51e62561eb67a4b70d5538b0c4 providers/implementations/ciphers/cipher_aes_gcm.h c6f091629dadb1b0b55e45636a28c31268fea4abfd3c068917c6c94b9aab704d providers/implementations/ciphers/cipher_aes_gcm_hw.c be18c20e0197f25fe7b9e0268657a2271a69d216b89cb100f082fa5fcaad1e07 providers/implementations/ciphers/cipher_aes_gcm_hw_aesni.inc 60c4f604cf9b5457be48f31cc24ca21729660381081b2dbf99f362a013a09684 providers/implementations/ciphers/cipher_aes_gcm_hw_vaes_avx512.inc d65415e14317e58673808b90a4dcd9aea47ae1ef2250edc1a8f1b872f0e9b1cf providers/implementations/ciphers/cipher_aes_hw.c 89de794c090192459d99d95bc4a422e7782e62192cd0fdb3bdef4128cfedee68 providers/implementations/ciphers/cipher_aes_hw_aesni.inc -d280d7ecd1da16248faf38f81059a7d76920bd54a8f551dda137c005acaeb01e providers/implementations/ciphers/cipher_aes_ocb.c +04df57a8e45aef30006a447779f9137273181950dd422eacbb1d82245ebf0a16 providers/implementations/ciphers/cipher_aes_ocb.c 88138a1aff9705e608c0557653be92eb4de65b152555a2b79ec8b2a8fae73e8f providers/implementations/ciphers/cipher_aes_ocb.h 634cd29f13e5dd8ced3467504e8313b454a90371735ef42a5fe82c027b473064 providers/implementations/ciphers/cipher_aes_ocb_hw.c -110f14e06311883d5e312b37e9d87c51f809592d3092ecd8eb449ea4bc7cac38 providers/implementations/ciphers/cipher_aes_wrp.c -a79fde91348c9df6bb359e5353a442800ca514a1ffcb68e5cc5f7afe7d57d5ec providers/implementations/ciphers/cipher_aes_xts.c +855d9ce6ef45c91a8b6a81d897265ea719cc65ee9c728dfbd9f2109b7f6fdf1f providers/implementations/ciphers/cipher_aes_wrp.c +97eac06ffd50a220f20b5b507f04d286158f7e5eaa71bc9a21e0c02976ed98b9 providers/implementations/ciphers/cipher_aes_xts.c c4a2499b214d7cf786dafaaee5c8c6963b3d5d1c27c144eec4b460f839074a3b providers/implementations/ciphers/cipher_aes_xts.h 281157d1da4d7285d878978e6d42d0d33b3a6bc16e3bc5b6879e39093a7d70da providers/implementations/ciphers/cipher_aes_xts_fips.c a4c4278d0dfae73d40e2758e4bb7d909f51a2b7cf4e980e4d33d4695ce8af44e providers/implementations/ciphers/cipher_aes_xts_hw.c -46ba8271917b53fd8fdf77aee19cc326a219c950b94e043d6d118dcac25ad7ad providers/implementations/ciphers/cipher_cts.c +dc4626becaabc3990549483d9ef5f05c7dd9a9c2cf9be96ade3ba6a6e203f7f5 providers/implementations/ciphers/cipher_cts.c 57ee5e4d0af6d6006b04e60c5727b43a71ed37b67aa2410e03ec8932ad4a69e4 providers/implementations/ciphers/cipher_cts.h fcc3bb0637864252402aaa9d543209909df9a39611127f777b168bc888498dc0 providers/implementations/ciphers/cipher_tdes.c -d4cd3672d769b38d5346c9b76fa3902b8bb2daee2aa5e1c1e70b75a54c2f43cd providers/implementations/ciphers/cipher_tdes.h -e5739a8201637f76f8daee987a535f1f278d6c2ad292dddd0a6a397108c65588 providers/implementations/ciphers/cipher_tdes_common.c +ccd6cc0ba06a8ecd8ce50019a6a62f8a185125d9ee045fd68a3c16e71c7a7794 providers/implementations/ciphers/cipher_tdes.h +b59e3978b70cecdf8b0d867bd1b9202e19bef0b8e5bc243db42704a49dc5b22d providers/implementations/ciphers/cipher_tdes_common.c 50645122f08ef4891cd96cace833bd550be7f5278ab785515fd61fe8993c8c25 providers/implementations/ciphers/cipher_tdes_hw.c -1f44963b1ac450cb77d75df9fbf956b04742e38d236d316c7eb8021bdf0573a4 providers/implementations/ciphers/ciphercommon.c +c5d1ca508847e0aa76462137bb7851df1ca2af1c3b62de9ff1f7403a28ba5ed6 providers/implementations/ciphers/ciphercommon.c ab9a2edb23aa61cf31da6addd8674a6028f93399eceeeee35a56ee770338fd6c providers/implementations/ciphers/ciphercommon_block.c 8af515e63a0c16ff35dcedcc43c7b4735a10943f1e937eeeb73eb1af3dc92782 providers/implementations/ciphers/ciphercommon_ccm.c 8b6828f188c2590c7d9c6cac13fa0eb6d38a522b0f2859e7c8a766580fa9b66e providers/implementations/ciphers/ciphercommon_ccm_hw.c -425384b22ca7b7265e163e5768da4a60773a6d88a0a96df7c990759063560cba providers/implementations/ciphers/ciphercommon_gcm.c +35d3d6329ac83aa203205cea8cb7afba3c8ad48987a97600ffae2bdf6254edd4 providers/implementations/ciphers/ciphercommon_gcm.c bb67eaa7a98494ca938726f9218213870fc97dd87b56bda950626cc794baf20b providers/implementations/ciphers/ciphercommon_gcm_hw.c 23fd89e3239e596c325a8c5d23eb1fe157a8d23aa4d90ed2c574bf06dfabd693 providers/implementations/ciphers/ciphercommon_hw.c c4b1cb143de15acc396ce2e03fdd165defd25ebc831de9cdfacf408ea883c666 providers/implementations/ciphers/ciphercommon_local.h 39b47b6ef9d71852964c26e07ef0e9b23f04c7493b1b16ba7c3dba7074b6b70d providers/implementations/digests/digestcommon.c 5f41dd1bf77bd08d287a875f9d6e5a423bf286524694ae7ee133cdd03ee763c0 providers/implementations/digests/sha2_prov.c -9aea6dc6275fe3d7fd62bfcb0f0482ca1d1c5ab8347c4ea1e65ed0ffc3531707 providers/implementations/digests/sha3_prov.c -4b774bf9267ebe05bf90076bc18e19a21e03ee2716bdb8fc4e6458774e9a820c providers/implementations/exchange/dh_exch.c -b2d80c38dd62b46f2dd71e81a5684f54f43200d3ddbb86178081760ecc93525c providers/implementations/exchange/ecdh_exch.c -4994df237719649b086a032bd64c1cf38ceb4e67dd8ec98da20edf5bc3eadb0b providers/implementations/exchange/ecx_exch.c +373a6613556b662423097be1f190c12b3c1ca5b4188f39c2555c1de7fde73834 providers/implementations/digests/sha3_prov.c +3f0ea2d3e63718db44dc4839dffffd4aeef90680a56b67662ab4a7e1b54e50b9 providers/implementations/exchange/dh_exch.c +c021875cd9985095b97ed2a8327ec2ec0418720fdbb7d9b4453a097682532453 providers/implementations/exchange/ecdh_exch.c +d44c5a6d3156392757415f34afc1ab164fb0e9cd1e97977386d7cd13f3555df5 providers/implementations/exchange/ecx_exch.c b1115636f53bf70f417b183cafeb6d38e230d11d8de731e6896ba60cc850d931 providers/implementations/exchange/kdf_exch.c 1f248e220109ead708d4e1189be85299b4d11a935ad6bf2e8e6fd020e680c879 providers/implementations/include/prov/ciphercommon.h a5ea831a23c0f52a37660437f6c61f129c3f8428daf6f8cd8dd458f358c56937 providers/implementations/include/prov/ciphercommon_aead.h @@ -607,44 +622,44 @@ a07b9c86346100feef15c9abb57e48a6099bc9fa782724a2283f17910ef192fb providers/impl b9a61ce951c1904d8315b1bb26c0ab0aaadb47e71d4ead5df0a891608c728c4b providers/implementations/include/prov/digestcommon.h 1baf1c06b20a0eb8ec271452544922d67c1cc168dbe9853b259191de4bd99918 providers/implementations/include/prov/ecx.h 062b49fc5cfa405fbcb184b1b48c9141db22531493bf828ba8543d24b0b72692 providers/implementations/include/prov/hmac_drbg.h -a6879c2e107597c49efa07fae48f0554ffbea9814c31d186bf0ce9f83e1ec9d2 providers/implementations/include/prov/implementations.h +290cb7c724a7b2cd06c9e59cd497663aa169189934dbd72aa6afab6c615efd7e providers/implementations/include/prov/implementations.h 05eedab6b16c80025f72281fa619d9480c437b800cb821b761fe4c05bc9d3af0 providers/implementations/include/prov/kdfexchange.h 4014246d44fa3f34aad5372c75d3f7eea528f1cf1798e30d5627e7620a356631 providers/implementations/include/prov/macsignature.h -27e57358e8ad201e382b50d5760f010badd9d6253deb34e6fb93a2af35450d9a providers/implementations/include/prov/names.h +d26026f801af111736489c5f885d53ac11ad9e9b132e2cba32698bb8f1cf8975 providers/implementations/include/prov/names.h b9f8781167f274ccd8b643b3bb6c4e1108fb27b2aae588518261af9415228dae providers/implementations/include/prov/seeding.h -266d76cd7ed2103dc031358e04e30c2f0ecf54af70c2d16b29307b3cb9968991 providers/implementations/kdfs/hkdf.c -ba0523cf3f664568f591c888a737a8ea008652e767d2239e998fdcfc7e3b99d4 providers/implementations/kdfs/kbkdf.c -03b3dffd32a2b8f94e7d39b97f3d7b36f00cd0177ee5e7329a39aeca20ed4baf providers/implementations/kdfs/pbkdf2.c +43a177f3f583bbe79c6f2d32850ca476d3a3822be1e7b262eddc98a620e6be4f providers/implementations/kdfs/hkdf.c +80617905cb429ed5e0ea28e4d1d26d0ebde3257f7f392fb8eb874b3bdf007865 providers/implementations/kdfs/kbkdf.c +6d02f8de3870334c91d4e43fdbe00155233b5ca5932911f74123663e23ab9e4d providers/implementations/kdfs/pbkdf2.c c0778565abff112c0c5257329a7750ec4605e62f26cc36851fa1fbee6e03c70c providers/implementations/kdfs/pbkdf2.h abe2b0f3711eaa34846e155cffc9242e4051c45de896f747afd5ac9d87f637dc providers/implementations/kdfs/pbkdf2_fips.c -c3502c75dfb8c97c907eb478be84cc9e09dc0c17ede2c739b433145abfef7202 providers/implementations/kdfs/sshkdf.c -da5fa36d4fbb2816221560f5cd1c1710b59b8f948c1b9d2a37ee8e30a07b04f2 providers/implementations/kdfs/sskdf.c -a0ab99ee26632a98f6c5e9ad9fdfbc87d21ea80caf100727d14ccde68f1d7bad providers/implementations/kdfs/tls1_prf.c -1664cb4137073e9c0e202b82ca251e8620dbc83aa3d3d6b85de440183288ea61 providers/implementations/kdfs/x942kdf.c -bb7ad10481d496f3227897c00b2a9d516ce8e0a6627f4addeabd9c72d9cf825f providers/implementations/kem/rsa_kem.c -cad07d02f629f0b1440a3137191e84a254181e283bee1f4ea011697984cb3f64 providers/implementations/keymgmt/dh_kmgmt.c -6db53db21d72bab2ab198a520a048fea370cfc9238d8a84906ffb2af1fecfe82 providers/implementations/keymgmt/dsa_kmgmt.c -3964a23ac071b0d6e54ea12c382e98abe1becfd9890194d94804715002b2b5b8 providers/implementations/keymgmt/ec_kmgmt.c +615f76976cbbe9a2126246f25906666c0d9794d2b1798e25c8c905c846e62c87 providers/implementations/kdfs/sshkdf.c +5c36ca6621c77991a00d075adc8aaeb1e26f85770b955ce617ddca6c9cba6a32 providers/implementations/kdfs/sskdf.c +08eb18efa684bb1a70b1aa808d350f7e38791f8df8593cfa6de74a502bc3714d providers/implementations/kdfs/tls1_prf.c +d8b5f2a17146cdfdbe6db518f8d4183d399a1dc163d3d7f0eb169665e84f3d56 providers/implementations/kdfs/x942kdf.c +b4b389ab297283b7e3e5e667793f24e62a99baa47b69ec44b70d0ba8f0ce1862 providers/implementations/kem/rsa_kem.c +0a3b96d2818ce09a2a07663f311de68d0e2db92265c32aeccf844a1bc114dc83 providers/implementations/keymgmt/dh_kmgmt.c +48470164b3c023503e75aaacee17fe7da6beb06f10c84ac2acc2bf19e823f810 providers/implementations/keymgmt/dsa_kmgmt.c +686e86f1f91eb8459ca3789e5d903dae7bd0f6e61c16bbf9b98b558de272fd99 providers/implementations/keymgmt/ec_kmgmt.c 258ae17bb2dd87ed1511a8eb3fe99eed9b77f5c2f757215ff6b3d0e8791fc251 providers/implementations/keymgmt/ec_kmgmt_imexport.inc -a67e230411dce1e0780ac44c5bc87988002a5db05aa9594ad63bda9d4bc6df32 providers/implementations/keymgmt/ecx_kmgmt.c +08264b248dcaf68140900871cb448210b4ef020eaac7a19275d0f54b3fb39614 providers/implementations/keymgmt/ecx_kmgmt.c daf35a7ab961ef70aefca981d80407935904c5da39dca6692432d6e6bc98759d providers/implementations/keymgmt/kdf_legacy_kmgmt.c 91832fb65cc8ee591989fcf0f039ad04ba463008b5be9549a2b0ae6882b257ab providers/implementations/keymgmt/mac_legacy_kmgmt.c 9034a66a4bae1a15e127a5eca94bcec2ecaa971b205e945fcf7fba6b6bb8e47d providers/implementations/keymgmt/rsa_kmgmt.c -f2fc18af21f11b0e0ff9895f8b438caab4808256eaa680728b5e50736cc2c4b1 providers/implementations/macs/cmac_prov.c +c421f7cc04588d2184420d18ef528e410a8f52dafe2ad5d951b1d1ebc2d8bded providers/implementations/macs/cmac_prov.c f29f282463f5bc432129850619edc427fe1d6cc8aa107b5703b11858b48790da providers/implementations/macs/gmac_prov.c -dece97b669da85cc9d867bfb7ffc227b7f48f36e198bd44e4b32c0cfc517d7fd providers/implementations/macs/hmac_prov.c -16f3dc42faceb235d7c4a495b9be7e8476094482de6ff421ab514390898154fd providers/implementations/macs/kmac_prov.c -3034074f99b02db045f2ccecc8782322e876dad07a3c169bdb24168b6b1f8cbd providers/implementations/rands/crngt.c -fcf5c044bbb92de1119759ead558ada3dfdf75db4874bd3bd0db1b46cb931190 providers/implementations/rands/drbg.c -4db4ec624c473960114966ca891a690481b029ed1a0b943458d7bfe7dff3fee5 providers/implementations/rands/drbg_ctr.c -e5c6f3ce421dc0e80e3c68c908e9338d2f74dfa6a3d2ebe0662ce61a165b0fca providers/implementations/rands/drbg_hash.c -2f762a617c9abd6d9355f54b35c4fe07164f200fbf31956c03bd0849f3e90f9d providers/implementations/rands/drbg_hmac.c -3e8a26ae26aab0b8ff02a20af59e5c187403df9a12c5bb69d7492b0843dfe47c providers/implementations/rands/drbg_local.h -e5fb82137f8afea68a67c1ea2d652831207961c53f14ab33ac0d879c9d0e8448 providers/implementations/rands/test_rng.c -a9aa31d091df5b8f6710dd36761dfe7d32b6da1881f8581bed85ad4e171b0969 providers/implementations/signature/dsa_sig.c -6c8b5f325c997014bd71331c9eb6c185838cd81c10c3ad74dd65289ae923d629 providers/implementations/signature/ecdsa_sig.c -d9d4bbbb0af0d1db6f586a36fd63236e4becdd52468a1e6510994e80988400aa providers/implementations/signature/eddsa_sig.c +af44fc4babe42e78c6ff3c16ea4f027ddeede57fca843dfaf0017ac49d45e310 providers/implementations/macs/hmac_prov.c +e14eb835ed11f9eab141e5e88a8115077894f4428080716540ee717abf666969 providers/implementations/macs/kmac_prov.c +e7db0498cb6a5d7f1e30d1b5c71905941231a4363dfbfa97d723deee4cae2026 providers/implementations/rands/drbg.c +07059a209427221ff67bbc083c7b4b612c09de627fdd5ee853ec0c099831ae7b providers/implementations/rands/drbg_ctr.c +adc2359e94453eebf879bda502b5e1da63ddff1241fa986255625b99e81d470d providers/implementations/rands/drbg_hash.c +7fb6180977b9579ffc6a154ce23c7e9083d85a8b763874e64506e7eaa554e64b providers/implementations/rands/drbg_hmac.c +b6dba662e23d8c762cc31d5ead7f42bbad682fb64a8b064bdc415b7b5d89fc13 providers/implementations/rands/drbg_local.h +ddae75f1e08416c92802faafba9d524e3bf58c13e9fcb51735733e161006f89e providers/implementations/rands/fips_crng_test.c +56661d9ad771f4b3c4c808456c29142d16b0fdc95422a93c0286cc8e6326e29e providers/implementations/rands/test_rng.c +b60c2da4f4a8c5be5e684f86fe985f85c44c765547912c1a56dd6d51b43101ad providers/implementations/signature/dsa_sig.c +5a5beb3552ec56d106601129dacafce8beca7952e63e349ffa019d3ce61dfad4 providers/implementations/signature/ecdsa_sig.c +720eadc94bd342f62fe6e0b58196899bb1c9c09f2b44ae5c1f8cbba827188110 providers/implementations/signature/eddsa_sig.c e0e67e402ff19b0d2eb5228d7ebd70b9477c12595ac34d6f201373d7c8a516f4 providers/implementations/signature/mac_legacy_sig.c -90c6ecba4a453b9af73844a25da30637f84f904bb27adc20d5cb3afb89262fa2 providers/implementations/signature/rsa_sig.c +06fe4428b0ee105aa2c387647df369d756994162015c95130cd95ac008d3ccaa providers/implementations/signature/rsa_sig.c 0b73a04f8a03106e2a0fea10978f9888158046c29c3993ca6557f5a6403d5580 ssl/record/methods/ssl3_cbc.c a8914c1661c53bcb0f435ec280c35c5a135e6c71296554c7322186847e194683 ssl/record/methods/tls_pad.c diff --git a/providers/fips.checksum b/providers/fips.checksum index d67ac669b4..e9ec7f53b1 100644 --- a/providers/fips.checksum +++ b/providers/fips.checksum @@ -1 +1 @@ -5338618ba25c4ff24729fbc475683fa5e9e44fd0910fc3d7b913a5b931d4f2eb providers/fips-sources.checksums +140904f4e82558130fb4ac0e418744e608112bd674b4c60cdb8f45267ca760df providers/fips-sources.checksums diff --git a/providers/fips.module.sources b/providers/fips.module.sources index 14e3d0722e..3fbd3ff490 100644 --- a/providers/fips.module.sources +++ b/providers/fips.module.sources @@ -232,6 +232,7 @@ crypto/ffc/ffc_key_validate.c crypto/ffc/ffc_params.c crypto/ffc/ffc_params_generate.c crypto/ffc/ffc_params_validate.c +crypto/hashtable/hashtable.c crypto/hmac/hmac.c crypto/hmac/hmac_local.h crypto/ia64cpuid.S @@ -389,6 +390,7 @@ include/crypto/asn1_dsa.h include/crypto/bn.h include/crypto/bn_conf.h.in include/crypto/bn_dh.h +include/crypto/cmac.h include/crypto/context.h include/crypto/cryptlib.h include/crypto/ctype.h @@ -422,6 +424,7 @@ include/internal/dsoerr.h include/internal/e_os.h include/internal/endian.h include/internal/ffc.h +include/internal/hashtable.h include/internal/namemap.h include/internal/nelem.h include/internal/numbers.h @@ -444,6 +447,7 @@ include/internal/thread_arch.h include/internal/thread_once.h include/internal/time.h include/internal/tlsgroups.h +include/internal/to_hex.h include/internal/tsan_assist.h include/openssl/aes.h include/openssl/asn1.h.in @@ -485,6 +489,8 @@ include/openssl/evperr.h include/openssl/fips_names.h include/openssl/fipskey.h.in include/openssl/hmac.h +include/openssl/http.h +include/openssl/indicator.h include/openssl/kdf.h include/openssl/lhash.h.in include/openssl/macros.h @@ -496,6 +502,8 @@ include/openssl/opensslconf.h include/openssl/opensslv.h.in include/openssl/param_build.h include/openssl/params.h +include/openssl/pkcs7.h.in +include/openssl/pkcs7err.h include/openssl/prov_ssl.h include/openssl/proverr.h include/openssl/provider.h @@ -511,6 +519,9 @@ include/openssl/symhacks.h include/openssl/thread.h include/openssl/trace.h include/openssl/types.h +include/openssl/x509.h.in +include/openssl/x509_vfy.h.in +include/openssl/x509err.h providers/common/bio_prov.c providers/common/capabilities.c providers/common/der/der_digests_gen.c.in @@ -534,7 +545,6 @@ providers/common/include/prov/der_ec.h.in providers/common/include/prov/der_ecx.h.in providers/common/include/prov/der_rsa.h.in providers/common/include/prov/der_wrap.h.in -providers/common/include/prov/fipscommon.h providers/common/include/prov/proverr.h providers/common/include/prov/provider_ctx.h providers/common/include/prov/provider_util.h @@ -547,7 +557,12 @@ providers/common/provider_util.c providers/common/securitycheck.c providers/common/securitycheck_fips.c providers/fips/fips_entry.c +providers/fips/fipsindicator.c providers/fips/fipsprov.c +providers/fips/include/fips/fipsindicator.h +providers/fips/include/fips_indicator_params.inc +providers/fips/include/fips_selftest_params.inc +providers/fips/include/fipscommon.h providers/fips/self_test.c providers/fips/self_test.h providers/fips/self_test_data.inc @@ -634,12 +649,12 @@ providers/implementations/macs/cmac_prov.c providers/implementations/macs/gmac_prov.c providers/implementations/macs/hmac_prov.c providers/implementations/macs/kmac_prov.c -providers/implementations/rands/crngt.c providers/implementations/rands/drbg.c providers/implementations/rands/drbg_ctr.c providers/implementations/rands/drbg_hash.c providers/implementations/rands/drbg_hmac.c providers/implementations/rands/drbg_local.h +providers/implementations/rands/fips_crng_test.c providers/implementations/rands/test_rng.c providers/implementations/signature/dsa_sig.c providers/implementations/signature/ecdsa_sig.c diff --git a/providers/fips/build.info b/providers/fips/build.info index 2bfc58501e..9756ad3f79 100644 --- a/providers/fips/build.info +++ b/providers/fips/build.info @@ -1,6 +1,6 @@ # We include the provider implementation into ../libfips.a, so that all # platforms can resolve symbols in other members of that library. -SOURCE[../libfips.a]=fipsprov.c self_test.c self_test_kats.c +SOURCE[../libfips.a]=fipsprov.c self_test.c self_test_kats.c fipsindicator.c # It is necessary to have an explicit entry point SOURCE[../fips]=fips_entry.c diff --git a/providers/fips/fipsindicator.c b/providers/fips/fipsindicator.c new file mode 100644 index 0000000000..d514ca6ecd --- /dev/null +++ b/providers/fips/fipsindicator.c @@ -0,0 +1,116 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include "internal/common.h" /* for ossl_assert() */ +#include "fips/fipsindicator.h" + +void ossl_FIPS_IND_init(OSSL_FIPS_IND *ind) +{ + int i; + + ossl_FIPS_IND_set_approved(ind); /* Assume we are approved by default */ + for (i = 0; i < OSSL_FIPS_IND_SETTABLE_MAX; i++) + ind->settable[i] = OSSL_FIPS_IND_STATE_UNKNOWN; +} + +void ossl_FIPS_IND_set_approved(OSSL_FIPS_IND *ind) +{ + ind->approved = 1; +} + +void ossl_FIPS_IND_copy(OSSL_FIPS_IND *dst, const OSSL_FIPS_IND *src) +{ + *dst = *src; +} + +void ossl_FIPS_IND_set_settable(OSSL_FIPS_IND *ind, int id, int state) +{ + if (!ossl_assert(id < OSSL_FIPS_IND_SETTABLE_MAX)) + return; + if (!ossl_assert(state == OSSL_FIPS_IND_STATE_STRICT + || state == OSSL_FIPS_IND_STATE_TOLERANT)) + return; + ind->settable[id] = state; +} + +int ossl_FIPS_IND_get_settable(const OSSL_FIPS_IND *ind, int id) +{ + if (!ossl_assert(id < OSSL_FIPS_IND_SETTABLE_MAX)) + return OSSL_FIPS_IND_STATE_UNKNOWN; + return ind->settable[id]; +} + +/* + * This should only be called when a strict FIPS algorithm check fails. + * It assumes that we are in strict mode by default. + * If the logic here is not sufficient for all cases, then additional + * ossl_FIPS_IND_on_unapproved() functions may be required. + */ +int ossl_FIPS_IND_on_unapproved(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + const char *algname, const char *opname, + OSSL_FIPS_IND_CHECK_CB *config_check_fn) +{ + /* Set to unapproved. Once unapproved mode is set this will not be reset */ + ind->approved = 0; + + /* + * We only trigger the indicator callback if the ctx variable is cleared OR + * the configurable item is cleared. If the values are unknown they are + * assumed to be strict. + */ + if (ossl_FIPS_IND_get_settable(ind, id) == OSSL_FIPS_IND_STATE_TOLERANT + || (config_check_fn != NULL + && config_check_fn(libctx) == OSSL_FIPS_IND_STATE_TOLERANT)) { + return ossl_FIPS_IND_callback(libctx, algname, opname); + } + /* Strict mode gets here: This returns an error */ + return 0; +} + +int ossl_FIPS_IND_set_ctx_param(OSSL_FIPS_IND *ind, int id, + const OSSL_PARAM params[], const char *name) +{ + int in = 0; + const OSSL_PARAM *p = OSSL_PARAM_locate_const(params, name); + + if (p != NULL) { + if (!OSSL_PARAM_get_int(p, &in)) + return 0; + ossl_FIPS_IND_set_settable(ind, id, in); + } + return 1; +} + +int ossl_FIPS_IND_get_ctx_param(const OSSL_FIPS_IND *ind, OSSL_PARAM params[]) +{ + OSSL_PARAM *p = OSSL_PARAM_locate(params, OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR); + + return p == NULL || OSSL_PARAM_set_int(p, ind->approved); +} + +/* + * Can be used during application testing to log that an indicator was + * triggered. The callback will return 1 if the application wants an error + * to occur based on the indicator type and description. + */ +int ossl_FIPS_IND_callback(OSSL_LIB_CTX *libctx, const char *type, + const char *desc) +{ + OSSL_INDICATOR_CALLBACK *cb = NULL; + + OSSL_INDICATOR_get_callback(libctx, &cb); + if (cb == NULL) + return 1; + + return cb(type, desc, NULL); +} diff --git a/providers/fips/fipsprov.c b/providers/fips/fipsprov.c index 86c18de28e..561f7123ad 100644 --- a/providers/fips/fipsprov.c +++ b/providers/fips/fipsprov.c @@ -12,8 +12,10 @@ #include #include #include +#include #include /* RAND_get0_public() */ #include +#include #include "internal/cryptlib.h" #include "prov/implementations.h" #include "prov/names.h" @@ -21,10 +23,10 @@ #include "prov/providercommon.h" #include "prov/provider_util.h" #include "prov/seeding.h" -#include "prov/fipscommon.h" #include "internal/nelem.h" #include "self_test.h" #include "crypto/context.h" +#include "fipscommon.h" #include "internal/core.h" static const char FIPS_DEFAULT_PROPERTIES[] = "provider=fips,fips=yes"; @@ -38,13 +40,11 @@ static OSSL_FUNC_provider_teardown_fn fips_teardown; static OSSL_FUNC_provider_gettable_params_fn fips_gettable_params; static OSSL_FUNC_provider_get_params_fn fips_get_params; static OSSL_FUNC_provider_query_operation_fn fips_query; +static OSSL_FUNC_provider_query_operation_fn fips_query_internal; #define ALGC(NAMES, FUNC, CHECK) \ { { NAMES, FIPS_DEFAULT_PROPERTIES, FUNC }, CHECK } -#define UNAPPROVED_ALGC(NAMES, FUNC, CHECK) \ - { { NAMES, FIPS_UNAPPROVED_PROPERTIES, FUNC }, CHECK } #define ALG(NAMES, FUNC) ALGC(NAMES, FUNC, NULL) -#define UNAPPROVED_ALG(NAMES, FUNC) UNAPPROVED_ALGC(NAMES, FUNC, NULL) extern OSSL_FUNC_core_thread_start_fn *c_thread_start; @@ -76,6 +76,7 @@ static OSSL_FUNC_CRYPTO_secure_clear_free_fn *c_CRYPTO_secure_clear_free; static OSSL_FUNC_CRYPTO_secure_allocated_fn *c_CRYPTO_secure_allocated; static OSSL_FUNC_BIO_vsnprintf_fn *c_BIO_vsnprintf; static OSSL_FUNC_self_test_cb_fn *c_stcbfn = NULL; +static OSSL_FUNC_indicator_cb_fn *c_indcbfn = NULL; static OSSL_FUNC_core_get_libctx_fn *c_get_libctx = NULL; typedef struct { @@ -86,9 +87,12 @@ typedef struct { typedef struct fips_global_st { const OSSL_CORE_HANDLE *handle; SELF_TEST_POST_PARAMS selftest_params; - FIPS_OPTION fips_security_checks; - FIPS_OPTION fips_tls1_prf_ems_check; - FIPS_OPTION fips_restricted_drgb_digests; + +#define OSSL_FIPS_PARAM(structname, paramname, initvalue) \ + FIPS_OPTION fips_##structname; +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM + } FIPS_GLOBAL; static void init_fips_option(FIPS_OPTION *opt, int enabled) @@ -103,9 +107,12 @@ void *ossl_fips_prov_ossl_ctx_new(OSSL_LIB_CTX *libctx) if (fgbl == NULL) return NULL; - init_fips_option(&fgbl->fips_security_checks, 1); - init_fips_option(&fgbl->fips_tls1_prf_ems_check, 0); /* Disabled by default */ - init_fips_option(&fgbl->fips_restricted_drgb_digests, 0); + +#define OSSL_FIPS_PARAM(structname, paramname, initvalue) \ + init_fips_option(&fgbl->fips_##structname, initvalue); +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM + return fgbl; } @@ -114,68 +121,32 @@ void ossl_fips_prov_ossl_ctx_free(void *fgbl) OPENSSL_free(fgbl); } -/* Parameters we provide to the core */ -static const OSSL_PARAM fips_param_types[] = { - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_NAME, OSSL_PARAM_UTF8_PTR, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_VERSION, OSSL_PARAM_UTF8_PTR, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_BUILDINFO, OSSL_PARAM_UTF8_PTR, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_STATUS, OSSL_PARAM_INTEGER, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_SECURITY_CHECKS, OSSL_PARAM_INTEGER, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_TLS1_PRF_EMS_CHECK, OSSL_PARAM_INTEGER, NULL, 0), - OSSL_PARAM_DEFN(OSSL_PROV_PARAM_DRBG_TRUNC_DIGEST, OSSL_PARAM_INTEGER, NULL, 0), - OSSL_PARAM_END -}; - +/* + * Parameters to retrieve from the core provider + * NOTE: inside core_get_params() these will be loaded from config items + * stored inside prov->parameters + */ static int fips_get_params_from_core(FIPS_GLOBAL *fgbl) { - /* - * Parameters to retrieve from the core provider - required for self testing. - * NOTE: inside core_get_params() these will be loaded from config items - * stored inside prov->parameters (except for - * OSSL_PROV_PARAM_CORE_MODULE_FILENAME). - * OSSL_PROV_FIPS_PARAM_SECURITY_CHECKS and - * OSSL_PROV_FIPS_PARAM_TLS1_PRF_EMS_CHECK are not self test parameters. - */ - OSSL_PARAM core_params[10], *p = core_params; - - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_PARAM_CORE_MODULE_FILENAME, - (char **)&fgbl->selftest_params.module_filename, - sizeof(fgbl->selftest_params.module_filename)); - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_FIPS_PARAM_MODULE_MAC, - (char **)&fgbl->selftest_params.module_checksum_data, - sizeof(fgbl->selftest_params.module_checksum_data)); - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_FIPS_PARAM_INSTALL_MAC, - (char **)&fgbl->selftest_params.indicator_checksum_data, - sizeof(fgbl->selftest_params.indicator_checksum_data)); - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_FIPS_PARAM_INSTALL_STATUS, - (char **)&fgbl->selftest_params.indicator_data, - sizeof(fgbl->selftest_params.indicator_data)); - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_FIPS_PARAM_INSTALL_VERSION, - (char **)&fgbl->selftest_params.indicator_version, - sizeof(fgbl->selftest_params.indicator_version)); - *p++ = OSSL_PARAM_construct_utf8_ptr( - OSSL_PROV_FIPS_PARAM_CONDITIONAL_ERRORS, - (char **)&fgbl->selftest_params.conditional_error_check, - sizeof(fgbl->selftest_params.conditional_error_check)); - -/* FIPS features can be enabled or disabled independently */ -#define FIPS_FEATURE_OPTION(fgbl, pname, field) \ - *p++ = OSSL_PARAM_construct_utf8_ptr( \ - pname, (char **)&fgbl->field.option, \ - sizeof(fgbl->field.option)) - - FIPS_FEATURE_OPTION(fgbl, OSSL_PROV_FIPS_PARAM_SECURITY_CHECKS, - fips_security_checks); - FIPS_FEATURE_OPTION(fgbl, OSSL_PROV_FIPS_PARAM_TLS1_PRF_EMS_CHECK, - fips_tls1_prf_ems_check); - FIPS_FEATURE_OPTION(fgbl, OSSL_PROV_FIPS_PARAM_DRBG_TRUNC_DIGEST, - fips_restricted_drgb_digests); -#undef FIPS_FEATURE_OPTION + OSSL_PARAM core_params[32], *p = core_params; + +#define OSSL_FIPS_PARAM(structname, paramname) \ + *p++ = OSSL_PARAM_construct_utf8_ptr( \ + paramname, (char **)&fgbl->selftest_params.structname, \ + sizeof(fgbl->selftest_params.structname)); + +/* Parameters required for self testing */ +#include "fips_selftest_params.inc" +#undef OSSL_FIPS_PARAM + +/* FIPS indicator options can be enabled or disabled independently */ +#define OSSL_FIPS_PARAM(structname, paramname, initvalue) \ + *p++ = OSSL_PARAM_construct_utf8_ptr( \ + OSSL_PROV_PARAM_##paramname, \ + (char **)&fgbl->fips_##structname.option, \ + sizeof(fgbl->fips_##structname.option)); +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM *p = OSSL_PARAM_construct_end(); @@ -189,6 +160,20 @@ static int fips_get_params_from_core(FIPS_GLOBAL *fgbl) static const OSSL_PARAM *fips_gettable_params(void *provctx) { + /* Parameters we provide to the core */ + static const OSSL_PARAM fips_param_types[] = { + OSSL_PARAM_DEFN(OSSL_PROV_PARAM_NAME, OSSL_PARAM_UTF8_PTR, NULL, 0), + OSSL_PARAM_DEFN(OSSL_PROV_PARAM_VERSION, OSSL_PARAM_UTF8_PTR, NULL, 0), + OSSL_PARAM_DEFN(OSSL_PROV_PARAM_BUILDINFO, OSSL_PARAM_UTF8_PTR, NULL, 0), + OSSL_PARAM_DEFN(OSSL_PROV_PARAM_STATUS, OSSL_PARAM_INTEGER, NULL, 0), + +#define OSSL_FIPS_PARAM(structname, paramname, initvalue) \ + OSSL_PARAM_DEFN(OSSL_PROV_PARAM_##paramname, OSSL_PARAM_INTEGER, NULL, 0), +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM + + OSSL_PARAM_END + }; return fips_param_types; } @@ -199,7 +184,7 @@ static int fips_get_params(void *provctx, OSSL_PARAM params[]) OSSL_LIB_CTX_FIPS_PROV_INDEX); p = OSSL_PARAM_locate(params, OSSL_PROV_PARAM_NAME); - if (p != NULL && !OSSL_PARAM_set_utf8_ptr(p, "OpenSSL FIPS Provider")) + if (p != NULL && !OSSL_PARAM_set_utf8_ptr(p, FIPS_VENDOR)) return 0; p = OSSL_PARAM_locate(params, OSSL_PROV_PARAM_VERSION); if (p != NULL && !OSSL_PARAM_set_utf8_ptr(p, OPENSSL_VERSION_STR)) @@ -211,18 +196,13 @@ static int fips_get_params(void *provctx, OSSL_PARAM params[]) if (p != NULL && !OSSL_PARAM_set_int(p, ossl_prov_is_running())) return 0; -#define FIPS_FEATURE_GET(fgbl, pname, field) \ - p = OSSL_PARAM_locate(params, pname); \ - if (p != NULL && !OSSL_PARAM_set_int(p, fgbl->field.enabled)) \ - return 0 - - FIPS_FEATURE_GET(fgbl, OSSL_PROV_PARAM_SECURITY_CHECKS, - fips_security_checks); - FIPS_FEATURE_GET(fgbl, OSSL_PROV_PARAM_TLS1_PRF_EMS_CHECK, - fips_tls1_prf_ems_check); - FIPS_FEATURE_GET(fgbl, OSSL_PROV_PARAM_DRBG_TRUNC_DIGEST, - fips_restricted_drgb_digests); -#undef FIPS_FEATURE_GET +#define OSSL_FIPS_PARAM(structname, paramname, initvalue) \ + p = OSSL_PARAM_locate(params, OSSL_PROV_PARAM_##paramname); \ + if (p != NULL && !OSSL_PARAM_set_int(p, fgbl->fips_##structname.enabled)) \ + return 0; +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM + return 1; } @@ -360,8 +340,8 @@ static const OSSL_ALGORITHM_CAPABLE fips_ciphers[] = { ALGC(PROV_NAMES_AES_256_CBC_HMAC_SHA256, ossl_aes256cbc_hmac_sha256_functions, ossl_cipher_capable_aes_cbc_hmac_sha256), #ifndef OPENSSL_NO_DES - UNAPPROVED_ALG(PROV_NAMES_DES_EDE3_ECB, ossl_tdes_ede3_ecb_functions), - UNAPPROVED_ALG(PROV_NAMES_DES_EDE3_CBC, ossl_tdes_ede3_cbc_functions), + ALG(PROV_NAMES_DES_EDE3_ECB, ossl_tdes_ede3_ecb_functions), + ALG(PROV_NAMES_DES_EDE3_CBC, ossl_tdes_ede3_cbc_functions), #endif /* OPENSSL_NO_DES */ { { NULL, NULL, NULL }, NULL } }; @@ -378,6 +358,16 @@ static const OSSL_ALGORITHM fips_macs[] = { { NULL, NULL, NULL } }; +static const OSSL_ALGORITHM fips_macs_internal[] = { +#ifndef OPENSSL_NO_CMAC + { PROV_NAMES_CMAC, FIPS_DEFAULT_PROPERTIES, ossl_cmac_functions }, +#endif + { PROV_NAMES_HMAC, FIPS_DEFAULT_PROPERTIES, ossl_hmac_internal_functions }, + { PROV_NAMES_KMAC_128, FIPS_DEFAULT_PROPERTIES, ossl_kmac128_internal_functions }, + { PROV_NAMES_KMAC_256, FIPS_DEFAULT_PROPERTIES, ossl_kmac256_internal_functions }, + { NULL, NULL, NULL } +}; + static const OSSL_ALGORITHM fips_kdfs[] = { { PROV_NAMES_HKDF, FIPS_DEFAULT_PROPERTIES, ossl_kdf_hkdf_functions }, { PROV_NAMES_TLS1_3_KDF, FIPS_DEFAULT_PROPERTIES, @@ -396,6 +386,7 @@ static const OSSL_ALGORITHM fips_kdfs[] = { }; static const OSSL_ALGORITHM fips_rands[] = { + { PROV_NAMES_CRNG_TEST, FIPS_UNAPPROVED_PROPERTIES, ossl_crng_test_functions }, { PROV_NAMES_CTR_DRBG, FIPS_DEFAULT_PROPERTIES, ossl_drbg_ctr_functions }, { PROV_NAMES_HASH_DRBG, FIPS_DEFAULT_PROPERTIES, ossl_drbg_hash_functions }, { PROV_NAMES_HMAC_DRBG, FIPS_DEFAULT_PROPERTIES, ossl_drbg_ossl_hmac_functions }, @@ -410,8 +401,8 @@ static const OSSL_ALGORITHM fips_keyexch[] = { #ifndef OPENSSL_NO_EC { PROV_NAMES_ECDH, FIPS_DEFAULT_PROPERTIES, ossl_ecdh_keyexch_functions }, # ifndef OPENSSL_NO_ECX - { PROV_NAMES_X25519, FIPS_DEFAULT_PROPERTIES, ossl_x25519_keyexch_functions }, - { PROV_NAMES_X448, FIPS_DEFAULT_PROPERTIES, ossl_x448_keyexch_functions }, + { PROV_NAMES_X25519, FIPS_UNAPPROVED_PROPERTIES, ossl_x25519_keyexch_functions }, + { PROV_NAMES_X448, FIPS_UNAPPROVED_PROPERTIES, ossl_x448_keyexch_functions }, # endif #endif { PROV_NAMES_TLS1_PRF, FIPS_DEFAULT_PROPERTIES, @@ -423,15 +414,62 @@ static const OSSL_ALGORITHM fips_keyexch[] = { static const OSSL_ALGORITHM fips_signature[] = { #ifndef OPENSSL_NO_DSA { PROV_NAMES_DSA, FIPS_DEFAULT_PROPERTIES, ossl_dsa_signature_functions }, + { PROV_NAMES_DSA_SHA1, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha1_signature_functions }, + { PROV_NAMES_DSA_SHA224, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha224_signature_functions }, + { PROV_NAMES_DSA_SHA256, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha256_signature_functions }, + { PROV_NAMES_DSA_SHA384, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha384_signature_functions }, + { PROV_NAMES_DSA_SHA512, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha512_signature_functions }, + { PROV_NAMES_DSA_SHA3_224, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha3_224_signature_functions }, + { PROV_NAMES_DSA_SHA3_256, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha3_256_signature_functions }, + { PROV_NAMES_DSA_SHA3_384, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha3_384_signature_functions }, + { PROV_NAMES_DSA_SHA3_512, FIPS_DEFAULT_PROPERTIES, ossl_dsa_sha3_512_signature_functions }, #endif { PROV_NAMES_RSA, FIPS_DEFAULT_PROPERTIES, ossl_rsa_signature_functions }, + { PROV_NAMES_RSA_SHA1, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha1_signature_functions }, + { PROV_NAMES_RSA_SHA224, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha224_signature_functions }, + { PROV_NAMES_RSA_SHA256, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha256_signature_functions }, + { PROV_NAMES_RSA_SHA384, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha384_signature_functions }, + { PROV_NAMES_RSA_SHA512, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha512_signature_functions }, + { PROV_NAMES_RSA_SHA512_224, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha512_224_signature_functions }, + { PROV_NAMES_RSA_SHA512_256, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha512_256_signature_functions }, + { PROV_NAMES_RSA_SHA3_224, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha3_224_signature_functions }, + { PROV_NAMES_RSA_SHA3_256, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha3_256_signature_functions }, + { PROV_NAMES_RSA_SHA3_384, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha3_384_signature_functions }, + { PROV_NAMES_RSA_SHA3_512, FIPS_DEFAULT_PROPERTIES, + ossl_rsa_sha3_512_signature_functions }, #ifndef OPENSSL_NO_EC # ifndef OPENSSL_NO_ECX - { PROV_NAMES_ED25519, FIPS_UNAPPROVED_PROPERTIES, + { PROV_NAMES_ED25519, FIPS_DEFAULT_PROPERTIES, ossl_ed25519_signature_functions }, - { PROV_NAMES_ED448, FIPS_UNAPPROVED_PROPERTIES, ossl_ed448_signature_functions }, + { PROV_NAMES_ED25519ph, FIPS_DEFAULT_PROPERTIES, + ossl_ed25519ph_signature_functions }, + { PROV_NAMES_ED25519ctx, FIPS_DEFAULT_PROPERTIES, + ossl_ed25519ctx_signature_functions }, + { PROV_NAMES_ED448, FIPS_DEFAULT_PROPERTIES, + ossl_ed448_signature_functions }, + { PROV_NAMES_ED448ph, FIPS_DEFAULT_PROPERTIES, + ossl_ed448ph_signature_functions }, # endif { PROV_NAMES_ECDSA, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_signature_functions }, + { PROV_NAMES_ECDSA_SHA1, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha1_signature_functions }, + { PROV_NAMES_ECDSA_SHA224, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha224_signature_functions }, + { PROV_NAMES_ECDSA_SHA256, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha256_signature_functions }, + { PROV_NAMES_ECDSA_SHA384, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha384_signature_functions }, + { PROV_NAMES_ECDSA_SHA512, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha512_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_224, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha3_224_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_256, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha3_256_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_384, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha3_384_signature_functions }, + { PROV_NAMES_ECDSA_SHA3_512, FIPS_DEFAULT_PROPERTIES, ossl_ecdsa_sha3_512_signature_functions }, #endif { PROV_NAMES_HMAC, FIPS_DEFAULT_PROPERTIES, ossl_mac_legacy_hmac_signature_functions }, @@ -471,13 +509,13 @@ static const OSSL_ALGORITHM fips_keymgmt[] = { { PROV_NAMES_EC, FIPS_DEFAULT_PROPERTIES, ossl_ec_keymgmt_functions, PROV_DESCS_EC }, # ifndef OPENSSL_NO_ECX - { PROV_NAMES_X25519, FIPS_DEFAULT_PROPERTIES, ossl_x25519_keymgmt_functions, + { PROV_NAMES_X25519, FIPS_UNAPPROVED_PROPERTIES, ossl_x25519_keymgmt_functions, PROV_DESCS_X25519 }, - { PROV_NAMES_X448, FIPS_DEFAULT_PROPERTIES, ossl_x448_keymgmt_functions, + { PROV_NAMES_X448, FIPS_UNAPPROVED_PROPERTIES, ossl_x448_keymgmt_functions, PROV_DESCS_X448 }, - { PROV_NAMES_ED25519, FIPS_UNAPPROVED_PROPERTIES, ossl_ed25519_keymgmt_functions, + { PROV_NAMES_ED25519, FIPS_DEFAULT_PROPERTIES, ossl_ed25519_keymgmt_functions, PROV_DESCS_ED25519 }, - { PROV_NAMES_ED448, FIPS_UNAPPROVED_PROPERTIES, ossl_ed448_keymgmt_functions, + { PROV_NAMES_ED448, FIPS_DEFAULT_PROPERTIES, ossl_ed448_keymgmt_functions, PROV_DESCS_ED448 }, # endif #endif @@ -527,6 +565,18 @@ static const OSSL_ALGORITHM *fips_query(void *provctx, int operation_id, return NULL; } +static const OSSL_ALGORITHM *fips_query_internal(void *provctx, int operation_id, + int *no_cache) +{ + if (operation_id == OSSL_OP_MAC) { + *no_cache = 0; + if (!ossl_prov_is_running()) + return NULL; + return fips_macs_internal; + } + return fips_query(provctx, operation_id, no_cache); +} + static void fips_teardown(void *provctx) { OSSL_LIB_CTX_free(PROV_LIBCTX_OF(provctx)); @@ -557,7 +607,7 @@ static const OSSL_DISPATCH fips_dispatch_table[] = { /* Functions we provide to ourself */ static const OSSL_DISPATCH intern_dispatch_table[] = { { OSSL_FUNC_PROVIDER_TEARDOWN, (void (*)(void))fips_intern_teardown }, - { OSSL_FUNC_PROVIDER_QUERY_OPERATION, (void (*)(void))fips_query }, + { OSSL_FUNC_PROVIDER_QUERY_OPERATION, (void (*)(void))fips_query_internal }, OSSL_DISPATCH_END }; @@ -689,6 +739,9 @@ int OSSL_provider_init_int(const OSSL_CORE_HANDLE *handle, case OSSL_FUNC_SELF_TEST_CB: set_func(c_stcbfn, OSSL_FUNC_self_test_cb(in)); break; + case OSSL_FUNC_INDICATOR_CB: + set_func(c_indcbfn, OSSL_FUNC_indicator_cb(in)); + break; default: /* Just ignore anything we don't understand */ break; @@ -740,20 +793,17 @@ int OSSL_provider_init_int(const OSSL_CORE_HANDLE *handle, SELF_TEST_disable_conditional_error_state(); /* Enable or disable FIPS provider options */ -#define FIPS_SET_OPTION(fgbl, field) \ - if (fgbl->field.option != NULL) { \ - if (strcmp(fgbl->field.option, "1") == 0) \ - fgbl->field.enabled = 1; \ - else if (strcmp(fgbl->field.option, "0") == 0) \ - fgbl->field.enabled = 0; \ - else \ - goto err; \ +#define OSSL_FIPS_PARAM(structname, paramname, unused) \ + if (fgbl->fips_##structname.option != NULL) { \ + if (strcmp(fgbl->fips_##structname.option, "1") == 0) \ + fgbl->fips_##structname.enabled = 1; \ + else if (strcmp(fgbl->fips_##structname.option, "0") == 0) \ + fgbl->fips_##structname.enabled = 0; \ + else \ + goto err; \ } - - FIPS_SET_OPTION(fgbl, fips_security_checks); - FIPS_SET_OPTION(fgbl, fips_tls1_prf_ems_check); - FIPS_SET_OPTION(fgbl, fips_restricted_drgb_digests); -#undef FIPS_SET_OPTION +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM ossl_prov_cache_exported_algorithms(fips_ciphers, exported_fips_ciphers); @@ -931,6 +981,12 @@ int CRYPTO_secure_allocated(const void *ptr) return c_CRYPTO_secure_allocated(ptr); } +void *CRYPTO_aligned_alloc(size_t num, size_t align, void **freeptr, + const char *file, int line) +{ + return NULL; +} + int BIO_snprintf(char *buf, size_t n, const char *format, ...) { va_list args; @@ -942,19 +998,16 @@ int BIO_snprintf(char *buf, size_t n, const char *format, ...) return ret; } -#define FIPS_FEATURE_CHECK(fname, field) \ - int fname(OSSL_LIB_CTX *libctx) \ - { \ - FIPS_GLOBAL *fgbl = \ - ossl_lib_ctx_get_data(libctx, OSSL_LIB_CTX_FIPS_PROV_INDEX); \ - return fgbl->field.enabled; \ +#define OSSL_FIPS_PARAM(structname, paramname, unused) \ + int ossl_fips_config_##structname(OSSL_LIB_CTX *libctx) \ + { \ + FIPS_GLOBAL *fgbl = \ + ossl_lib_ctx_get_data(libctx, OSSL_LIB_CTX_FIPS_PROV_INDEX); \ + \ + return fgbl->fips_##structname.enabled; \ } - -FIPS_FEATURE_CHECK(FIPS_security_check_enabled, fips_security_checks) -FIPS_FEATURE_CHECK(FIPS_tls_prf_ems_check, fips_tls1_prf_ems_check) -FIPS_FEATURE_CHECK(FIPS_restricted_drbg_digests_enabled, - fips_restricted_drgb_digests) -#undef FIPS_FEATURE_CHECK +#include "fips_indicator_params.inc" +#undef OSSL_FIPS_PARAM void OSSL_SELF_TEST_get_callback(OSSL_LIB_CTX *libctx, OSSL_CALLBACK **cb, void **cbarg) @@ -971,3 +1024,17 @@ void OSSL_SELF_TEST_get_callback(OSSL_LIB_CTX *libctx, OSSL_CALLBACK **cb, *cbarg = NULL; } } + +void OSSL_INDICATOR_get_callback(OSSL_LIB_CTX *libctx, + OSSL_INDICATOR_CALLBACK **cb) +{ + assert(libctx != NULL); + + if (c_indcbfn != NULL && c_get_libctx != NULL) { + /* Get the parent libctx */ + c_indcbfn(c_get_libctx(FIPS_get_core_handle(libctx)), cb); + } else { + if (cb != NULL) + *cb = NULL; + } +} diff --git a/providers/fips/include/fips/fipsindicator.h b/providers/fips/include/fips/fipsindicator.h new file mode 100644 index 0000000000..045d2108d5 --- /dev/null +++ b/providers/fips/include/fips/fipsindicator.h @@ -0,0 +1,151 @@ +/* + * Copyright 2023-2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#ifdef FIPS_MODULE + +# include /* OSSL_CALLBACK, OSSL_LIB_CTX */ +# include +# include "crypto/types.h" +# include +# include "fipscommon.h" + +/* + * There may be multiple settables associated with an algorithm that allow + * overriding the default status. + * We associate an id with each of these. + */ +# define OSSL_FIPS_IND_SETTABLE0 0 +# define OSSL_FIPS_IND_SETTABLE1 1 +# define OSSL_FIPS_IND_SETTABLE2 2 +# define OSSL_FIPS_IND_SETTABLE3 3 +# define OSSL_FIPS_IND_SETTABLE4 4 +# define OSSL_FIPS_IND_SETTABLE5 5 +# define OSSL_FIPS_IND_SETTABLE6 6 +# define OSSL_FIPS_IND_SETTABLE7 7 +# define OSSL_FIPS_IND_SETTABLE_MAX (1 + OSSL_FIPS_IND_SETTABLE7) + +/* Each settable is in one of 3 states */ +#define OSSL_FIPS_IND_STATE_UNKNOWN -1 /* Initial unknown state */ +#define OSSL_FIPS_IND_STATE_STRICT 1 /* Strict enforcement */ +#define OSSL_FIPS_IND_STATE_TOLERANT 0 /* Relaxation of rules */ + +/* + * For each algorithm context there may be multiple checks that determine if + * the algorithm is approved or not. These checks may be in different stages. + * To keep it simple it is assumed that the algorithm is initially approved, + * and may be unapproved when each check happens. Once unapproved the operation + * will remain unapproved (otherwise we need to maintain state for each check). + * The approved state should only be queried after the operation has completed + * e.g. A digest final, or a KDF derive. + * + * If a FIPS approved check fails then we must decide what to do in this case. + * In strict mode we would just return an error. + * To override strict mode we either need to have a settable variable or have a + * fips config flag that overrides strict mode. + * If there are multiple checks, each one could possible have a different + * configurable item. Each configurable item can be overridden by a different + * settable. + */ +typedef struct ossl_fips_ind_st { + unsigned char approved; + signed char settable[OSSL_FIPS_IND_SETTABLE_MAX]; /* See OSSL_FIPS_IND_STATE */ +} OSSL_FIPS_IND; + +typedef int (OSSL_FIPS_IND_CHECK_CB)(OSSL_LIB_CTX *libctx); + +int ossl_FIPS_IND_callback(OSSL_LIB_CTX *libctx, const char *type, + const char *desc); + +void ossl_FIPS_IND_init(OSSL_FIPS_IND *ind); +void ossl_FIPS_IND_set_approved(OSSL_FIPS_IND *ind); +void ossl_FIPS_IND_set_settable(OSSL_FIPS_IND *ind, int id, int enable); +int ossl_FIPS_IND_get_settable(const OSSL_FIPS_IND *ind, int id); +int ossl_FIPS_IND_on_unapproved(OSSL_FIPS_IND *ind, int id, OSSL_LIB_CTX *libctx, + const char *algname, const char *opname, + OSSL_FIPS_IND_CHECK_CB *config_check_fn); +int ossl_FIPS_IND_set_ctx_param(OSSL_FIPS_IND *ind, int id, + const OSSL_PARAM params[], const char *name); +int ossl_FIPS_IND_get_ctx_param(const OSSL_FIPS_IND *ind, + OSSL_PARAM params[]); +void ossl_FIPS_IND_copy(OSSL_FIPS_IND *dst, const OSSL_FIPS_IND *src); + +/* Place this in the algorithm ctx structure */ +# define OSSL_FIPS_IND_DECLARE OSSL_FIPS_IND indicator; +/* Call this to initialize the indicator */ +# define OSSL_FIPS_IND_INIT(ctx) ossl_FIPS_IND_init(&ctx->indicator); +/* + * Use the copy if an algorithm has a dup function that does not copy the src to + * the dst. + */ +# define OSSL_FIPS_IND_COPY(dst, src) ossl_FIPS_IND_copy(&dst->indicator, &src->indicator); + +/* + * Required for reset - since once something becomes unapproved it will remain + * unapproved unless this is used. This should be used in the init before + * params are set into the ctx & before any FIPS checks are done. + */ +# define OSSL_FIPS_IND_SET_APPROVED(ctx) ossl_FIPS_IND_set_approved(&ctx->indicator); +/* + * This should be called if a FIPS check fails, to indicate the operation is not approved + * If there is more than 1 strict check flag per algorithm ctx, the id represents + * the index. + */ +# define OSSL_FIPS_IND_ON_UNAPPROVED(ctx, id, libctx, algname, opname, config_check_fn) \ + ossl_FIPS_IND_on_unapproved(&ctx->indicator, id, libctx, algname, opname, config_check_fn) + +# define OSSL_FIPS_IND_SETTABLE_CTX_PARAM(name) \ + OSSL_PARAM_int(name, NULL), + +/* + * The id here must match the one used by OSSL_FIPS_IND_ON_UNAPPROVED + * The name must match the param used by OSSL_FIPS_IND_SETTABLE_CTX_PARAM + */ +# define OSSL_FIPS_IND_SET_CTX_PARAM(ctx, id, params, name) \ + ossl_FIPS_IND_set_ctx_param(&((ctx)->indicator), id, params, name) + +# define OSSL_FIPS_IND_GETTABLE_CTX_PARAM() \ + OSSL_PARAM_int(OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR, NULL), + +# define OSSL_FIPS_IND_GET_CTX_PARAM(ctx, prms) \ + ossl_FIPS_IND_get_ctx_param(&((ctx)->indicator), prms) + +# define OSSL_FIPS_IND_GET(ctx) (&((ctx)->indicator)) + +# define OSSL_FIPS_IND_GET_PARAM(ctx, p, settable, id, name) \ + *settable = ossl_FIPS_IND_get_settable(&((ctx)->indicator), id); \ + if (*settable != OSSL_FIPS_IND_STATE_UNKNOWN) \ + *p = OSSL_PARAM_construct_int(name, settable); + +int ossl_fips_ind_rsa_key_check(OSSL_FIPS_IND *ind, int id, OSSL_LIB_CTX *libctx, + const RSA *rsa, const char *desc, int protect); +# ifndef OPENSSL_NO_EC +int ossl_fips_ind_ec_key_check(OSSL_FIPS_IND *ind, int id, OSSL_LIB_CTX *libctx, + const EC_GROUP *group, const char *desc, + int protect); +# endif +int ossl_fips_ind_digest_exch_check(OSSL_FIPS_IND *ind, int id, OSSL_LIB_CTX *libctx, + const EVP_MD *md, const char *desc); +int ossl_fips_ind_digest_sign_check(OSSL_FIPS_IND *ind, int id, + OSSL_LIB_CTX *libctx, + int nid, int sha1_allowed, + const char *desc, + OSSL_FIPS_IND_CHECK_CB *config_check_f); + +#else +# define OSSL_FIPS_IND_DECLARE +# define OSSL_FIPS_IND_INIT(ctx) +# define OSSL_FIPS_IND_SET_APPROVED(ctx) +# define OSSL_FIPS_IND_ON_UNAPPROVED(ctx, id, libctx, algname, opname, configopt_fn) +# define OSSL_FIPS_IND_SETTABLE_CTX_PARAM(name) +# define OSSL_FIPS_IND_SET_CTX_PARAM(ctx, id, params, name) 1 +# define OSSL_FIPS_IND_GETTABLE_CTX_PARAM() +# define OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params) 1 +# define OSSL_FIPS_IND_COPY(dst, src) + +#endif diff --git a/providers/fips/include/fips_indicator_params.inc b/providers/fips/include/fips_indicator_params.inc new file mode 100644 index 0000000000..78f9fc0655 --- /dev/null +++ b/providers/fips/include/fips_indicator_params.inc @@ -0,0 +1,28 @@ +OSSL_FIPS_PARAM(security_checks, SECURITY_CHECKS, 1) +OSSL_FIPS_PARAM(tls1_prf_ems_check, TLS1_PRF_EMS_CHECK, 0) +OSSL_FIPS_PARAM(no_short_mac, NO_SHORT_MAC, 1) +OSSL_FIPS_PARAM(hmac_key_check, HMAC_KEY_CHECK, 0) +OSSL_FIPS_PARAM(kmac_key_check, KMAC_KEY_CHECK, 0) +OSSL_FIPS_PARAM(restricted_drbg_digests, DRBG_TRUNC_DIGEST, 0) +OSSL_FIPS_PARAM(signature_digest_check, SIGNATURE_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(hkdf_digest_check, HKDF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(tls13_kdf_digest_check, TLS13_KDF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(tls1_prf_digest_check, TLS1_PRF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(sshkdf_digest_check, SSHKDF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(sskdf_digest_check, SSKDF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(x963kdf_digest_check, X963KDF_DIGEST_CHECK, 0) +OSSL_FIPS_PARAM(dsa_sign_disallowed, DSA_SIGN_DISABLED, 0) +OSSL_FIPS_PARAM(tdes_encrypt_disallowed, TDES_ENCRYPT_DISABLED, 0) +OSSL_FIPS_PARAM(rsa_pkcs15_padding_disabled, RSA_PKCS15_PAD_DISABLED, 0) +OSSL_FIPS_PARAM(rsa_pss_saltlen_check, RSA_PSS_SALTLEN_CHECK, 0) +OSSL_FIPS_PARAM(rsa_sign_x931_disallowed, RSA_SIGN_X931_PAD_DISABLED, 0) +OSSL_FIPS_PARAM(hkdf_key_check, HKDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(kbkdf_key_check, KBKDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(tls13_kdf_key_check, TLS13_KDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(tls1_prf_key_check, TLS1_PRF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(sshkdf_key_check, SSHKDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(sskdf_key_check, SSKDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(x963kdf_key_check, X963KDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(x942kdf_key_check, X942KDF_KEY_CHECK, 0) +OSSL_FIPS_PARAM(pbkdf2_lower_bound_check, PBKDF2_LOWER_BOUND_CHECK, 1) +OSSL_FIPS_PARAM(ecdh_cofactor_check, ECDH_COFACTOR_CHECK, 0) diff --git a/providers/fips/include/fips_selftest_params.inc b/providers/fips/include/fips_selftest_params.inc new file mode 100644 index 0000000000..df942d9cea --- /dev/null +++ b/providers/fips/include/fips_selftest_params.inc @@ -0,0 +1,3 @@ +OSSL_FIPS_PARAM(module_filename, OSSL_PROV_PARAM_CORE_MODULE_FILENAME) +OSSL_FIPS_PARAM(module_checksum_data, OSSL_PROV_FIPS_PARAM_MODULE_MAC) +OSSL_FIPS_PARAM(conditional_error_check, OSSL_PROV_FIPS_PARAM_CONDITIONAL_ERRORS) diff --git a/providers/common/include/prov/fipscommon.h b/providers/fips/include/fipscommon.h similarity index 55% rename from providers/common/include/prov/fipscommon.h rename to providers/fips/include/fipscommon.h index 45ed248e99..5cbf347d1b 100644 --- a/providers/common/include/prov/fipscommon.h +++ b/providers/fips/include/fipscommon.h @@ -1,5 +1,5 @@ /* - * Copyright 2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2023-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -10,8 +10,9 @@ #ifdef FIPS_MODULE # include -int FIPS_security_check_enabled(OSSL_LIB_CTX *libctx); -int FIPS_tls_prf_ems_check(OSSL_LIB_CTX *libctx); -int FIPS_restricted_drbg_digests_enabled(OSSL_LIB_CTX *libctx); +# define OSSL_FIPS_PARAM(structname, paramname, unused) \ + int ossl_fips_config_##structname(OSSL_LIB_CTX *libctx); +# include "fips_indicator_params.inc" +# undef OSSL_FIPS_PARAM #endif diff --git a/providers/fips/self_test.c b/providers/fips/self_test.c index b8dc9817b2..551fadecde 100644 --- a/providers/fips/self_test.c +++ b/providers/fips/self_test.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -50,9 +50,12 @@ static int FIPS_conditional_error_check = 1; static CRYPTO_RWLOCK *self_test_lock = NULL; -static unsigned char fixed_key[32] = { FIPS_KEY_ELEMENTS }; static CRYPTO_ONCE fips_self_test_init = CRYPTO_ONCE_STATIC_INIT; +#if !defined(OPENSSL_NO_FIPS_POST) +static unsigned char fixed_key[32] = { FIPS_KEY_ELEMENTS }; +#endif + DEFINE_RUN_ONCE_STATIC(do_fips_self_test_init) { /* @@ -172,6 +175,7 @@ DEP_FINI_ATTRIBUTE void cleanup(void) } #endif +#if !defined(OPENSSL_NO_FIPS_POST) /* * We need an explicit HMAC-SHA-256 KAT even though it is also * checked as part of the KDF KATs. Refer IG 10.3. @@ -287,6 +291,7 @@ static int verify_integrity(OSSL_CORE_BIO *bio, OSSL_FUNC_BIO_read_ex_fn read_ex EVP_MAC_free(mac); return ret; } +#endif /* OPENSSL_NO_FIPS_POST */ static void set_fips_state(int state) { @@ -296,16 +301,16 @@ static void set_fips_state(int state) /* This API is triggered either on loading of the FIPS module or on demand */ int SELF_TEST_post(SELF_TEST_POST_PARAMS *st, int on_demand_test) { + int loclstate; +#if !defined(OPENSSL_NO_FIPS_POST) int ok = 0; - int kats_already_passed = 0; long checksum_len; - OSSL_CORE_BIO *bio_module = NULL, *bio_indicator = NULL; + OSSL_CORE_BIO *bio_module = NULL; unsigned char *module_checksum = NULL; - unsigned char *indicator_checksum = NULL; - int loclstate; OSSL_SELF_TEST *ev = NULL; EVP_RAND *testrand = NULL; EVP_RAND_CTX *rng; +#endif if (!RUN_ONCE(&fips_self_test_init, do_fips_self_test_init)) return 0; @@ -322,6 +327,8 @@ int SELF_TEST_post(SELF_TEST_POST_PARAMS *st, int on_demand_test) if (!CRYPTO_THREAD_write_lock(self_test_lock)) return 0; + +#if !defined(OPENSSL_NO_FIPS_POST) loclstate = tsan_load(&FIPS_state); if (loclstate == FIPS_STATE_RUNNING) { if (!on_demand_test) { @@ -362,48 +369,9 @@ int SELF_TEST_post(SELF_TEST_POST_PARAMS *st, int on_demand_test) goto end; } - /* This will be NULL during installation - so the self test KATS will run */ - if (st->indicator_data != NULL) { - /* - * If the kats have already passed indicator is set - then check the - * integrity of the indicator. - */ - if (st->indicator_checksum_data == NULL) { - ERR_raise(ERR_LIB_PROV, PROV_R_MISSING_CONFIG_DATA); - goto end; - } - indicator_checksum = OPENSSL_hexstr2buf(st->indicator_checksum_data, - &checksum_len); - if (indicator_checksum == NULL) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_CONFIG_DATA); - goto end; - } - - bio_indicator = - (*st->bio_new_buffer_cb)(st->indicator_data, - strlen(st->indicator_data)); - if (bio_indicator == NULL - || !verify_integrity(bio_indicator, st->bio_read_ex_cb, - indicator_checksum, checksum_len, - st->libctx, ev, - OSSL_SELF_TEST_TYPE_INSTALL_INTEGRITY)) { - ERR_raise(ERR_LIB_PROV, PROV_R_INDICATOR_INTEGRITY_FAILURE); - goto end; - } else { - kats_already_passed = 1; - } - } - - /* - * Only runs the KAT's during installation OR on_demand(). - * NOTE: If the installation option 'self_test_onload' is chosen then this - * path will always be run, since kats_already_passed will always be 0. - */ - if (on_demand_test || kats_already_passed == 0) { - if (!SELF_TEST_kats(ev, st->libctx)) { - ERR_raise(ERR_LIB_PROV, PROV_R_SELF_TEST_KAT_FAILURE); - goto end; - } + if (!SELF_TEST_kats(ev, st->libctx)) { + ERR_raise(ERR_LIB_PROV, PROV_R_SELF_TEST_KAT_FAILURE); + goto end; } /* Verify that the RNG has been restored properly */ @@ -421,12 +389,10 @@ int SELF_TEST_post(SELF_TEST_POST_PARAMS *st, int on_demand_test) EVP_RAND_free(testrand); OSSL_SELF_TEST_free(ev); OPENSSL_free(module_checksum); - OPENSSL_free(indicator_checksum); - if (st != NULL) { - (*st->bio_free_cb)(bio_indicator); + if (st != NULL) (*st->bio_free_cb)(bio_module); - } + if (ok) set_fips_state(FIPS_STATE_RUNNING); else @@ -434,6 +400,11 @@ int SELF_TEST_post(SELF_TEST_POST_PARAMS *st, int on_demand_test) CRYPTO_THREAD_unlock(self_test_lock); return ok; +#else + set_fips_state(FIPS_STATE_RUNNING); + CRYPTO_THREAD_unlock(self_test_lock); + return 1; +#endif /* !defined(OPENSSL_NO_FIPS_POST) */ } void SELF_TEST_disable_conditional_error_state(void) diff --git a/providers/fips/self_test.h b/providers/fips/self_test.h index ff5928eeb4..cdc90d8d04 100644 --- a/providers/fips/self_test.h +++ b/providers/fips/self_test.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,11 +16,6 @@ typedef struct self_test_post_params_st { const char *module_filename; /* Module file to perform MAC on */ const char *module_checksum_data; /* Expected module MAC integrity */ - /* Used for KAT install indicator integrity check */ - const char *indicator_version; /* version - for future proofing */ - const char *indicator_data; /* data to perform MAC on */ - const char *indicator_checksum_data; /* Expected MAC integrity value */ - /* Used for continuous tests */ const char *conditional_error_check; diff --git a/providers/fips/self_test_data.inc b/providers/fips/self_test_data.inc index d2a4778e92..65ed70f406 100644 --- a/providers/fips/self_test_data.inc +++ b/providers/fips/self_test_data.inc @@ -7,6 +7,15 @@ * https://www.openssl.org/source/license.html */ +/* + * This file contains self test data required by FIPS 140-3 IG + * 10.3.A Cryptographic Algorithm Self test Requirements + * + * Note that in the 'General CAST requirements': Note33 Allows individual + * self tests for low level algorithms (such as digests) to be omitted, if + * they are tested as part of a higher level algorithm (such as HMAC). + */ + /* Macros to build Self test data */ #define ITM(x) ((void *)&x), sizeof(x) #define ITM_STR(x) ((void *)&x), (sizeof(x) - 1) @@ -44,6 +53,11 @@ typedef struct st_kat_st { #define CIPHER_MODE_DECRYPT 2 #define CIPHER_MODE_ALL (CIPHER_MODE_ENCRYPT | CIPHER_MODE_DECRYPT) +/* FIPS 140-3 only allows DSA verification for legacy purposes */ +#define SIGNATURE_MODE_VERIFY_ONLY 1 +#define SIGNATURE_MODE_SIGN_ONLY 2 +#define SIGNATURE_MODE_ONESHOT 4 + typedef ST_KAT ST_KAT_DIGEST; typedef struct st_kat_cipher_st { ST_KAT base; @@ -105,7 +119,10 @@ typedef struct st_kat_sign_st { const char *desc; const char *algorithm; const char *mdalgorithm; + int mode; const ST_KAT_PARAM *key; + const unsigned char *msg; + size_t msg_len; const unsigned char *entropy; size_t entropy_len; const unsigned char *nonce; @@ -114,6 +131,7 @@ typedef struct st_kat_sign_st { size_t persstr_len; const unsigned char *sig_expected; /* Set to NULL if this value changes */ size_t sig_expected_len; + const ST_KAT_PARAM *init; } ST_KAT_SIGN; typedef struct st_kat_asym_cipher_st { @@ -128,13 +146,7 @@ typedef struct st_kat_asym_cipher_st { size_t expected_len; } ST_KAT_ASYM_CIPHER; -/*- DIGEST TEST DATA */ -static const unsigned char sha1_pt[] = "abc"; -static const unsigned char sha1_digest[] = { - 0xA9, 0x99, 0x3E, 0x36, 0x47, 0x06, 0x81, 0x6A, 0xBA, 0x3E, 0x25, 0x71, - 0x78, 0x50, 0xC2, 0x6C, 0x9C, 0xD0, 0xD8, 0x9D -}; - +/*- DIGEST SELF TEST DATA */ static const unsigned char sha512_pt[] = "abc"; static const unsigned char sha512_digest[] = { 0xDD, 0xAF, 0x35, 0xA1, 0x93, 0x61, 0x7A, 0xBA, 0xCC, 0x41, 0x73, 0x49, @@ -151,14 +163,13 @@ static const unsigned char sha3_256_digest[] = { 0x89, 0x77, 0x7f, 0x05, 0x1e, 0x40, 0x46, 0xae }; +/* + * Note: + * SHA1 and SHA256 are tested by higher level algorithms so a + * CAST is not needed. + */ static const ST_KAT_DIGEST st_kat_digest_tests[] = { - { - OSSL_SELF_TEST_DESC_MD_SHA1, - "SHA1", - ITM_STR(sha1_pt), - ITM(sha1_digest), - }, { OSSL_SELF_TEST_DESC_MD_SHA2, "SHA512", @@ -173,7 +184,6 @@ static const ST_KAT_DIGEST st_kat_digest_tests[] = }, }; - /*- CIPHER TEST DATA */ /* DES3 test data */ @@ -240,6 +250,23 @@ static const unsigned char aes_128_ecb_ct[] = { 0x4e, 0xaa, 0x6f, 0xb4, 0xdb, 0xf7, 0x84, 0x65 }; +/* + * TDES-ECB test data from + * https://github.com/usnistgov/ACVP-Server/blob/master/gen-val/json-files/ACVP-TDES-ECB-1.0 + * Decrypt + */ +static const unsigned char tdes_key[] = { + 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, + 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, 0x07, + 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE, 0xFE +}; +static const unsigned char tdes_ct[] = { + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01 +}; +static const unsigned char tdes_pt[] = { + 0x4B, 0xAB, 0x3B, 0xE1, 0x50, 0x2E, 0x3B, 0x36 +}; + static const ST_KAT_CIPHER st_kat_cipher_tests[] = { { { @@ -263,14 +290,46 @@ static const ST_KAT_CIPHER st_kat_cipher_tests[] = { }, CIPHER_MODE_DECRYPT, ITM(aes_128_ecb_key) + }, + { + { + OSSL_SELF_TEST_DESC_CIPHER_TDES, + "DES-EDE3-ECB", + ITM(tdes_pt), + ITM(tdes_ct) + }, + CIPHER_MODE_DECRYPT, + ITM(tdes_key) } }; static const char hkdf_digest[] = "SHA256"; -static const unsigned char hkdf_secret[] = { 's', 'e', 'c', 'r', 'e', 't' }; -static const unsigned char hkdf_salt[] = { 's', 'a', 'l', 't' }; -static const unsigned char hkdf_info[] = { 'l', 'a', 'b', 'e', 'l' }; - +/* + * Input parameters and expected result are from RFC 5869 test case 1, which is + * with a key-derivation key >= 112 bits required by NIST SP 800-131Ar2 + * section 8. + */ +static const unsigned char hkdf_secret[] = { + 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, + 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, + 0x0b, 0x0b, 0x0b, 0x0b, 0x0b, 0x0b +}; +static const unsigned char hkdf_salt[] = { + 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, + 0x08, 0x09, 0x0a, 0x0b, 0x0c +}; +static const unsigned char hkdf_info[] = { + 0xf0, 0xf1, 0xf2, 0xf3, 0xf4, 0xf5, 0xf6, 0xf7, + 0xf8, 0xf9 +}; +static const unsigned char hkdf_expected[] = { + 0x3c, 0xb2, 0x5f, 0x25, 0xfa, 0xac, 0xd5, 0x7a, + 0x90, 0x43, 0x4f, 0x64, 0xd0, 0x36, 0x2f, 0x2a, + 0x2d, 0x2d, 0x0a, 0x90, 0xcf, 0x1a, 0x5a, 0x4c, + 0x5d, 0xb0, 0x2d, 0x56, 0xec, 0xc4, 0xc5, 0xbf, + 0x34, 0x00, 0x72, 0x08, 0xd5, 0xb8, 0x87, 0x18, + 0x58, 0x65 +}; static const ST_KAT_PARAM hkdf_params[] = { ST_KAT_PARAM_UTF8STRING(OSSL_KDF_PARAM_DIGEST, hkdf_digest), ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_KEY, hkdf_secret), @@ -278,10 +337,6 @@ static const ST_KAT_PARAM hkdf_params[] = { ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_INFO, hkdf_info), ST_KAT_PARAM_END() }; -static const unsigned char hkdf_expected[] = { - 0x2a, 0xc4, 0x36, 0x9f, 0x52, 0x59, 0x96, 0xf8, - 0xde, 0x13 -}; static const char sskdf_digest[] = "SHA224"; static const unsigned char sskdf_secret[] = { @@ -376,7 +431,7 @@ static const unsigned char pbkdf2_expected[] = { 0x1c }; static int pbkdf2_iterations = 4096; -static int pbkdf2_pkcs5 = 0; +static int pbkdf2_pkcs5 = 0; /* Enable compliance checks */ static const ST_KAT_PARAM pbkdf2_params[] = { ST_KAT_PARAM_UTF8STRING(OSSL_KDF_PARAM_DIGEST, pbkdf2_digest), ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_PASSWORD, pbkdf2_password), @@ -386,49 +441,6 @@ static const ST_KAT_PARAM pbkdf2_params[] = { ST_KAT_PARAM_END() }; -static const char sshkdf_digest[] = "SHA1"; -static const char sshkdf_type = EVP_KDF_SSHKDF_TYPE_INITIAL_IV_CLI_TO_SRV; -static const unsigned char sshkdf_key[] = { - 0x00, 0x00, 0x00, 0x80, 0x55, 0xba, 0xe9, 0x31, - 0xc0, 0x7f, 0xd8, 0x24, 0xbf, 0x10, 0xad, 0xd1, - 0x90, 0x2b, 0x6f, 0xbc, 0x7c, 0x66, 0x53, 0x47, - 0x38, 0x34, 0x98, 0xa6, 0x86, 0x92, 0x9f, 0xf5, - 0xa2, 0x5f, 0x8e, 0x40, 0xcb, 0x66, 0x45, 0xea, - 0x81, 0x4f, 0xb1, 0xa5, 0xe0, 0xa1, 0x1f, 0x85, - 0x2f, 0x86, 0x25, 0x56, 0x41, 0xe5, 0xed, 0x98, - 0x6e, 0x83, 0xa7, 0x8b, 0xc8, 0x26, 0x94, 0x80, - 0xea, 0xc0, 0xb0, 0xdf, 0xd7, 0x70, 0xca, 0xb9, - 0x2e, 0x7a, 0x28, 0xdd, 0x87, 0xff, 0x45, 0x24, - 0x66, 0xd6, 0xae, 0x86, 0x7c, 0xea, 0xd6, 0x3b, - 0x36, 0x6b, 0x1c, 0x28, 0x6e, 0x6c, 0x48, 0x11, - 0xa9, 0xf1, 0x4c, 0x27, 0xae, 0xa1, 0x4c, 0x51, - 0x71, 0xd4, 0x9b, 0x78, 0xc0, 0x6e, 0x37, 0x35, - 0xd3, 0x6e, 0x6a, 0x3b, 0xe3, 0x21, 0xdd, 0x5f, - 0xc8, 0x23, 0x08, 0xf3, 0x4e, 0xe1, 0xcb, 0x17, - 0xfb, 0xa9, 0x4a, 0x59, -}; -static const unsigned char sshkdf_xcghash[] = { - 0xa4, 0xeb, 0xd4, 0x59, 0x34, 0xf5, 0x67, 0x92, - 0xb5, 0x11, 0x2d, 0xcd, 0x75, 0xa1, 0x07, 0x5f, - 0xdc, 0x88, 0x92, 0x45, -}; -static const unsigned char sshkdf_session_id[] = { - 0xa4, 0xeb, 0xd4, 0x59, 0x34, 0xf5, 0x67, 0x92, - 0xb5, 0x11, 0x2d, 0xcd, 0x75, 0xa1, 0x07, 0x5f, - 0xdc, 0x88, 0x92, 0x45, -}; -static const unsigned char sshkdf_expected[] = { - 0xe2, 0xf6, 0x27, 0xc0, 0xb4, 0x3f, 0x1a, 0xc1, -}; -static const ST_KAT_PARAM sshkdf_params[] = { - ST_KAT_PARAM_UTF8STRING(OSSL_KDF_PARAM_DIGEST, sshkdf_digest), - ST_KAT_PARAM_UTF8CHAR(OSSL_KDF_PARAM_SSHKDF_TYPE, sshkdf_type), - ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_KEY, sshkdf_key), - ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_SSHKDF_XCGHASH, sshkdf_xcghash), - ST_KAT_PARAM_OCTET(OSSL_KDF_PARAM_SSHKDF_SESSION_ID, sshkdf_session_id), - ST_KAT_PARAM_END() -}; - static const char tls12prf_digest[] = "SHA256"; static const unsigned char tls12prf_secret[] = { 0x20, 0x2c, 0x88, 0xc0, 0x0f, 0x84, 0xa1, 0x7a, @@ -576,6 +588,11 @@ static const ST_KAT_PARAM tls13_kdf_client_early_secret_params[] = { ST_KAT_PARAM_END() }; +/* + * NOTES: + * According to FIPS 140-3 10.3.A Note18: SSH KDF is not required, since it is + * sufficient to self-test the underlying SHA hash functions. + */ static const ST_KAT_KDF st_kat_kdf_tests[] = { { @@ -602,12 +619,6 @@ static const ST_KAT_KDF st_kat_kdf_tests[] = pbkdf2_params, ITM(pbkdf2_expected) }, - { - OSSL_SELF_TEST_DESC_KDF_SSHKDF, - OSSL_KDF_NAME_SSHKDF, - sshkdf_params, - ITM(sshkdf_expected) - }, { OSSL_SELF_TEST_DESC_KDF_KBKDF, OSSL_KDF_NAME_KBKDF, @@ -857,80 +868,6 @@ static const ST_KAT_DRBG st_kat_drbg_tests[] = #ifndef OPENSSL_NO_DH /* DH KAT */ -static const unsigned char dh_p[] = { - 0xdc, 0xca, 0x15, 0x11, 0xb2, 0x31, 0x32, 0x25, - 0xf5, 0x21, 0x16, 0xe1, 0x54, 0x27, 0x89, 0xe0, - 0x01, 0xf0, 0x42, 0x5b, 0xcc, 0xc7, 0xf3, 0x66, - 0xf7, 0x40, 0x64, 0x07, 0xf1, 0xc9, 0xfa, 0x8b, - 0xe6, 0x10, 0xf1, 0x77, 0x8b, 0xb1, 0x70, 0xbe, - 0x39, 0xdb, 0xb7, 0x6f, 0x85, 0xbf, 0x24, 0xce, - 0x68, 0x80, 0xad, 0xb7, 0x62, 0x9f, 0x7c, 0x6d, - 0x01, 0x5e, 0x61, 0xd4, 0x3f, 0xa3, 0xee, 0x4d, - 0xe1, 0x85, 0xf2, 0xcf, 0xd0, 0x41, 0xff, 0xde, - 0x9d, 0x41, 0x84, 0x07, 0xe1, 0x51, 0x38, 0xbb, - 0x02, 0x1d, 0xae, 0xb3, 0x5f, 0x76, 0x2d, 0x17, - 0x82, 0xac, 0xc6, 0x58, 0xd3, 0x2b, 0xd4, 0xb0, - 0x23, 0x2c, 0x92, 0x7d, 0xd3, 0x8f, 0xa0, 0x97, - 0xb3, 0xd1, 0x85, 0x9f, 0xa8, 0xac, 0xaf, 0xb9, - 0x8f, 0x06, 0x66, 0x08, 0xfc, 0x64, 0x4e, 0xc7, - 0xdd, 0xb6, 0xf0, 0x85, 0x99, 0xf9, 0x2a, 0xc1, - 0xb5, 0x98, 0x25, 0xda, 0x84, 0x32, 0x07, 0x7d, - 0xef, 0x69, 0x56, 0x46, 0x06, 0x3c, 0x20, 0x82, - 0x3c, 0x95, 0x07, 0xab, 0x6f, 0x01, 0x76, 0xd4, - 0x73, 0x0d, 0x99, 0x0d, 0xbb, 0xe6, 0x36, 0x1c, - 0xd8, 0xb2, 0xb9, 0x4d, 0x3d, 0x2f, 0x32, 0x9b, - 0x82, 0x09, 0x9b, 0xd6, 0x61, 0xf4, 0x29, 0x50, - 0xf4, 0x03, 0xdf, 0x3e, 0xde, 0x62, 0xa3, 0x31, - 0x88, 0xb0, 0x27, 0x98, 0xba, 0x82, 0x3f, 0x44, - 0xb9, 0x46, 0xfe, 0x9d, 0xf6, 0x77, 0xa0, 0xc5, - 0xa1, 0x23, 0x8e, 0xaa, 0x97, 0xb7, 0x0f, 0x80, - 0xda, 0x8c, 0xac, 0x88, 0xe0, 0x92, 0xb1, 0x12, - 0x70, 0x60, 0xff, 0xbf, 0x45, 0x57, 0x99, 0x94, - 0x01, 0x1d, 0xc2, 0xfa, 0xa5, 0xe7, 0xf6, 0xc7, - 0x62, 0x45, 0xe1, 0xcc, 0x31, 0x22, 0x31, 0xc1, - 0x7d, 0x1c, 0xa6, 0xb1, 0x90, 0x07, 0xef, 0x0d, - 0xb9, 0x9f, 0x9c, 0xb6, 0x0e, 0x1d, 0x5f, 0x69 -}; -static const unsigned char dh_q[] = { - 0x89, 0x8b, 0x22, 0x67, 0x17, 0xef, 0x03, 0x9e, - 0x60, 0x3e, 0x82, 0xe5, 0xc7, 0xaf, 0xe4, 0x83, - 0x74, 0xac, 0x5f, 0x62, 0x5c, 0x54, 0xf1, 0xea, - 0x11, 0xac, 0xb5, 0x7d -}; -static const unsigned char dh_g[] = { - 0x5e, 0xf7, 0xb8, 0x8f, 0x2d, 0xf6, 0x01, 0x39, - 0x35, 0x1d, 0xfb, 0xfe, 0x12, 0x66, 0x80, 0x5f, - 0xdf, 0x35, 0x6c, 0xdf, 0xd1, 0x3a, 0x4d, 0xa0, - 0x05, 0x0c, 0x7e, 0xde, 0x24, 0x6d, 0xf5, 0x9f, - 0x6a, 0xbf, 0x96, 0xad, 0xe5, 0xf2, 0xb2, 0x8f, - 0xfe, 0x88, 0xd6, 0xbc, 0xe7, 0xf7, 0x89, 0x4a, - 0x3d, 0x53, 0x5f, 0xc8, 0x21, 0x26, 0xdd, 0xd4, - 0x24, 0x87, 0x2e, 0x16, 0xb8, 0x38, 0xdf, 0x8c, - 0x51, 0xe9, 0x01, 0x6f, 0x88, 0x9c, 0x7c, 0x20, - 0x3e, 0x98, 0xa8, 0xb6, 0x31, 0xf9, 0xc7, 0x25, - 0x63, 0xd3, 0x8a, 0x49, 0x58, 0x9a, 0x07, 0x53, - 0xd3, 0x58, 0xe7, 0x83, 0x31, 0x8c, 0xef, 0xd9, - 0x67, 0x7c, 0x7b, 0x2d, 0xbb, 0x77, 0xd6, 0xdc, - 0xe2, 0xa1, 0x96, 0x37, 0x95, 0xca, 0x64, 0xb9, - 0x2d, 0x1c, 0x9a, 0xac, 0x6d, 0x0e, 0x8d, 0x43, - 0x1d, 0xe5, 0xe5, 0x00, 0x60, 0xdf, 0xf7, 0x86, - 0x89, 0xc9, 0xec, 0xa1, 0xc1, 0x24, 0x8c, 0x16, - 0xed, 0x09, 0xc7, 0xad, 0x41, 0x2a, 0x17, 0x40, - 0x6d, 0x2b, 0x52, 0x5a, 0xa1, 0xca, 0xbb, 0x23, - 0x7b, 0x97, 0x34, 0xec, 0x7b, 0x8c, 0xe3, 0xfa, - 0xe0, 0x2f, 0x29, 0xc5, 0xef, 0xed, 0x30, 0xd6, - 0x91, 0x87, 0xda, 0x10, 0x9c, 0x2c, 0x9f, 0xe2, - 0xaa, 0xdb, 0xb0, 0xc2, 0x2a, 0xf5, 0x4c, 0x61, - 0x66, 0x55, 0x00, 0x0c, 0x43, 0x1c, 0x6b, 0x4a, - 0x37, 0x97, 0x63, 0xb0, 0xa9, 0x16, 0x58, 0xef, - 0xc8, 0x4e, 0x8b, 0x06, 0x35, 0x8c, 0x8b, 0x4f, - 0x21, 0x37, 0x10, 0xfd, 0x10, 0x17, 0x2c, 0xf3, - 0x9b, 0x83, 0x0c, 0x2d, 0xd8, 0x4a, 0x0c, 0x8a, - 0xb8, 0x25, 0x16, 0xec, 0xab, 0x99, 0x5f, 0xa4, - 0x21, 0x5e, 0x02, 0x3e, 0x4e, 0xcf, 0x80, 0x74, - 0xc3, 0x9d, 0x6c, 0x88, 0xb7, 0x0d, 0x1e, 0xe4, - 0xe9, 0x6f, 0xdc, 0x20, 0xea, 0x11, 0x5c, 0x32 -}; static const unsigned char dh_priv[] = { 0x14, 0x33, 0xe0, 0xb5, 0xa9, 0x17, 0xb6, 0x0a, 0x30, 0x23, 0xf2, 0xf8, 0xaa, 0x2c, 0x2d, 0x70, @@ -1006,45 +943,44 @@ static const unsigned char dh_peer_pub[] = { 0x34, 0xf9, 0x67, 0x39, 0xf1, 0x7f, 0xf4, 0x8b }; -static const unsigned char dh_secret_expected[] = { - 0x08, 0xff, 0x33, 0xbb, 0x2e, 0xcf, 0xf4, 0x9a, - 0x7d, 0x4a, 0x79, 0x12, 0xae, 0xb1, 0xbb, 0x6a, - 0xb5, 0x11, 0x64, 0x1b, 0x4a, 0x76, 0x77, 0x0c, - 0x8c, 0xc1, 0xbc, 0xc2, 0x33, 0x34, 0x3d, 0xfe, - 0x70, 0x0d, 0x11, 0x81, 0x3d, 0x2c, 0x9e, 0xd2, - 0x3b, 0x21, 0x1c, 0xa9, 0xe8, 0x78, 0x69, 0x21, - 0xed, 0xca, 0x28, 0x3c, 0x68, 0xb1, 0x61, 0x53, - 0xfa, 0x01, 0xe9, 0x1a, 0xb8, 0x2c, 0x90, 0xdd, - 0xab, 0x4a, 0x95, 0x81, 0x67, 0x70, 0xa9, 0x87, - 0x10, 0xe1, 0x4c, 0x92, 0xab, 0x83, 0xb6, 0xe4, - 0x6e, 0x1e, 0x42, 0x6e, 0xe8, 0x52, 0x43, 0x0d, - 0x61, 0x87, 0xda, 0xa3, 0x72, 0x0a, 0x6b, 0xcd, - 0x73, 0x23, 0x5c, 0x6b, 0x0f, 0x94, 0x1f, 0x33, - 0x64, 0xf5, 0x04, 0x20, 0x55, 0x1a, 0x4b, 0xfe, - 0xaf, 0xe2, 0xbc, 0x43, 0x85, 0x05, 0xa5, 0x9a, - 0x4a, 0x40, 0xda, 0xca, 0x7a, 0x89, 0x5a, 0x73, - 0xdb, 0x57, 0x5c, 0x74, 0xc1, 0x3a, 0x23, 0xad, - 0x88, 0x32, 0x95, 0x7d, 0x58, 0x2d, 0x38, 0xf0, - 0xa6, 0x16, 0x5f, 0xb0, 0xd7, 0xe9, 0xb8, 0x79, - 0x9e, 0x42, 0xfd, 0x32, 0x20, 0xe3, 0x32, 0xe9, - 0x81, 0x85, 0xa0, 0xc9, 0x42, 0x97, 0x57, 0xb2, - 0xd0, 0xd0, 0x2c, 0x17, 0xdb, 0xaa, 0x1f, 0xf6, - 0xed, 0x93, 0xd7, 0xe7, 0x3e, 0x24, 0x1e, 0xae, - 0xd9, 0x0c, 0xaf, 0x39, 0x4d, 0x2b, 0xc6, 0x57, - 0x0f, 0x18, 0xc8, 0x1f, 0x2b, 0xe5, 0xd0, 0x1a, - 0x2c, 0xa9, 0x9f, 0xf1, 0x42, 0xb5, 0xd9, 0x63, - 0xf9, 0xf5, 0x00, 0x32, 0x5e, 0x75, 0x56, 0xf9, - 0x58, 0x49, 0xb3, 0xff, 0xc7, 0x47, 0x94, 0x86, - 0xbe, 0x1d, 0x45, 0x96, 0xa3, 0x10, 0x6b, 0xd5, - 0xcb, 0x4f, 0x61, 0xc5, 0x7e, 0xc5, 0xf1, 0x00, - 0xfb, 0x7a, 0x0c, 0x82, 0xa1, 0x0b, 0x82, 0x52, - 0x6a, 0x97, 0xd1, 0xd9, 0x7d, 0x98, 0xea, 0xf6 -}; - +static const unsigned char dh_secret_expected[256] = { + 0xa0, 0x38, 0x64, 0x37, 0xdf, 0x2d, 0x2c, 0x78, + 0x49, 0xb9, 0xa7, 0x77, 0xfb, 0xc1, 0x69, 0x94, + 0x85, 0xc5, 0x5a, 0xbc, 0x8d, 0x43, 0x32, 0x23, + 0x94, 0xf5, 0xba, 0xb4, 0x5f, 0x22, 0x4b, 0x4e, + 0xc4, 0xfd, 0x89, 0x41, 0x56, 0x41, 0xe8, 0x9f, + 0x2d, 0x0d, 0x26, 0x33, 0x60, 0x13, 0x8a, 0x20, + 0xf1, 0x7e, 0xb3, 0x76, 0x38, 0x03, 0x0e, 0x48, + 0x4f, 0x27, 0x8c, 0x32, 0xdb, 0x66, 0x5c, 0xbf, + 0x7f, 0xc7, 0xeb, 0xc6, 0x2d, 0xfd, 0x00, 0x08, + 0xb0, 0x98, 0x4e, 0xad, 0x68, 0x65, 0xca, 0x9e, + 0x78, 0xe1, 0xaa, 0xb7, 0x8e, 0x08, 0x4d, 0x67, + 0xa6, 0x15, 0x16, 0xbb, 0x41, 0xac, 0x15, 0xb5, + 0x08, 0x92, 0x5d, 0x25, 0x1d, 0x7f, 0xf3, 0x1b, + 0x5c, 0xea, 0x21, 0x6b, 0xe5, 0x00, 0x4d, 0xb6, + 0x8e, 0xae, 0x84, 0xb4, 0xee, 0xf7, 0xcc, 0xdd, + 0x64, 0x19, 0x4e, 0x25, 0xce, 0x37, 0x4f, 0xde, + 0xb6, 0x21, 0xba, 0xd9, 0xc0, 0x7a, 0x87, 0xc7, + 0x90, 0x0a, 0x78, 0x8b, 0xdd, 0xbc, 0x68, 0x77, + 0x2d, 0xa6, 0xdf, 0x4d, 0x2e, 0xca, 0xdc, 0x86, + 0xb6, 0x1e, 0x54, 0x2b, 0x3a, 0xa9, 0x52, 0x67, + 0xf3, 0x1a, 0x35, 0xb7, 0x5a, 0xcd, 0x99, 0x59, + 0xe9, 0x07, 0x6f, 0xd7, 0xd7, 0x96, 0x8a, 0x47, + 0xdf, 0x9f, 0x51, 0x1b, 0x04, 0xa9, 0x45, 0x30, + 0x89, 0x8a, 0x3f, 0x7e, 0xca, 0xfc, 0x05, 0x2d, + 0x18, 0x77, 0x8f, 0x45, 0x25, 0x39, 0xdb, 0xf2, + 0x13, 0x36, 0x31, 0xdb, 0x50, 0x65, 0x63, 0x4a, + 0xae, 0x3e, 0xd1, 0x3e, 0xde, 0xc1, 0x32, 0x4b, + 0x78, 0x19, 0x03, 0x70, 0x0a, 0xc2, 0xa2, 0x6f, + 0x9b, 0xd4, 0xa6, 0x1d, 0x47, 0xf2, 0xa6, 0x91, + 0x61, 0x4a, 0x74, 0xf8, 0x70, 0x39, 0x42, 0x72, + 0xd5, 0x58, 0x7f, 0xcd, 0x16, 0xeb, 0x82, 0x0c, + 0x2c, 0xf4, 0xd0, 0x95, 0x22, 0xf9, 0xbe, 0x99, +}; + +static const char dh_ffdhe2048[] = "ffdhe2048"; static const ST_KAT_PARAM dh_group[] = { - ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_FFC_P, dh_p), - ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_FFC_Q, dh_q), - ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_FFC_G, dh_g), + ST_KAT_PARAM_UTF8STRING(OSSL_PKEY_PARAM_GROUP_NAME, dh_ffdhe2048), ST_KAT_PARAM_END() }; @@ -1339,6 +1275,8 @@ static const ST_KAT_PARAM rsa_enc_params[] = { ST_KAT_PARAM_END() }; +static const unsigned char rsa_sig_msg[] = "Hello World!"; + static const unsigned char rsa_expected_sig[256] = { 0xad, 0xbe, 0x2a, 0xaf, 0x16, 0x85, 0xc5, 0x00, 0x91, 0x3e, 0xd0, 0x49, 0xfb, 0x3a, 0x81, 0xb9, @@ -1485,6 +1423,83 @@ static const ST_KAT_PARAM ecdsa_bin_key[] = { ST_KAT_PARAM_END() }; # endif /* OPENSSL_NO_EC2M */ + +# ifndef OPENSSL_NO_ECX +static const unsigned char ecx_sig_msg[] = { + 0x64, 0xa6, 0x5f, 0x3c, 0xde, 0xdc, 0xdd, 0x66, + 0x81, 0x1e, 0x29, 0x15 +}; +static const unsigned char ed25519_pub[] = { + 0xfc, 0x51, 0xcd, 0x8e, 0x62, 0x18, 0xa1, 0xa3, + 0x8d, 0xa4, 0x7e, 0xd0, 0x02, 0x30, 0xf0, 0x58, + 0x08, 0x16, 0xed, 0x13, 0xba, 0x33, 0x03, 0xac, + 0x5d, 0xeb, 0x91, 0x15, 0x48, 0x90, 0x80, 0x25 +}; +static const unsigned char ed25519_priv[] = { + 0xc5, 0xaa, 0x8d, 0xf4, 0x3f, 0x9f, 0x83, 0x7b, + 0xed, 0xb7, 0x44, 0x2f, 0x31, 0xdc, 0xb7, 0xb1, + 0x66, 0xd3, 0x85, 0x35, 0x07, 0x6f, 0x09, 0x4b, + 0x85, 0xce, 0x3a, 0x2e, 0x0b, 0x44, 0x58, 0xf7 +}; +static const ST_KAT_PARAM ed25519_key[] = { + ST_KAT_PARAM_OCTET(OSSL_PKEY_PARAM_PUB_KEY, ed25519_pub), + ST_KAT_PARAM_OCTET(OSSL_PKEY_PARAM_PRIV_KEY, ed25519_priv), + ST_KAT_PARAM_END() +}; +static const unsigned char ed25519_expected_sig[] = { + 0x1e, 0xf4, 0xc5, 0x61, 0xdc, 0x97, 0x9f, 0xaf, + 0x55, 0x6b, 0x46, 0xa1, 0xae, 0xb0, 0x64, 0x13, + 0x1c, 0x98, 0x09, 0x96, 0x88, 0xe0, 0x9d, 0x0e, + 0x4e, 0x7d, 0xc4, 0xa5, 0xa1, 0x91, 0x09, 0xca, + 0xd9, 0x5b, 0x4f, 0x1c, 0x80, 0x82, 0x9f, 0x65, + 0xc1, 0x41, 0xa4, 0xe8, 0x02, 0x05, 0x0c, 0xa6, + 0x7e, 0xa0, 0xfa, 0x01, 0xee, 0xeb, 0xaa, 0x91, + 0x62, 0xfd, 0x0f, 0x25, 0xa0, 0x2d, 0x37, 0x09 +}; + +static const unsigned char ed448_pub[] = { + 0x3b, 0xa1, 0x6d, 0xa0, 0xc6, 0xf2, 0xcc, 0x1f, + 0x30, 0x18, 0x77, 0x40, 0x75, 0x6f, 0x5e, 0x79, + 0x8d, 0x6b, 0xc5, 0xfc, 0x01, 0x5d, 0x7c, 0x63, + 0xcc, 0x95, 0x10, 0xee, 0x3f, 0xd4, 0x4a, 0xdc, + 0x24, 0xd8, 0xe9, 0x68, 0xb6, 0xe4, 0x6e, 0x6f, + 0x94, 0xd1, 0x9b, 0x94, 0x53, 0x61, 0x72, 0x6b, + 0xd7, 0x5e, 0x14, 0x9e, 0xf0, 0x98, 0x17, 0xf5, + 0x80 +}; +static const unsigned char ed448_priv[] = { + 0x25, 0x8c, 0xdd, 0x4a, 0xda, 0x32, 0xed, 0x9c, + 0x9f, 0xf5, 0x4e, 0x63, 0x75, 0x6a, 0xe5, 0x82, + 0xfb, 0x8f, 0xab, 0x2a, 0xc7, 0x21, 0xf2, 0xc8, + 0xe6, 0x76, 0xa7, 0x27, 0x68, 0x51, 0x3d, 0x93, + 0x9f, 0x63, 0xdd, 0xdb, 0x55, 0x60, 0x91, 0x33, + 0xf2, 0x9a, 0xdf, 0x86, 0xec, 0x99, 0x29, 0xdc, + 0xcb, 0x52, 0xc1, 0xc5, 0xfd, 0x2f, 0xf7, 0xe2, + 0x1b +}; +static const ST_KAT_PARAM ed448_key[] = { + ST_KAT_PARAM_OCTET(OSSL_PKEY_PARAM_PUB_KEY, ed448_pub), + ST_KAT_PARAM_OCTET(OSSL_PKEY_PARAM_PRIV_KEY, ed448_priv), + ST_KAT_PARAM_END() +}; +static const unsigned char ed448_expected_sig[] = { + 0x7e, 0xee, 0xab, 0x7c, 0x4e, 0x50, 0xfb, 0x79, + 0x9b, 0x41, 0x8e, 0xe5, 0xe3, 0x19, 0x7f, 0xf6, + 0xbf, 0x15, 0xd4, 0x3a, 0x14, 0xc3, 0x43, 0x89, + 0xb5, 0x9d, 0xd1, 0xa7, 0xb1, 0xb8, 0x5b, 0x4a, + 0xe9, 0x04, 0x38, 0xac, 0xa6, 0x34, 0xbe, 0xa4, + 0x5e, 0x3a, 0x26, 0x95, 0xf1, 0x27, 0x0f, 0x07, + 0xfd, 0xcd, 0xf7, 0xc6, 0x2b, 0x8e, 0xfe, 0xaf, + 0x00, 0xb4, 0x5c, 0x2c, 0x96, 0xba, 0x45, 0x7e, + 0xb1, 0xa8, 0xbf, 0x07, 0x5a, 0x3d, 0xb2, 0x8e, + 0x5c, 0x24, 0xf6, 0xb9, 0x23, 0xed, 0x4a, 0xd7, + 0x47, 0xc3, 0xc9, 0xe0, 0x3c, 0x70, 0x79, 0xef, + 0xb8, 0x7c, 0xb1, 0x10, 0xd3, 0xa9, 0x98, 0x61, + 0xe7, 0x20, 0x03, 0xcb, 0xae, 0x6d, 0x6b, 0x8b, + 0x82, 0x7e, 0x4e, 0x6c, 0x14, 0x30, 0x64, 0xff, + 0x3c, 0x00 +}; +# endif /* OPENSSL_NO_ECX */ #endif /* OPENSSL_NO_EC */ #ifndef OPENSSL_NO_DSA @@ -1597,12 +1612,6 @@ static const unsigned char dsa_pub[] = { 0xe5, 0x1b, 0x16, 0xa4, 0xe3, 0x92, 0x15, 0xea, 0x0b, 0x17, 0xc4, 0x73, 0x59, 0x74, 0xc5, 0x16 }; -static const unsigned char dsa_priv[] = { - 0x6c, 0xca, 0xee, 0xf6, 0xd7, 0x3b, 0x4e, 0x80, - 0xf1, 0x1c, 0x17, 0xb8, 0xe9, 0x62, 0x7c, 0x03, - 0x66, 0x35, 0xba, 0xc3, 0x94, 0x23, 0x50, 0x5e, - 0x40, 0x7e, 0x5c, 0xb7 -}; static const unsigned char dsa_expected_sig[] = { 0x30, 0x3c, 0x02, 0x1c, 0x69, 0xc6, 0xd6, 0x9e, 0x2b, 0x91, 0xea, 0x72, 0xb3, 0x8b, 0x7c, 0x57, @@ -1619,7 +1628,6 @@ static const ST_KAT_PARAM dsa_key[] = { ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_FFC_Q, dsa_q), ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_FFC_G, dsa_g), ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_PUB_KEY, dsa_pub), - ST_KAT_PARAM_BIGNUM(OSSL_PKEY_PARAM_PRIV_KEY, dsa_priv), ST_KAT_PARAM_END() }; #endif /* OPENSSL_NO_DSA */ @@ -1643,9 +1651,9 @@ static const unsigned char sig_kat_persstr[] = { static const ST_KAT_SIGN st_kat_sign_tests[] = { { OSSL_SELF_TEST_DESC_SIGN_RSA, - "RSA", - "SHA-256", + "RSA", "SHA-256", 0, rsa_crt_key, + ITM_STR(rsa_sig_msg), ITM(sig_kat_entropyin), ITM(sig_kat_nonce), ITM(sig_kat_persstr), @@ -1654,9 +1662,9 @@ static const ST_KAT_SIGN st_kat_sign_tests[] = { #ifndef OPENSSL_NO_EC { OSSL_SELF_TEST_DESC_SIGN_ECDSA, - "EC", - "SHA-256", + "EC", "SHA-256", 0, ecdsa_prime_key, + ITM_STR(rsa_sig_msg), ITM(sig_kat_entropyin), ITM(sig_kat_nonce), ITM(sig_kat_persstr), @@ -1665,22 +1673,40 @@ static const ST_KAT_SIGN st_kat_sign_tests[] = { # ifndef OPENSSL_NO_EC2M { OSSL_SELF_TEST_DESC_SIGN_ECDSA, - "EC", - "SHA-256", + "EC", "SHA-256", 0, ecdsa_bin_key, + ITM_STR(rsa_sig_msg), ITM(sig_kat_entropyin), ITM(sig_kat_nonce), ITM(sig_kat_persstr), ITM(ecdsa_bin_expected_sig) }, # endif +# ifndef OPENSSL_NO_ECX + { + OSSL_SELF_TEST_DESC_SIGN_EDDSA, + "ED448", NULL, SIGNATURE_MODE_ONESHOT, + ed448_key, + ITM(ecx_sig_msg), + NULL, 0, NULL, 0, NULL, 0, + ITM(ed448_expected_sig), + }, + { + OSSL_SELF_TEST_DESC_SIGN_EDDSA, + "ED25519", NULL, SIGNATURE_MODE_ONESHOT, + ed25519_key, + ITM(ecx_sig_msg), + NULL, 0, NULL, 0, NULL, 0, + ITM(ed25519_expected_sig), + }, +# endif /* OPENSSL_NO_ECX */ #endif /* OPENSSL_NO_EC */ #ifndef OPENSSL_NO_DSA { OSSL_SELF_TEST_DESC_SIGN_DSA, - "DSA", - "SHA-256", + "DSA", "SHA-256", SIGNATURE_MODE_VERIFY_ONLY, dsa_key, + ITM_STR(rsa_sig_msg), ITM(sig_kat_entropyin), ITM(sig_kat_nonce), ITM(sig_kat_persstr), diff --git a/providers/fips/self_test_kats.c b/providers/fips/self_test_kats.c index 856b367e45..8c9c5b5b34 100644 --- a/providers/fips/self_test_kats.c +++ b/providers/fips/self_test_kats.c @@ -162,8 +162,7 @@ static int add_params(OSSL_PARAM_BLD *bld, const ST_KAT_PARAM *params, if (params == NULL) return 1; - for (p = params; p->data != NULL; ++p) - { + for (p = params; p->data != NULL; ++p) { switch (p->type) { case OSSL_PARAM_UNSIGNED_INTEGER: { BIGNUM *bn = BN_CTX_get(ctx); @@ -376,12 +375,15 @@ static int self_test_ka(const ST_KAT_KAS *t, OSSL_PARAM *params = NULL; OSSL_PARAM *params_peer = NULL; unsigned char secret[256]; - size_t secret_len = sizeof(secret); + size_t secret_len = t->expected_len; OSSL_PARAM_BLD *bld = NULL; BN_CTX *bnctx = NULL; OSSL_SELF_TEST_onbegin(st, OSSL_SELF_TEST_TYPE_KAT_KA, t->desc); + if (secret_len > sizeof(secret)) + goto err; + bnctx = BN_CTX_new_ex(libctx); if (bnctx == NULL) goto err; @@ -444,22 +446,19 @@ static int self_test_ka(const ST_KAT_KAS *t, } #endif /* !defined(OPENSSL_NO_DH) || !defined(OPENSSL_NO_EC) */ -static int self_test_sign(const ST_KAT_SIGN *t, - OSSL_SELF_TEST *st, OSSL_LIB_CTX *libctx) +static int self_test_digest_sign(const ST_KAT_SIGN *t, + OSSL_SELF_TEST *st, OSSL_LIB_CTX *libctx) { int ret = 0; - OSSL_PARAM *params = NULL, *params_sig = NULL; - OSSL_PARAM_BLD *bld = NULL; - EVP_PKEY_CTX *sctx = NULL, *kctx = NULL; + OSSL_PARAM *paramskey = NULL, *paramsinit = NULL; + OSSL_PARAM_BLD *bldkey = NULL, *bldinit = NULL; + EVP_MD_CTX *mctx = NULL; + EVP_PKEY_CTX *fromctx = NULL; EVP_PKEY *pkey = NULL; unsigned char sig[256]; BN_CTX *bnctx = NULL; size_t siglen = sizeof(sig); - static const unsigned char dgst[] = { - 0x7f, 0x83, 0xb1, 0x65, 0x7f, 0xf1, 0xfc, 0x53, 0xb9, 0x2d, 0xc1, 0x81, - 0x48, 0xa1, 0xd6, 0x5d, 0xfc, 0x2d, 0x4b, 0x1f, 0xa3, 0xd6, 0x77, 0x28, - 0x4a, 0xdd, 0xd2, 0x00, 0x12, 0x6d, 0x90, 0x69 - }; + int oneshot = 0; const char *typ = OSSL_SELF_TEST_TYPE_KAT_SIGNATURE; if (t->sig_expected == NULL) @@ -467,63 +466,94 @@ static int self_test_sign(const ST_KAT_SIGN *t, OSSL_SELF_TEST_onbegin(st, typ, t->desc); + if (t->entropy != NULL) { + if (!set_kat_drbg(libctx, t->entropy, t->entropy_len, + t->nonce, t->nonce_len, t->persstr, t->persstr_len)) + goto err; + } + bnctx = BN_CTX_new_ex(libctx); if (bnctx == NULL) goto err; - bld = OSSL_PARAM_BLD_new(); - if (bld == NULL) + bldkey = OSSL_PARAM_BLD_new(); + bldinit = OSSL_PARAM_BLD_new(); + if (bldkey == NULL || bldinit == NULL) goto err; - if (!add_params(bld, t->key, bnctx)) + if (!add_params(bldkey, t->key, bnctx)) goto err; - params = OSSL_PARAM_BLD_to_param(bld); + if (!add_params(bldinit, t->init, bnctx)) + goto err; + paramskey = OSSL_PARAM_BLD_to_param(bldkey); + paramsinit = OSSL_PARAM_BLD_to_param(bldinit); - /* Create a EVP_PKEY_CTX to load the DSA key into */ - kctx = EVP_PKEY_CTX_new_from_name(libctx, t->algorithm, ""); - if (kctx == NULL || params == NULL) + fromctx = EVP_PKEY_CTX_new_from_name(libctx, t->algorithm, ""); + if (fromctx == NULL + || paramskey == NULL + || paramsinit == NULL) goto err; - if (EVP_PKEY_fromdata_init(kctx) <= 0 - || EVP_PKEY_fromdata(kctx, &pkey, EVP_PKEY_KEYPAIR, params) <= 0) + if (EVP_PKEY_fromdata_init(fromctx) <= 0 + || EVP_PKEY_fromdata(fromctx, &pkey, EVP_PKEY_KEYPAIR, paramskey) <= 0) goto err; - /* Create a EVP_PKEY_CTX to use for the signing operation */ - sctx = EVP_PKEY_CTX_new_from_pkey(libctx, pkey, NULL); - if (sctx == NULL - || EVP_PKEY_sign_init(sctx) <= 0) + mctx = EVP_MD_CTX_new(); + if (mctx == NULL) goto err; - /* set signature parameters */ - if (!OSSL_PARAM_BLD_push_utf8_string(bld, OSSL_SIGNATURE_PARAM_DIGEST, - t->mdalgorithm, - strlen(t->mdalgorithm) + 1)) - goto err; - params_sig = OSSL_PARAM_BLD_to_param(bld); - if (EVP_PKEY_CTX_set_params(sctx, params_sig) <= 0) - goto err; + oneshot = ((t->mode & SIGNATURE_MODE_ONESHOT) != 0); - if (EVP_PKEY_sign(sctx, sig, &siglen, dgst, sizeof(dgst)) <= 0 - || EVP_PKEY_verify_init(sctx) <= 0 - || EVP_PKEY_CTX_set_params(sctx, params_sig) <= 0) - goto err; + if ((t->mode & SIGNATURE_MODE_VERIFY_ONLY) != 0) { + memcpy(sig, t->sig_expected, t->sig_expected_len); + siglen = t->sig_expected_len; + } else { + if (EVP_DigestSignInit_ex(mctx, NULL, t->mdalgorithm, libctx, NULL, + pkey, paramsinit) <= 0) + goto err; - if (t->sig_expected != NULL - && (siglen != t->sig_expected_len - || memcmp(sig, t->sig_expected, t->sig_expected_len) != 0)) - goto err; + if (oneshot) { + if (EVP_DigestSign(mctx, sig, &siglen, t->msg, t->msg_len) <= 0) + goto err; + } else { + if (EVP_DigestSignUpdate(mctx, t->msg, t->msg_len) <= 0 + || EVP_DigestSignFinal(mctx, sig, &siglen) <= 0) + goto err; + } - OSSL_SELF_TEST_oncorrupt_byte(st, sig); - if (EVP_PKEY_verify(sctx, sig, siglen, dgst, sizeof(dgst)) <= 0) - goto err; + if (t->sig_expected != NULL + && (siglen != t->sig_expected_len + || memcmp(sig, t->sig_expected, t->sig_expected_len) != 0)) + goto err; + } + + if ((t->mode & SIGNATURE_MODE_SIGN_ONLY) == 0) { + if (EVP_DigestVerifyInit_ex(mctx, NULL, t->mdalgorithm, libctx, NULL, + pkey, paramsinit) <= 0) + goto err; + OSSL_SELF_TEST_oncorrupt_byte(st, sig); + if (oneshot) { + if (EVP_DigestVerify(mctx, sig, siglen, t->msg, t->msg_len) <= 0) + goto err; + } else { + if (EVP_DigestVerifyUpdate(mctx, t->msg, t->msg_len) <= 0 + || EVP_DigestVerifyFinal(mctx, sig, siglen) <= 0) + goto err; + } + } ret = 1; err: BN_CTX_free(bnctx); EVP_PKEY_free(pkey); - EVP_PKEY_CTX_free(kctx); - EVP_PKEY_CTX_free(sctx); - OSSL_PARAM_free(params); - OSSL_PARAM_free(params_sig); - OSSL_PARAM_BLD_free(bld); + EVP_PKEY_CTX_free(fromctx); + EVP_MD_CTX_free(mctx); + OSSL_PARAM_free(paramskey); + OSSL_PARAM_free(paramsinit); + OSSL_PARAM_BLD_free(bldkey); + OSSL_PARAM_BLD_free(bldinit); + if (t->entropy != NULL) { + if (!reset_main_drbg(libctx)) + ret = 0; + } OSSL_SELF_TEST_onend(st, ret); return ret; } @@ -693,16 +723,9 @@ static int self_test_kas(OSSL_SELF_TEST *st, OSSL_LIB_CTX *libctx) static int self_test_signatures(OSSL_SELF_TEST *st, OSSL_LIB_CTX *libctx) { int i, ret = 1; - const ST_KAT_SIGN *t; - for (i = 0; ret && i < (int)OSSL_NELEM(st_kat_sign_tests); ++i) { - t = st_kat_sign_tests + i; - if (!set_kat_drbg(libctx, t->entropy, t->entropy_len, - t->nonce, t->nonce_len, t->persstr, t->persstr_len)) - return 0; - if (!self_test_sign(t, st, libctx)) - ret = 0; - if (!reset_main_drbg(libctx)) + for (i = 0; i < (int)OSSL_NELEM(st_kat_sign_tests); ++i) { + if (!self_test_digest_sign(&st_kat_sign_tests[i], st, libctx)) ret = 0; } return ret; diff --git a/providers/implementations/asymciphers/rsa_enc.c b/providers/implementations/asymciphers/rsa_enc.c index 71bfa344d4..3e7fd0f488 100644 --- a/providers/implementations/asymciphers/rsa_enc.c +++ b/providers/implementations/asymciphers/rsa_enc.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -30,7 +30,6 @@ #include "prov/implementations.h" #include "prov/providercommon.h" #include "prov/securitycheck.h" - #include static OSSL_FUNC_asym_cipher_newctx_fn rsa_newctx; @@ -50,7 +49,6 @@ static OSSL_ITEM padding_item[] = { { RSA_NO_PADDING, OSSL_PKEY_RSA_PAD_MODE_NONE }, { RSA_PKCS1_OAEP_PADDING, OSSL_PKEY_RSA_PAD_MODE_OAEP }, /* Correct spelling first */ { RSA_PKCS1_OAEP_PADDING, "oeap" }, - { RSA_X931_PADDING, OSSL_PKEY_RSA_PAD_MODE_X931 }, { 0, NULL } }; @@ -77,6 +75,7 @@ typedef struct { unsigned int alt_version; /* PKCS#1 v1.5 decryption mode */ unsigned int implicit_rejection; + OSSL_FIPS_IND_DECLARE } PROV_RSA_CTX; static void *rsa_newctx(void *provctx) @@ -89,21 +88,22 @@ static void *rsa_newctx(void *provctx) if (prsactx == NULL) return NULL; prsactx->libctx = PROV_LIBCTX_OF(provctx); + OSSL_FIPS_IND_INIT(prsactx) return prsactx; } static int rsa_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[], - int operation) + int operation, const char *desc) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + int protect = 0; if (!ossl_prov_is_running() || prsactx == NULL || vrsa == NULL) return 0; - if (!ossl_rsa_check_key(prsactx->libctx, vrsa, operation)) + if (!ossl_rsa_key_op_get_protect(vrsa, operation, &protect)) return 0; - if (!RSA_up_ref(vrsa)) return 0; RSA_free(prsactx->rsa); @@ -120,19 +120,31 @@ static int rsa_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[], ERR_raise(ERR_LIB_PROV, ERR_R_INTERNAL_ERROR); return 0; } - return rsa_set_ctx_params(prsactx, params); + + OSSL_FIPS_IND_SET_APPROVED(prsactx) + if (!rsa_set_ctx_params(prsactx, params)) + return 0; +#ifdef FIPS_MODULE + if (!ossl_fips_ind_rsa_key_check(OSSL_FIPS_IND_GET(prsactx), + OSSL_FIPS_IND_SETTABLE0, prsactx->libctx, + prsactx->rsa, desc, protect)) + return 0; +#endif + return 1; } static int rsa_encrypt_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - return rsa_init(vprsactx, vrsa, params, EVP_PKEY_OP_ENCRYPT); + return rsa_init(vprsactx, vrsa, params, EVP_PKEY_OP_ENCRYPT, + "RSA Encrypt Init"); } static int rsa_decrypt_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - return rsa_init(vprsactx, vrsa, params, EVP_PKEY_OP_DECRYPT); + return rsa_init(vprsactx, vrsa, params, EVP_PKEY_OP_DECRYPT, + "RSA Decrypt Init"); } static int rsa_encrypt(void *vprsactx, unsigned char *out, size_t *outlen, @@ -144,6 +156,18 @@ static int rsa_encrypt(void *vprsactx, unsigned char *out, size_t *outlen, if (!ossl_prov_is_running()) return 0; +#ifdef FIPS_MODULE + if ((prsactx->pad_mode == RSA_PKCS1_PADDING + || prsactx->pad_mode == RSA_PKCS1_WITH_TLS_PADDING) + && !OSSL_FIPS_IND_ON_UNAPPROVED(prsactx, OSSL_FIPS_IND_SETTABLE1, + prsactx->libctx, "RSA Encrypt", + "PKCS#1 v1.5 padding", + ossl_fips_config_rsa_pkcs15_padding_disabled)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_PADDING_MODE); + return 0; + } +#endif + if (out == NULL) { size_t len = RSA_size(prsactx->rsa); @@ -408,7 +432,8 @@ static int rsa_get_ctx_params(void *vprsactx, OSSL_PARAM *params) p = OSSL_PARAM_locate(params, OSSL_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION); if (p != NULL && !OSSL_PARAM_set_uint(p, prsactx->implicit_rejection)) return 0; - + if (!OSSL_FIPS_IND_GET_CTX_PARAM(prsactx, params)) + return 0; return 1; } @@ -421,6 +446,7 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_TLS_CLIENT_VERSION, NULL), OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_TLS_NEGOTIATED_VERSION, NULL), OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -443,6 +469,13 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_ASYM_CIPHER_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_ASYM_CIPHER_PARAM_FIPS_RSA_PKCS15_PAD_DISABLED)) + return 0; + p = OSSL_PARAM_locate_const(params, OSSL_ASYM_CIPHER_PARAM_OAEP_DIGEST); if (p != NULL) { str = mdname; @@ -566,7 +599,6 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) return 0; prsactx->implicit_rejection = implicit_rejection; } - return 1; } @@ -580,6 +612,8 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_TLS_CLIENT_VERSION, NULL), OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_TLS_NEGOTIATED_VERSION, NULL), OSSL_PARAM_uint(OSSL_ASYM_CIPHER_PARAM_IMPLICIT_REJECTION, NULL), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_ASYM_CIPHER_PARAM_FIPS_KEY_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_ASYM_CIPHER_PARAM_FIPS_RSA_PKCS15_PAD_DISABLED) OSSL_PARAM_END }; diff --git a/providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c b/providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c index 28d3909c4d..abcd747446 100644 --- a/providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c +++ b/providers/implementations/ciphers/cipher_aes_cbc_hmac_sha.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -338,6 +338,9 @@ static void *aes_cbc_hmac_sha1_dupctx(void *provctx) { PROV_AES_HMAC_SHA1_CTX *ctx = provctx; + if (!ossl_prov_is_running()) + return NULL; + if (ctx == NULL) return NULL; @@ -375,6 +378,9 @@ static void *aes_cbc_hmac_sha256_dupctx(void *provctx) { PROV_AES_HMAC_SHA256_CTX *ctx = provctx; + if (!ossl_prov_is_running()) + return NULL; + return OPENSSL_memdup(ctx, sizeof(*ctx)); } diff --git a/providers/implementations/ciphers/cipher_aes_ccm.c b/providers/implementations/ciphers/cipher_aes_ccm.c index 8c96328096..81822c03f9 100644 --- a/providers/implementations/ciphers/cipher_aes_ccm.c +++ b/providers/implementations/ciphers/cipher_aes_ccm.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -38,6 +38,9 @@ static void *aes_ccm_dupctx(void *provctx) PROV_AES_CCM_CTX *ctx = provctx; PROV_AES_CCM_CTX *dupctx = NULL; + if (!ossl_prov_is_running()) + return NULL; + if (ctx == NULL) return NULL; dupctx = OPENSSL_memdup(provctx, sizeof(*ctx)); diff --git a/providers/implementations/ciphers/cipher_aes_gcm.c b/providers/implementations/ciphers/cipher_aes_gcm.c index 1114bd8740..0a45ad70fc 100644 --- a/providers/implementations/ciphers/cipher_aes_gcm.c +++ b/providers/implementations/ciphers/cipher_aes_gcm.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -39,6 +39,9 @@ static void *aes_gcm_dupctx(void *provctx) PROV_AES_GCM_CTX *ctx = provctx; PROV_AES_GCM_CTX *dctx = NULL; + if (!ossl_prov_is_running()) + return NULL; + if (ctx == NULL) return NULL; diff --git a/providers/implementations/ciphers/cipher_aes_gcm_siv_hw.c b/providers/implementations/ciphers/cipher_aes_gcm_siv_hw.c index 9887e1c3a4..2c17ff2375 100644 --- a/providers/implementations/ciphers/cipher_aes_gcm_siv_hw.c +++ b/providers/implementations/ciphers/cipher_aes_gcm_siv_hw.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -318,8 +318,7 @@ static int aes_gcm_siv_dup_ctx(void *vdst, void *vsrc) return 0; } -static const PROV_CIPHER_HW_AES_GCM_SIV aes_gcm_siv_hw = -{ +static const PROV_CIPHER_HW_AES_GCM_SIV aes_gcm_siv_hw = { aes_gcm_siv_initkey, aes_gcm_siv_cipher, aes_gcm_siv_dup_ctx, diff --git a/providers/implementations/ciphers/cipher_aes_ocb.c b/providers/implementations/ciphers/cipher_aes_ocb.c index aec988e44e..ac9224dbb6 100644 --- a/providers/implementations/ciphers/cipher_aes_ocb.c +++ b/providers/implementations/ciphers/cipher_aes_ocb.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -367,12 +367,20 @@ static int aes_ocb_set_ctx_params(void *vctx, const OSSL_PARAM params[]) } if (p->data == NULL) { /* Tag len must be 0 to 16 */ - if (p->data_size > OCB_MAX_TAG_LEN) + if (p->data_size > OCB_MAX_TAG_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_TAG_LENGTH); return 0; + } ctx->taglen = p->data_size; } else { - if (p->data_size != ctx->taglen || ctx->base.enc) + if (ctx->base.enc) { + ERR_raise(ERR_LIB_PROV, ERR_R_PASSED_INVALID_ARGUMENT); + return 0; + } + if (p->data_size != ctx->taglen) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_TAG_LENGTH); return 0; + } memcpy(ctx->tag, p->data, p->data_size); } } diff --git a/providers/implementations/ciphers/cipher_aes_siv_hw.c b/providers/implementations/ciphers/cipher_aes_siv_hw.c index 1e6b3d56e4..fb302c3a88 100644 --- a/providers/implementations/ciphers/cipher_aes_siv_hw.c +++ b/providers/implementations/ciphers/cipher_aes_siv_hw.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -120,8 +120,7 @@ static int aes_siv_cipher(void *vctx, unsigned char *out, return ossl_siv128_decrypt(sctx, in, out, len) > 0; } -static const PROV_CIPHER_HW_AES_SIV aes_siv_hw = -{ +static const PROV_CIPHER_HW_AES_SIV aes_siv_hw = { aes_siv_initkey, aes_siv_cipher, aes_siv_setspeed, diff --git a/providers/implementations/ciphers/cipher_aes_wrp.c b/providers/implementations/ciphers/cipher_aes_wrp.c index 912a47e3fe..e011f4780a 100644 --- a/providers/implementations/ciphers/cipher_aes_wrp.c +++ b/providers/implementations/ciphers/cipher_aes_wrp.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -71,6 +71,9 @@ static void *aes_wrap_dupctx(void *wctx) PROV_AES_WRAP_CTX *ctx = wctx; PROV_AES_WRAP_CTX *dctx = wctx; + if (!ossl_prov_is_running()) + return NULL; + if (ctx == NULL) return NULL; dctx = OPENSSL_memdup(ctx, sizeof(*ctx)); diff --git a/providers/implementations/ciphers/cipher_aes_xts.c b/providers/implementations/ciphers/cipher_aes_xts.c index cce2537ea7..960830e8a6 100644 --- a/providers/implementations/ciphers/cipher_aes_xts.c +++ b/providers/implementations/ciphers/cipher_aes_xts.c @@ -1,6 +1,6 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -111,8 +111,12 @@ static int aes_xts_dinit(void *vctx, const unsigned char *key, size_t keylen, static void *aes_xts_newctx(void *provctx, unsigned int mode, uint64_t flags, size_t kbits, size_t blkbits, size_t ivbits) { - PROV_AES_XTS_CTX *ctx = OPENSSL_zalloc(sizeof(*ctx)); + PROV_AES_XTS_CTX *ctx; + if (!ossl_prov_is_running()) + return NULL; + + ctx = OPENSSL_zalloc(sizeof(*ctx)); if (ctx != NULL) { ossl_cipher_generic_initkey(&ctx->base, kbits, blkbits, ivbits, mode, flags, ossl_prov_cipher_hw_aes_xts(kbits), diff --git a/providers/implementations/ciphers/cipher_chacha20_poly1305_hw.c b/providers/implementations/ciphers/cipher_chacha20_poly1305_hw.c index 8173663e5e..29533efe0e 100644 --- a/providers/implementations/ciphers/cipher_chacha20_poly1305_hw.c +++ b/providers/implementations/ciphers/cipher_chacha20_poly1305_hw.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -398,8 +398,7 @@ static int chacha20_poly1305_aead_cipher(PROV_CIPHER_CTX *bctx, return rv; } -static const PROV_CIPHER_HW_CHACHA20_POLY1305 chacha20poly1305_hw = -{ +static const PROV_CIPHER_HW_CHACHA20_POLY1305 chacha20poly1305_hw = { { chacha20_poly1305_initkey, NULL }, chacha20_poly1305_aead_cipher, chacha20_poly1305_initiv, diff --git a/providers/implementations/ciphers/cipher_cts.c b/providers/implementations/ciphers/cipher_cts.c index 6a596508da..9f58b06c4c 100644 --- a/providers/implementations/ciphers/cipher_cts.c +++ b/providers/implementations/ciphers/cipher_cts.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -68,8 +68,7 @@ typedef struct cts_mode_name2id_st { const char *name; } CTS_MODE_NAME2ID; -static CTS_MODE_NAME2ID cts_modes[] = -{ +static CTS_MODE_NAME2ID cts_modes[] = { { CTS_CS1, OSSL_CIPHER_CTS_MODE_CS1 }, { CTS_CS2, OSSL_CIPHER_CTS_MODE_CS2 }, { CTS_CS3, OSSL_CIPHER_CTS_MODE_CS3 }, diff --git a/providers/implementations/ciphers/cipher_desx_hw.c b/providers/implementations/ciphers/cipher_desx_hw.c index 7dc4c50ef5..31fd18e54c 100644 --- a/providers/implementations/ciphers/cipher_desx_hw.c +++ b/providers/implementations/ciphers/cipher_desx_hw.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -67,8 +67,7 @@ static int cipher_hw_desx_cbc(PROV_CIPHER_CTX *ctx, unsigned char *out, return 1; } -static const PROV_CIPHER_HW desx_cbc = -{ +static const PROV_CIPHER_HW desx_cbc = { cipher_hw_desx_cbc_initkey, cipher_hw_desx_cbc, cipher_hw_desx_copyctx diff --git a/providers/implementations/ciphers/cipher_null.c b/providers/implementations/ciphers/cipher_null.c index c911049e2d..7e934093ce 100644 --- a/providers/implementations/ciphers/cipher_null.c +++ b/providers/implementations/ciphers/cipher_null.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -82,7 +82,7 @@ static int null_cipher(void *vctx, unsigned char *out, size_t *outl, } if (outsize < inl) return 0; - if (in != out) + if (out != NULL && in != out) memcpy(out, in, inl); *outl = inl; return 1; diff --git a/providers/implementations/ciphers/cipher_rc2.c b/providers/implementations/ciphers/cipher_rc2.c index a4cd6bd533..0732098832 100644 --- a/providers/implementations/ciphers/cipher_rc2.c +++ b/providers/implementations/ciphers/cipher_rc2.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -106,7 +106,7 @@ static int rc2_dinit(void *ctx, const unsigned char *key, size_t keylen, static int rc2_get_ctx_params(void *vctx, OSSL_PARAM params[]) { PROV_RC2_CTX *ctx = (PROV_RC2_CTX *)vctx; - OSSL_PARAM *p; + OSSL_PARAM *p, *p1, *p2; if (!ossl_cipher_generic_get_ctx_params(vctx, params)) return 0; @@ -115,15 +115,19 @@ static int rc2_get_ctx_params(void *vctx, OSSL_PARAM params[]) ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); return 0; } - p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS); - if (p != NULL) { + p1 = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS); + p2 = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_ALGORITHM_ID_PARAMS_OLD); + if (p1 != NULL || p2 != NULL) { long num; int i; ASN1_TYPE *type; - unsigned char *d = p->data; - unsigned char **dd = d == NULL ? NULL : &d; + unsigned char *d1 = (p1 == NULL) ? NULL : p1->data; + unsigned char *d2 = (p2 == NULL) ? NULL : p2->data; + unsigned char **dd1 = d1 == NULL ? NULL : &d1; + unsigned char **dd2 = d2 == NULL ? NULL : &d2; - if (p->data_type != OSSL_PARAM_OCTET_STRING) { + if ((p1 != NULL && p1->data_type != OSSL_PARAM_OCTET_STRING) + || (p2 != NULL && p2->data_type != OSSL_PARAM_OCTET_STRING)) { ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); return 0; } @@ -140,13 +144,23 @@ static int rc2_get_ctx_params(void *vctx, OSSL_PARAM params[]) ERR_raise(ERR_LIB_PROV, ERR_R_ASN1_LIB); return 0; } + /* * IF the caller has a buffer, we pray to the gods they got the * size right. There's no way to tell the i2d functions... */ - i = i2d_ASN1_TYPE(type, dd); - if (i >= 0) - p->return_size = (size_t)i; + i = i2d_ASN1_TYPE(type, dd1); + if (p1 != NULL && i >= 0) + p1->return_size = (size_t)i; + + /* + * If the buffers differ, redo the i2d on the second buffer. + * Otherwise, just use |i| as computed above + */ + if (d1 != d2) + i = i2d_ASN1_TYPE(type, dd2); + if (p2 != NULL && i >= 0) + p2->return_size = (size_t)i; ASN1_TYPE_free(type); if (i < 0) { diff --git a/providers/implementations/ciphers/cipher_tdes.h b/providers/implementations/ciphers/cipher_tdes.h index 3c98ed241d..55bd760451 100644 --- a/providers/implementations/ciphers/cipher_tdes.h +++ b/providers/implementations/ciphers/cipher_tdes.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -9,6 +9,7 @@ #include #include +#include "prov/securitycheck.h" #include "crypto/des_platform.h" #define DES_BLOCK_SIZE 8 @@ -25,6 +26,7 @@ typedef struct prov_tdes_ctx_st { void (*cbc) (const void *, void *, size_t, const DES_key_schedule *, unsigned char *); } tstream; + OSSL_FIPS_IND_DECLARE } PROV_TDES_CTX; @@ -40,8 +42,8 @@ static void *tdes_##type##_##lcmode##_newctx(void *provctx) \ static OSSL_FUNC_cipher_get_params_fn tdes_##type##_##lcmode##_get_params; \ static int tdes_##type##_##lcmode##_get_params(OSSL_PARAM params[]) \ { \ - return ossl_cipher_generic_get_params(params, EVP_CIPH_##UCMODE##_MODE, \ - flags, kbits, blkbits, ivbits); \ + return ossl_tdes_get_params(params, EVP_CIPH_##UCMODE##_MODE, \ + flags, kbits, blkbits, ivbits); \ } \ const OSSL_DISPATCH ossl_tdes_##type##_##lcmode##_functions[] = { \ { OSSL_FUNC_CIPHER_ENCRYPT_INIT, (void (*)(void))ossl_tdes_einit }, \ @@ -64,20 +66,25 @@ const OSSL_DISPATCH ossl_tdes_##type##_##lcmode##_functions[] = { \ { OSSL_FUNC_CIPHER_GETTABLE_CTX_PARAMS, \ (void (*)(void))ossl_tdes_gettable_ctx_params }, \ { OSSL_FUNC_CIPHER_SET_CTX_PARAMS, \ - (void (*)(void))ossl_cipher_generic_set_ctx_params }, \ + (void (*)(void))ossl_tdes_set_ctx_params }, \ { OSSL_FUNC_CIPHER_SETTABLE_CTX_PARAMS, \ - (void (*)(void))ossl_cipher_generic_settable_ctx_params }, \ + (void (*)(void))ossl_tdes_settable_ctx_params }, \ OSSL_DISPATCH_END \ } void *ossl_tdes_newctx(void *provctx, int mode, size_t kbits, size_t blkbits, size_t ivbits, uint64_t flags, const PROV_CIPHER_HW *hw); +int ossl_tdes_get_params(OSSL_PARAM params[], unsigned int md, uint64_t flags, + size_t kbits, size_t blkbits, size_t ivbits); + OSSL_FUNC_cipher_dupctx_fn ossl_tdes_dupctx; OSSL_FUNC_cipher_freectx_fn ossl_tdes_freectx; OSSL_FUNC_cipher_encrypt_init_fn ossl_tdes_einit; OSSL_FUNC_cipher_decrypt_init_fn ossl_tdes_dinit; OSSL_FUNC_cipher_get_ctx_params_fn ossl_tdes_get_ctx_params; OSSL_FUNC_cipher_gettable_ctx_params_fn ossl_tdes_gettable_ctx_params; +OSSL_FUNC_cipher_set_ctx_params_fn ossl_tdes_set_ctx_params; +OSSL_FUNC_cipher_settable_ctx_params_fn ossl_tdes_settable_ctx_params; #define PROV_CIPHER_HW_tdes_mode(type, mode) \ static const PROV_CIPHER_HW type##_##mode = { \ diff --git a/providers/implementations/ciphers/cipher_tdes_common.c b/providers/implementations/ciphers/cipher_tdes_common.c index c80d9f16b1..e8564c3d0f 100644 --- a/providers/implementations/ciphers/cipher_tdes_common.c +++ b/providers/implementations/ciphers/cipher_tdes_common.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -29,9 +29,11 @@ void *ossl_tdes_newctx(void *provctx, int mode, size_t kbits, size_t blkbits, return NULL; tctx = OPENSSL_zalloc(sizeof(*tctx)); - if (tctx != NULL) + if (tctx != NULL) { + OSSL_FIPS_IND_INIT(tctx) ossl_cipher_generic_initkey(tctx, kbits, blkbits, ivbits, mode, flags, hw, provctx); + } return tctx; } @@ -46,6 +48,7 @@ void *ossl_tdes_dupctx(void *ctx) ret = OPENSSL_malloc(sizeof(*ret)); if (ret == NULL) return NULL; + OSSL_FIPS_IND_COPY(ret, in) in->base.hw->copyctx(&ret->base, &in->base); return ret; @@ -59,6 +62,19 @@ void ossl_tdes_freectx(void *vctx) OPENSSL_clear_free(ctx, sizeof(*ctx)); } +#ifdef FIPS_MODULE +static int tdes_encrypt_check_approved(PROV_TDES_CTX *ctx, int enc) +{ + /* Triple-DES encryption is not approved in FIPS 140-3 */ + if (enc && !OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + ctx->base.libctx, + "Triple-DES", "Encryption", + ossl_fips_config_tdes_encrypt_disallowed)) + return 0; + return 1; +} +#endif + static int tdes_init(void *vctx, const unsigned char *key, size_t keylen, const unsigned char *iv, size_t ivlen, const OSSL_PARAM params[], int enc) @@ -92,7 +108,13 @@ static int tdes_init(void *vctx, const unsigned char *key, size_t keylen, return 0; ctx->key_set = 1; } - return ossl_cipher_generic_set_ctx_params(ctx, params); + if (!ossl_tdes_set_ctx_params(ctx, params)) + return 0; +#ifdef FIPS_MODULE + if (!tdes_encrypt_check_approved((PROV_TDES_CTX *)ctx, enc)) + return 0; +#endif + return 1; } int ossl_tdes_einit(void *vctx, const unsigned char *key, size_t keylen, @@ -111,11 +133,11 @@ int ossl_tdes_dinit(void *vctx, const unsigned char *key, size_t keylen, CIPHER_DEFAULT_GETTABLE_CTX_PARAMS_START(ossl_tdes) OSSL_PARAM_octet_string(OSSL_CIPHER_PARAM_RANDOM_KEY, NULL, 0), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() CIPHER_DEFAULT_GETTABLE_CTX_PARAMS_END(ossl_tdes) static int tdes_generatekey(PROV_CIPHER_CTX *ctx, void *ptr) { - DES_cblock *deskey = ptr; size_t kl = ctx->keylen; @@ -132,7 +154,7 @@ static int tdes_generatekey(PROV_CIPHER_CTX *ctx, void *ptr) int ossl_tdes_get_ctx_params(void *vctx, OSSL_PARAM params[]) { - PROV_CIPHER_CTX *ctx = (PROV_CIPHER_CTX *)vctx; + PROV_CIPHER_CTX *ctx = (PROV_CIPHER_CTX *)vctx; OSSL_PARAM *p; if (!ossl_cipher_generic_get_ctx_params(vctx, params)) @@ -143,5 +165,42 @@ int ossl_tdes_get_ctx_params(void *vctx, OSSL_PARAM params[]) ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GENERATE_KEY); return 0; } + if (!OSSL_FIPS_IND_GET_CTX_PARAM((PROV_TDES_CTX *)vctx, params)) + return 0; return 1; } + +CIPHER_DEFAULT_SETTABLE_CTX_PARAMS_START(ossl_tdes) + OSSL_PARAM_uint(OSSL_CIPHER_PARAM_PADDING, NULL), + OSSL_PARAM_uint(OSSL_CIPHER_PARAM_NUM, NULL), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK) +CIPHER_DEFAULT_SETTABLE_CTX_PARAMS_END(ossl_tdes) + +int ossl_tdes_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + if (!OSSL_FIPS_IND_SET_CTX_PARAM((PROV_TDES_CTX *)vctx, + OSSL_FIPS_IND_SETTABLE0, params, + OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK)) + return 0; + return ossl_cipher_generic_set_ctx_params(vctx, params); +} + +int ossl_tdes_get_params(OSSL_PARAM params[], unsigned int md, uint64_t flags, + size_t kbits, size_t blkbits, size_t ivbits) +{ +#ifdef FIPS_MODULE + const int decrypt_only = 1; +#else + const int decrypt_only = 0; +#endif + OSSL_PARAM *p; + + p = OSSL_PARAM_locate(params, OSSL_CIPHER_PARAM_DECRYPT_ONLY); + if (p != NULL && !OSSL_PARAM_set_int(p, decrypt_only)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SET_PARAMETER); + return 0; + } + + return ossl_cipher_generic_get_params(params, md, flags, + kbits, blkbits, ivbits); +} diff --git a/providers/implementations/ciphers/cipher_tdes_wrap.c b/providers/implementations/ciphers/cipher_tdes_wrap.c index 391383b550..b48c02ae25 100644 --- a/providers/implementations/ciphers/cipher_tdes_wrap.c +++ b/providers/implementations/ciphers/cipher_tdes_wrap.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -27,8 +27,7 @@ static OSSL_FUNC_cipher_update_fn tdes_wrap_update; static OSSL_FUNC_cipher_cipher_fn tdes_wrap_cipher; -static const unsigned char wrap_iv[8] = -{ +static const unsigned char wrap_iv[8] = { 0x4a, 0xdd, 0xa2, 0x2c, 0x79, 0xe8, 0x21, 0x05 }; diff --git a/providers/implementations/ciphers/ciphercommon.c b/providers/implementations/ciphers/ciphercommon.c index 7ad3eb0a1f..78a5a7b9ef 100644 --- a/providers/implementations/ciphers/ciphercommon.c +++ b/providers/implementations/ciphers/ciphercommon.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -152,6 +152,7 @@ static const OSSL_PARAM cipher_aead_known_gettable_ctx_params[] = { OSSL_PARAM_octet_string(OSSL_CIPHER_PARAM_AEAD_TAG, NULL, 0), OSSL_PARAM_size_t(OSSL_CIPHER_PARAM_AEAD_TLS1_AAD_PAD, NULL), OSSL_PARAM_octet_string(OSSL_CIPHER_PARAM_AEAD_TLS1_GET_IV_GEN, NULL, 0), + OSSL_PARAM_uint(OSSL_CIPHER_PARAM_AEAD_IV_GENERATED, NULL), OSSL_PARAM_END }; const OSSL_PARAM *ossl_cipher_aead_gettable_ctx_params( diff --git a/providers/implementations/ciphers/ciphercommon_gcm.c b/providers/implementations/ciphers/ciphercommon_gcm.c index fe24b450a5..d7f843b376 100644 --- a/providers/implementations/ciphers/ciphercommon_gcm.c +++ b/providers/implementations/ciphers/ciphercommon_gcm.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -236,6 +236,9 @@ int ossl_gcm_get_ctx_params(void *vctx, OSSL_PARAM params[]) || !getivgen(ctx, p->data, p->data_size)) return 0; break; + case PIDX_CIPHER_PARAM_AEAD_IV_GENERATED: + if (!OSSL_PARAM_set_uint(p, ctx->iv_gen_rand)) + return 0; } } return 1; @@ -513,9 +516,11 @@ static int gcm_tls_iv_set_fixed(PROV_GCM_CTX *ctx, unsigned char *iv, return 0; if (len > 0) memcpy(ctx->iv, iv, len); - if (ctx->enc - && RAND_bytes_ex(ctx->libctx, ctx->iv + len, ctx->ivlen - len, 0) <= 0) + if (ctx->enc) { + if (RAND_bytes_ex(ctx->libctx, ctx->iv + len, ctx->ivlen - len, 0) <= 0) return 0; + ctx->iv_gen_rand = 1; + } ctx->iv_gen = 1; ctx->iv_state = IV_STATE_BUFFERED; return 1; diff --git a/providers/implementations/digests/blake2s_prov.c b/providers/implementations/digests/blake2s_prov.c index 72cab1e9a1..a9251d8996 100644 --- a/providers/implementations/digests/blake2s_prov.c +++ b/providers/implementations/digests/blake2s_prov.c @@ -20,14 +20,12 @@ #include "blake2_impl.h" #include "prov/blake2.h" -static const uint32_t blake2s_IV[8] = -{ +static const uint32_t blake2s_IV[8] = { 0x6A09E667U, 0xBB67AE85U, 0x3C6EF372U, 0xA54FF53AU, 0x510E527FU, 0x9B05688CU, 0x1F83D9ABU, 0x5BE0CD19U }; -static const uint8_t blake2s_sigma[10][16] = -{ +static const uint8_t blake2s_sigma[10][16] = { { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15 } , { 14, 10, 4, 8, 9, 15, 13, 6, 1, 12, 0, 2, 11, 7, 5, 3 } , { 11, 8, 12, 0, 5, 2, 15, 13, 10, 14, 3, 6, 7, 1, 9, 4 } , diff --git a/providers/implementations/digests/sha3_prov.c b/providers/implementations/digests/sha3_prov.c index 2fd0f928e7..29c23c2f09 100644 --- a/providers/implementations/digests/sha3_prov.c +++ b/providers/implementations/digests/sha3_prov.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -14,6 +14,7 @@ #include #include #include +#include "internal/numbers.h" #include "internal/sha3.h" #include "prov/digestcommon.h" #include "prov/implementations.h" @@ -34,6 +35,8 @@ static OSSL_FUNC_digest_final_fn keccak_final; static OSSL_FUNC_digest_freectx_fn keccak_freectx; static OSSL_FUNC_digest_dupctx_fn keccak_dupctx; static OSSL_FUNC_digest_squeeze_fn shake_squeeze; +static OSSL_FUNC_digest_get_ctx_params_fn shake_get_ctx_params; +static OSSL_FUNC_digest_gettable_ctx_params_fn shake_gettable_ctx_params; static OSSL_FUNC_digest_set_ctx_params_fn shake_set_ctx_params; static OSSL_FUNC_digest_settable_ctx_params_fn shake_settable_ctx_params; static sha3_absorb_fn generic_sha3_absorb; @@ -112,6 +115,10 @@ static int keccak_final(void *vctx, unsigned char *out, size_t *outl, if (!ossl_prov_is_running()) return 0; + if (ctx->md_size == SIZE_MAX) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); + return 0; + } if (outlen > 0) ret = ctx->meth.final(ctx, out, ctx->md_size); @@ -160,8 +167,7 @@ static int generic_sha3_squeeze(void *vctx, unsigned char *out, size_t outlen) return ossl_sha3_squeeze((KECCAK1600_CTX *)vctx, out, outlen); } -static PROV_SHA3_METHOD sha3_generic_md = -{ +static PROV_SHA3_METHOD sha3_generic_md = { generic_sha3_absorb, generic_sha3_final, NULL @@ -187,26 +193,34 @@ static size_t s390x_sha3_absorb(void *vctx, const void *inp, size_t len) { KECCAK1600_CTX *ctx = vctx; size_t rem = len % ctx->block_size; + unsigned int fc; if (!(ctx->xof_state == XOF_STATE_INIT || ctx->xof_state == XOF_STATE_ABSORB)) return 0; - ctx->xof_state = XOF_STATE_ABSORB; - s390x_kimd(inp, len - rem, ctx->pad, ctx->A); + if (len - rem > 0) { + fc = ctx->pad; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KIMD_NIP : 0; + ctx->xof_state = XOF_STATE_ABSORB; + s390x_kimd(inp, len - rem, fc, ctx->A); + } return rem; } static int s390x_sha3_final(void *vctx, unsigned char *out, size_t outlen) { KECCAK1600_CTX *ctx = vctx; + unsigned int fc; if (!ossl_prov_is_running()) return 0; if (!(ctx->xof_state == XOF_STATE_INIT || ctx->xof_state == XOF_STATE_ABSORB)) return 0; + fc = ctx->pad | S390X_KLMD_DUFOP; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KLMD_NIP : 0; ctx->xof_state = XOF_STATE_FINAL; - s390x_klmd(ctx->buf, ctx->bufsz, NULL, 0, ctx->pad, ctx->A); + s390x_klmd(ctx->buf, ctx->bufsz, NULL, 0, fc, ctx->A); memcpy(out, ctx->A, outlen); return 1; } @@ -214,20 +228,24 @@ static int s390x_sha3_final(void *vctx, unsigned char *out, size_t outlen) static int s390x_shake_final(void *vctx, unsigned char *out, size_t outlen) { KECCAK1600_CTX *ctx = vctx; + unsigned int fc; if (!ossl_prov_is_running()) return 0; if (!(ctx->xof_state == XOF_STATE_INIT || ctx->xof_state == XOF_STATE_ABSORB)) return 0; + fc = ctx->pad | S390X_KLMD_DUFOP; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KLMD_NIP : 0; ctx->xof_state = XOF_STATE_FINAL; - s390x_klmd(ctx->buf, ctx->bufsz, out, outlen, ctx->pad, ctx->A); + s390x_klmd(ctx->buf, ctx->bufsz, out, outlen, fc, ctx->A); return 1; } static int s390x_shake_squeeze(void *vctx, unsigned char *out, size_t outlen) { KECCAK1600_CTX *ctx = vctx; + unsigned int fc; size_t len; if (!ossl_prov_is_running()) @@ -238,8 +256,10 @@ static int s390x_shake_squeeze(void *vctx, unsigned char *out, size_t outlen) * On the first squeeze call, finish the absorb process (incl. padding). */ if (ctx->xof_state != XOF_STATE_SQUEEZE) { + fc = ctx->pad; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KLMD_NIP : 0; ctx->xof_state = XOF_STATE_SQUEEZE; - s390x_klmd(ctx->buf, ctx->bufsz, out, outlen, ctx->pad, ctx->A); + s390x_klmd(ctx->buf, ctx->bufsz, out, outlen, fc, ctx->A); ctx->bufsz = outlen % ctx->block_size; /* reuse ctx->bufsz to count bytes squeezed from current sponge */ return 1; @@ -271,24 +291,28 @@ static int s390x_keccakc_final(void *vctx, unsigned char *out, size_t outlen, size_t bsz = ctx->block_size; size_t num = ctx->bufsz; size_t needed = outlen; + unsigned int fc; if (!ossl_prov_is_running()) return 0; if (!(ctx->xof_state == XOF_STATE_INIT || ctx->xof_state == XOF_STATE_ABSORB)) return 0; + fc = ctx->pad; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KIMD_NIP : 0; ctx->xof_state = XOF_STATE_FINAL; if (outlen == 0) return 1; memset(ctx->buf + num, 0, bsz - num); ctx->buf[num] = padding; ctx->buf[bsz - 1] |= 0x80; - s390x_kimd(ctx->buf, bsz, ctx->pad, ctx->A); + s390x_kimd(ctx->buf, bsz, fc, ctx->A); num = needed > bsz ? bsz : needed; memcpy(out, ctx->A, num); needed -= num; if (needed > 0) - s390x_klmd(NULL, 0, out + bsz, needed, ctx->pad | S390X_KLMD_PS, ctx->A); + s390x_klmd(NULL, 0, out + bsz, needed, + ctx->pad | S390X_KLMD_PS | S390X_KLMD_DUFOP, ctx->A); return 1; } @@ -308,6 +332,7 @@ static int s390x_keccakc_squeeze(void *vctx, unsigned char *out, size_t outlen, { KECCAK1600_CTX *ctx = vctx; size_t len; + unsigned int fc; if (!ossl_prov_is_running()) return 0; @@ -323,7 +348,9 @@ static int s390x_keccakc_squeeze(void *vctx, unsigned char *out, size_t outlen, memset(ctx->buf + ctx->bufsz, 0, len); ctx->buf[ctx->bufsz] = padding; ctx->buf[ctx->block_size - 1] |= 0x80; - s390x_kimd(ctx->buf, ctx->block_size, ctx->pad, ctx->A); + fc = ctx->pad; + fc |= ctx->xof_state == XOF_STATE_INIT ? S390X_KIMD_NIP : 0; + s390x_kimd(ctx->buf, ctx->block_size, fc, ctx->A); ctx->bufsz = 0; /* reuse ctx->bufsz to count bytes squeezed from current sponge */ } @@ -357,29 +384,25 @@ static int s390x_kmac_squeeze(void *vctx, unsigned char *out, size_t outlen) return s390x_keccakc_squeeze(vctx, out, outlen, 0x04); } -static PROV_SHA3_METHOD sha3_s390x_md = -{ +static PROV_SHA3_METHOD sha3_s390x_md = { s390x_sha3_absorb, s390x_sha3_final, NULL, }; -static PROV_SHA3_METHOD keccak_s390x_md = -{ +static PROV_SHA3_METHOD keccak_s390x_md = { s390x_sha3_absorb, s390x_keccak_final, s390x_keccak_squeeze, }; -static PROV_SHA3_METHOD shake_s390x_md = -{ +static PROV_SHA3_METHOD shake_s390x_md = { s390x_sha3_absorb, s390x_shake_final, s390x_shake_squeeze, }; -static PROV_SHA3_METHOD kmac_s390x_md = -{ +static PROV_SHA3_METHOD kmac_s390x_md = { s390x_sha3_absorb, s390x_kmac_final, s390x_kmac_squeeze, @@ -424,8 +447,7 @@ static size_t armsha3_sha3_absorb(void *vctx, const void *inp, size_t len) return SHA3_absorb_cext(ctx->A, inp, len, ctx->block_size); } -static PROV_SHA3_METHOD sha3_ARMSHA3_md = -{ +static PROV_SHA3_METHOD sha3_ARMSHA3_md = { armsha3_sha3_absorb, generic_sha3_final }; @@ -474,7 +496,7 @@ static void *name##_newctx(void *provctx) \ return ctx; \ } -#define SHAKE_newctx(typ, uname, name, bitlen, pad) \ +#define SHAKE_newctx(typ, uname, name, bitlen, mdlen, pad) \ static OSSL_FUNC_digest_newctx_fn name##_newctx; \ static void *name##_newctx(void *provctx) \ { \ @@ -483,7 +505,9 @@ static void *name##_newctx(void *provctx) \ \ if (ctx == NULL) \ return NULL; \ - ossl_sha3_init(ctx, pad, bitlen); \ + ossl_keccak_init(ctx, pad, bitlen, mdlen); \ + if (mdlen == 0) \ + ctx->md_size = SIZE_MAX; \ SHAKE_SET_MD(uname, typ) \ return ctx; \ } @@ -497,7 +521,7 @@ static void *uname##_newctx(void *provctx) \ \ if (ctx == NULL) \ return NULL; \ - ossl_keccak_kmac_init(ctx, pad, bitlen); \ + ossl_keccak_init(ctx, pad, bitlen, 2 * bitlen); \ KMAC_SET_MD(bitlen) \ return ctx; \ } @@ -524,6 +548,9 @@ const OSSL_DISPATCH ossl_##name##_functions[] = { \ { OSSL_FUNC_DIGEST_SET_CTX_PARAMS, (void (*)(void))shake_set_ctx_params }, \ { OSSL_FUNC_DIGEST_SETTABLE_CTX_PARAMS, \ (void (*)(void))shake_settable_ctx_params }, \ + { OSSL_FUNC_DIGEST_GET_CTX_PARAMS, (void (*)(void))shake_get_ctx_params }, \ + { OSSL_FUNC_DIGEST_GETTABLE_CTX_PARAMS, \ + (void (*)(void))shake_gettable_ctx_params }, \ PROV_DISPATCH_FUNC_DIGEST_CONSTRUCT_END static void keccak_freectx(void *vctx) @@ -544,13 +571,50 @@ static void *keccak_dupctx(void *ctx) return ret; } -static const OSSL_PARAM known_shake_settable_ctx_params[] = { - {OSSL_DIGEST_PARAM_XOFLEN, OSSL_PARAM_UNSIGNED_INTEGER, NULL, 0, 0}, - OSSL_PARAM_END -}; +static const OSSL_PARAM *shake_gettable_ctx_params(ossl_unused void *ctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_shake_gettable_ctx_params[] = { + {OSSL_DIGEST_PARAM_XOFLEN, OSSL_PARAM_UNSIGNED_INTEGER, NULL, 0, 0}, + {OSSL_DIGEST_PARAM_SIZE, OSSL_PARAM_UNSIGNED_INTEGER, NULL, 0, 0}, + OSSL_PARAM_END + }; + return known_shake_gettable_ctx_params; +} + +static int shake_get_ctx_params(void *vctx, OSSL_PARAM params[]) +{ + OSSL_PARAM *p; + KECCAK1600_CTX *ctx = (KECCAK1600_CTX *)vctx; + + if (ctx == NULL) + return 0; + if (params == NULL) + return 1; + + p = OSSL_PARAM_locate(params, OSSL_DIGEST_PARAM_XOFLEN); + if (p != NULL && !OSSL_PARAM_set_size_t(p, ctx->md_size)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + /* Size is an alias of xoflen */ + p = OSSL_PARAM_locate(params, OSSL_DIGEST_PARAM_SIZE); + if (p != NULL && !OSSL_PARAM_set_size_t(p, ctx->md_size)) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); + return 0; + } + return 1; +} + static const OSSL_PARAM *shake_settable_ctx_params(ossl_unused void *ctx, ossl_unused void *provctx) { + static const OSSL_PARAM known_shake_settable_ctx_params[] = { + {OSSL_DIGEST_PARAM_XOFLEN, OSSL_PARAM_UNSIGNED_INTEGER, NULL, 0, 0}, + {OSSL_DIGEST_PARAM_SIZE, OSSL_PARAM_UNSIGNED_INTEGER, NULL, 0, 0}, + OSSL_PARAM_END + }; + return known_shake_settable_ctx_params; } @@ -565,6 +629,9 @@ static int shake_set_ctx_params(void *vctx, const OSSL_PARAM params[]) return 1; p = OSSL_PARAM_locate_const(params, OSSL_DIGEST_PARAM_XOFLEN); + if (p == NULL) + p = OSSL_PARAM_locate_const(params, OSSL_DIGEST_PARAM_SIZE); + if (p != NULL && !OSSL_PARAM_get_size_t(p, &ctx->md_size)) { ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_GET_PARAMETER); return 0; @@ -585,10 +652,12 @@ static int shake_set_ctx_params(void *vctx, const OSSL_PARAM params[]) SHA3_FLAGS) #define IMPLEMENT_SHAKE_functions(bitlen) \ - SHAKE_newctx(shake, SHAKE_##bitlen, shake_##bitlen, bitlen, '\x1f') \ + SHAKE_newctx(shake, SHAKE_##bitlen, shake_##bitlen, bitlen, \ + 0 /* no default md length */, '\x1f') \ PROV_FUNC_SHAKE_DIGEST(shake_##bitlen, bitlen, \ - SHA3_BLOCKSIZE(bitlen), SHA3_MDSIZE(bitlen), \ - SHAKE_FLAGS) + SHA3_BLOCKSIZE(bitlen), 0, \ + SHAKE_FLAGS) + #define IMPLEMENT_KMAC_functions(bitlen) \ KMAC_newctx(keccak_kmac_##bitlen, bitlen, '\x04') \ PROV_FUNC_SHAKE_DIGEST(keccak_kmac_##bitlen, bitlen, \ diff --git a/providers/implementations/encode_decode/decode_der2key.c b/providers/implementations/encode_decode/decode_der2key.c index ee66ab02ae..0384cb5e89 100644 --- a/providers/implementations/encode_decode/decode_der2key.c +++ b/providers/implementations/encode_decode/decode_der2key.c @@ -563,15 +563,23 @@ static void *rsa_d2i_PKCS8(void **key, const unsigned char **der, long der_len, static int rsa_check(void *key, struct der2key_ctx_st *ctx) { + int valid; + switch (RSA_test_flags(key, RSA_FLAG_TYPE_MASK)) { case RSA_FLAG_TYPE_RSA: - return ctx->desc->evp_type == EVP_PKEY_RSA; + valid = (ctx->desc->evp_type == EVP_PKEY_RSA); + break; case RSA_FLAG_TYPE_RSASSAPSS: - return ctx->desc->evp_type == EVP_PKEY_RSA_PSS; + valid = (ctx->desc->evp_type == EVP_PKEY_RSA_PSS); + break; + default: + /* Currently unsupported RSA key type */ + valid = 0; } - /* Currently unsupported RSA key type */ - return 0; + valid = (valid && ossl_rsa_check_factors(key)); + + return valid; } static void rsa_adjust(void *key, struct der2key_ctx_st *ctx) diff --git a/providers/implementations/encode_decode/encode_key2text.c b/providers/implementations/encode_decode/encode_key2text.c index c0c2923285..7124671274 100644 --- a/providers/implementations/encode_decode/encode_key2text.c +++ b/providers/implementations/encode_decode/encode_key2text.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -112,7 +112,8 @@ static int print_labeled_bignum(BIO *out, const char *label, const BIGNUM *bn) use_sep = 0; /* The first byte on the next line doesn't have a : */ } if (BIO_printf(out, "%s%c%c", use_sep ? ":" : "", - tolower(p[0]), tolower(p[1])) <= 0) + tolower((unsigned char)p[0]), + tolower((unsigned char)p[1])) <= 0) goto err; ++bytes; p += 2; diff --git a/providers/implementations/exchange/dh_exch.c b/providers/implementations/exchange/dh_exch.c index 20b8fa0078..b7fee87cc9 100644 --- a/providers/implementations/exchange/dh_exch.c +++ b/providers/implementations/exchange/dh_exch.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -76,6 +76,7 @@ typedef struct { /* KDF output length */ size_t kdf_outlen; char *kdf_cekalg; + OSSL_FIPS_IND_DECLARE } PROV_DH_CTX; static void *dh_newctx(void *provctx) @@ -88,11 +89,36 @@ static void *dh_newctx(void *provctx) pdhctx = OPENSSL_zalloc(sizeof(PROV_DH_CTX)); if (pdhctx == NULL) return NULL; + OSSL_FIPS_IND_INIT(pdhctx) pdhctx->libctx = PROV_LIBCTX_OF(provctx); pdhctx->kdf_type = PROV_DH_KDF_NONE; return pdhctx; } +#ifdef FIPS_MODULE +static int dh_check_key(PROV_DH_CTX *ctx) +{ + int key_approved = ossl_dh_check_key(ctx->dh); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + ctx->libctx, "DH Init", "DH Key", + ossl_fips_config_securitycheck_enabled)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} + +static int digest_check(PROV_DH_CTX *ctx, const EVP_MD *md) +{ + return ossl_fips_ind_digest_exch_check(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE1, ctx->libctx, + md, "DH Set Ctx"); +} +#endif + static int dh_init(void *vpdhctx, void *vdh, const OSSL_PARAM params[]) { PROV_DH_CTX *pdhctx = (PROV_DH_CTX *)vpdhctx; @@ -105,8 +131,15 @@ static int dh_init(void *vpdhctx, void *vdh, const OSSL_PARAM params[]) DH_free(pdhctx->dh); pdhctx->dh = vdh; pdhctx->kdf_type = PROV_DH_KDF_NONE; - return dh_set_ctx_params(pdhctx, params) - && ossl_dh_check_key(pdhctx->libctx, vdh); + + OSSL_FIPS_IND_SET_APPROVED(pdhctx) + if (!dh_set_ctx_params(pdhctx, params)) + return 0; +#ifdef FIPS_MODULE + if (!dh_check_key(pdhctx)) + return 0; +#endif + return 1; } /* The 2 parties must share the same domain parameters */ @@ -317,6 +350,13 @@ static int dh_set_ctx_params(void *vpdhctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pdhctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_EXCHANGE_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pdhctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_EXCHANGE_PARAM_FIPS_DIGEST_CHECK)) + return 0; + p = OSSL_PARAM_locate_const(params, OSSL_EXCHANGE_PARAM_KDF_TYPE); if (p != NULL) { str = name; @@ -351,11 +391,18 @@ static int dh_set_ctx_params(void *vpdhctx, const OSSL_PARAM params[]) pdhctx->kdf_md = EVP_MD_fetch(pdhctx->libctx, name, mdprops); if (pdhctx->kdf_md == NULL) return 0; - if (!ossl_digest_is_allowed(pdhctx->libctx, pdhctx->kdf_md)) { + /* XOF digests are not allowed */ + if (EVP_MD_xof(pdhctx->kdf_md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } +#ifdef FIPS_MODULE + if (!digest_check(pdhctx, pdhctx->kdf_md)) { EVP_MD_free(pdhctx->kdf_md); pdhctx->kdf_md = NULL; return 0; } +#endif } p = OSSL_PARAM_locate_const(params, OSSL_EXCHANGE_PARAM_KDF_OUTLEN); @@ -416,6 +463,8 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_EXCHANGE_PARAM_KDF_OUTLEN, NULL), OSSL_PARAM_octet_string(OSSL_EXCHANGE_PARAM_KDF_UKM, NULL, 0), OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_CEK_ALG, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_EXCHANGE_PARAM_FIPS_KEY_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_EXCHANGE_PARAM_FIPS_DIGEST_CHECK) OSSL_PARAM_END }; @@ -432,6 +481,7 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_DEFN(OSSL_EXCHANGE_PARAM_KDF_UKM, OSSL_PARAM_OCTET_PTR, NULL, 0), OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_CEK_ALG, NULL, 0), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -490,7 +540,8 @@ static int dh_get_ctx_params(void *vpdhctx, OSSL_PARAM params[]) && !OSSL_PARAM_set_utf8_string(p, pdhctx->kdf_cekalg == NULL ? "" : pdhctx->kdf_cekalg)) return 0; - + if (!OSSL_FIPS_IND_GET_CTX_PARAM(pdhctx, params)) + return 0; return 1; } diff --git a/providers/implementations/exchange/ecdh_exch.c b/providers/implementations/exchange/ecdh_exch.c index 5b8412aba1..760ebc5190 100644 --- a/providers/implementations/exchange/ecdh_exch.c +++ b/providers/implementations/exchange/ecdh_exch.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -77,6 +77,7 @@ typedef struct { size_t kdf_ukmlen; /* KDF output length */ size_t kdf_outlen; + OSSL_FIPS_IND_DECLARE } PROV_ECDH_CTX; static @@ -94,6 +95,7 @@ void *ecdh_newctx(void *provctx) pectx->libctx = PROV_LIBCTX_OF(provctx); pectx->cofactor_mode = -1; pectx->kdf_type = PROV_ECDH_KDF_NONE; + OSSL_FIPS_IND_INIT(pectx) return (void *)pectx; } @@ -106,14 +108,24 @@ int ecdh_init(void *vpecdhctx, void *vecdh, const OSSL_PARAM params[]) if (!ossl_prov_is_running() || pecdhctx == NULL || vecdh == NULL + || (EC_KEY_get0_group(vecdh) == NULL) || !EC_KEY_up_ref(vecdh)) return 0; EC_KEY_free(pecdhctx->k); pecdhctx->k = vecdh; pecdhctx->cofactor_mode = -1; pecdhctx->kdf_type = PROV_ECDH_KDF_NONE; - return ecdh_set_ctx_params(pecdhctx, params) - && ossl_ec_check_key(pecdhctx->libctx, vecdh, 1); + + OSSL_FIPS_IND_SET_APPROVED(pecdhctx) + if (!ecdh_set_ctx_params(pecdhctx, params)) + return 0; +#ifdef FIPS_MODULE + if (!ossl_fips_ind_ec_key_check(OSSL_FIPS_IND_GET(pecdhctx), + OSSL_FIPS_IND_SETTABLE0, pecdhctx->libctx, + EC_KEY_get0_group(vecdh), "ECDH Init", 1)) + return 0; +#endif + return 1; } static @@ -146,9 +158,16 @@ int ecdh_set_peer(void *vpecdhctx, void *vecdh) if (!ossl_prov_is_running() || pecdhctx == NULL || vecdh == NULL - || !ecdh_match_params(pecdhctx->k, vecdh) - || !ossl_ec_check_key(pecdhctx->libctx, vecdh, 1) - || !EC_KEY_up_ref(vecdh)) + || !ecdh_match_params(pecdhctx->k, vecdh)) + return 0; +#ifdef FIPS_MODULE + if (!ossl_fips_ind_ec_key_check(OSSL_FIPS_IND_GET(pecdhctx), + OSSL_FIPS_IND_SETTABLE0, pecdhctx->libctx, + EC_KEY_get0_group(vecdh), "ECDH Set Peer", + 1)) + return 0; +#endif + if (!EC_KEY_up_ref(vecdh)) return 0; EC_KEY_free(pecdhctx->peerk); @@ -237,6 +256,16 @@ int ecdh_set_ctx_params(void *vpecdhctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pectx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_EXCHANGE_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pectx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_EXCHANGE_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pectx, OSSL_FIPS_IND_SETTABLE2, params, + OSSL_EXCHANGE_PARAM_FIPS_ECDH_COFACTOR_CHECK)) + return 0; + p = OSSL_PARAM_locate_const(params, OSSL_EXCHANGE_PARAM_EC_ECDH_COFACTOR_MODE); if (p != NULL) { int mode; @@ -285,11 +314,20 @@ int ecdh_set_ctx_params(void *vpecdhctx, const OSSL_PARAM params[]) pectx->kdf_md = EVP_MD_fetch(pectx->libctx, name, mdprops); if (pectx->kdf_md == NULL) return 0; - if (!ossl_digest_is_allowed(pectx->libctx, pectx->kdf_md)) { + /* XOF digests are not allowed */ + if (EVP_MD_xof(pectx->kdf_md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } +#ifdef FIPS_MODULE + if (!ossl_fips_ind_digest_exch_check(OSSL_FIPS_IND_GET(pectx), + OSSL_FIPS_IND_SETTABLE1, pectx->libctx, + pectx->kdf_md, "ECDH Set Ctx")) { EVP_MD_free(pectx->kdf_md); pectx->kdf_md = NULL; return 0; } +#endif } p = OSSL_PARAM_locate_const(params, OSSL_EXCHANGE_PARAM_KDF_OUTLEN); @@ -323,6 +361,9 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_EXCHANGE_PARAM_KDF_DIGEST_PROPS, NULL, 0), OSSL_PARAM_size_t(OSSL_EXCHANGE_PARAM_KDF_OUTLEN, NULL), OSSL_PARAM_octet_string(OSSL_EXCHANGE_PARAM_KDF_UKM, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_EXCHANGE_PARAM_FIPS_KEY_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_EXCHANGE_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_EXCHANGE_PARAM_FIPS_ECDH_COFACTOR_CHECK) OSSL_PARAM_END }; @@ -390,7 +431,8 @@ int ecdh_get_ctx_params(void *vpecdhctx, OSSL_PARAM params[]) if (p != NULL && !OSSL_PARAM_set_octet_ptr(p, pectx->kdf_ukm, pectx->kdf_ukmlen)) return 0; - + if (!OSSL_FIPS_IND_GET_CTX_PARAM(pectx, params)) + return 0; return 1; } @@ -401,6 +443,7 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_EXCHANGE_PARAM_KDF_OUTLEN, NULL), OSSL_PARAM_DEFN(OSSL_EXCHANGE_PARAM_KDF_UKM, OSSL_PARAM_OCTET_PTR, NULL, 0), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -438,6 +481,10 @@ int ecdh_plain_derive(void *vpecdhctx, unsigned char *secret, const EC_GROUP *group; const BIGNUM *cofactor; int key_cofactor_mode; + int has_cofactor; +#ifdef FIPS_MODULE + int cofactor_approved = 0; +#endif if (pecdhctx->k == NULL || pecdhctx->peerk == NULL) { ERR_raise(ERR_LIB_PROV, PROV_R_MISSING_KEY); @@ -454,6 +501,8 @@ int ecdh_plain_derive(void *vpecdhctx, unsigned char *secret, || (cofactor = EC_GROUP_get0_cofactor(group)) == NULL) return 0; + has_cofactor = !BN_is_one(cofactor); + /* * NB: unlike PKCS#3 DH, if outlen is less than maximum size this is not * an error, the result is truncated. @@ -476,17 +525,39 @@ int ecdh_plain_derive(void *vpecdhctx, unsigned char *secret, (EC_KEY_get_flags(pecdhctx->k) & EC_FLAG_COFACTOR_ECDH) ? 1 : 0; if (pecdhctx->cofactor_mode != -1 && pecdhctx->cofactor_mode != key_cofactor_mode - && !BN_is_one(cofactor)) { + && has_cofactor) { if ((privk = EC_KEY_dup(pecdhctx->k)) == NULL) return 0; - if (pecdhctx->cofactor_mode == 1) + if (pecdhctx->cofactor_mode == 1) { EC_KEY_set_flags(privk, EC_FLAG_COFACTOR_ECDH); - else +#ifdef FIPS_MODULE + cofactor_approved = 1; +#endif + } else { EC_KEY_clear_flags(privk, EC_FLAG_COFACTOR_ECDH); + } } else { privk = pecdhctx->k; +#ifdef FIPS_MODULE + cofactor_approved = key_cofactor_mode; +#endif + } + +#ifdef FIPS_MODULE + /* + * SP800-56A r3 Section 5.7.1.2 requires ECC Cofactor DH to be used. + * This applies to the 'B' and 'K' curves that have cofactors that are not 1. + */ + if (has_cofactor && !cofactor_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(pecdhctx, OSSL_FIPS_IND_SETTABLE2, + pecdhctx->libctx, "ECDH", "Cofactor", + ossl_fips_config_ecdh_cofactor_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_COFACTOR_REQUIRED); + goto end; + } } +#endif ppubkey = EC_KEY_get0_public_key(pecdhctx->peerk); diff --git a/providers/implementations/exchange/ecx_exch.c b/providers/implementations/exchange/ecx_exch.c index ccf39462ed..28e2ff61c7 100644 --- a/providers/implementations/exchange/ecx_exch.c +++ b/providers/implementations/exchange/ecx_exch.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,14 +17,18 @@ #include "crypto/ecx.h" #include "prov/implementations.h" #include "prov/providercommon.h" +#include "prov/securitycheck.h" static OSSL_FUNC_keyexch_newctx_fn x25519_newctx; static OSSL_FUNC_keyexch_newctx_fn x448_newctx; -static OSSL_FUNC_keyexch_init_fn ecx_init; +static OSSL_FUNC_keyexch_init_fn x25519_init; +static OSSL_FUNC_keyexch_init_fn x448_init; static OSSL_FUNC_keyexch_set_peer_fn ecx_set_peer; static OSSL_FUNC_keyexch_derive_fn ecx_derive; static OSSL_FUNC_keyexch_freectx_fn ecx_freectx; static OSSL_FUNC_keyexch_dupctx_fn ecx_dupctx; +static OSSL_FUNC_keyexch_gettable_ctx_params_fn ecx_gettable_ctx_params; +static OSSL_FUNC_keyexch_get_ctx_params_fn ecx_get_ctx_params; /* * What's passed as an actual key is defined by the KEYMGMT interface. @@ -64,8 +68,7 @@ static void *x448_newctx(void *provctx) return ecx_newctx(provctx, X448_KEYLEN); } -static int ecx_init(void *vecxctx, void *vkey, - ossl_unused const OSSL_PARAM params[]) +static int ecx_init(void *vecxctx, void *vkey, const char *algname) { PROV_ECX_CTX *ecxctx = (PROV_ECX_CTX *)vecxctx; ECX_KEY *key = vkey; @@ -84,9 +87,25 @@ static int ecx_init(void *vecxctx, void *vkey, ossl_ecx_key_free(ecxctx->key); ecxctx->key = key; +#ifdef FIPS_MODULE + if (!ossl_FIPS_IND_callback(key->libctx, algname, "Init")) + return 0; +#endif return 1; } +static int x25519_init(void *vecxctx, void *vkey, + ossl_unused const OSSL_PARAM params[]) +{ + return ecx_init(vecxctx, vkey, "X25519"); +} + +static int x448_init(void *vecxctx, void *vkey, + ossl_unused const OSSL_PARAM params[]) +{ + return ecx_init(vecxctx, vkey, "X448"); +} + static int ecx_set_peer(void *vecxctx, void *vkey) { PROV_ECX_CTX *ecxctx = (PROV_ECX_CTX *)vecxctx; @@ -158,22 +177,51 @@ static void *ecx_dupctx(void *vecxctx) return dstctx; } +static const OSSL_PARAM *ecx_gettable_ctx_params(ossl_unused void *vctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_gettable_ctx_params[] = { + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; + return known_gettable_ctx_params; +} + +static int ecx_get_ctx_params(ossl_unused void *vctx, OSSL_PARAM params[]) +{ +#ifdef FIPS_MODULE + int approved = 0; + OSSL_PARAM *p = OSSL_PARAM_locate(params, + OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR); + + if (p != NULL && !OSSL_PARAM_set_int(p, approved)) + return 0; +#endif + return 1; +} + const OSSL_DISPATCH ossl_x25519_keyexch_functions[] = { { OSSL_FUNC_KEYEXCH_NEWCTX, (void (*)(void))x25519_newctx }, - { OSSL_FUNC_KEYEXCH_INIT, (void (*)(void))ecx_init }, + { OSSL_FUNC_KEYEXCH_INIT, (void (*)(void))x25519_init }, { OSSL_FUNC_KEYEXCH_DERIVE, (void (*)(void))ecx_derive }, { OSSL_FUNC_KEYEXCH_SET_PEER, (void (*)(void))ecx_set_peer }, { OSSL_FUNC_KEYEXCH_FREECTX, (void (*)(void))ecx_freectx }, { OSSL_FUNC_KEYEXCH_DUPCTX, (void (*)(void))ecx_dupctx }, + { OSSL_FUNC_KEYEXCH_GET_CTX_PARAMS, (void (*)(void))ecx_get_ctx_params }, + { OSSL_FUNC_KEYEXCH_GETTABLE_CTX_PARAMS, + (void (*)(void))ecx_gettable_ctx_params }, OSSL_DISPATCH_END }; const OSSL_DISPATCH ossl_x448_keyexch_functions[] = { { OSSL_FUNC_KEYEXCH_NEWCTX, (void (*)(void))x448_newctx }, - { OSSL_FUNC_KEYEXCH_INIT, (void (*)(void))ecx_init }, + { OSSL_FUNC_KEYEXCH_INIT, (void (*)(void))x448_init }, { OSSL_FUNC_KEYEXCH_DERIVE, (void (*)(void))ecx_derive }, { OSSL_FUNC_KEYEXCH_SET_PEER, (void (*)(void))ecx_set_peer }, { OSSL_FUNC_KEYEXCH_FREECTX, (void (*)(void))ecx_freectx }, { OSSL_FUNC_KEYEXCH_DUPCTX, (void (*)(void))ecx_dupctx }, + { OSSL_FUNC_KEYEXCH_GET_CTX_PARAMS, (void (*)(void))ecx_get_ctx_params }, + { OSSL_FUNC_KEYEXCH_GETTABLE_CTX_PARAMS, + (void (*)(void))ecx_gettable_ctx_params }, OSSL_DISPATCH_END }; diff --git a/providers/implementations/include/prov/implementations.h b/providers/implementations/include/prov/implementations.h index 80b544c429..5b91905657 100644 --- a/providers/implementations/include/prov/implementations.h +++ b/providers/implementations/include/prov/implementations.h @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -258,6 +258,11 @@ extern const OSSL_DISPATCH ossl_blake2smac_functions[]; extern const OSSL_DISPATCH ossl_cmac_functions[]; extern const OSSL_DISPATCH ossl_gmac_functions[]; extern const OSSL_DISPATCH ossl_hmac_functions[]; +#ifdef FIPS_MODULE +extern const OSSL_DISPATCH ossl_hmac_internal_functions[]; +extern const OSSL_DISPATCH ossl_kmac128_internal_functions[]; +extern const OSSL_DISPATCH ossl_kmac256_internal_functions[]; +#endif extern const OSSL_DISPATCH ossl_kmac128_functions[]; extern const OSSL_DISPATCH ossl_kmac256_functions[]; extern const OSSL_DISPATCH ossl_siphash_functions[]; @@ -290,6 +295,8 @@ extern const OSSL_DISPATCH ossl_kdf_argon2id_functions[]; /* RNGs */ extern const OSSL_DISPATCH ossl_test_rng_functions[]; extern const OSSL_DISPATCH ossl_seed_src_functions[]; +extern const OSSL_DISPATCH ossl_jitter_functions[]; +extern const OSSL_DISPATCH ossl_crng_test_functions[]; extern const OSSL_DISPATCH ossl_drbg_hash_functions[]; extern const OSSL_DISPATCH ossl_drbg_ossl_hmac_functions[]; extern const OSSL_DISPATCH ossl_drbg_ctr_functions[]; @@ -326,10 +333,51 @@ extern const OSSL_DISPATCH ossl_kdf_scrypt_keyexch_functions[]; /* Signature */ extern const OSSL_DISPATCH ossl_dsa_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha1_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha224_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha256_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha384_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha512_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha3_224_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha3_256_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha3_384_signature_functions[]; +extern const OSSL_DISPATCH ossl_dsa_sha3_512_signature_functions[]; extern const OSSL_DISPATCH ossl_rsa_signature_functions[]; +#ifndef OPENSSL_NO_MD5 +extern const OSSL_DISPATCH ossl_rsa_md5_signature_functions[]; +#endif +#ifndef OPENSSL_NO_RMD160 +extern const OSSL_DISPATCH ossl_rsa_ripemd160_signature_functions[]; +#endif +extern const OSSL_DISPATCH ossl_rsa_sha1_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha224_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha256_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha384_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha512_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha512_224_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha512_256_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha3_224_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha3_256_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha3_384_signature_functions[]; +extern const OSSL_DISPATCH ossl_rsa_sha3_512_signature_functions[]; +#ifndef OPENSSL_NO_SM3 +extern const OSSL_DISPATCH ossl_rsa_sm3_signature_functions[]; +#endif extern const OSSL_DISPATCH ossl_ed25519_signature_functions[]; +extern const OSSL_DISPATCH ossl_ed25519ph_signature_functions[]; +extern const OSSL_DISPATCH ossl_ed25519ctx_signature_functions[]; extern const OSSL_DISPATCH ossl_ed448_signature_functions[]; +extern const OSSL_DISPATCH ossl_ed448ph_signature_functions[]; extern const OSSL_DISPATCH ossl_ecdsa_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha1_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha224_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha256_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha384_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha512_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha3_224_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha3_256_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha3_384_signature_functions[]; +extern const OSSL_DISPATCH ossl_ecdsa_sha3_512_signature_functions[]; extern const OSSL_DISPATCH ossl_mac_legacy_hmac_signature_functions[]; extern const OSSL_DISPATCH ossl_mac_legacy_siphash_signature_functions[]; extern const OSSL_DISPATCH ossl_mac_legacy_poly1305_signature_functions[]; diff --git a/providers/implementations/include/prov/names.h b/providers/implementations/include/prov/names.h index f0ad435346..d422dbac29 100644 --- a/providers/implementations/include/prov/names.h +++ b/providers/implementations/include/prov/names.h @@ -1,5 +1,5 @@ /* - * Copyright 2021-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2021-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -235,7 +235,7 @@ #define PROV_NAMES_SHAKE_256 "SHAKE-256:SHAKE256:2.16.840.1.101.3.4.2.12" /* - * KECCAK-KMAC-128 and KECCAK-KMAC-256 as hashes are mostly useful for + * KECCAK-KMAC-128 and KECCAK-KMAC-256 as hashes are mostly useful for * KMAC128 and KMAC256. */ #define PROV_NAMES_KECCAK_KMAC_128 "KECCAK-KMAC-128:KECCAK-KMAC128" @@ -306,11 +306,13 @@ * RANDs * ----- */ +#define PROV_NAMES_CRNG_TEST "CRNG-TEST" #define PROV_NAMES_CTR_DRBG "CTR-DRBG" #define PROV_NAMES_HASH_DRBG "HASH-DRBG" #define PROV_NAMES_HMAC_DRBG "HMAC-DRBG" #define PROV_NAMES_TEST_RAND "TEST-RAND" #define PROV_NAMES_SEED_SRC "SEED-SRC" +#define PROV_NAMES_JITTER "JITTER" /*- * Asymmetric algos @@ -321,6 +323,15 @@ #define PROV_NAMES_ECDH "ECDH" #define PROV_DESCS_ECDH "OpenSSL ECDH implementation" #define PROV_NAMES_ECDSA "ECDSA" +#define PROV_NAMES_ECDSA_SHA1 "ECDSA-SHA1:ECDSA-SHA-1:ecdsa-with-SHA1:1.2.840.10045.4.1" +#define PROV_NAMES_ECDSA_SHA224 "ECDSA-SHA2-224:ECDSA-SHA224:ecdsa-with-SHA224:1.2.840.10045.4.3.1" +#define PROV_NAMES_ECDSA_SHA256 "ECDSA-SHA2-256:ECDSA-SHA256:ecdsa-with-SHA256:1.2.840.10045.4.3.2" +#define PROV_NAMES_ECDSA_SHA384 "ECDSA-SHA2-384:ECDSA-SHA384:ecdsa-with-SHA384:1.2.840.10045.4.3.3" +#define PROV_NAMES_ECDSA_SHA512 "ECDSA-SHA2-512:ECDSA-SHA512:ecdsa-with-SHA512:1.2.840.10045.4.3.4" +#define PROV_NAMES_ECDSA_SHA3_224 "ECDSA-SHA3-224:ecdsa_with_SHA3-224:id-ecdsa-with-sha3-224:2.16.840.1.101.3.4.3.9" +#define PROV_NAMES_ECDSA_SHA3_256 "ECDSA-SHA3-256:ecdsa_with_SHA3-256:id-ecdsa-with-sha3-256:2.16.840.1.101.3.4.3.10" +#define PROV_NAMES_ECDSA_SHA3_384 "ECDSA-SHA3-384:ecdsa_with_SHA3-384:id-ecdsa-with-sha3-384:2.16.840.1.101.3.4.3.11" +#define PROV_NAMES_ECDSA_SHA3_512 "ECDSA-SHA3-512:ecdsa_with_SHA3-512:id-ecdsa-with-sha3-512:2.16.840.1.101.3.4.3.12" #define PROV_DESCS_ECDSA "OpenSSL ECDSA implementation" #define PROV_NAMES_X25519 "X25519:1.3.101.110" #define PROV_DESCS_X25519 "OpenSSL X25519 implementation" @@ -328,15 +339,46 @@ #define PROV_DESCS_X448 "OpenSSL X448 implementation" #define PROV_NAMES_ED25519 "ED25519:1.3.101.112" #define PROV_DESCS_ED25519 "OpenSSL ED25519 implementation" +#define PROV_NAMES_ED25519ph "ED25519ph" +#define PROV_DESCS_ED25519ph "OpenSSL ED25519ph implementation" +#define PROV_NAMES_ED25519ctx "ED25519ctx" +#define PROV_DESCS_ED25519ctx "OpenSSL ED25519ctx implementation" #define PROV_NAMES_ED448 "ED448:1.3.101.113" #define PROV_DESCS_ED448 "OpenSSL ED448 implementation" +#define PROV_NAMES_ED448ph "ED448ph" +#define PROV_DESCS_ED448ph "OpenSSL ED448ph implementation" #define PROV_NAMES_DH "DH:dhKeyAgreement:1.2.840.113549.1.3.1" #define PROV_DESCS_DH "OpenSSL PKCS#3 DH implementation" #define PROV_NAMES_DHX "DHX:X9.42 DH:dhpublicnumber:1.2.840.10046.2.1" #define PROV_DESCS_DHX "OpenSSL X9.42 DH implementation" #define PROV_NAMES_DSA "DSA:dsaEncryption:1.2.840.10040.4.1" +#define PROV_NAMES_DSA_SHA1 "DSA-SHA1:DSA-SHA-1:dsaWithSHA1:1.2.840.10040.4.3" +#define PROV_NAMES_DSA_SHA224 "DSA-SHA2-224:DSA-SHA224:dsa_with_SHA224:2.16.840.1.101.3.4.3.1" +#define PROV_NAMES_DSA_SHA256 "DSA-SHA2-256:DSA-SHA256:dsa_with_SHA256:2.16.840.1.101.3.4.3.2" +#define PROV_NAMES_DSA_SHA384 "DSA-SHA2-384:DSA-SHA384:dsa_with_SHA384:id-dsa-with-sha384:1.2.840.1.101.3.4.3.3" +#define PROV_NAMES_DSA_SHA512 "DSA-SHA2-512:DSA-SHA512:dsa_with_SHA512:id-dsa-with-sha512:1.2.840.1.101.3.4.3.4" +#define PROV_NAMES_DSA_SHA3_224 "DSA-SHA3-224:dsa_with_SHA3-224:id-dsa-with-sha3-224:2.16.840.1.101.3.4.3.5" +#define PROV_NAMES_DSA_SHA3_256 "DSA-SHA3-256:dsa_with_SHA3-256:id-dsa-with-sha3-256:2.16.840.1.101.3.4.3.6" +#define PROV_NAMES_DSA_SHA3_384 "DSA-SHA3-384:dsa_with_SHA3-384:id-dsa-with-sha3-384:2.16.840.1.101.3.4.3.7" +#define PROV_NAMES_DSA_SHA3_512 "DSA-SHA3-512:dsa_with_SHA3-512:id-dsa-with-sha3-512:2.16.840.1.101.3.4.3.8" #define PROV_DESCS_DSA "OpenSSL DSA implementation" #define PROV_NAMES_RSA "RSA:rsaEncryption:1.2.840.113549.1.1.1" +#define PROV_NAMES_RSA_MD2 "RSA-MD2:md2WithRSAEncryption:1.2.840.113549.1.1.2" +#define PROV_NAMES_RSA_MD4 "RSA-MD4:md4WithEncryption:1.2.840.113549.1.1.3" +#define PROV_NAMES_RSA_MD5 "RSA-MD5:md5WithRSAEncryption:1.2.840.113549.1.1.4" +#define PROV_NAMES_RSA_RIPEMD160 "RSA-RIPEMD160:ripemd160WithRSA:1.3.36.3.3.1.2" +#define PROV_NAMES_RSA_SHA1 "RSA-SHA1:RSA-SHA-1:sha1WithRSAEncryption:1.2.840.113549.1.1.5" +#define PROV_NAMES_RSA_SHA256 "RSA-SHA2-256:RSA-SHA256:sha256WithRSAEncryption:1.2.840.113549.1.1.11" +#define PROV_NAMES_RSA_SHA384 "RSA-SHA2-384:RSA-SHA384:sha384WithRSAEncryption:1.2.840.113549.1.1.12" +#define PROV_NAMES_RSA_SHA512 "RSA-SHA2-512:RSA-SHA512:sha512WithRSAEncryption:1.2.840.113549.1.1.13" +#define PROV_NAMES_RSA_SHA224 "RSA-SHA2-224:RSA-SHA224:sha224WithRSAEncryption:1.2.840.113549.1.1.14" +#define PROV_NAMES_RSA_SHA512_224 "RSA-SHA2-512/224:RSA-SHA512-224:sha512-224WithRSAEncryption:1.2.840.113549.1.1.15" +#define PROV_NAMES_RSA_SHA512_256 "RSA-SHA2-512/256:RSA-SHA512-256:sha512-256WithRSAEncryption:1.2.840.113549.1.1.16" +#define PROV_NAMES_RSA_SM3 "RSA-SM3:sm3WithRSAEncryption:1.2.156.10197.1.504" +#define PROV_NAMES_RSA_SHA3_224 "RSA-SHA3-224:id-rsassa-pkcs1-v1_5-with-sha3-224:2.16.840.1.101.3.4.3.13" +#define PROV_NAMES_RSA_SHA3_256 "RSA-SHA3-256:id-rsassa-pkcs1-v1_5-with-sha3-256:2.16.840.1.101.3.4.3.14" +#define PROV_NAMES_RSA_SHA3_384 "RSA-SHA3-384:id-rsassa-pkcs1-v1_5-with-sha3-384:2.16.840.1.101.3.4.3.15" +#define PROV_NAMES_RSA_SHA3_512 "RSA-SHA3-512:id-rsassa-pkcs1-v1_5-with-sha3-512:2.16.840.1.101.3.4.3.16" #define PROV_DESCS_RSA "OpenSSL RSA implementation" #define PROV_NAMES_RSA_PSS "RSA-PSS:RSASSA-PSS:1.2.840.113549.1.1.10" #define PROV_DESCS_RSA_PSS "OpenSSL RSA-PSS implementation" diff --git a/providers/implementations/kdfs/argon2.c b/providers/implementations/kdfs/argon2.c index fe84ab54ca..ec2bf7b947 100644 --- a/providers/implementations/kdfs/argon2.c +++ b/providers/implementations/kdfs/argon2.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -1071,8 +1071,8 @@ static int kdf_argon2_derive(void *vctx, unsigned char *out, size_t outlen, # else if (ctx->threads > ossl_get_avail_threads(ctx->libctx)) { ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_THREAD_POOL_SIZE, - "requested %u threads, available: 1", - ossl_get_avail_threads(ctx->libctx)); + "requested %u threads, available: %u", + ctx->threads, ossl_get_avail_threads(ctx->libctx)); return 0; } # endif diff --git a/providers/implementations/kdfs/hkdf.c b/providers/implementations/kdfs/hkdf.c index 4a24013bfc..c7454b00cf 100644 --- a/providers/implementations/kdfs/hkdf.c +++ b/providers/implementations/kdfs/hkdf.c @@ -29,6 +29,7 @@ #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_util.h" +#include "prov/securitycheck.h" #include "internal/e_os.h" #include "internal/params.h" @@ -47,6 +48,8 @@ static OSSL_FUNC_kdf_get_ctx_params_fn kdf_hkdf_get_ctx_params; static OSSL_FUNC_kdf_derive_fn kdf_tls1_3_derive; static OSSL_FUNC_kdf_settable_ctx_params_fn kdf_tls1_3_settable_ctx_params; static OSSL_FUNC_kdf_set_ctx_params_fn kdf_tls1_3_set_ctx_params; +static OSSL_FUNC_kdf_gettable_ctx_params_fn kdf_tls1_3_gettable_ctx_params; +static OSSL_FUNC_kdf_get_ctx_params_fn kdf_tls1_3_get_ctx_params; static int HKDF(OSSL_LIB_CTX *libctx, const EVP_MD *evp_md, const unsigned char *salt, size_t salt_len, @@ -63,13 +66,18 @@ static int HKDF_Expand(const EVP_MD *evp_md, unsigned char *okm, size_t okm_len); /* Settable context parameters that are common across HKDF and the TLS KDF */ -#define HKDF_COMMON_SETTABLES \ - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_MODE, NULL, 0), \ - OSSL_PARAM_int(OSSL_KDF_PARAM_MODE, NULL), \ - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_PROPERTIES, NULL, 0), \ - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_DIGEST, NULL, 0), \ - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_KEY, NULL, 0), \ - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SALT, NULL, 0) +#define HKDF_COMMON_SETTABLES \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_MODE, NULL, 0), \ + OSSL_PARAM_int(OSSL_KDF_PARAM_MODE, NULL), \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_PROPERTIES, NULL, 0), \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_DIGEST, NULL, 0), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_KEY, NULL, 0), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SALT, NULL, 0) + +/* Gettable context parameters that are common across HKDF and the TLS KDF */ +#define HKDF_COMMON_GETTABLES \ + OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_INFO, NULL, 0) typedef struct { void *provctx; @@ -87,6 +95,7 @@ typedef struct { size_t data_len; unsigned char *info; size_t info_len; + OSSL_FIPS_IND_DECLARE } KDF_HKDF; static void *kdf_hkdf_new(void *provctx) @@ -96,8 +105,10 @@ static void *kdf_hkdf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) + if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) { ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) + } return ctx; } @@ -117,7 +128,11 @@ static void kdf_hkdf_reset(void *vctx) void *provctx = ctx->provctx; ossl_prov_digest_reset(&ctx->digest); +#ifdef FIPS_MODULE + OPENSSL_clear_free(ctx->salt, ctx->salt_len); +#else OPENSSL_free(ctx->salt); +#endif OPENSSL_free(ctx->prefix); OPENSSL_free(ctx->label); OPENSSL_clear_free(ctx->data, ctx->data_len); @@ -149,6 +164,7 @@ static void *kdf_hkdf_dup(void *vctx) || !ossl_prov_digest_copy(&dest->digest, &src->digest)) goto err; dest->mode = src->mode; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -170,12 +186,30 @@ static size_t kdf_hkdf_size(KDF_HKDF *ctx) return 0; } sz = EVP_MD_get_size(md); - if (sz < 0) + if (sz <= 0) return 0; return sz; } +#ifdef FIPS_MODULE +static int fips_hkdf_key_check_passed(KDF_HKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->key_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "HKDF", "Key size", + ossl_fips_config_hkdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int kdf_hkdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -225,8 +259,18 @@ static int hkdf_common_set_ctx_params(KDF_HKDF *ctx, const OSSL_PARAM params[]) if (params == NULL) return 1; - if (!ossl_prov_digest_load_from_params(&ctx->digest, params, libctx)) - return 0; + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + const EVP_MD *md = NULL; + + if (!ossl_prov_digest_load_from_params(&ctx->digest, params, libctx)) + return 0; + + md = ossl_prov_digest_md(&ctx->digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + } if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_MODE)) != NULL) { if (p->data_type == OSSL_PARAM_UTF8_STRING) { @@ -282,6 +326,10 @@ static int kdf_hkdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!hkdf_common_set_ctx_params(ctx, params)) return 0; @@ -290,6 +338,12 @@ static int kdf_hkdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) HKDF_MAXINFO) == 0) return 0; +#ifdef FIPS_MODULE + if (OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY) != NULL) + if (!fips_hkdf_key_check_passed(ctx)) + return 0; +#endif + return 1; } @@ -299,39 +353,60 @@ static const OSSL_PARAM *kdf_hkdf_settable_ctx_params(ossl_unused void *ctx, static const OSSL_PARAM known_settable_ctx_params[] = { HKDF_COMMON_SETTABLES, OSSL_PARAM_octet_string(OSSL_KDF_PARAM_INFO, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; } -static int kdf_hkdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) +static int hkdf_common_get_ctx_params(KDF_HKDF *ctx, OSSL_PARAM params[]) { - KDF_HKDF *ctx = (KDF_HKDF *)vctx; OSSL_PARAM *p; + if (params == NULL) + return 1; + if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) { size_t sz = kdf_hkdf_size(ctx); if (sz == 0) return 0; - return OSSL_PARAM_set_size_t(p, sz); + if (!OSSL_PARAM_set_size_t(p, sz)) + return 0; } + if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_INFO)) != NULL) { - if (ctx->info == NULL || ctx->info_len == 0) { + if (ctx->info == NULL || ctx->info_len == 0) p->return_size = 0; - return 1; - } - return OSSL_PARAM_set_octet_string(p, ctx->info, ctx->info_len); + else if (!OSSL_PARAM_set_octet_string(p, ctx->info, ctx->info_len)) + return 0; } - return -2; + + return 1; +} + +static int kdf_hkdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) +{ + KDF_HKDF *ctx = (KDF_HKDF *)vctx; + + if (params == NULL) + return 1; + + if (!hkdf_common_get_ctx_params(ctx, params)) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + + return 1; } static const OSSL_PARAM *kdf_hkdf_gettable_ctx_params(ossl_unused void *ctx, ossl_unused void *provctx) { static const OSSL_PARAM known_gettable_ctx_params[] = { - OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_INFO, NULL, 0), + HKDF_COMMON_GETTABLES, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -388,7 +463,7 @@ static int HKDF(OSSL_LIB_CTX *libctx, const EVP_MD *evp_md, size_t prk_len; sz = EVP_MD_get_size(evp_md); - if (sz < 0) + if (sz <= 0) return 0; prk_len = (size_t)sz; @@ -435,7 +510,7 @@ static int HKDF_Extract(OSSL_LIB_CTX *libctx, const EVP_MD *evp_md, { int sz = EVP_MD_get_size(evp_md); - if (sz < 0) + if (sz <= 0) return 0; if (prk_len != (size_t)sz) { ERR_raise(ERR_LIB_PROV, PROV_R_WRONG_OUTPUT_BUFFER_SIZE); @@ -631,7 +706,7 @@ static int prov_tls13_hkdf_generate_secret(OSSL_LIB_CTX *libctx, } if (prevsecret == NULL) { prevsecret = default_zeros; - prevsecretlen = 0; + prevsecretlen = mdlen; } else { EVP_MD_CTX *mctx = EVP_MD_CTX_new(); unsigned char hash[EVP_MAX_MD_SIZE]; @@ -646,7 +721,7 @@ static int prov_tls13_hkdf_generate_secret(OSSL_LIB_CTX *libctx, EVP_MD_CTX_free(mctx); /* Generate the pre-extract secret */ - if (!prov_tls13_hkdf_expand(md, prevsecret, mdlen, + if (!prov_tls13_hkdf_expand(md, prevsecret, prevsecretlen, prefix, prefixlen, label, labellen, hash, mdlen, preextractsec, mdlen)) return 0; @@ -662,6 +737,68 @@ static int prov_tls13_hkdf_generate_secret(OSSL_LIB_CTX *libctx, return ret; } +#ifdef FIPS_MODULE +static int fips_tls1_3_digest_check_passed(KDF_HKDF *ctx, const EVP_MD *md) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + /* + * Perform digest check + * + * According to RFC 8446 appendix B.4, the valid hash functions are + * specified in FIPS 180-4. However, it only lists SHA2-256 and SHA2-384 in + * the table. ACVP also only lists the same set of hash functions. + */ + int digest_unapproved = !EVP_MD_is_a(md, SN_sha256) + && !EVP_MD_is_a(md, SN_sha384); + + if (digest_unapproved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "TLS13 KDF", "Digest", + ossl_fips_config_tls13_kdf_digest_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); + return 0; + } + } + return 1; +} + +/* + * Calculate the correct length of the secret key. + * + * RFC 8446: + * If a given secret is not available, then the 0-value consisting of a + * string of Hash.length bytes set to zeros is used. + */ +static size_t fips_tls1_3_key_size(KDF_HKDF *ctx) +{ + const EVP_MD *md = ossl_prov_digest_md(&ctx->digest); + size_t key_size = 0; + + if (ctx->key != NULL) + key_size = ctx->key_len; + else if (md != NULL) + key_size = EVP_MD_size(md); + + return key_size; +} + +static int fips_tls1_3_key_check_passed(KDF_HKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(fips_tls1_3_key_size(ctx)); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE1, + libctx, "TLS13 KDF", "Key size", + ossl_fips_config_tls13_kdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int kdf_tls1_3_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -707,6 +844,13 @@ static int kdf_tls1_3_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!hkdf_common_set_ctx_params(ctx, params)) return 0; @@ -737,6 +881,20 @@ static int kdf_tls1_3_set_ctx_params(void *vctx, const OSSL_PARAM params[]) && !OSSL_PARAM_get_octet_string(p, (void **)&ctx->data, 0, &ctx->data_len)) return 0; + +#ifdef FIPS_MODULE + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + const EVP_MD *md = ossl_prov_digest_md(&ctx->digest); + + if (!fips_tls1_3_digest_check_passed(ctx, md)) + return 0; + } + + if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY)) != NULL) + if (!fips_tls1_3_key_check_passed(ctx)) + return 0; +#endif + return 1; } @@ -748,11 +906,40 @@ static const OSSL_PARAM *kdf_tls1_3_settable_ctx_params(ossl_unused void *ctx, OSSL_PARAM_octet_string(OSSL_KDF_PARAM_PREFIX, NULL, 0), OSSL_PARAM_octet_string(OSSL_KDF_PARAM_LABEL, NULL, 0), OSSL_PARAM_octet_string(OSSL_KDF_PARAM_DATA, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; } +static int kdf_tls1_3_get_ctx_params(void *vctx, OSSL_PARAM params[]) +{ + KDF_HKDF *ctx = (KDF_HKDF *)vctx; + + if (params == NULL) + return 1; + + if (!hkdf_common_get_ctx_params(ctx, params)) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + + return 1; +} + +static const OSSL_PARAM *kdf_tls1_3_gettable_ctx_params(ossl_unused void *ctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_gettable_ctx_params[] = { + HKDF_COMMON_GETTABLES, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; + return known_gettable_ctx_params; +} + const OSSL_DISPATCH ossl_kdf_tls1_3_kdf_functions[] = { { OSSL_FUNC_KDF_NEWCTX, (void(*)(void))kdf_hkdf_new }, { OSSL_FUNC_KDF_DUPCTX, (void(*)(void))kdf_hkdf_dup }, @@ -763,7 +950,7 @@ const OSSL_DISPATCH ossl_kdf_tls1_3_kdf_functions[] = { (void(*)(void))kdf_tls1_3_settable_ctx_params }, { OSSL_FUNC_KDF_SET_CTX_PARAMS, (void(*)(void))kdf_tls1_3_set_ctx_params }, { OSSL_FUNC_KDF_GETTABLE_CTX_PARAMS, - (void(*)(void))kdf_hkdf_gettable_ctx_params }, - { OSSL_FUNC_KDF_GET_CTX_PARAMS, (void(*)(void))kdf_hkdf_get_ctx_params }, + (void(*)(void))kdf_tls1_3_gettable_ctx_params }, + { OSSL_FUNC_KDF_GET_CTX_PARAMS, (void(*)(void))kdf_tls1_3_get_ctx_params }, OSSL_DISPATCH_END }; diff --git a/providers/implementations/kdfs/hmacdrbg_kdf.c b/providers/implementations/kdfs/hmacdrbg_kdf.c index 30f1dfbd24..afcb13ee31 100644 --- a/providers/implementations/kdfs/hmacdrbg_kdf.c +++ b/providers/implementations/kdfs/hmacdrbg_kdf.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -183,6 +183,7 @@ static int hmac_drbg_kdf_set_ctx_params(void *vctx, const OSSL_PARAM *p; void *ptr = NULL; size_t size = 0; + int md_size; if (params == NULL) return 1; @@ -216,11 +217,14 @@ static int hmac_drbg_kdf_set_ctx_params(void *vctx, /* Confirm digest is allowed. Allow all digests that are not XOF */ md = ossl_prov_digest_md(&drbg->digest); if (md != NULL) { - if ((EVP_MD_get_flags(md) & EVP_MD_FLAG_XOF) != 0) { + if (EVP_MD_xof(md)) { ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); return 0; } - drbg->blocklen = EVP_MD_get_size(md); + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + return 0; + drbg->blocklen = (size_t)md_size; } return ossl_prov_macctx_load_from_params(&drbg->ctx, params, "HMAC", NULL, NULL, libctx); diff --git a/providers/implementations/kdfs/kbkdf.c b/providers/implementations/kdfs/kbkdf.c index 5d6ebdf396..a2eae5f42d 100644 --- a/providers/implementations/kdfs/kbkdf.c +++ b/providers/implementations/kdfs/kbkdf.c @@ -43,7 +43,7 @@ #include "prov/provider_ctx.h" #include "prov/provider_util.h" #include "prov/providercommon.h" - +#include "prov/securitycheck.h" #include "internal/e_os.h" #include "internal/params.h" @@ -73,6 +73,7 @@ typedef struct { int use_l; int is_kmac; int use_separator; + OSSL_FIPS_IND_DECLARE } KBKDF; /* Definitions needed for typechecking. */ @@ -122,6 +123,7 @@ static void *kbkdf_new(void *provctx) return NULL; ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) init(ctx); return ctx; } @@ -174,6 +176,7 @@ static void *kbkdf_dup(void *vctx) dest->use_l = src->use_l; dest->use_separator = src->use_separator; dest->is_kmac = src->is_kmac; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -182,6 +185,24 @@ static void *kbkdf_dup(void *vctx) return NULL; } +#ifdef FIPS_MODULE +static int fips_kbkdf_key_check_passed(KBKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->ki_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "KBKDF", "Key size", + ossl_fips_config_kbkdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + /* SP800-108 section 5.1 or section 5.2 depending on mode. */ static int derive(EVP_MAC_CTX *ctx_init, kbkdf_mode mode, unsigned char *iv, size_t iv_len, unsigned char *label, size_t label_len, @@ -351,6 +372,10 @@ static int kbkdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!ossl_prov_macctx_load_from_params(&ctx->ctx_init, params, NULL, NULL, NULL, libctx)) return 0; @@ -382,9 +407,16 @@ static int kbkdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) return 0; } - if (ossl_param_get1_octet_string(params, OSSL_KDF_PARAM_KEY, - &ctx->ki, &ctx->ki_len) == 0) + p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY); + if (p != NULL) { + if (ossl_param_get1_octet_string(p, OSSL_KDF_PARAM_KEY, + &ctx->ki, &ctx->ki_len) == 0) + return 0; +#ifdef FIPS_MODULE + if (!fips_kbkdf_key_check_passed(ctx)) return 0; +#endif + } if (ossl_param_get1_octet_string(params, OSSL_KDF_PARAM_SALT, &ctx->label, &ctx->label_len) == 0) @@ -443,6 +475,7 @@ static const OSSL_PARAM *kbkdf_settable_ctx_params(ossl_unused void *ctx, OSSL_PARAM_int(OSSL_KDF_PARAM_KBKDF_USE_L, NULL), OSSL_PARAM_int(OSSL_KDF_PARAM_KBKDF_USE_SEPARATOR, NULL), OSSL_PARAM_int(OSSL_KDF_PARAM_KBKDF_R, NULL), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END, }; return known_settable_ctx_params; @@ -450,21 +483,29 @@ static const OSSL_PARAM *kbkdf_settable_ctx_params(ossl_unused void *ctx, static int kbkdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) { +#ifdef FIPS_MODULE + KBKDF *ctx = (KBKDF *)vctx; +#endif OSSL_PARAM *p; + /* KBKDF can produce results as large as you like. */ p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE); - if (p == NULL) - return -2; + if (p != NULL && !OSSL_PARAM_set_size_t(p, SIZE_MAX)) + return 0; - /* KBKDF can produce results as large as you like. */ - return OSSL_PARAM_set_size_t(p, SIZE_MAX); + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + return 1; } static const OSSL_PARAM *kbkdf_gettable_ctx_params(ossl_unused void *ctx, ossl_unused void *provctx) { - static const OSSL_PARAM known_gettable_ctx_params[] = - { OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), OSSL_PARAM_END }; + static const OSSL_PARAM known_gettable_ctx_params[] = { + OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; return known_gettable_ctx_params; } diff --git a/providers/implementations/kdfs/pbkdf1.c b/providers/implementations/kdfs/pbkdf1.c index 69d3f7cb29..1b7e4d8a2e 100644 --- a/providers/implementations/kdfs/pbkdf1.c +++ b/providers/implementations/kdfs/pbkdf1.c @@ -70,7 +70,7 @@ static int kdf_pbkdf1_do_derive(const unsigned char *pass, size_t passlen, || !EVP_DigestFinal_ex(ctx, md_tmp, NULL)) goto err; mdsize = EVP_MD_size(md_type); - if (mdsize < 0) + if (mdsize <= 0) goto err; if (n > (size_t)mdsize) { ERR_raise(ERR_LIB_PROV, PROV_R_LENGTH_TOO_LARGE); diff --git a/providers/implementations/kdfs/pbkdf2.c b/providers/implementations/kdfs/pbkdf2.c index f2d190c308..19d1149341 100644 --- a/providers/implementations/kdfs/pbkdf2.c +++ b/providers/implementations/kdfs/pbkdf2.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -28,10 +28,11 @@ #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_util.h" +#include "prov/securitycheck.h" #include "pbkdf2.h" /* Constants specified in SP800-132 */ -#define KDF_PBKDF2_MIN_KEY_LEN_BITS 112 +#define KDF_PBKDF2_MIN_KEY_LEN_BITS 112 #define KDF_PBKDF2_MAX_KEY_LEN_DIGEST_RATIO 0xFFFFFFFF #define KDF_PBKDF2_MIN_ITERATIONS 1000 #define KDF_PBKDF2_MIN_SALT_LEN (128 / 8) @@ -46,11 +47,6 @@ static OSSL_FUNC_kdf_set_ctx_params_fn kdf_pbkdf2_set_ctx_params; static OSSL_FUNC_kdf_gettable_ctx_params_fn kdf_pbkdf2_gettable_ctx_params; static OSSL_FUNC_kdf_get_ctx_params_fn kdf_pbkdf2_get_ctx_params; -static int pbkdf2_derive(const char *pass, size_t passlen, - const unsigned char *salt, int saltlen, uint64_t iter, - const EVP_MD *digest, unsigned char *key, - size_t keylen, int extra_checks); - typedef struct { void *provctx; unsigned char *pass; @@ -60,8 +56,14 @@ typedef struct { uint64_t iter; PROV_DIGEST digest; int lower_bound_checks; + OSSL_FIPS_IND_DECLARE } KDF_PBKDF2; +static int pbkdf2_derive(KDF_PBKDF2 *ctx, const char *pass, size_t passlen, + const unsigned char *salt, int saltlen, uint64_t iter, + const EVP_MD *digest, unsigned char *key, + size_t keylen, int lower_bound_checks); + static void kdf_pbkdf2_init(KDF_PBKDF2 *ctx); static void *kdf_pbkdf2_new_no_init(void *provctx) @@ -75,6 +77,7 @@ static void *kdf_pbkdf2_new_no_init(void *provctx) if (ctx == NULL) return NULL; ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx); return ctx; } @@ -90,7 +93,11 @@ static void *kdf_pbkdf2_new(void *provctx) static void kdf_pbkdf2_cleanup(KDF_PBKDF2 *ctx) { ossl_prov_digest_reset(&ctx->digest); +#ifdef FIPS_MODULE + OPENSSL_clear_free(ctx->salt, ctx->salt_len); +#else OPENSSL_free(ctx->salt); +#endif OPENSSL_clear_free(ctx->pass, ctx->pass_len); memset(ctx, 0, sizeof(*ctx)); } @@ -131,6 +138,7 @@ static void *kdf_pbkdf2_dup(void *vctx) goto err; dest->iter = src->iter; dest->lower_bound_checks = src->lower_bound_checks; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -170,6 +178,53 @@ static int pbkdf2_set_membuf(unsigned char **buffer, size_t *buflen, return 1; } +static int pbkdf2_lower_bound_check_passed(int saltlen, uint64_t iter, + size_t keylen, int *error, + const char **desc) +{ + if ((keylen * 8) < KDF_PBKDF2_MIN_KEY_LEN_BITS) { + *error = PROV_R_KEY_SIZE_TOO_SMALL; + if (desc != NULL) + *desc = "Key size"; + return 0; + } + if (saltlen < KDF_PBKDF2_MIN_SALT_LEN) { + *error = PROV_R_INVALID_SALT_LENGTH; + if (desc != NULL) + *desc = "Salt size"; + return 0; + } + if (iter < KDF_PBKDF2_MIN_ITERATIONS) { + *error = PROV_R_INVALID_ITERATION_COUNT; + if (desc != NULL) + *desc = "Iteration count"; + return 0; + } + + return 1; +} + +#ifdef FIPS_MODULE +static int fips_lower_bound_check_passed(KDF_PBKDF2 *ctx, size_t keylen) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int error = 0; + const char *desc = NULL; + int approved = pbkdf2_lower_bound_check_passed(ctx->salt_len, ctx->iter, + keylen, &error, &desc); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, libctx, + "PBKDF2", desc, + ossl_fips_config_pbkdf2_lower_bound_check)) { + ERR_raise(ERR_LIB_PROV, error); + return 0; + } + } + return 1; +} +#endif + static int kdf_pbkdf2_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -190,7 +245,7 @@ static int kdf_pbkdf2_derive(void *vctx, unsigned char *key, size_t keylen, } md = ossl_prov_digest_md(&ctx->digest); - return pbkdf2_derive((char *)ctx->pass, ctx->pass_len, + return pbkdf2_derive(ctx, (char *)ctx->pass, ctx->pass_len, ctx->salt, ctx->salt_len, ctx->iter, md, key, keylen, ctx->lower_bound_checks); } @@ -202,17 +257,30 @@ static int kdf_pbkdf2_set_ctx_params(void *vctx, const OSSL_PARAM params[]) OSSL_LIB_CTX *provctx = PROV_LIBCTX_OF(ctx->provctx); int pkcs5; uint64_t iter, min_iter; + const EVP_MD *md; if (params == NULL) return 1; - if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) - return 0; + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) + return 0; + md = ossl_prov_digest_md(&ctx->digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + } if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_PKCS5)) != NULL) { if (!OSSL_PARAM_get_int(p, &pkcs5)) return 0; ctx->lower_bound_checks = pkcs5 == 0; +#ifdef FIPS_MODULE + ossl_FIPS_IND_set_settable(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE0, + ctx->lower_bound_checks); +#endif } if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_PASSWORD)) != NULL) @@ -262,8 +330,12 @@ static int kdf_pbkdf2_get_ctx_params(void *vctx, OSSL_PARAM params[]) OSSL_PARAM *p; if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) - return OSSL_PARAM_set_size_t(p, SIZE_MAX); - return -2; + if (!OSSL_PARAM_set_size_t(p, SIZE_MAX)) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM((KDF_PBKDF2 *) vctx, params)) + return 0; + return 1; } static const OSSL_PARAM *kdf_pbkdf2_gettable_ctx_params(ossl_unused void *ctx, @@ -271,6 +343,7 @@ static const OSSL_PARAM *kdf_pbkdf2_gettable_ctx_params(ossl_unused void *ctx, { static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -301,7 +374,7 @@ const OSSL_DISPATCH ossl_kdf_pbkdf2_functions[] = { * - Minimum iteration count of 1000. * - Randomly-generated portion of the salt shall be at least 128 bits. */ -static int pbkdf2_derive(const char *pass, size_t passlen, +static int pbkdf2_derive(KDF_PBKDF2 *ctx, const char *pass, size_t passlen, const unsigned char *salt, int saltlen, uint64_t iter, const EVP_MD *digest, unsigned char *key, size_t keylen, int lower_bound_checks) @@ -326,20 +399,21 @@ static int pbkdf2_derive(const char *pass, size_t passlen, return 0; } +#ifdef FIPS_MODULE + if (!fips_lower_bound_check_passed(ctx, keylen)) + return 0; +#else if (lower_bound_checks) { - if ((keylen * 8) < KDF_PBKDF2_MIN_KEY_LEN_BITS) { - ERR_raise(ERR_LIB_PROV, PROV_R_KEY_SIZE_TOO_SMALL); - return 0; - } - if (saltlen < KDF_PBKDF2_MIN_SALT_LEN) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_SALT_LENGTH); - return 0; - } - if (iter < KDF_PBKDF2_MIN_ITERATIONS) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_ITERATION_COUNT); + int error = 0; + int passed = pbkdf2_lower_bound_check_passed(saltlen, iter, keylen, + &error, NULL); + + if (!passed) { + ERR_raise(ERR_LIB_PROV, error); return 0; } } +#endif hctx_tpl = HMAC_CTX_new(); if (hctx_tpl == NULL) diff --git a/providers/implementations/kdfs/sshkdf.c b/providers/implementations/kdfs/sshkdf.c index 90986bc762..767ec9c71d 100644 --- a/providers/implementations/kdfs/sshkdf.c +++ b/providers/implementations/kdfs/sshkdf.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -21,6 +21,7 @@ #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_util.h" +#include "prov/securitycheck.h" /* See RFC 4253, Section 7.2 */ static OSSL_FUNC_kdf_newctx_fn kdf_sshkdf_new; @@ -49,6 +50,7 @@ typedef struct { char type; /* X */ unsigned char *session_id; size_t session_id_len; + OSSL_FIPS_IND_DECLARE } KDF_SSHKDF; static void *kdf_sshkdf_new(void *provctx) @@ -58,8 +60,10 @@ static void *kdf_sshkdf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) + if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) { ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) + } return ctx; } @@ -102,6 +106,7 @@ static void *kdf_sshkdf_dup(void *vctx) || !ossl_prov_digest_copy(&dest->digest, &src->digest)) goto err; dest->type = src->type; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -119,6 +124,51 @@ static int sshkdf_set_membuf(unsigned char **dst, size_t *dst_len, return OSSL_PARAM_get_octet_string(p, (void **)dst, 0, dst_len); } +#ifdef FIPS_MODULE +static int fips_digest_check_passed(KDF_SSHKDF *ctx, const EVP_MD *md) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + /* + * Perform digest check + * + * According to NIST SP 800-135r1 section 5.2, the valid hash functions are + * specified in FIPS 180-3. ACVP also only lists the same set of hash + * functions. + */ + int digest_unapproved = !EVP_MD_is_a(md, SN_sha1) + && !EVP_MD_is_a(md, SN_sha224) + && !EVP_MD_is_a(md, SN_sha256) + && !EVP_MD_is_a(md, SN_sha384) + && !EVP_MD_is_a(md, SN_sha512); + + if (digest_unapproved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "SSHKDF", "Digest", + ossl_fips_config_sshkdf_digest_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); + return 0; + } + } + return 1; +} + +static int fips_key_check_passed(KDF_SSHKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->key_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE1, + libctx, "SSHKDF", "Key size", + ossl_fips_config_sshkdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int kdf_sshkdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -149,6 +199,7 @@ static int kdf_sshkdf_derive(void *vctx, unsigned char *key, size_t keylen, ERR_raise(ERR_LIB_PROV, PROV_R_MISSING_TYPE); return 0; } + return SSHKDF(md, ctx->key, ctx->key_len, ctx->xcghash, ctx->xcghash_len, ctx->session_id, ctx->session_id_len, @@ -164,13 +215,41 @@ static int kdf_sshkdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (params == NULL) return 1; - if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) return 0; - if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY)) != NULL) + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + const EVP_MD *md = NULL; + + if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) + return 0; + + md = ossl_prov_digest_md(&ctx->digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + +#ifdef FIPS_MODULE + if (!fips_digest_check_passed(ctx, md)) + return 0; +#endif + } + + if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY)) != NULL) { if (!sshkdf_set_membuf(&ctx->key, &ctx->key_len, p)) return 0; +#ifdef FIPS_MODULE + if (!fips_key_check_passed(ctx)) + return 0; +#endif + } + if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SSHKDF_XCGHASH)) != NULL) if (!sshkdf_set_membuf(&ctx->xcghash, &ctx->xcghash_len, p)) @@ -209,6 +288,8 @@ static const OSSL_PARAM *kdf_sshkdf_settable_ctx_params(ossl_unused void *ctx, OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SSHKDF_XCGHASH, NULL, 0), OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SSHKDF_SESSION_ID, NULL, 0), OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_SSHKDF_TYPE, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; @@ -218,9 +299,13 @@ static int kdf_sshkdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) { OSSL_PARAM *p; - if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) - return OSSL_PARAM_set_size_t(p, SIZE_MAX); - return -2; + if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) { + if (!OSSL_PARAM_set_size_t(p, SIZE_MAX)) + return 0; + } + if (!OSSL_FIPS_IND_GET_CTX_PARAM(((KDF_SSHKDF *)vctx), params)) + return 0; + return 1; } static const OSSL_PARAM *kdf_sshkdf_gettable_ctx_params(ossl_unused void *ctx, @@ -228,6 +313,7 @@ static const OSSL_PARAM *kdf_sshkdf_gettable_ctx_params(ossl_unused void *ctx, { static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -323,4 +409,3 @@ static int SSHKDF(const EVP_MD *evp_md, OPENSSL_cleanse(digest, EVP_MAX_MD_SIZE); return ret; } - diff --git a/providers/implementations/kdfs/sskdf.c b/providers/implementations/kdfs/sskdf.c index db750a4f23..b9612020d6 100644 --- a/providers/implementations/kdfs/sskdf.c +++ b/providers/implementations/kdfs/sskdf.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -50,6 +50,7 @@ #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_util.h" +#include "prov/securitycheck.h" #include "internal/params.h" typedef struct { @@ -64,6 +65,7 @@ typedef struct { size_t salt_len; size_t out_len; /* optional KMAC parameter */ int is_kmac; + OSSL_FIPS_IND_DECLARE } KDF_SSKDF; #define SSKDF_MAX_INLEN (1<<30) @@ -78,11 +80,30 @@ static OSSL_FUNC_kdf_dupctx_fn sskdf_dup; static OSSL_FUNC_kdf_freectx_fn sskdf_free; static OSSL_FUNC_kdf_reset_fn sskdf_reset; static OSSL_FUNC_kdf_derive_fn sskdf_derive; -static OSSL_FUNC_kdf_derive_fn x963kdf_derive; static OSSL_FUNC_kdf_settable_ctx_params_fn sskdf_settable_ctx_params; static OSSL_FUNC_kdf_set_ctx_params_fn sskdf_set_ctx_params; static OSSL_FUNC_kdf_gettable_ctx_params_fn sskdf_gettable_ctx_params; static OSSL_FUNC_kdf_get_ctx_params_fn sskdf_get_ctx_params; +static OSSL_FUNC_kdf_derive_fn x963kdf_derive; +static OSSL_FUNC_kdf_settable_ctx_params_fn x963kdf_settable_ctx_params; +static OSSL_FUNC_kdf_set_ctx_params_fn x963kdf_set_ctx_params; +static OSSL_FUNC_kdf_gettable_ctx_params_fn x963kdf_gettable_ctx_params; +static OSSL_FUNC_kdf_get_ctx_params_fn x963kdf_get_ctx_params; + +/* Settable context parameters that are common across SSKDF and X963 KDF */ +#define SSKDF_COMMON_SETTABLES \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SECRET, NULL, 0), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_KEY, NULL, 0), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_INFO, NULL, 0), \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_PROPERTIES, NULL, 0), \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_DIGEST, NULL, 0), \ + OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_MAC, NULL, 0), \ + OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SALT, NULL, 0), \ + OSSL_PARAM_size_t(OSSL_KDF_PARAM_MAC_SIZE, NULL) + +/* Gettable context parameters that are common across SSKDF and X963 KDF */ +#define SSKDF_COMMON_GETTABLES \ + OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL) /* * Refer to https://csrc.nist.gov/publications/detail/sp/800-56c/rev-1/final @@ -292,8 +313,10 @@ static void *sskdf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) + if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) { ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) + } return ctx; } @@ -343,6 +366,7 @@ static void *sskdf_dup(void *vctx) goto err; dest->out_len = src->out_len; dest->is_kmac = src->is_kmac; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -368,6 +392,24 @@ static size_t sskdf_size(KDF_SSKDF *ctx) return (len <= 0) ? 0 : (size_t)len; } +#ifdef FIPS_MODULE +static int fips_sskdf_key_check_passed(KDF_SSKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->secret_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "SSKDF", "Key size", + ossl_fips_config_sskdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int sskdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -380,6 +422,7 @@ static int sskdf_derive(void *vctx, unsigned char *key, size_t keylen, ERR_raise(ERR_LIB_PROV, PROV_R_MISSING_SECRET); return 0; } + md = ossl_prov_digest_md(&ctx->digest); if (ctx->macctx != NULL) { @@ -435,13 +478,54 @@ static int sskdf_derive(void *vctx, unsigned char *key, size_t keylen, } } +#ifdef FIPS_MODULE +static int fips_x963kdf_digest_check_passed(KDF_SSKDF *ctx, const EVP_MD *md) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + /* + * Perform digest check + * + * X963KDF is a KDF defined in ANSI-X9.63. According to ACVP specification + * section 7.3.1, only SHA-2 and SHA-3 can be regarded as valid hash + * functions. + */ + int digest_unapproved = (ctx->is_kmac != 1) && EVP_MD_is_a(md, SN_sha1); + + if (digest_unapproved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "X963KDF", "Digest", + ossl_fips_config_x963kdf_digest_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); + return 0; + } + } + return 1; +} + +static int fips_x963kdf_key_check_passed(KDF_SSKDF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->secret_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE1, + libctx, "X963KDF", "Key size", + ossl_fips_config_x963kdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int x963kdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { KDF_SSKDF *ctx = (KDF_SSKDF *)vctx; const EVP_MD *md; - if (!ossl_prov_is_running() || !sskdf_set_ctx_params(ctx, params)) + if (!ossl_prov_is_running() || !x963kdf_set_ctx_params(ctx, params)) return 0; if (ctx->secret == NULL) { @@ -465,11 +549,11 @@ static int x963kdf_derive(void *vctx, unsigned char *key, size_t keylen, ctx->info, ctx->info_len, 1, key, keylen); } -static int sskdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +static int sskdf_common_set_ctx_params(KDF_SSKDF *ctx, const OSSL_PARAM params[]) { const OSSL_PARAM *p; - KDF_SSKDF *ctx = vctx; OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + const EVP_MD *md = NULL; size_t sz; int r; @@ -488,8 +572,16 @@ static int sskdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) } } - if (!ossl_prov_digest_load_from_params(&ctx->digest, params, libctx)) - return 0; + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + if (!ossl_prov_digest_load_from_params(&ctx->digest, params, libctx)) + return 0; + + md = ossl_prov_digest_md(&ctx->digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + } r = ossl_param_get1_octet_string(params, OSSL_KDF_PARAM_SECRET, &ctx->secret, &ctx->secret_len); @@ -516,38 +608,148 @@ static int sskdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) return 1; } +static int sskdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + KDF_SSKDF *ctx = (KDF_SSKDF *)vctx; + + if (params == NULL) + return 1; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + + if (!sskdf_common_set_ctx_params(ctx, params)) + return 0; + +#ifdef FIPS_MODULE + if ((OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY) != NULL) || + (OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SECRET) != NULL)) + if (!fips_sskdf_key_check_passed(ctx)) + return 0; +#endif + + return 1; +} + static const OSSL_PARAM *sskdf_settable_ctx_params(ossl_unused void *ctx, ossl_unused void *provctx) { static const OSSL_PARAM known_settable_ctx_params[] = { - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SECRET, NULL, 0), - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_KEY, NULL, 0), - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_INFO, NULL, 0), - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_PROPERTIES, NULL, 0), - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_DIGEST, NULL, 0), - OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_MAC, NULL, 0), - OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SALT, NULL, 0), - OSSL_PARAM_size_t(OSSL_KDF_PARAM_MAC_SIZE, NULL), + SSKDF_COMMON_SETTABLES, + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; } +static int sskdf_common_get_ctx_params(KDF_SSKDF *ctx, OSSL_PARAM params[]) +{ + OSSL_PARAM *p; + + if (params == NULL) + return 1; + + if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) { + if (!OSSL_PARAM_set_size_t(p, sskdf_size(ctx))) + return 0; + } + + return 1; +} + static int sskdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) { KDF_SSKDF *ctx = (KDF_SSKDF *)vctx; - OSSL_PARAM *p; - if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) - return OSSL_PARAM_set_size_t(p, sskdf_size(ctx)); - return -2; + if (params == NULL) + return 1; + + if (!sskdf_common_get_ctx_params(ctx, params)) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + + return 1; } static const OSSL_PARAM *sskdf_gettable_ctx_params(ossl_unused void *ctx, ossl_unused void *provctx) { static const OSSL_PARAM known_gettable_ctx_params[] = { - OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + SSKDF_COMMON_GETTABLES, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; + return known_gettable_ctx_params; +} + +static int x963kdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + KDF_SSKDF *ctx = (KDF_SSKDF *)vctx; + + if (params == NULL) + return 1; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + + if (!sskdf_common_set_ctx_params(ctx, params)) + return 0; + +#ifdef FIPS_MODULE + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + const EVP_MD *md = ossl_prov_digest_md(&ctx->digest); + + if (!fips_x963kdf_digest_check_passed(ctx, md)) + return 0; + } + + if ((OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY) != NULL) || + (OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SECRET) != NULL)) + if (!fips_x963kdf_key_check_passed(ctx)) + return 0; +#endif + + return 1; +} + +static const OSSL_PARAM *x963kdf_settable_ctx_params(ossl_unused void *ctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_settable_ctx_params[] = { + SSKDF_COMMON_SETTABLES, + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) + OSSL_PARAM_END + }; + return known_settable_ctx_params; +} + +static int x963kdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) +{ + KDF_SSKDF *ctx = (KDF_SSKDF *)vctx; + + if (!sskdf_common_get_ctx_params(ctx, params)) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + + return 1; +} + +static const OSSL_PARAM *x963kdf_gettable_ctx_params(ossl_unused void *ctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_gettable_ctx_params[] = { + SSKDF_COMMON_GETTABLES, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -575,10 +777,10 @@ const OSSL_DISPATCH ossl_kdf_x963_kdf_functions[] = { { OSSL_FUNC_KDF_RESET, (void(*)(void))sskdf_reset }, { OSSL_FUNC_KDF_DERIVE, (void(*)(void))x963kdf_derive }, { OSSL_FUNC_KDF_SETTABLE_CTX_PARAMS, - (void(*)(void))sskdf_settable_ctx_params }, - { OSSL_FUNC_KDF_SET_CTX_PARAMS, (void(*)(void))sskdf_set_ctx_params }, + (void(*)(void))x963kdf_settable_ctx_params }, + { OSSL_FUNC_KDF_SET_CTX_PARAMS, (void(*)(void))x963kdf_set_ctx_params }, { OSSL_FUNC_KDF_GETTABLE_CTX_PARAMS, - (void(*)(void))sskdf_gettable_ctx_params }, - { OSSL_FUNC_KDF_GET_CTX_PARAMS, (void(*)(void))sskdf_get_ctx_params }, + (void(*)(void))x963kdf_gettable_ctx_params }, + { OSSL_FUNC_KDF_GET_CTX_PARAMS, (void(*)(void))x963kdf_get_ctx_params }, OSSL_DISPATCH_END }; diff --git a/providers/implementations/kdfs/tls1_prf.c b/providers/implementations/kdfs/tls1_prf.c index 2792486924..31316401bc 100644 --- a/providers/implementations/kdfs/tls1_prf.c +++ b/providers/implementations/kdfs/tls1_prf.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -106,6 +106,8 @@ typedef struct { /* Concatenated seed data */ unsigned char *seed; size_t seedlen; + + OSSL_FIPS_IND_DECLARE } TLS1_PRF; static void *kdf_tls1_prf_new(void *provctx) @@ -115,8 +117,10 @@ static void *kdf_tls1_prf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) + if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) != NULL) { ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) + } return ctx; } @@ -161,6 +165,7 @@ static void *kdf_tls1_prf_dup(void *vctx) if (!ossl_prov_memdup(src->seed, src->seedlen, &dest->seed, &dest->seedlen)) goto err; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -169,11 +174,80 @@ static void *kdf_tls1_prf_dup(void *vctx) return NULL; } +#ifdef FIPS_MODULE + +static int fips_ems_check_passed(TLS1_PRF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + /* + * Check that TLS is using EMS. + * + * The seed buffer is prepended with a label. + * If EMS mode is enforced then the label "master secret" is not allowed, + * We do the check this way since the PRF is used for other purposes, as well + * as "extended master secret". + */ + int ems_approved = (ctx->seedlen < TLS_MD_MASTER_SECRET_CONST_SIZE + || memcmp(ctx->seed, TLS_MD_MASTER_SECRET_CONST, + TLS_MD_MASTER_SECRET_CONST_SIZE) != 0); + + if (!ems_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "TLS_PRF", "EMS", + ossl_fips_config_tls1_prf_ems_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_EMS_NOT_ENABLED); + return 0; + } + } + return 1; +} + +static int fips_digest_check_passed(TLS1_PRF *ctx, const EVP_MD *md) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + /* + * Perform digest check + * + * According to NIST SP 800-135r1 section 5.2, the valid hash functions are + * specified in FIPS 180-3. ACVP also only lists the same set of hash + * functions. + */ + int digest_unapproved = !EVP_MD_is_a(md, SN_sha256) + && !EVP_MD_is_a(md, SN_sha384) + && !EVP_MD_is_a(md, SN_sha512); + + if (digest_unapproved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE1, + libctx, "TLS_PRF", "Digest", + ossl_fips_config_tls1_prf_digest_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); + return 0; + } + } + return 1; +} + +static int fips_key_check_passed(TLS1_PRF *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->seclen); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE2, + libctx, "TLS_PRF", "Key size", + ossl_fips_config_tls1_prf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int kdf_tls1_prf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { TLS1_PRF *ctx = (TLS1_PRF *)vctx; - OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); if (!ossl_prov_is_running() || !kdf_tls1_prf_set_ctx_params(ctx, params)) return 0; @@ -195,20 +269,10 @@ static int kdf_tls1_prf_derive(void *vctx, unsigned char *key, size_t keylen, return 0; } - /* - * The seed buffer is prepended with a label. - * If EMS mode is enforced then the label "master secret" is not allowed, - * We do the check this way since the PRF is used for other purposes, as well - * as "extended master secret". - */ - if (ossl_tls1_prf_ems_check_enabled(libctx)) { - if (ctx->seedlen >= TLS_MD_MASTER_SECRET_CONST_SIZE - && memcmp(ctx->seed, TLS_MD_MASTER_SECRET_CONST, - TLS_MD_MASTER_SECRET_CONST_SIZE) == 0) { - ERR_raise(ERR_LIB_PROV, PROV_R_EMS_NOT_ENABLED); - return 0; - } - } +#ifdef FIPS_MODULE + if (!fips_ems_check_passed(ctx)) + return 0; +#endif return tls1_prf_alg(ctx->P_hash, ctx->P_sha1, ctx->sec, ctx->seclen, @@ -225,7 +289,20 @@ static int kdf_tls1_prf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_EMS_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_KDF_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE2, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) + return 0; + if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_DIGEST)) != NULL) { + PROV_DIGEST digest; + const EVP_MD *md = NULL; + if (OPENSSL_strcasecmp(p->data, SN_md5_sha1) == 0) { if (!ossl_prov_macctx_load_from_params(&ctx->P_hash, params, OSSL_MAC_NAME_HMAC, @@ -241,6 +318,26 @@ static int kdf_tls1_prf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) NULL, NULL, libctx)) return 0; } + + memset(&digest, 0, sizeof(digest)); + if (!ossl_prov_digest_load_from_params(&digest, params, libctx)) + return 0; + + md = ossl_prov_digest_md(&digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + ossl_prov_digest_reset(&digest); + return 0; + } + +#ifdef FIPS_MODULE + if (!fips_digest_check_passed(ctx, md)) { + ossl_prov_digest_reset(&digest); + return 0; + } +#endif + + ossl_prov_digest_reset(&digest); } if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SECRET)) != NULL) { @@ -248,6 +345,11 @@ static int kdf_tls1_prf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) ctx->sec = NULL; if (!OSSL_PARAM_get_octet_string(p, (void **)&ctx->sec, 0, &ctx->seclen)) return 0; + +#ifdef FIPS_MODULE + if (!fips_key_check_passed(ctx)) + return 0; +#endif } /* The seed fields concatenate, so process them all */ if ((p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SEED)) != NULL) { @@ -289,6 +391,9 @@ static const OSSL_PARAM *kdf_tls1_prf_settable_ctx_params( OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_DIGEST, NULL, 0), OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SECRET, NULL, 0), OSSL_PARAM_octet_string(OSSL_KDF_PARAM_SEED, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_EMS_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; @@ -298,9 +403,13 @@ static int kdf_tls1_prf_get_ctx_params(void *vctx, OSSL_PARAM params[]) { OSSL_PARAM *p; - if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) - return OSSL_PARAM_set_size_t(p, SIZE_MAX); - return -2; + if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) { + if (!OSSL_PARAM_set_size_t(p, SIZE_MAX)) + return 0; + } + if (!OSSL_FIPS_IND_GET_CTX_PARAM(((TLS1_PRF *)vctx), params)) + return 0; + return 1; } static const OSSL_PARAM *kdf_tls1_prf_gettable_ctx_params( @@ -308,6 +417,7 @@ static const OSSL_PARAM *kdf_tls1_prf_gettable_ctx_params( { static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; diff --git a/providers/implementations/kdfs/x942kdf.c b/providers/implementations/kdfs/x942kdf.c index 19b54493ef..8b72a6a9f2 100644 --- a/providers/implementations/kdfs/x942kdf.c +++ b/providers/implementations/kdfs/x942kdf.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -22,6 +22,7 @@ #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_util.h" +#include "prov/securitycheck.h" #include "prov/der_wrap.h" #define X942KDF_MAX_INLEN (1 << 30) @@ -49,6 +50,7 @@ typedef struct { const unsigned char *cek_oid; size_t cek_oid_len; int use_keybits; + OSSL_FIPS_IND_DECLARE } KDF_X942; /* @@ -336,9 +338,12 @@ static void *x942kdf_new(void *provctx) if (!ossl_prov_is_running()) return NULL; - if ((ctx = OPENSSL_zalloc(sizeof(*ctx))) == NULL) + ctx = OPENSSL_zalloc(sizeof(*ctx)); + if (ctx == NULL) return NULL; + ctx->provctx = provctx; + OSSL_FIPS_IND_INIT(ctx) ctx->use_keybits = 1; return ctx; } @@ -397,6 +402,7 @@ static void *x942kdf_dup(void *vctx) dest->cek_oid_len = src->cek_oid_len; dest->dkm_len = src->dkm_len; dest->use_keybits = src->use_keybits; + OSSL_FIPS_IND_COPY(dest, src) } return dest; @@ -429,6 +435,24 @@ static size_t x942kdf_size(KDF_X942 *ctx) return (len <= 0) ? 0 : (size_t)len; } +#ifdef FIPS_MODULE +static int fips_x942kdf_key_check_passed(KDF_X942 *ctx) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); + int key_approved = ossl_kdf_check_key_size(ctx->secret_len); + + if (!key_approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "X942KDF", "Key size", + ossl_fips_config_x942kdf_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + static int x942kdf_derive(void *vctx, unsigned char *key, size_t keylen, const OSSL_PARAM params[]) { @@ -507,18 +531,37 @@ static int x942kdf_set_ctx_params(void *vctx, const OSSL_PARAM params[]) KDF_X942 *ctx = vctx; OSSL_LIB_CTX *provctx = PROV_LIBCTX_OF(ctx->provctx); const char *propq = NULL; + const EVP_MD *md; size_t id; if (params == NULL) return 1; - if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KDF_PARAM_FIPS_KEY_CHECK)) return 0; + if (OSSL_PARAM_locate_const(params, OSSL_ALG_PARAM_DIGEST) != NULL) { + if (!ossl_prov_digest_load_from_params(&ctx->digest, params, provctx)) + return 0; + md = ossl_prov_digest_md(&ctx->digest); + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + } + p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_SECRET); if (p == NULL) p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_KEY); - if (p != NULL && !x942kdf_set_buffer(&ctx->secret, &ctx->secret_len, p)) - return 0; + if (p != NULL) { + if (!x942kdf_set_buffer(&ctx->secret, &ctx->secret_len, p)) + return 0; +#ifdef FIPS_MODULE + if (!fips_x942kdf_key_check_passed(ctx)) + return 0; +#endif + } p = OSSL_PARAM_locate_const(params, OSSL_KDF_PARAM_X942_ACVPINFO); if (p != NULL @@ -589,6 +632,7 @@ static const OSSL_PARAM *x942kdf_settable_ctx_params(ossl_unused void *ctx, OSSL_PARAM_octet_string(OSSL_KDF_PARAM_X942_SUPP_PRIVINFO, NULL, 0), OSSL_PARAM_int(OSSL_KDF_PARAM_X942_USE_KEYBITS, NULL), OSSL_PARAM_utf8_string(OSSL_KDF_PARAM_CEK_ALG, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KDF_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; @@ -599,9 +643,13 @@ static int x942kdf_get_ctx_params(void *vctx, OSSL_PARAM params[]) KDF_X942 *ctx = (KDF_X942 *)vctx; OSSL_PARAM *p; - if ((p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE)) != NULL) - return OSSL_PARAM_set_size_t(p, x942kdf_size(ctx)); - return -2; + p = OSSL_PARAM_locate(params, OSSL_KDF_PARAM_SIZE); + if (p != NULL && !OSSL_PARAM_set_size_t(p, x942kdf_size(ctx))) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + return 1; } static const OSSL_PARAM *x942kdf_gettable_ctx_params(ossl_unused void *ctx, @@ -609,6 +657,7 @@ static const OSSL_PARAM *x942kdf_gettable_ctx_params(ossl_unused void *ctx, { static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_KDF_PARAM_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; diff --git a/providers/implementations/kem/rsa_kem.c b/providers/implementations/kem/rsa_kem.c index ff22ddffcf..0ac400cbe0 100644 --- a/providers/implementations/kem/rsa_kem.c +++ b/providers/implementations/kem/rsa_kem.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -13,7 +13,6 @@ */ #include "internal/deprecated.h" #include "internal/nelem.h" - #include #include #include @@ -21,10 +20,10 @@ #include #include #include -#include "crypto/rsa.h" #include -#include "internal/nelem.h" +#include "crypto/rsa.h" #include "prov/provider_ctx.h" +#include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/securitycheck.h" @@ -56,6 +55,7 @@ typedef struct { OSSL_LIB_CTX *libctx; RSA *rsa; int op; + OSSL_FIPS_IND_DECLARE } PROV_RSA_CTX; static const OSSL_ITEM rsakem_opname_id_map[] = { @@ -83,12 +83,17 @@ static int rsakem_opname2id(const char *name) static void *rsakem_newctx(void *provctx) { - PROV_RSA_CTX *prsactx = OPENSSL_zalloc(sizeof(PROV_RSA_CTX)); + PROV_RSA_CTX *prsactx; + + if (!ossl_prov_is_running()) + return NULL; + prsactx = OPENSSL_zalloc(sizeof(PROV_RSA_CTX)); if (prsactx == NULL) return NULL; prsactx->libctx = PROV_LIBCTX_OF(provctx); prsactx->op = KEM_OP_UNDEFINED; + OSSL_FIPS_IND_INIT(prsactx) return prsactx; } @@ -106,6 +111,9 @@ static void *rsakem_dupctx(void *vprsactx) PROV_RSA_CTX *srcctx = (PROV_RSA_CTX *)vprsactx; PROV_RSA_CTX *dstctx; + if (!ossl_prov_is_running()) + return NULL; + dstctx = OPENSSL_zalloc(sizeof(*srcctx)); if (dstctx == NULL) return NULL; @@ -119,44 +127,65 @@ static void *rsakem_dupctx(void *vprsactx) } static int rsakem_init(void *vprsactx, void *vrsa, - const OSSL_PARAM params[], int operation) + const OSSL_PARAM params[], int operation, + const char *desc) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + int protect = 0; - if (prsactx == NULL || vrsa == NULL) + if (!ossl_prov_is_running()) return 0; - if (!ossl_rsa_check_key(prsactx->libctx, vrsa, operation)) + if (prsactx == NULL || vrsa == NULL) return 0; + if (!ossl_rsa_key_op_get_protect(vrsa, operation, &protect)) + return 0; if (!RSA_up_ref(vrsa)) return 0; RSA_free(prsactx->rsa); prsactx->rsa = vrsa; - return rsakem_set_ctx_params(prsactx, params); + OSSL_FIPS_IND_SET_APPROVED(prsactx) + if (!rsakem_set_ctx_params(prsactx, params)) + return 0; +#ifdef FIPS_MODULE + if (!ossl_fips_ind_rsa_key_check(OSSL_FIPS_IND_GET(prsactx), + OSSL_FIPS_IND_SETTABLE0, prsactx->libctx, + prsactx->rsa, desc, protect)) + return 0; +#endif + return 1; } static int rsakem_encapsulate_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - return rsakem_init(vprsactx, vrsa, params, EVP_PKEY_OP_ENCAPSULATE); + return rsakem_init(vprsactx, vrsa, params, EVP_PKEY_OP_ENCAPSULATE, + "RSA Encapsulate Init"); } static int rsakem_decapsulate_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - return rsakem_init(vprsactx, vrsa, params, EVP_PKEY_OP_DECAPSULATE); + return rsakem_init(vprsactx, vrsa, params, EVP_PKEY_OP_DECAPSULATE, + "RSA Decapsulate Init"); } static int rsakem_get_ctx_params(void *vprsactx, OSSL_PARAM *params) { PROV_RSA_CTX *ctx = (PROV_RSA_CTX *)vprsactx; - return ctx != NULL; + if (ctx == NULL) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; + return 1; } static const OSSL_PARAM known_gettable_rsakem_ctx_params[] = { + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -177,7 +206,9 @@ static int rsakem_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) if (params == NULL) return 1; - + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_KEM_PARAM_FIPS_KEY_CHECK)) + return 0; p = OSSL_PARAM_locate_const(params, OSSL_KEM_PARAM_OPERATION); if (p != NULL) { if (p->data_type != OSSL_PARAM_UTF8_STRING) @@ -192,6 +223,7 @@ static int rsakem_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) static const OSSL_PARAM known_settable_rsakem_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_KEM_PARAM_OPERATION, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_KEM_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; @@ -265,6 +297,17 @@ static int rsasve_generate(PROV_RSA_CTX *prsactx, *secretlen = nlen; return 1; } + + /* + * If outlen is specified, then it must report the length + * of the out buffer on input so that we can confirm + * its size is sufficent for encapsulation + */ + if (outlen != NULL && *outlen < nlen) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_OUTPUT_LENGTH); + return 0; + } + /* * Step (2): Generate a random byte string z of nlen bytes where * 1 < z < n - 1 @@ -286,15 +329,33 @@ static int rsasve_generate(PROV_RSA_CTX *prsactx, return ret; } -/* - * NIST.SP.800-56Br2 +/** + * rsasve_recover - Recovers a secret value from ciphertext using an RSA + * private key. Once, recovered, the secret value is considered to be a + * shared secret. Algorithm is preformed as per + * NIST SP 800-56B Rev 2 * 7.2.1.3 RSASVE Recovery Operation (RSASVE.RECOVER). + * + * This function performs RSA decryption using the private key from the + * provided RSA context (`prsactx`). It takes the input ciphertext, decrypts + * it, and writes the decrypted message to the output buffer. + * + * @prsactx: The RSA context containing the private key. + * @out: The output buffer to store the decrypted message. + * @outlen: On input, the size of the output buffer. On successful + * completion, the actual length of the decrypted message. + * @in: The input buffer containing the ciphertext to be decrypted. + * @inlen: The length of the input ciphertext in bytes. + * + * Returns 1 on success, or 0 on error. In case of error, appropriate + * error messages are raised using the ERR_raise function. */ static int rsasve_recover(PROV_RSA_CTX *prsactx, unsigned char *out, size_t *outlen, const unsigned char *in, size_t inlen) { size_t nlen; + int ret; /* Step (1): get the byte length of n */ nlen = RSA_size(prsactx->rsa); @@ -308,13 +369,30 @@ static int rsasve_recover(PROV_RSA_CTX *prsactx, return 1; } - /* Step (2): check the input ciphertext 'inlen' matches the nlen */ + /* + * Step (2): check the input ciphertext 'inlen' matches the nlen + * and that outlen is at least nlen bytes + */ if (inlen != nlen) { ERR_raise(ERR_LIB_PROV, PROV_R_BAD_LENGTH); return 0; } + + /* + * If outlen is specified, then it must report the length + * of the out buffer, so that we can confirm that it is of + * sufficient size to hold the output of decapsulation + */ + if (outlen != NULL && *outlen < nlen) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_OUTPUT_LENGTH); + return 0; + } + /* Step (3): out = RSADP((n,d), in) */ - return (RSA_private_decrypt(inlen, in, out, prsactx->rsa, RSA_NO_PADDING) > 0); + ret = RSA_private_decrypt(inlen, in, out, prsactx->rsa, RSA_NO_PADDING); + if (ret > 0 && outlen != NULL) + *outlen = ret; + return ret > 0; } static int rsakem_generate(void *vprsactx, unsigned char *out, size_t *outlen, @@ -322,6 +400,9 @@ static int rsakem_generate(void *vprsactx, unsigned char *out, size_t *outlen, { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + if (!ossl_prov_is_running()) + return 0; + switch (prsactx->op) { case KEM_OP_RSASVE: return rsasve_generate(prsactx, out, outlen, secret, secretlen); @@ -335,6 +416,9 @@ static int rsakem_recover(void *vprsactx, unsigned char *out, size_t *outlen, { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + if (!ossl_prov_is_running()) + return 0; + switch (prsactx->op) { case KEM_OP_RSASVE: return rsasve_recover(prsactx, out, outlen, in, inlen); diff --git a/providers/implementations/keymgmt/dh_kmgmt.c b/providers/implementations/keymgmt/dh_kmgmt.c index 82c3093b12..d1e1e3c0d3 100644 --- a/providers/implementations/keymgmt/dh_kmgmt.c +++ b/providers/implementations/keymgmt/dh_kmgmt.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -388,9 +388,11 @@ static int dh_validate_public(const DH *dh, int checktype) if (pub_key == NULL) return 0; - /* The partial test is only valid for named group's with q = (p - 1) / 2 */ - if (checktype == OSSL_KEYMGMT_VALIDATE_QUICK_CHECK - && ossl_dh_is_named_safe_prime_group(dh)) + /* + * The partial test is only valid for named group's with q = (p - 1) / 2 + * but for that case it is also fully sufficient to check the key validity. + */ + if (ossl_dh_is_named_safe_prime_group(dh)) return ossl_dh_check_pub_key_partial(dh, pub_key, &res); return DH_check_pub_key_ex(dh, pub_key); diff --git a/providers/implementations/keymgmt/dsa_kmgmt.c b/providers/implementations/keymgmt/dsa_kmgmt.c index 88a2feda57..2187568b2b 100644 --- a/providers/implementations/keymgmt/dsa_kmgmt.c +++ b/providers/implementations/keymgmt/dsa_kmgmt.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -17,6 +17,7 @@ #include #include #include +#include "prov/securitycheck.h" #include "prov/providercommon.h" #include "prov/implementations.h" #include "prov/provider_ctx.h" @@ -31,6 +32,8 @@ static OSSL_FUNC_keymgmt_gen_init_fn dsa_gen_init; static OSSL_FUNC_keymgmt_gen_set_template_fn dsa_gen_set_template; static OSSL_FUNC_keymgmt_gen_set_params_fn dsa_gen_set_params; static OSSL_FUNC_keymgmt_gen_settable_params_fn dsa_gen_settable_params; +static OSSL_FUNC_keymgmt_gen_get_params_fn dsa_gen_get_params; +static OSSL_FUNC_keymgmt_gen_gettable_params_fn dsa_gen_gettable_params; static OSSL_FUNC_keymgmt_gen_fn dsa_gen; static OSSL_FUNC_keymgmt_gen_cleanup_fn dsa_gen_cleanup; static OSSL_FUNC_keymgmt_load_fn dsa_load; @@ -67,14 +70,14 @@ struct dsa_gen_ctx { char *mdprops; OSSL_CALLBACK *cb; void *cbarg; + OSSL_FIPS_IND_DECLARE }; typedef struct dh_name2id_st{ const char *name; int id; } DSA_GENTYPE_NAME2ID; -static const DSA_GENTYPE_NAME2ID dsatype2id[]= -{ +static const DSA_GENTYPE_NAME2ID dsatype2id[] = { #ifdef FIPS_MODULE { "default", DSA_PARAMGEN_TYPE_FIPS_186_4 }, #else @@ -424,6 +427,7 @@ static void *dsa_gen_init(void *provctx, int selection, gctx->gindex = -1; gctx->pcounter = -1; gctx->hindex = 0; + OSSL_FIPS_IND_INIT(gctx) } if (!dsa_gen_set_params(gctx, params)) { OPENSSL_free(gctx); @@ -469,6 +473,9 @@ static int dsa_gen_set_params(void *genctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(gctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_PKEY_PARAM_FIPS_SIGN_CHECK)) + return 0; p = OSSL_PARAM_locate_const(params, OSSL_PKEY_PARAM_FFC_TYPE); if (p != NULL) { @@ -543,11 +550,36 @@ static const OSSL_PARAM *dsa_gen_settable_params(ossl_unused void *genctx, OSSL_PARAM_octet_string(OSSL_PKEY_PARAM_FFC_SEED, NULL, 0), OSSL_PARAM_int(OSSL_PKEY_PARAM_FFC_PCOUNTER, NULL), OSSL_PARAM_int(OSSL_PKEY_PARAM_FFC_H, NULL), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_PKEY_PARAM_FIPS_SIGN_CHECK) OSSL_PARAM_END }; return settable; } +static int dsa_gen_get_params(void *genctx, OSSL_PARAM *params) +{ + struct dsa_gen_ctx *gctx = genctx; + + if (gctx == NULL) + return 0; + if (params == NULL) + return 1; + if (!OSSL_FIPS_IND_GET_CTX_PARAM(gctx, params)) + return 0; + return 1; +} + +static const OSSL_PARAM *dsa_gen_gettable_params(ossl_unused void *ctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM dsa_gen_gettable_params_table[] = { + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; + + return dsa_gen_gettable_params_table; +} + static int dsa_gencb(int p, int n, BN_GENCB *cb) { struct dsa_gen_ctx *gctx = BN_GENCB_get_arg(cb); @@ -569,6 +601,18 @@ static void *dsa_gen(void *genctx, OSSL_CALLBACK *osslcb, void *cbarg) if (!ossl_prov_is_running() || gctx == NULL) return NULL; + +#ifdef FIPS_MODULE + /* + * DSA signing is not approved in FIPS 140-3, so there is no + * need for DSA keygen either. + */ + if (!OSSL_FIPS_IND_ON_UNAPPROVED(gctx, OSSL_FIPS_IND_SETTABLE0, + gctx->libctx, "DSA", "Keygen", + ossl_fips_config_dsa_sign_disallowed)) + return 0; +#endif + dsa = ossl_dsa_new(gctx->libctx); if (dsa == NULL) return NULL; @@ -683,6 +727,9 @@ const OSSL_DISPATCH ossl_dsa_keymgmt_functions[] = { { OSSL_FUNC_KEYMGMT_GEN_SET_PARAMS, (void (*)(void))dsa_gen_set_params }, { OSSL_FUNC_KEYMGMT_GEN_SETTABLE_PARAMS, (void (*)(void))dsa_gen_settable_params }, + { OSSL_FUNC_KEYMGMT_GEN_GET_PARAMS, (void (*)(void))dsa_gen_get_params }, + { OSSL_FUNC_KEYMGMT_GEN_GETTABLE_PARAMS, + (void (*)(void))dsa_gen_gettable_params }, { OSSL_FUNC_KEYMGMT_GEN, (void (*)(void))dsa_gen }, { OSSL_FUNC_KEYMGMT_GEN_CLEANUP, (void (*)(void))dsa_gen_cleanup }, { OSSL_FUNC_KEYMGMT_LOAD, (void (*)(void))dsa_load }, diff --git a/providers/implementations/keymgmt/ec_kmgmt.c b/providers/implementations/keymgmt/ec_kmgmt.c index 9390935394..820b66b770 100644 --- a/providers/implementations/keymgmt/ec_kmgmt.c +++ b/providers/implementations/keymgmt/ec_kmgmt.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -25,6 +25,7 @@ #include "prov/implementations.h" #include "prov/providercommon.h" #include "prov/provider_ctx.h" +#include "prov/securitycheck.h" #include "internal/param_build_set.h" #ifndef FIPS_MODULE @@ -38,6 +39,8 @@ static OSSL_FUNC_keymgmt_gen_init_fn ec_gen_init; static OSSL_FUNC_keymgmt_gen_set_template_fn ec_gen_set_template; static OSSL_FUNC_keymgmt_gen_set_params_fn ec_gen_set_params; static OSSL_FUNC_keymgmt_gen_settable_params_fn ec_gen_settable_params; +static OSSL_FUNC_keymgmt_gen_get_params_fn ec_gen_get_params; +static OSSL_FUNC_keymgmt_gen_gettable_params_fn ec_gen_gettable_params; static OSSL_FUNC_keymgmt_gen_fn ec_gen; static OSSL_FUNC_keymgmt_gen_cleanup_fn ec_gen_cleanup; static OSSL_FUNC_keymgmt_load_fn ec_load; @@ -991,6 +994,7 @@ struct ec_gen_ctx { EC_GROUP *gen_group; unsigned char *dhkem_ikm; size_t dhkem_ikmlen; + OSSL_FIPS_IND_DECLARE }; static void *ec_gen_init(void *provctx, int selection, @@ -1006,6 +1010,7 @@ static void *ec_gen_init(void *provctx, int selection, gctx->libctx = libctx; gctx->selection = selection; gctx->ecdh_mode = 0; + OSSL_FIPS_IND_INIT(gctx) if (!ec_gen_set_params(gctx, params)) { OPENSSL_free(gctx); gctx = NULL; @@ -1105,6 +1110,10 @@ static int ec_gen_set_params(void *genctx, const OSSL_PARAM params[]) const OSSL_PARAM *p; EC_GROUP *group = NULL; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(gctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_PKEY_PARAM_FIPS_KEY_CHECK)) + goto err; + COPY_INT_PARAM(params, OSSL_PKEY_PARAM_USE_COFACTOR_ECDH, gctx->ecdh_mode); COPY_UTF8_PARAM(params, OSSL_PKEY_PARAM_GROUP_NAME, gctx->group_name); @@ -1226,12 +1235,35 @@ static const OSSL_PARAM *ec_gen_settable_params(ossl_unused void *genctx, OSSL_PARAM_BN(OSSL_PKEY_PARAM_EC_COFACTOR, NULL, 0), OSSL_PARAM_octet_string(OSSL_PKEY_PARAM_EC_SEED, NULL, 0), OSSL_PARAM_octet_string(OSSL_PKEY_PARAM_DHKEM_IKM, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_PKEY_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; - return settable; } +static const OSSL_PARAM *ec_gen_gettable_params(ossl_unused void *genctx, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_ec_gen_gettable_ctx_params[] = { + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() + OSSL_PARAM_END + }; + return known_ec_gen_gettable_ctx_params; +} + +static int ec_gen_get_params(void *genctx, OSSL_PARAM *params) +{ + struct ec_gen_ctx *gctx = genctx; + + if (gctx == NULL) + return 0; + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(gctx, params)) + return 0; + + return 1; +} + static int ec_gen_assign_group(EC_KEY *ec, EC_GROUP *group) { if (group == NULL) { @@ -1274,6 +1306,16 @@ static void *ec_gen(void *genctx, OSSL_CALLBACK *osslcb, void *cbarg) EC_GROUP_set_point_conversion_form(gctx->gen_group, format); } } +#ifdef FIPS_MODULE + if (!ossl_ec_check_security_strength(gctx->gen_group, 1)) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(gctx, OSSL_FIPS_IND_SETTABLE0, + gctx->libctx, "EC KeyGen", "key size", + ossl_fips_config_securitycheck_enabled)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + goto err; + } + } +#endif /* We must always assign a group, no matter what */ ret = ec_gen_assign_group(ec, gctx->gen_group); @@ -1426,6 +1468,9 @@ const OSSL_DISPATCH ossl_ec_keymgmt_functions[] = { { OSSL_FUNC_KEYMGMT_GEN_SET_PARAMS, (void (*)(void))ec_gen_set_params }, { OSSL_FUNC_KEYMGMT_GEN_SETTABLE_PARAMS, (void (*)(void))ec_gen_settable_params }, + { OSSL_FUNC_KEYMGMT_GEN_GET_PARAMS, (void (*)(void))ec_gen_get_params }, + { OSSL_FUNC_KEYMGMT_GEN_GETTABLE_PARAMS, + (void (*)(void))ec_gen_gettable_params }, { OSSL_FUNC_KEYMGMT_GEN, (void (*)(void))ec_gen }, { OSSL_FUNC_KEYMGMT_GEN_CLEANUP, (void (*)(void))ec_gen_cleanup }, { OSSL_FUNC_KEYMGMT_LOAD, (void (*)(void))ec_load }, diff --git a/providers/implementations/keymgmt/ecx_kmgmt.c b/providers/implementations/keymgmt/ecx_kmgmt.c index ae11fd4bc0..958fc37a47 100644 --- a/providers/implementations/keymgmt/ecx_kmgmt.c +++ b/providers/implementations/keymgmt/ecx_kmgmt.c @@ -24,6 +24,7 @@ #include "prov/providercommon.h" #include "prov/provider_ctx.h" #include "prov/ecx.h" +#include "prov/securitycheck.h" #ifdef S390X_EC_ASM # include "s390x_arch.h" # include /* For SHA512_DIGEST_LENGTH */ @@ -303,6 +304,16 @@ static int ecx_get_params(void *key, OSSL_PARAM params[], int bits, int secbits, if (!OSSL_PARAM_set_octet_string(p, ecx->pubkey, ecx->keylen)) return 0; } +#ifdef FIPS_MODULE + { + /* X25519 and X448 are not approved */ + int approved = 0; + + p = OSSL_PARAM_locate(params, OSSL_ALG_PARAM_FIPS_APPROVED_INDICATOR); + if (p != NULL && !OSSL_PARAM_set_int(p, approved)) + return 0; + } +#endif return key_to_params(ecx, NULL, params, 1); } @@ -351,6 +362,7 @@ static const OSSL_PARAM ecx_gettable_params[] = { OSSL_PARAM_utf8_string(OSSL_PKEY_PARAM_MANDATORY_DIGEST, NULL, 0), OSSL_PARAM_octet_string(OSSL_PKEY_PARAM_ENCODED_PUBLIC_KEY, NULL, 0), ECX_KEY_TYPES(), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -475,7 +487,8 @@ static const OSSL_PARAM *ed448_settable_params(void *provctx) } static void *ecx_gen_init(void *provctx, int selection, - const OSSL_PARAM params[], ECX_KEY_TYPE type) + const OSSL_PARAM params[], ECX_KEY_TYPE type, + const char *algdesc) { OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(provctx); struct ecx_gen_ctx *gctx = NULL; @@ -487,6 +500,14 @@ static void *ecx_gen_init(void *provctx, int selection, gctx->libctx = libctx; gctx->type = type; gctx->selection = selection; +#ifdef FIPS_MODULE + /* X25519/X448 are not FIPS approved, (ED25519/ED448 are approved) */ + if (algdesc != NULL + && !ossl_FIPS_IND_callback(libctx, algdesc, "KeyGen Init")) { + OPENSSL_free(gctx); + return 0; + } +#endif } if (!ecx_gen_set_params(gctx, params)) { OPENSSL_free(gctx); @@ -498,25 +519,25 @@ static void *ecx_gen_init(void *provctx, int selection, static void *x25519_gen_init(void *provctx, int selection, const OSSL_PARAM params[]) { - return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_X25519); + return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_X25519, "X25519"); } static void *x448_gen_init(void *provctx, int selection, const OSSL_PARAM params[]) { - return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_X448); + return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_X448, "X448"); } static void *ed25519_gen_init(void *provctx, int selection, const OSSL_PARAM params[]) { - return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_ED25519); + return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_ED25519, NULL); } static void *ed448_gen_init(void *provctx, int selection, const OSSL_PARAM params[]) { - return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_ED448); + return ecx_gen_init(provctx, selection, params, ECX_KEY_TYPE_ED448, NULL); } static int ecx_gen_set_params(void *genctx, const OSSL_PARAM params[]) @@ -865,6 +886,25 @@ static int ecx_key_pairwise_check(const ECX_KEY *ecx, int type) return CRYPTO_memcmp(ecx->pubkey, pub, ecx->keylen) == 0; } +#ifdef FIPS_MODULE +/* + * FIPS ACVP testing requires the ability to check if the public key is valid + * This is not required normally since the ED signature verify does the test + * internally. + */ +static int ecd_key_pub_check(const ECX_KEY *ecx, int type) +{ + switch (type) { + case ECX_KEY_TYPE_ED25519: + return ossl_ed25519_pubkey_verify(ecx->pubkey, ecx->keylen); + case ECX_KEY_TYPE_ED448: + return ossl_ed448_pubkey_verify(ecx->pubkey, ecx->keylen); + default: + return 1; + } +} +#endif + #ifdef FIPS_MODULE static int ecd_key_pairwise_check(const ECX_KEY *ecx, int type) { @@ -893,7 +933,8 @@ static int ecd_key_pairwise_check(const ECX_KEY *ecx, int type) } #endif -static int ecx_validate(const void *keydata, int selection, int type, size_t keylen) +static int ecx_validate(const void *keydata, int selection, int type, + size_t keylen) { const ECX_KEY *ecx = keydata; int ok = keylen == ecx->keylen; @@ -909,8 +950,12 @@ static int ecx_validate(const void *keydata, int selection, int type, size_t key return 0; } - if ((selection & OSSL_KEYMGMT_SELECT_PUBLIC_KEY) != 0) + if ((selection & OSSL_KEYMGMT_SELECT_PUBLIC_KEY) != 0) { ok = ok && ecx->haspubkey; +#ifdef FIPS_MODULE + ok = ok && ecd_key_pub_check(ecx, type); +#endif + } if ((selection & OSSL_KEYMGMT_SELECT_PRIVATE_KEY) != 0) ok = ok && ecx->privkey != NULL; diff --git a/providers/implementations/macs/cmac_prov.c b/providers/implementations/macs/cmac_prov.c index fa0b576b97..9b2d8eb19c 100644 --- a/providers/implementations/macs/cmac_prov.c +++ b/providers/implementations/macs/cmac_prov.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -21,10 +21,12 @@ #include #include +#include "prov/securitycheck.h" #include "prov/implementations.h" #include "prov/provider_ctx.h" #include "prov/provider_util.h" #include "prov/providercommon.h" +#include "crypto/cmac.h" /* * Forward declaration of everything implemented here. This is not strictly @@ -48,6 +50,7 @@ struct cmac_data_st { void *provctx; CMAC_CTX *ctx; PROV_CIPHER cipher; + OSSL_FIPS_IND_DECLARE }; static void *cmac_new(void *provctx) @@ -63,6 +66,7 @@ static void *cmac_new(void *provctx) macctx = NULL; } else { macctx->provctx = provctx; + OSSL_FIPS_IND_INIT(macctx) } return macctx; @@ -95,6 +99,7 @@ static void *cmac_dup(void *vsrc) cmac_free(dst); return NULL; } + OSSL_FIPS_IND_COPY(dst, src) return dst; } @@ -109,12 +114,55 @@ static size_t cmac_size(void *vmacctx) return EVP_CIPHER_CTX_get_block_size(cipherctx); } +#ifdef FIPS_MODULE +/* + * TDES Encryption is not approved in FIPS 140-3. + * + * In strict approved mode we just fail here (by returning 0). + * If we are going to bypass it using a FIPS indicator then we need to pass that + * information down to the cipher also. + * This function returns the param to pass down in 'p'. + * state will return OSSL_FIPS_IND_STATE_UNKNOWN if the param has not been set. + * + * The name 'OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK' used below matches the + * key name used by the Triple-DES. + */ +static int tdes_check_param(struct cmac_data_st *macctx, OSSL_PARAM *p, + int *state) +{ + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(macctx->provctx); + const EVP_CIPHER *cipher = ossl_prov_cipher_cipher(&macctx->cipher); + + *state = OSSL_FIPS_IND_STATE_UNKNOWN; + if (EVP_CIPHER_is_a(cipher, "DES-EDE3-CBC")) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(macctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "CMAC", "Triple-DES", + ossl_fips_config_tdes_encrypt_disallowed)) + return 0; + OSSL_FIPS_IND_GET_PARAM(macctx, p, state, OSSL_FIPS_IND_SETTABLE0, + OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK) + } + return 1; +} +#endif + static int cmac_setkey(struct cmac_data_st *macctx, const unsigned char *key, size_t keylen) { - int rv = CMAC_Init(macctx->ctx, key, keylen, - ossl_prov_cipher_cipher(&macctx->cipher), - ossl_prov_cipher_engine(&macctx->cipher)); + int rv; + OSSL_PARAM *p = NULL; +#ifdef FIPS_MODULE + int state = OSSL_FIPS_IND_STATE_UNKNOWN; + OSSL_PARAM prms[2] = { OSSL_PARAM_END, OSSL_PARAM_END }; + + if (!tdes_check_param(macctx, &prms[0], &state)) + return 0; + if (state != OSSL_FIPS_IND_STATE_UNKNOWN) + p = prms; +#endif + rv = ossl_cmac_init(macctx->ctx, key, keylen, + ossl_prov_cipher_cipher(&macctx->cipher), + ossl_prov_cipher_engine(&macctx->cipher), p); ossl_prov_cipher_reset(&macctx->cipher); return rv; } @@ -154,6 +202,7 @@ static int cmac_final(void *vmacctx, unsigned char *out, size_t *outl, static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_MAC_PARAM_SIZE, NULL), OSSL_PARAM_size_t(OSSL_MAC_PARAM_BLOCK_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; static const OSSL_PARAM *cmac_gettable_ctx_params(ossl_unused void *ctx, @@ -174,6 +223,8 @@ static int cmac_get_ctx_params(void *vmacctx, OSSL_PARAM params[]) && !OSSL_PARAM_set_size_t(p, cmac_size(vmacctx))) return 0; + if (!OSSL_FIPS_IND_GET_CTX_PARAM((struct cmac_data_st *)vmacctx, params)) + return 0; return 1; } @@ -181,6 +232,7 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_MAC_PARAM_CIPHER, NULL, 0), OSSL_PARAM_utf8_string(OSSL_MAC_PARAM_PROPERTIES, NULL, 0), OSSL_PARAM_octet_string(OSSL_MAC_PARAM_KEY, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK) OSSL_PARAM_END }; static const OSSL_PARAM *cmac_settable_ctx_params(ossl_unused void *ctx, @@ -201,6 +253,11 @@ static int cmac_set_ctx_params(void *vmacctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(macctx, + OSSL_FIPS_IND_SETTABLE0, params, + OSSL_CIPHER_PARAM_FIPS_ENCRYPT_CHECK)) + return 0; + if ((p = OSSL_PARAM_locate_const(params, OSSL_MAC_PARAM_CIPHER)) != NULL) { if (!ossl_prov_cipher_load_from_params(&macctx->cipher, params, ctx)) return 0; @@ -210,6 +267,19 @@ static int cmac_set_ctx_params(void *vmacctx, const OSSL_PARAM params[]) ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_MODE); return 0; } +#ifdef FIPS_MODULE + { + const EVP_CIPHER *cipher = ossl_prov_cipher_cipher(&macctx->cipher); + + if (!EVP_CIPHER_is_a(cipher, "AES-256-CBC") + && !EVP_CIPHER_is_a(cipher, "AES-192-CBC") + && !EVP_CIPHER_is_a(cipher, "AES-128-CBC") + && !EVP_CIPHER_is_a(cipher, "DES-EDE3-CBC")) { + ERR_raise(ERR_LIB_PROV, EVP_R_UNSUPPORTED_CIPHER); + return 0; + } + } +#endif } if ((p = OSSL_PARAM_locate_const(params, OSSL_MAC_PARAM_KEY)) != NULL) { diff --git a/providers/implementations/macs/hmac_prov.c b/providers/implementations/macs/hmac_prov.c index c72c1e6c0f..4139204b94 100644 --- a/providers/implementations/macs/hmac_prov.c +++ b/providers/implementations/macs/hmac_prov.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -20,6 +20,8 @@ #include #include #include +#include +#include #include "internal/ssl3_cbc.h" @@ -27,6 +29,7 @@ #include "prov/provider_ctx.h" #include "prov/provider_util.h" #include "prov/providercommon.h" +#include "prov/securitycheck.h" /* * Forward declaration of everything implemented here. This is not strictly @@ -59,6 +62,15 @@ struct hmac_data_st { int tls_header_set; unsigned char tls_mac_out[EVP_MAX_MD_SIZE]; size_t tls_mac_out_size; +#ifdef FIPS_MODULE + /* + * 'internal' is set to 1 if HMAC is used inside another algorithm such as a + * KDF. In this case it is the parent algorithm that is responsible for + * performing any conditional FIPS indicator related checks for the HMAC. + */ + int internal; +#endif + OSSL_FIPS_IND_DECLARE }; static void *hmac_new(void *provctx) @@ -74,6 +86,7 @@ static void *hmac_new(void *provctx) return NULL; } macctx->provctx = provctx; + OSSL_FIPS_IND_INIT(macctx) return macctx; } @@ -144,12 +157,33 @@ static int hmac_setkey(struct hmac_data_st *macctx, { const EVP_MD *digest; +#ifdef FIPS_MODULE + /* + * KDF's pass a salt rather than a key, + * which is why it skips the key check unless "HMAC" is fetched directly. + */ + if (!macctx->internal) { + OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(macctx->provctx); + int approved = ossl_mac_check_key_size(keylen); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(macctx, OSSL_FIPS_IND_SETTABLE0, + libctx, "HMAC", "keysize", + ossl_fips_config_hmac_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + } +#endif + if (macctx->key != NULL) OPENSSL_secure_clear_free(macctx->key, macctx->keylen); /* Keep a copy of the key in case we need it for TLS HMAC */ macctx->key = OPENSSL_secure_malloc(keylen > 0 ? keylen : 1); if (macctx->key == NULL) return 0; + memcpy(macctx->key, key, keylen); macctx->keylen = keylen; @@ -235,6 +269,7 @@ static int hmac_final(void *vmacctx, unsigned char *out, size_t *outl, static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_MAC_PARAM_SIZE, NULL), OSSL_PARAM_size_t(OSSL_MAC_PARAM_BLOCK_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; static const OSSL_PARAM *hmac_gettable_ctx_params(ossl_unused void *ctx, @@ -256,6 +291,17 @@ static int hmac_get_ctx_params(void *vmacctx, OSSL_PARAM params[]) && !OSSL_PARAM_set_int(p, hmac_block_size(macctx))) return 0; +#ifdef FIPS_MODULE + p = OSSL_PARAM_locate(params, OSSL_MAC_PARAM_FIPS_APPROVED_INDICATOR); + if (p != NULL) { + int approved = 0; + + if (!macctx->internal) + approved = OSSL_FIPS_IND_GET(macctx)->approved; + if (!OSSL_PARAM_set_int(p, approved)) + return 0; + } +#endif return 1; } @@ -266,6 +312,7 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_int(OSSL_MAC_PARAM_DIGEST_NOINIT, NULL), OSSL_PARAM_int(OSSL_MAC_PARAM_DIGEST_ONESHOT, NULL), OSSL_PARAM_size_t(OSSL_MAC_PARAM_TLS_DATA_SIZE, NULL), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_MAC_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; static const OSSL_PARAM *hmac_settable_ctx_params(ossl_unused void *ctx, @@ -286,12 +333,17 @@ static int hmac_set_ctx_params(void *vmacctx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(macctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_MAC_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!ossl_prov_digest_load_from_params(&macctx->digest, params, ctx)) return 0; if ((p = OSSL_PARAM_locate_const(params, OSSL_MAC_PARAM_KEY)) != NULL) { if (p->data_type != OSSL_PARAM_OCTET_STRING) return 0; + if (!hmac_setkey(macctx, p->data, p->data_size)) return 0; } @@ -319,3 +371,33 @@ const OSSL_DISPATCH ossl_hmac_functions[] = { { OSSL_FUNC_MAC_SET_CTX_PARAMS, (void (*)(void))hmac_set_ctx_params }, OSSL_DISPATCH_END }; + +#ifdef FIPS_MODULE +static OSSL_FUNC_mac_newctx_fn hmac_internal_new; + +static void *hmac_internal_new(void *provctx) +{ + struct hmac_data_st *macctx = hmac_new(provctx); + + if (macctx != NULL) + macctx->internal = 1; + return macctx; +} + +const OSSL_DISPATCH ossl_hmac_internal_functions[] = { + { OSSL_FUNC_MAC_NEWCTX, (void (*)(void))hmac_internal_new }, + { OSSL_FUNC_MAC_DUPCTX, (void (*)(void))hmac_dup }, + { OSSL_FUNC_MAC_FREECTX, (void (*)(void))hmac_free }, + { OSSL_FUNC_MAC_INIT, (void (*)(void))hmac_init }, + { OSSL_FUNC_MAC_UPDATE, (void (*)(void))hmac_update }, + { OSSL_FUNC_MAC_FINAL, (void (*)(void))hmac_final }, + { OSSL_FUNC_MAC_GETTABLE_CTX_PARAMS, + (void (*)(void))hmac_gettable_ctx_params }, + { OSSL_FUNC_MAC_GET_CTX_PARAMS, (void (*)(void))hmac_get_ctx_params }, + { OSSL_FUNC_MAC_SETTABLE_CTX_PARAMS, + (void (*)(void))hmac_settable_ctx_params }, + { OSSL_FUNC_MAC_SET_CTX_PARAMS, (void (*)(void))hmac_set_ctx_params }, + OSSL_DISPATCH_END +}; + +#endif /* FIPS_MODULE */ diff --git a/providers/implementations/macs/kmac_prov.c b/providers/implementations/macs/kmac_prov.c index ddaab4ba86..13e6020cbb 100644 --- a/providers/implementations/macs/kmac_prov.c +++ b/providers/implementations/macs/kmac_prov.c @@ -1,5 +1,5 @@ /* - * Copyright 2018-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2018-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -54,7 +54,8 @@ #include #include #include - +#include +#include "prov/securitycheck.h" #include "prov/implementations.h" #include "prov/provider_ctx.h" #include "prov/provider_util.h" @@ -126,6 +127,15 @@ struct kmac_data_st { /* key and custom are stored in encoded form */ unsigned char key[KMAC_MAX_KEY_ENCODED]; unsigned char custom[KMAC_MAX_CUSTOM_ENCODED]; +#ifdef FIPS_MODULE + /* + * 'internal' is set to 1 if KMAC is used inside another algorithm such as a + * KDF. In this case it is the parent algorithm that is responsible for + * performing any conditional FIPS indicator related checks for KMAC. + */ + int internal; +#endif + OSSL_FIPS_IND_DECLARE }; static int encode_string(unsigned char *out, size_t out_max_len, size_t *out_len, @@ -172,12 +182,14 @@ static struct kmac_data_st *kmac_new(void *provctx) return NULL; } kctx->provctx = provctx; + OSSL_FIPS_IND_INIT(kctx) return kctx; } static void *kmac_fetch_new(void *provctx, const OSSL_PARAM *params) { struct kmac_data_st *kctx = kmac_new(provctx); + int md_size; if (kctx == NULL) return 0; @@ -187,7 +199,12 @@ static void *kmac_fetch_new(void *provctx, const OSSL_PARAM *params) return 0; } - kctx->out_len = EVP_MD_get_size(ossl_prov_digest_md(&kctx->digest)); + md_size = EVP_MD_get_size(ossl_prov_digest_md(&kctx->digest)); + if (md_size <= 0) { + kmac_free(kctx); + return 0; + } + kctx->out_len = (size_t)md_size; return kctx; } @@ -228,13 +245,16 @@ static void *kmac_dup(void *vsrc) kmac_free(dst); return NULL; } - +#ifdef FIPS_MODULE + dst->internal = src->internal; +#endif dst->out_len = src->out_len; dst->key_len = src->key_len; dst->custom_len = src->custom_len; dst->xof_mode = src->xof_mode; memcpy(dst->key, src->key, src->key_len); memcpy(dst->custom, src->custom, dst->custom_len); + OSSL_FIPS_IND_COPY(dst, src) return dst; } @@ -249,6 +269,25 @@ static int kmac_setkey(struct kmac_data_st *kctx, const unsigned char *key, ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); return 0; } +#ifdef FIPS_MODULE + /* + * Only do the key check if KMAC is fetched directly. + * Other algorithms that embed KMAC such as SSKDF will ignore this check. + */ + if (!kctx->internal) { + int approved = ossl_mac_check_key_size(keylen); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(kctx, OSSL_FIPS_IND_SETTABLE1, + PROV_LIBCTX_OF(kctx->provctx), + "KMAC", "Key size", + ossl_fips_config_kmac_key_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + } +#endif if (w <= 0) { ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); return 0; @@ -353,6 +392,7 @@ static int kmac_final(void *vmacctx, unsigned char *out, size_t *outl, static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_MAC_PARAM_SIZE, NULL), OSSL_PARAM_size_t(OSSL_MAC_PARAM_BLOCK_SIZE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; static const OSSL_PARAM *kmac_gettable_ctx_params(ossl_unused void *ctx, @@ -377,6 +417,9 @@ static int kmac_get_ctx_params(void *vmacctx, OSSL_PARAM params[]) return 0; } + if (!OSSL_FIPS_IND_GET_CTX_PARAM(kctx, params)) + return 0; + return 1; } @@ -385,6 +428,8 @@ static const OSSL_PARAM known_settable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_MAC_PARAM_SIZE, NULL), OSSL_PARAM_octet_string(OSSL_MAC_PARAM_KEY, NULL, 0), OSSL_PARAM_octet_string(OSSL_MAC_PARAM_CUSTOM, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_MAC_PARAM_FIPS_NO_SHORT_MAC) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_MAC_PARAM_FIPS_KEY_CHECK) OSSL_PARAM_END }; static const OSSL_PARAM *kmac_settable_ctx_params(ossl_unused void *ctx, @@ -410,6 +455,13 @@ static int kmac_set_ctx_params(void *vmacctx, const OSSL_PARAM *params) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(kctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_MAC_PARAM_FIPS_NO_SHORT_MAC)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(kctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_MAC_PARAM_FIPS_KEY_CHECK)) + return 0; + if ((p = OSSL_PARAM_locate_const(params, OSSL_MAC_PARAM_XOF)) != NULL && !OSSL_PARAM_get_int(p, &kctx->xof_mode)) return 0; @@ -422,6 +474,18 @@ static int kmac_set_ctx_params(void *vmacctx, const OSSL_PARAM *params) ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_OUTPUT_LENGTH); return 0; } +#ifdef FIPS_MODULE + /* SP 800-185 8.4.2 mandates a minimum of 32 bits of output */ + if (sz < 32 / 8) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(kctx, OSSL_FIPS_IND_SETTABLE0, + PROV_LIBCTX_OF(kctx->provctx), + "KMAC", "length", + ossl_fips_config_no_short_mac)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_OUTPUT_LENGTH); + return 0; + } + } +#endif kctx->out_len = sz; } if ((p = OSSL_PARAM_locate_const(params, OSSL_MAC_PARAM_KEY)) != NULL @@ -592,34 +656,42 @@ static int kmac_bytepad_encode_key(unsigned char *out, size_t out_max_len, return bytepad(out, NULL, tmp, tmp_len, NULL, 0, w); } -const OSSL_DISPATCH ossl_kmac128_functions[] = { - { OSSL_FUNC_MAC_NEWCTX, (void (*)(void))kmac128_new }, - { OSSL_FUNC_MAC_DUPCTX, (void (*)(void))kmac_dup }, - { OSSL_FUNC_MAC_FREECTX, (void (*)(void))kmac_free }, - { OSSL_FUNC_MAC_INIT, (void (*)(void))kmac_init }, - { OSSL_FUNC_MAC_UPDATE, (void (*)(void))kmac_update }, - { OSSL_FUNC_MAC_FINAL, (void (*)(void))kmac_final }, - { OSSL_FUNC_MAC_GETTABLE_CTX_PARAMS, - (void (*)(void))kmac_gettable_ctx_params }, - { OSSL_FUNC_MAC_GET_CTX_PARAMS, (void (*)(void))kmac_get_ctx_params }, - { OSSL_FUNC_MAC_SETTABLE_CTX_PARAMS, - (void (*)(void))kmac_settable_ctx_params }, - { OSSL_FUNC_MAC_SET_CTX_PARAMS, (void (*)(void))kmac_set_ctx_params }, - OSSL_DISPATCH_END -}; +#define IMPLEMENT_KMAC_TABLE(size, funcname, newname) \ +const OSSL_DISPATCH ossl_kmac##size##_##funcname[] = \ +{ \ + { OSSL_FUNC_MAC_NEWCTX, (void (*)(void))kmac##size##_##newname }, \ + { OSSL_FUNC_MAC_DUPCTX, (void (*)(void))kmac_dup }, \ + { OSSL_FUNC_MAC_FREECTX, (void (*)(void))kmac_free }, \ + { OSSL_FUNC_MAC_INIT, (void (*)(void))kmac_init }, \ + { OSSL_FUNC_MAC_UPDATE, (void (*)(void))kmac_update }, \ + { OSSL_FUNC_MAC_FINAL, (void (*)(void))kmac_final }, \ + { OSSL_FUNC_MAC_GETTABLE_CTX_PARAMS, \ + (void (*)(void))kmac_gettable_ctx_params }, \ + { OSSL_FUNC_MAC_GET_CTX_PARAMS, (void (*)(void))kmac_get_ctx_params }, \ + { OSSL_FUNC_MAC_SETTABLE_CTX_PARAMS, \ + (void (*)(void))kmac_settable_ctx_params }, \ + { OSSL_FUNC_MAC_SET_CTX_PARAMS, (void (*)(void))kmac_set_ctx_params }, \ + OSSL_DISPATCH_END \ +} -const OSSL_DISPATCH ossl_kmac256_functions[] = { - { OSSL_FUNC_MAC_NEWCTX, (void (*)(void))kmac256_new }, - { OSSL_FUNC_MAC_DUPCTX, (void (*)(void))kmac_dup }, - { OSSL_FUNC_MAC_FREECTX, (void (*)(void))kmac_free }, - { OSSL_FUNC_MAC_INIT, (void (*)(void))kmac_init }, - { OSSL_FUNC_MAC_UPDATE, (void (*)(void))kmac_update }, - { OSSL_FUNC_MAC_FINAL, (void (*)(void))kmac_final }, - { OSSL_FUNC_MAC_GETTABLE_CTX_PARAMS, - (void (*)(void))kmac_gettable_ctx_params }, - { OSSL_FUNC_MAC_GET_CTX_PARAMS, (void (*)(void))kmac_get_ctx_params }, - { OSSL_FUNC_MAC_SETTABLE_CTX_PARAMS, - (void (*)(void))kmac_settable_ctx_params }, - { OSSL_FUNC_MAC_SET_CTX_PARAMS, (void (*)(void))kmac_set_ctx_params }, - OSSL_DISPATCH_END -}; +#define KMAC_TABLE(size) IMPLEMENT_KMAC_TABLE(size, functions, new) + +KMAC_TABLE(128); +KMAC_TABLE(256); + +#ifdef FIPS_MODULE +# define KMAC_INTERNAL_TABLE(size) \ +static OSSL_FUNC_mac_newctx_fn kmac##size##_internal_new; \ +static void *kmac##size##_internal_new(void *provctx) \ +{ \ + struct kmac_data_st *macctx = kmac##size##_new(provctx); \ + \ + if (macctx != NULL) \ + macctx->internal = 1; \ + return macctx; \ +} \ +IMPLEMENT_KMAC_TABLE(size, internal_functions, internal_new) + +KMAC_INTERNAL_TABLE(128); +KMAC_INTERNAL_TABLE(256); +#endif /* FIPS_MODULE */ diff --git a/providers/implementations/rands/build.info b/providers/implementations/rands/build.info index 8bcac43be7..8e0894faa6 100644 --- a/providers/implementations/rands/build.info +++ b/providers/implementations/rands/build.info @@ -2,5 +2,6 @@ SUBDIRS=seeding $RANDS_GOAL=../../libdefault.a ../../libfips.a -SOURCE[$RANDS_GOAL]=drbg.c test_rng.c drbg_ctr.c drbg_hash.c drbg_hmac.c crngt.c -SOURCE[../../libdefault.a]=seed_src.c +SOURCE[$RANDS_GOAL]=drbg.c test_rng.c drbg_ctr.c drbg_hash.c drbg_hmac.c +SOURCE[../../libdefault.a]=seed_src.c seed_src_jitter.c +SOURCE[../../libfips.a]=fips_crng_test.c diff --git a/providers/implementations/rands/crngt.c b/providers/implementations/rands/crngt.c deleted file mode 100644 index fa4a2db14a..0000000000 --- a/providers/implementations/rands/crngt.c +++ /dev/null @@ -1,192 +0,0 @@ -/* - * Copyright 2019-2022 The OpenSSL Project Authors. All Rights Reserved. - * Copyright (c) 2019, Oracle and/or its affiliates. All rights reserved. - * - * Licensed under the Apache License 2.0 (the "License"). You may not use - * this file except in compliance with the License. You can obtain a copy - * in the file LICENSE in the source distribution or at - * https://www.openssl.org/source/license.html - */ - -/* - * Implementation of the FIPS 140-2 section 4.9.2 Conditional Tests. - */ - -#include -#include -#include -#include -#include -#include "prov/providercommon.h" -#include "prov/provider_ctx.h" -#include "internal/cryptlib.h" -#include "crypto/rand_pool.h" -#include "drbg_local.h" -#include "prov/seeding.h" -#include "crypto/context.h" - -typedef struct crng_test_global_st { - unsigned char crngt_prev[EVP_MAX_MD_SIZE]; - EVP_MD *md; - int preloaded; - CRYPTO_RWLOCK *lock; -} CRNG_TEST_GLOBAL; - -static int crngt_get_entropy(PROV_CTX *provctx, const EVP_MD *digest, - unsigned char *buf, unsigned char *md, - unsigned int *md_size) -{ - int r; - size_t n; - unsigned char *p; - - n = ossl_prov_get_entropy(provctx, &p, 0, CRNGT_BUFSIZ, CRNGT_BUFSIZ); - if (n == CRNGT_BUFSIZ) { - r = EVP_Digest(p, CRNGT_BUFSIZ, md, md_size, digest, NULL); - if (r != 0) - memcpy(buf, p, CRNGT_BUFSIZ); - ossl_prov_cleanup_entropy(provctx, p, n); - return r != 0; - } - if (n != 0) - ossl_prov_cleanup_entropy(provctx, p, n); - return 0; -} - -void ossl_rand_crng_ctx_free(void *vcrngt_glob) -{ - CRNG_TEST_GLOBAL *crngt_glob = vcrngt_glob; - - CRYPTO_THREAD_lock_free(crngt_glob->lock); - EVP_MD_free(crngt_glob->md); - OPENSSL_free(crngt_glob); -} - -void *ossl_rand_crng_ctx_new(OSSL_LIB_CTX *ctx) -{ - CRNG_TEST_GLOBAL *crngt_glob = OPENSSL_zalloc(sizeof(*crngt_glob)); - - if (crngt_glob == NULL) - return NULL; - - if ((crngt_glob->md = EVP_MD_fetch(ctx, "SHA256", "")) == NULL) { - OPENSSL_free(crngt_glob); - return NULL; - } - - if ((crngt_glob->lock = CRYPTO_THREAD_lock_new()) == NULL) { - EVP_MD_free(crngt_glob->md); - OPENSSL_free(crngt_glob); - return NULL; - } - - return crngt_glob; -} - -static int prov_crngt_compare_previous(const unsigned char *prev, - const unsigned char *cur, - size_t sz) -{ - const int res = memcmp(prev, cur, sz) != 0; - - if (!res) - ossl_set_error_state(OSSL_SELF_TEST_TYPE_CRNG); - return res; -} - -size_t ossl_crngt_get_entropy(PROV_DRBG *drbg, - unsigned char **pout, - int entropy, size_t min_len, size_t max_len, - int prediction_resistance) -{ - unsigned char md[EVP_MAX_MD_SIZE]; - unsigned char buf[CRNGT_BUFSIZ]; - unsigned char *ent, *entp, *entbuf; - unsigned int sz; - size_t bytes_needed; - size_t r = 0, s, t; - int crng_test_pass = 1; - OSSL_LIB_CTX *libctx = ossl_prov_ctx_get0_libctx(drbg->provctx); - CRNG_TEST_GLOBAL *crngt_glob - = ossl_lib_ctx_get_data(libctx, OSSL_LIB_CTX_RAND_CRNGT_INDEX); - OSSL_CALLBACK *stcb = NULL; - void *stcbarg = NULL; - OSSL_SELF_TEST *st = NULL; - - if (crngt_glob == NULL) - return 0; - - if (!CRYPTO_THREAD_write_lock(crngt_glob->lock)) - return 0; - - if (!crngt_glob->preloaded) { - if (!crngt_get_entropy(drbg->provctx, crngt_glob->md, buf, - crngt_glob->crngt_prev, NULL)) { - OPENSSL_cleanse(buf, sizeof(buf)); - goto unlock_return; - } - crngt_glob->preloaded = 1; - } - - /* - * Calculate how many bytes of seed material we require, rounded up - * to the nearest byte. If the entropy is of less than full quality, - * the amount required should be scaled up appropriately here. - */ - bytes_needed = (entropy + 7) / 8; - if (bytes_needed < min_len) - bytes_needed = min_len; - if (bytes_needed > max_len) - goto unlock_return; - entp = ent = OPENSSL_secure_malloc(bytes_needed); - if (ent == NULL) - goto unlock_return; - - OSSL_SELF_TEST_get_callback(libctx, &stcb, &stcbarg); - if (stcb != NULL) { - st = OSSL_SELF_TEST_new(stcb, stcbarg); - if (st == NULL) - goto err; - OSSL_SELF_TEST_onbegin(st, OSSL_SELF_TEST_TYPE_CRNG, - OSSL_SELF_TEST_DESC_RNG); - } - - for (t = bytes_needed; t > 0;) { - /* Care needs to be taken to avoid overrunning the buffer */ - s = t >= CRNGT_BUFSIZ ? CRNGT_BUFSIZ : t; - entbuf = t >= CRNGT_BUFSIZ ? entp : buf; - if (!crngt_get_entropy(drbg->provctx, crngt_glob->md, entbuf, md, &sz)) - goto err; - if (t < CRNGT_BUFSIZ) - memcpy(entp, buf, t); - /* Force a failure here if the callback returns 1 */ - if (OSSL_SELF_TEST_oncorrupt_byte(st, md)) - memcpy(md, crngt_glob->crngt_prev, sz); - if (!prov_crngt_compare_previous(crngt_glob->crngt_prev, md, sz)) { - crng_test_pass = 0; - goto err; - } - /* Update for next block */ - memcpy(crngt_glob->crngt_prev, md, sz); - entp += s; - t -= s; - } - r = bytes_needed; - *pout = ent; - ent = NULL; - - err: - OSSL_SELF_TEST_onend(st, crng_test_pass); - OSSL_SELF_TEST_free(st); - OPENSSL_secure_clear_free(ent, bytes_needed); - - unlock_return: - CRYPTO_THREAD_unlock(crngt_glob->lock); - return r; -} - -void ossl_crngt_cleanup_entropy(ossl_unused PROV_DRBG *drbg, - unsigned char *out, size_t outlen) -{ - OPENSSL_secure_clear_free(out, outlen); -} diff --git a/providers/implementations/rands/drbg.c b/providers/implementations/rands/drbg.c index 4d48a48449..f9aa5e2fae 100644 --- a/providers/implementations/rands/drbg.c +++ b/providers/implementations/rands/drbg.c @@ -21,7 +21,6 @@ #include "crypto/rand_pool.h" #include "prov/provider_ctx.h" #include "prov/providercommon.h" -#include "prov/fipscommon.h" #include "crypto/context.h" /* @@ -31,7 +30,7 @@ * * The OpenSSL model is to have new and free functions, and that new * does all initialization. That is not the NIST model, which has - * instantiation and un-instantiate, and re-use within a new/free + * instantiation and un-instantiate, and reuse within a new/free * lifecycle. (No doubt this comes from the desire to support hardware * DRBG, where allocation of resources on something like an HSM is * a much bigger deal than just re-setting an allocated resource.) @@ -198,18 +197,12 @@ static size_t get_entropy(PROV_DRBG *drbg, unsigned char **pout, int entropy, unsigned int p_str; if (drbg->parent == NULL) -#ifdef FIPS_MODULE - return ossl_crngt_get_entropy(drbg, pout, entropy, min_len, max_len, - prediction_resistance); -#else /* * In normal use (i.e. OpenSSL's own uses), this is never called. - * Outside of the FIPS provider, OpenSSL sets its DRBGs up so that - * they always have a parent. This remains purely for legacy reasons. + * This remains purely for legacy reasons. */ return ossl_prov_get_entropy(drbg->provctx, pout, entropy, min_len, max_len); -#endif if (drbg->parent_get_seed == NULL) { ERR_raise(ERR_LIB_PROV, PROV_R_PARENT_CANNOT_SUPPLY_ENTROPY_SEED); @@ -252,11 +245,7 @@ static size_t get_entropy(PROV_DRBG *drbg, unsigned char **pout, int entropy, static void cleanup_entropy(PROV_DRBG *drbg, unsigned char *out, size_t outlen) { if (drbg->parent == NULL) { -#ifdef FIPS_MODULE - ossl_crngt_cleanup_entropy(drbg, out, outlen); -#else ossl_prov_cleanup_entropy(drbg->provctx, out, outlen); -#endif } else if (drbg->parent_clear_seed != NULL) { if (!ossl_drbg_lock_parent(drbg)) return; @@ -428,7 +417,7 @@ int ossl_prov_drbg_instantiate(PROV_DRBG *drbg, unsigned int strength, } #ifndef PROV_RAND_GET_RANDOM_NONCE else { /* parent == NULL */ - noncelen = prov_drbg_get_nonce(drbg, &nonce, drbg->min_noncelen, + noncelen = prov_drbg_get_nonce(drbg, &nonce, drbg->min_noncelen, drbg->max_noncelen); if (noncelen < drbg->min_noncelen || noncelen > drbg->max_noncelen) { @@ -935,7 +924,8 @@ int ossl_drbg_get_ctx_params(PROV_DRBG *drbg, OSSL_PARAM params[]) p = OSSL_PARAM_locate(params, OSSL_DRBG_PARAM_RESEED_TIME_INTERVAL); if (p != NULL && !OSSL_PARAM_set_time_t(p, drbg->reseed_time_interval)) return 0; - + if (!OSSL_FIPS_IND_GET_CTX_PARAM(drbg, params)) + return 0; return 1; } @@ -990,13 +980,13 @@ int ossl_drbg_set_ctx_params(PROV_DRBG *drbg, const OSSL_PARAM params[]) p = OSSL_PARAM_locate_const(params, OSSL_DRBG_PARAM_RESEED_TIME_INTERVAL); if (p != NULL && !OSSL_PARAM_get_time_t(p, &drbg->reseed_time_interval)) return 0; + return 1; } -/* Confirm digest is allowed to be used with a DRBG */ -int ossl_drbg_verify_digest(ossl_unused OSSL_LIB_CTX *libctx, const EVP_MD *md) -{ #ifdef FIPS_MODULE +static int digest_allowed(const EVP_MD *md) +{ /* FIPS 140-3 IG D.R limited DRBG digests to a specific set */ static const char *const allowed_digests[] = { "SHA1", /* SHA 1 allowed */ @@ -1005,18 +995,35 @@ int ossl_drbg_verify_digest(ossl_unused OSSL_LIB_CTX *libctx, const EVP_MD *md) }; size_t i; - if (FIPS_restricted_drbg_digests_enabled(libctx)) { - for (i = 0; i < OSSL_NELEM(allowed_digests); i++) - if (EVP_MD_is_a(md, allowed_digests[i])) - return 1; - ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); - return 0; + for (i = 0; i < OSSL_NELEM(allowed_digests); i++) { + if (EVP_MD_is_a(md, allowed_digests[i])) + return 1; } + return 0; +} #endif + +/* Confirm digest is allowed to be used with a DRBG */ +int ossl_drbg_verify_digest(PROV_DRBG *drbg, OSSL_LIB_CTX *libctx, + const EVP_MD *md) +{ +#ifdef FIPS_MODULE + int approved = digest_allowed(md); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(drbg, OSSL_FIPS_IND_SETTABLE0, + libctx, "DRBG", "Digest", + ossl_fips_config_restricted_drbg_digests)) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); + return 0; + } + } +#else /* FIPS_MODULE */ /* Outside of FIPS, any digests that are not XOF are allowed */ - if ((EVP_MD_get_flags(md) & EVP_MD_FLAG_XOF) != 0) { + if (EVP_MD_xof(md)) { ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); return 0; } +#endif /* FIPS_MODULE */ return 1; } diff --git a/providers/implementations/rands/drbg_ctr.c b/providers/implementations/rands/drbg_ctr.c index 0c4553ad58..abd0b1a1c8 100644 --- a/providers/implementations/rands/drbg_ctr.c +++ b/providers/implementations/rands/drbg_ctr.c @@ -625,6 +625,7 @@ static int drbg_ctr_new(PROV_DRBG *drbg) ctr->use_df = 1; drbg->data = ctr; + OSSL_FIPS_IND_INIT(drbg) return drbg_ctr_init_lengths(drbg); } @@ -697,6 +698,7 @@ static const OSSL_PARAM *drbg_ctr_gettable_ctx_params(ossl_unused void *vctx, OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_CIPHER, NULL, 0), OSSL_PARAM_int(OSSL_DRBG_PARAM_USE_DF, NULL), OSSL_PARAM_DRBG_GETTABLE_CTX_COMMON, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; diff --git a/providers/implementations/rands/drbg_hash.c b/providers/implementations/rands/drbg_hash.c index b9854a9aa9..458b356b82 100644 --- a/providers/implementations/rands/drbg_hash.c +++ b/providers/implementations/rands/drbg_hash.c @@ -424,6 +424,8 @@ static int drbg_hash_new(PROV_DRBG *ctx) if (hash == NULL) return 0; + OSSL_FIPS_IND_INIT(ctx) + ctx->data = hash; ctx->seedlen = HASH_PRNG_MAX_SEEDLEN; ctx->max_entropylen = DRBG_MAX_LENGTH; @@ -496,6 +498,7 @@ static const OSSL_PARAM *drbg_hash_gettable_ctx_params(ossl_unused void *vctx, static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_DIGEST, NULL, 0), OSSL_PARAM_DRBG_GETTABLE_CTX_COMMON, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -507,17 +510,25 @@ static int drbg_hash_set_ctx_params_locked(void *vctx, const OSSL_PARAM params[] PROV_DRBG_HASH *hash = (PROV_DRBG_HASH *)ctx->data; OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); const EVP_MD *md; + int md_size; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_DRBG_PARAM_FIPS_DIGEST_CHECK)) + return 0; if (!ossl_prov_digest_load_from_params(&hash->digest, params, libctx)) return 0; md = ossl_prov_digest_md(&hash->digest); if (md != NULL) { - if (!ossl_drbg_verify_digest(libctx, md)) + if (!ossl_drbg_verify_digest(ctx, libctx, md)) return 0; /* Error already raised for us */ /* These are taken from SP 800-90 10.1 Table 2 */ - hash->blocklen = EVP_MD_get_size(md); + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + return 0; + hash->blocklen = md_size; /* See SP800-57 Part1 Rev4 5.6.1 Table 3 */ ctx->strength = 64 * (hash->blocklen >> 3); if (ctx->strength > 256) @@ -557,6 +568,7 @@ static const OSSL_PARAM *drbg_hash_settable_ctx_params(ossl_unused void *vctx, OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_PROPERTIES, NULL, 0), OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_DIGEST, NULL, 0), OSSL_PARAM_DRBG_SETTABLE_CTX_COMMON, + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_DRBG_PARAM_FIPS_DIGEST_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; diff --git a/providers/implementations/rands/drbg_hmac.c b/providers/implementations/rands/drbg_hmac.c index 03b43a3c39..43c75bf434 100644 --- a/providers/implementations/rands/drbg_hmac.c +++ b/providers/implementations/rands/drbg_hmac.c @@ -316,6 +316,8 @@ static int drbg_hmac_new(PROV_DRBG *drbg) if (hmac == NULL) return 0; + OSSL_FIPS_IND_INIT(drbg) + drbg->data = hmac; /* See SP800-57 Part1 Rev4 5.6.1 Table 3 */ drbg->max_entropylen = DRBG_MAX_LENGTH; @@ -399,6 +401,7 @@ static const OSSL_PARAM *drbg_hmac_gettable_ctx_params(ossl_unused void *vctx, OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_MAC, NULL, 0), OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_DIGEST, NULL, 0), OSSL_PARAM_DRBG_GETTABLE_CTX_COMMON, + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; @@ -410,12 +413,17 @@ static int drbg_hmac_set_ctx_params_locked(void *vctx, const OSSL_PARAM params[] PROV_DRBG_HMAC *hmac = (PROV_DRBG_HMAC *)ctx->data; OSSL_LIB_CTX *libctx = PROV_LIBCTX_OF(ctx->provctx); const EVP_MD *md; + int md_size; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_DRBG_PARAM_FIPS_DIGEST_CHECK)) + return 0; if (!ossl_prov_digest_load_from_params(&hmac->digest, params, libctx)) return 0; md = ossl_prov_digest_md(&hmac->digest); - if (md != NULL && !ossl_drbg_verify_digest(libctx, md)) + if (md != NULL && !ossl_drbg_verify_digest(ctx, libctx, md)) return 0; /* Error already raised for us */ if (!ossl_prov_macctx_load_from_params(&hmac->ctx, params, @@ -424,7 +432,10 @@ static int drbg_hmac_set_ctx_params_locked(void *vctx, const OSSL_PARAM params[] if (md != NULL && hmac->ctx != NULL) { /* These are taken from SP 800-90 10.1 Table 2 */ - hmac->blocklen = EVP_MD_get_size(md); + md_size = EVP_MD_get_size(md); + if (md_size <= 0) + return 0; + hmac->blocklen = (size_t)md_size; /* See SP800-57 Part1 Rev4 5.6.1 Table 3 */ ctx->strength = 64 * (int)(hmac->blocklen >> 3); if (ctx->strength > 256) @@ -461,6 +472,7 @@ static const OSSL_PARAM *drbg_hmac_settable_ctx_params(ossl_unused void *vctx, OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_DRBG_PARAM_MAC, NULL, 0), OSSL_PARAM_DRBG_SETTABLE_CTX_COMMON, + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_DRBG_PARAM_FIPS_DIGEST_CHECK) OSSL_PARAM_END }; return known_settable_ctx_params; diff --git a/providers/implementations/rands/drbg_local.h b/providers/implementations/rands/drbg_local.h index 902dfc937d..e591e0b3d1 100644 --- a/providers/implementations/rands/drbg_local.h +++ b/providers/implementations/rands/drbg_local.h @@ -18,6 +18,7 @@ # include "internal/nelem.h" # include "internal/numbers.h" # include "prov/provider_ctx.h" +# include "prov/securitycheck.h" /* How many times to read the TSC as a randomness source. */ # define TSC_READ_COUNT 4 @@ -69,7 +70,7 @@ struct prov_drbg_st { CRYPTO_RWLOCK *lock; PROV_CTX *provctx; - /* Virtual functions are cache here */ + /* Virtual functions are cached here */ int (*instantiate)(PROV_DRBG *drbg, const unsigned char *entropy, size_t entropylen, const unsigned char *nonce, size_t noncelen, @@ -90,8 +91,6 @@ struct prov_drbg_st { OSSL_FUNC_rand_get_seed_fn *parent_get_seed; OSSL_FUNC_rand_clear_seed_fn *parent_clear_seed; - const OSSL_DISPATCH *parent_dispatch; - /* * Stores the return value of openssl_get_fork_id() as of when we last * reseeded. The DRBG reseeds automatically whenever drbg->fork_id != @@ -171,6 +170,8 @@ struct prov_drbg_st { OSSL_CALLBACK *cleanup_entropy_fn; OSSL_INOUT_CALLBACK *get_nonce_fn; OSSL_CALLBACK *cleanup_nonce_fn; + + OSSL_FIPS_IND_DECLARE }; PROV_DRBG *ossl_rand_drbg_new @@ -255,6 +256,6 @@ void ossl_crngt_cleanup_entropy(PROV_DRBG *drbg, unsigned char *out, size_t outlen); /* Confirm digest is allowed to be used with a DRBG */ -int ossl_drbg_verify_digest(ossl_unused OSSL_LIB_CTX *libctx, const EVP_MD *md); +int ossl_drbg_verify_digest(PROV_DRBG *drbg, OSSL_LIB_CTX *libctx, const EVP_MD *md); #endif diff --git a/providers/implementations/rands/fips_crng_test.c b/providers/implementations/rands/fips_crng_test.c new file mode 100644 index 0000000000..209a1adb27 --- /dev/null +++ b/providers/implementations/rands/fips_crng_test.c @@ -0,0 +1,428 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +/* + * Implementation of SP 800-90B section 4.4 Approved Continuous Health Tests. + */ + +#include +#include +#include +#include +#include +#include +#include "prov/providercommon.h" +#include "prov/provider_ctx.h" +#include "prov/implementations.h" +#include "internal/cryptlib.h" +#include "crypto/rand_pool.h" +#include "drbg_local.h" +#include "prov/seeding.h" +#include "crypto/context.h" + +static OSSL_FUNC_rand_newctx_fn crng_test_new; +static OSSL_FUNC_rand_freectx_fn crng_test_free; +static OSSL_FUNC_rand_instantiate_fn crng_test_instantiate; +static OSSL_FUNC_rand_uninstantiate_fn crng_test_uninstantiate; +static OSSL_FUNC_rand_generate_fn crng_test_generate; +static OSSL_FUNC_rand_reseed_fn crng_test_reseed; +static OSSL_FUNC_rand_gettable_ctx_params_fn crng_test_gettable_ctx_params; +static OSSL_FUNC_rand_get_ctx_params_fn crng_test_get_ctx_params; +static OSSL_FUNC_rand_verify_zeroization_fn crng_test_verify_zeroization; +static OSSL_FUNC_rand_enable_locking_fn crng_test_enable_locking; +static OSSL_FUNC_rand_lock_fn crng_test_lock; +static OSSL_FUNC_rand_unlock_fn crng_test_unlock; +static OSSL_FUNC_rand_get_seed_fn crng_test_get_seed; +static OSSL_FUNC_rand_clear_seed_fn crng_test_clear_seed; + +#ifndef ENTROPY_H +# define ENTROPY_H 6 /* default to six bits per byte of entropy */ +#endif +#ifndef ENTROPY_APT_W +# define ENTROPY_APT_W 512 +#endif + +typedef struct crng_testal_st { + void *provctx; + CRYPTO_RWLOCK *lock; + int state; + + /* State for SP 800-90B 4.4.1 Repetition Count Test */ + struct { + unsigned int b; + uint8_t a; + } rct; + + /* State for SP 800-90B 4.4.2 Adaptive Proportion Test */ + struct { + unsigned int b; + unsigned int i; + uint8_t a; + } apt; + + /* Parent PROV_RAND and its dispatch table functions */ + void *parent; + OSSL_FUNC_rand_enable_locking_fn *parent_enable_locking; + OSSL_FUNC_rand_lock_fn *parent_lock; + OSSL_FUNC_rand_unlock_fn *parent_unlock; + OSSL_FUNC_rand_get_ctx_params_fn *parent_get_ctx_params; + OSSL_FUNC_rand_gettable_ctx_params_fn *parent_gettable_ctx_params; + OSSL_FUNC_rand_get_seed_fn *parent_get_seed; + OSSL_FUNC_rand_clear_seed_fn *parent_clear_seed; +} CRNG_TEST; + +/* + * Some helper functions + */ +static int lock_parent(CRNG_TEST *crngt) +{ + void *parent = crngt->parent; + + if (parent != NULL + && crngt->parent_lock != NULL + && !crngt->parent_lock(parent)) { + ERR_raise(ERR_LIB_PROV, PROV_R_PARENT_LOCKING_NOT_ENABLED); + return 0; + } + return 1; +} + +static void unlock_parent(CRNG_TEST *crngt) +{ + void *parent = crngt->parent; + + if (parent != NULL && crngt->parent_unlock != NULL) + crngt->parent_unlock(parent); +} + +/* + * Implementation of SP 800-90B section 4.4.1: Repetition Count Test + */ +static int RCT_test(CRNG_TEST *crngt, uint8_t next) +{ + /* + * Critical values for this test are computed using: + * + * C = 1 + \left\lceil\frac{-log_2 \alpha}H\right\rceil + * + * where alpha = 2^-20 and H is the expected entropy per sample. + */ + static const unsigned int rct_c[9] = { + 41, /* H = 0.5 */ + 21, 11, 8, 6, 5, 5, 4, 4 /* H = 1, ..., 8 */ + }; + + if (ossl_likely(crngt->rct.b != 0) + && ossl_unlikely(next == crngt->rct.a)) + return ossl_likely(++crngt->rct.b < rct_c[ENTROPY_H]); + crngt->rct.a = next; + crngt->rct.b = 1; + return 1; +} + +/* + * Implementation of SP 800-90B section 4.4.2: Adaptive Proportion Test + */ +static int APT_test(CRNG_TEST *crngt, uint8_t next) +{ + /* + * Critical values for this test are drawn from a binomial + * distribution with n = 512, p = 2^-H at a critical threshold of + * 2^-20. H being the expected entropy per sample. Refer SP 800-90B + * section 4.4.2, table 2. + */ + static const unsigned int apt_c[9] = { + 410, /* H = 0.5 */ + 311, 177, 103, 62, 39, 25, 18, 13 /* H = 1, ..., 8 */ + }; + + if (ossl_likely(crngt->apt.b != 0)) { + if (ossl_unlikely(crngt->apt.a == next) + && ossl_unlikely(++crngt->apt.b >= apt_c[ENTROPY_H])) { + crngt->apt.b = 0; + return 0; + } + if (ossl_unlikely(++crngt->apt.i >= ENTROPY_APT_W)) + crngt->apt.b = 0; + return 1; + } + crngt->apt.a = next; + crngt->apt.b = 1; + crngt->apt.i = 1; + return 1; +} + +static int crng_test(CRNG_TEST *crngt, const unsigned char *buf, size_t n) +{ + size_t i; + + for (i = 0; i < n; i++) + if (!RCT_test(crngt, buf[i]) || !APT_test(crngt, buf[i])) { + crngt->state = EVP_RAND_STATE_ERROR; + ERR_raise(ERR_LIB_PROV, + PROV_R_ENTROPY_SOURCE_FAILED_CONTINUOUS_TESTS); + return 0; + } + return 1; +} + +static const OSSL_DISPATCH *find_call(const OSSL_DISPATCH *dispatch, + int function) +{ + if (dispatch != NULL) + while (dispatch->function_id != 0) { + if (dispatch->function_id == function) + return dispatch; + dispatch++; + } + return NULL; +} + +static void *crng_test_new(void *provctx, void *parent, + const OSSL_DISPATCH *p_dispatch) +{ + CRNG_TEST *crngt = OPENSSL_zalloc(sizeof(*crngt)); + const OSSL_DISPATCH *pfunc; + + if (crngt == NULL) + return NULL; + + crngt->provctx = provctx; + crngt->state = EVP_RAND_STATE_UNINITIALISED; + + /* Extract parent's functions */ + if (parent != NULL) { + crngt->parent = parent; + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_ENABLE_LOCKING)) != NULL) + crngt->parent_enable_locking = OSSL_FUNC_rand_enable_locking(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_LOCK)) != NULL) + crngt->parent_lock = OSSL_FUNC_rand_lock(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_UNLOCK)) != NULL) + crngt->parent_unlock = OSSL_FUNC_rand_unlock(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_GETTABLE_CTX_PARAMS)) != NULL) + crngt->parent_gettable_ctx_params = OSSL_FUNC_rand_gettable_ctx_params(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_GET_CTX_PARAMS)) != NULL) + crngt->parent_get_ctx_params = OSSL_FUNC_rand_get_ctx_params(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_GET_SEED)) != NULL) + crngt->parent_get_seed = OSSL_FUNC_rand_get_seed(pfunc); + if ((pfunc = find_call(p_dispatch, OSSL_FUNC_RAND_CLEAR_SEED)) != NULL) + crngt->parent_clear_seed = OSSL_FUNC_rand_clear_seed(pfunc); + } + + return crngt; +} + +static void crng_test_free(void *vcrngt) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + if (crngt != NULL) { + CRYPTO_THREAD_lock_free(crngt->lock); + OPENSSL_free(crngt); + } +} + +static int crng_test_instantiate(void *vcrngt, unsigned int strength, + int prediction_resistance, + const unsigned char *pstr, + size_t pstr_len, + ossl_unused const OSSL_PARAM params[]) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + /* Start up health tests should go here */ + crngt->state = EVP_RAND_STATE_READY; + return 1; +} + +static int crng_test_uninstantiate(void *vcrngt) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + crngt->state = EVP_RAND_STATE_UNINITIALISED; + return 1; +} + +static int crng_test_generate(void *vcrngt, unsigned char *out, size_t outlen, + unsigned int strength, int prediction_resistance, + const unsigned char *adin, size_t adin_len) +{ + unsigned char *p; + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + if (!crng_test_get_seed(crngt, &p, 0, outlen, outlen, prediction_resistance, + adin, adin_len)) + return 0; + memcpy(out, p, outlen); + crng_test_clear_seed(crngt, p, outlen); + return 1; +} + +static int crng_test_reseed(ossl_unused void *vcrngt, + ossl_unused int prediction_resistance, + ossl_unused const unsigned char *ent, + ossl_unused size_t ent_len, + ossl_unused const unsigned char *adin, + ossl_unused size_t adin_len) +{ + return 1; +} + +static int crng_test_verify_zeroization(ossl_unused void *vcrngt) +{ + return 1; +} + +static size_t crng_test_get_seed(void *vcrngt, unsigned char **pout, + int entropy, size_t min_len, + size_t max_len, + int prediction_resistance, + const unsigned char *adin, + size_t adin_len) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + size_t n; + int r = 0; + + /* Without a parent, we rely on the up calls */ + if (crngt->parent == NULL + || crngt->parent_get_seed == NULL) { + n = ossl_prov_get_entropy(crngt->provctx, pout, entropy, + min_len, max_len); + if (n == 0) + return 0; + r = crng_test(crngt, *pout, n); + return r > 0 ? n : 0; + } + + /* Grab seed from our parent */ + if (!lock_parent(crngt)) + return 0; + + n = crngt->parent_get_seed(crngt->parent, pout, entropy, + min_len, max_len, prediction_resistance, + adin, adin_len); + if (n > 0 && crng_test(crngt, *pout, n) > 0) + r = n; + else if (crngt->parent_clear_seed != NULL) + crngt->parent_clear_seed(crngt->parent, *pout, n); + unlock_parent(crngt); + return r; +} + +static void crng_test_clear_seed(void *vcrngt, + unsigned char *out, size_t outlen) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + if (crngt->parent == NULL || crngt->parent_get_seed == NULL) + ossl_prov_cleanup_entropy(crngt->provctx, out, outlen); + else if (crngt->parent_clear_seed != NULL) + crngt->parent_clear_seed(crngt->parent, out, outlen); +} + +static int crng_test_enable_locking(void *vcrngt) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + if (crngt != NULL && crngt->lock == NULL) { + if (crngt->parent_enable_locking != NULL) + if (!crngt->parent_enable_locking(crngt->parent)) { + ERR_raise(ERR_LIB_PROV, PROV_R_PARENT_LOCKING_NOT_ENABLED); + return 0; + } + crngt->lock = CRYPTO_THREAD_lock_new(); + if (crngt->lock == NULL) { + ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_CREATE_LOCK); + return 0; + } + } + return 1; +} + +static int crng_test_lock(ossl_unused void *vcrngt) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + return crngt->lock == NULL || CRYPTO_THREAD_write_lock(crngt->lock); +} + +static void crng_test_unlock(ossl_unused void *vcrngt) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + + if (crngt->lock != NULL) + CRYPTO_THREAD_unlock(crngt->lock); +} + +static int crng_test_get_ctx_params(void *vcrngt, OSSL_PARAM params[]) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + OSSL_PARAM *p; + + if (crngt->parent != NULL && crngt->parent_get_ctx_params != NULL) + return crngt->parent_get_ctx_params(crngt->parent, params); + + /* No parent means we are using call backs for entropy */ + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_STATE); + if (p != NULL && !OSSL_PARAM_set_int(p, crngt->state)) + return 0; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_STRENGTH); + if (p != NULL && !OSSL_PARAM_set_int(p, 1024)) + return 0; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_MAX_REQUEST); + if (p != NULL && !OSSL_PARAM_set_size_t(p, 128)) + return 0; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_FIPS_APPROVED_INDICATOR); + if (p != NULL && !OSSL_PARAM_set_int(p, 0)) + return 0; + return 1; +} + +static const OSSL_PARAM *crng_test_gettable_ctx_params(void *vcrngt, + void *provctx) +{ + CRNG_TEST *crngt = (CRNG_TEST *)vcrngt; + static const OSSL_PARAM known_gettable_ctx_params[] = { + OSSL_PARAM_int(OSSL_RAND_PARAM_STATE, NULL), + OSSL_PARAM_uint(OSSL_RAND_PARAM_STRENGTH, NULL), + OSSL_PARAM_size_t(OSSL_RAND_PARAM_MAX_REQUEST, NULL), + OSSL_PARAM_int(OSSL_RAND_PARAM_FIPS_APPROVED_INDICATOR, NULL), + OSSL_PARAM_END + }; + + if (crngt->parent != NULL && crngt->parent_gettable_ctx_params != NULL) + return crngt->parent_gettable_ctx_params(crngt->parent, provctx); + return known_gettable_ctx_params; +} + +const OSSL_DISPATCH ossl_crng_test_functions[] = { + { OSSL_FUNC_RAND_NEWCTX, (void(*)(void))crng_test_new }, + { OSSL_FUNC_RAND_FREECTX, (void(*)(void))crng_test_free }, + { OSSL_FUNC_RAND_INSTANTIATE, + (void(*)(void))crng_test_instantiate }, + { OSSL_FUNC_RAND_UNINSTANTIATE, + (void(*)(void))crng_test_uninstantiate }, + { OSSL_FUNC_RAND_GENERATE, (void(*)(void))crng_test_generate }, + { OSSL_FUNC_RAND_RESEED, (void(*)(void))crng_test_reseed }, + { OSSL_FUNC_RAND_ENABLE_LOCKING, (void(*)(void))crng_test_enable_locking }, + { OSSL_FUNC_RAND_LOCK, (void(*)(void))crng_test_lock }, + { OSSL_FUNC_RAND_UNLOCK, (void(*)(void))crng_test_unlock }, + { OSSL_FUNC_RAND_GETTABLE_CTX_PARAMS, + (void(*)(void))crng_test_gettable_ctx_params }, + { OSSL_FUNC_RAND_GET_CTX_PARAMS, (void(*)(void))crng_test_get_ctx_params }, + { OSSL_FUNC_RAND_VERIFY_ZEROIZATION, + (void(*)(void))crng_test_verify_zeroization }, + { OSSL_FUNC_RAND_GET_SEED, (void(*)(void))crng_test_get_seed }, + { OSSL_FUNC_RAND_CLEAR_SEED, (void(*)(void))crng_test_clear_seed }, + OSSL_DISPATCH_END +}; diff --git a/providers/implementations/rands/seed_src_jitter.c b/providers/implementations/rands/seed_src_jitter.c new file mode 100644 index 0000000000..3dea0959d4 --- /dev/null +++ b/providers/implementations/rands/seed_src_jitter.c @@ -0,0 +1,336 @@ +/* + * Copyright 2024 The OpenSSL Project Authors. All Rights Reserved. + * + * Licensed under the Apache License 2.0 (the "License"). You may not use + * this file except in compliance with the License. You can obtain a copy + * in the file LICENSE in the source distribution or at + * https://www.openssl.org/source/license.html + */ + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include "prov/implementations.h" +#include "prov/provider_ctx.h" +#include "crypto/rand.h" +#include "crypto/rand_pool.h" + +#ifndef OPENSSL_NO_JITTER +# include + +# define JITTER_MAX_NUM_TRIES 3 + +static OSSL_FUNC_rand_newctx_fn jitter_new; +static OSSL_FUNC_rand_freectx_fn jitter_free; +static OSSL_FUNC_rand_instantiate_fn jitter_instantiate; +static OSSL_FUNC_rand_uninstantiate_fn jitter_uninstantiate; +static OSSL_FUNC_rand_generate_fn jitter_generate; +static OSSL_FUNC_rand_reseed_fn jitter_reseed; +static OSSL_FUNC_rand_gettable_ctx_params_fn jitter_gettable_ctx_params; +static OSSL_FUNC_rand_get_ctx_params_fn jitter_get_ctx_params; +static OSSL_FUNC_rand_verify_zeroization_fn jitter_verify_zeroization; +static OSSL_FUNC_rand_enable_locking_fn jitter_enable_locking; +static OSSL_FUNC_rand_lock_fn jitter_lock; +static OSSL_FUNC_rand_unlock_fn jitter_unlock; +static OSSL_FUNC_rand_get_seed_fn jitter_get_seed; +static OSSL_FUNC_rand_clear_seed_fn jitter_clear_seed; + +typedef struct { + void *provctx; + int state; +} PROV_JITTER; + +static size_t get_jitter_random_value(PROV_JITTER *s, unsigned char *buf, size_t len); + +/* + * Acquire entropy from jitterentropy library + * + * Returns the total entropy count, if it exceeds the requested + * entropy count. Otherwise, returns an entropy count of 0. + */ +static size_t ossl_prov_acquire_entropy_from_jitter(PROV_JITTER *s, + RAND_POOL *pool) +{ + size_t bytes_needed; + unsigned char *buffer; + + bytes_needed = ossl_rand_pool_bytes_needed(pool, 1 /* entropy_factor */); + if (bytes_needed > 0) { + buffer = ossl_rand_pool_add_begin(pool, bytes_needed); + + if (buffer != NULL) { + if (get_jitter_random_value(s, buffer, bytes_needed) == bytes_needed) { + ossl_rand_pool_add_end(pool, bytes_needed, 8 * bytes_needed); + } else { + ossl_rand_pool_add_end(pool, 0, 0); + } + } + } + + return ossl_rand_pool_entropy_available(pool); +} + +/* Obtain random bytes from the jitter library */ +static size_t get_jitter_random_value(PROV_JITTER *s, + unsigned char *buf, size_t len) +{ + struct rand_data *jitter_ec = NULL; + ssize_t result = 0; + size_t num_tries; + + /* Retry intermittent failures, then give up */ + for (num_tries = 0; num_tries < JITTER_MAX_NUM_TRIES; num_tries++) { + /* Allocate a fresh collector */ + jitter_ec = jent_entropy_collector_alloc(0, JENT_FORCE_FIPS); + if (jitter_ec == NULL) + continue; + + /* Do not use _safe API as per typical security policies */ + result = jent_read_entropy(jitter_ec, (char *) buf, len); + jent_entropy_collector_free(jitter_ec); + + /* + * Permanent Failure + * https://github.com/smuellerDD/jitterentropy-library/issues/118 + */ + if (result < -5) + break; + + /* Success */ + if (result == len) + return len; + } + + /* Permanent failure or too many intermittent failures */ + s->state = EVP_RAND_STATE_ERROR; + ERR_raise_data(ERR_LIB_RAND, RAND_R_ERROR_RETRIEVING_ENTROPY, + "jent_read_entropy (%d)", result); + return 0; +} + +static void *jitter_new(void *provctx, void *parent, + const OSSL_DISPATCH *parent_dispatch) +{ + PROV_JITTER *s; + + if (parent != NULL) { + ERR_raise(ERR_LIB_PROV, PROV_R_SEED_SOURCES_MUST_NOT_HAVE_A_PARENT); + return NULL; + } + + s = OPENSSL_zalloc(sizeof(*s)); + if (s == NULL) + return NULL; + + s->provctx = provctx; + s->state = EVP_RAND_STATE_UNINITIALISED; + return s; +} + +static void jitter_free(void *vseed) +{ + OPENSSL_free(vseed); +} + +static int jitter_instantiate(void *vseed, unsigned int strength, + int prediction_resistance, + const unsigned char *pstr, + size_t pstr_len, + ossl_unused const OSSL_PARAM params[]) +{ + PROV_JITTER *s = (PROV_JITTER *)vseed; + int ret; + + if ((ret = jent_entropy_init_ex(0, JENT_FORCE_FIPS)) != 0) { + ERR_raise_data(ERR_LIB_RAND, RAND_R_ERROR_RETRIEVING_ENTROPY, + "jent_entropy_init_ex (%d)", ret); + s->state = EVP_RAND_STATE_ERROR; + return 0; + } + + s->state = EVP_RAND_STATE_READY; + return 1; +} + +static int jitter_uninstantiate(void *vseed) +{ + PROV_JITTER *s = (PROV_JITTER *)vseed; + + s->state = EVP_RAND_STATE_UNINITIALISED; + return 1; +} + +static int jitter_generate(void *vseed, unsigned char *out, size_t outlen, + unsigned int strength, + ossl_unused int prediction_resistance, + ossl_unused const unsigned char *adin, + ossl_unused size_t adin_len) +{ + PROV_JITTER *s = (PROV_JITTER *)vseed; + size_t entropy_available; + RAND_POOL *pool; + + if (s->state != EVP_RAND_STATE_READY) { + ERR_raise(ERR_LIB_PROV, + s->state == EVP_RAND_STATE_ERROR ? PROV_R_IN_ERROR_STATE + : PROV_R_NOT_INSTANTIATED); + return 0; + } + + pool = ossl_rand_pool_new(strength, 1, outlen, outlen); + if (pool == NULL) { + ERR_raise(ERR_LIB_PROV, ERR_R_RAND_LIB); + return 0; + } + + /* Get entropy from jitter entropy library. */ + entropy_available = ossl_prov_acquire_entropy_from_jitter(s, pool); + + if (entropy_available > 0) + memcpy(out, ossl_rand_pool_buffer(pool), ossl_rand_pool_length(pool)); + + ossl_rand_pool_free(pool); + return entropy_available > 0; +} + +static int jitter_reseed(void *vseed, + ossl_unused int prediction_resistance, + ossl_unused const unsigned char *ent, + ossl_unused size_t ent_len, + ossl_unused const unsigned char *adin, + ossl_unused size_t adin_len) +{ + PROV_JITTER *s = (PROV_JITTER *)vseed; + + if (s->state != EVP_RAND_STATE_READY) { + ERR_raise(ERR_LIB_PROV, + s->state == EVP_RAND_STATE_ERROR ? PROV_R_IN_ERROR_STATE + : PROV_R_NOT_INSTANTIATED); + return 0; + } + return 1; +} + +static int jitter_get_ctx_params(void *vseed, OSSL_PARAM params[]) +{ + PROV_JITTER *s = (PROV_JITTER *)vseed; + OSSL_PARAM *p; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_STATE); + if (p != NULL && !OSSL_PARAM_set_int(p, s->state)) + return 0; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_STRENGTH); + if (p != NULL && !OSSL_PARAM_set_int(p, 1024)) + return 0; + + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_MAX_REQUEST); + if (p != NULL && !OSSL_PARAM_set_size_t(p, 128)) + return 0; + return 1; +} + +static const OSSL_PARAM *jitter_gettable_ctx_params(ossl_unused void *vseed, + ossl_unused void *provctx) +{ + static const OSSL_PARAM known_gettable_ctx_params[] = { + OSSL_PARAM_int(OSSL_RAND_PARAM_STATE, NULL), + OSSL_PARAM_uint(OSSL_RAND_PARAM_STRENGTH, NULL), + OSSL_PARAM_size_t(OSSL_RAND_PARAM_MAX_REQUEST, NULL), + OSSL_PARAM_END + }; + return known_gettable_ctx_params; +} + +static int jitter_verify_zeroization(ossl_unused void *vseed) +{ + return 1; +} + +static size_t jitter_get_seed(void *vseed, unsigned char **pout, + int entropy, size_t min_len, + size_t max_len, + int prediction_resistance, + const unsigned char *adin, + size_t adin_len) +{ + size_t ret = 0; + size_t entropy_available = 0; + size_t i; + RAND_POOL *pool; + PROV_JITTER *s = (PROV_JITTER *)vseed; + + pool = ossl_rand_pool_new(entropy, 1, min_len, max_len); + if (pool == NULL) { + ERR_raise(ERR_LIB_PROV, ERR_R_RAND_LIB); + return 0; + } + + /* Get entropy from jitter entropy library. */ + entropy_available = ossl_prov_acquire_entropy_from_jitter(s, pool); + + if (entropy_available > 0) { + ret = ossl_rand_pool_length(pool); + *pout = ossl_rand_pool_detach(pool); + + /* xor the additional data into the output */ + for (i = 0; i < adin_len; ++i) + (*pout)[i % ret] ^= adin[i]; + } else { + ERR_raise(ERR_LIB_PROV, PROV_R_ENTROPY_SOURCE_STRENGTH_TOO_WEAK); + } + ossl_rand_pool_free(pool); + return ret; +} + +static void jitter_clear_seed(ossl_unused void *vdrbg, + unsigned char *out, size_t outlen) +{ + OPENSSL_secure_clear_free(out, outlen); +} + +static int jitter_enable_locking(ossl_unused void *vseed) +{ + return 1; +} + +int jitter_lock(ossl_unused void *vctx) +{ + return 1; +} + +void jitter_unlock(ossl_unused void *vctx) +{ +} + +const OSSL_DISPATCH ossl_jitter_functions[] = { + { OSSL_FUNC_RAND_NEWCTX, (void(*)(void))jitter_new }, + { OSSL_FUNC_RAND_FREECTX, (void(*)(void))jitter_free }, + { OSSL_FUNC_RAND_INSTANTIATE, + (void(*)(void))jitter_instantiate }, + { OSSL_FUNC_RAND_UNINSTANTIATE, + (void(*)(void))jitter_uninstantiate }, + { OSSL_FUNC_RAND_GENERATE, (void(*)(void))jitter_generate }, + { OSSL_FUNC_RAND_RESEED, (void(*)(void))jitter_reseed }, + { OSSL_FUNC_RAND_ENABLE_LOCKING, (void(*)(void))jitter_enable_locking }, + { OSSL_FUNC_RAND_LOCK, (void(*)(void))jitter_lock }, + { OSSL_FUNC_RAND_UNLOCK, (void(*)(void))jitter_unlock }, + { OSSL_FUNC_RAND_GETTABLE_CTX_PARAMS, + (void(*)(void))jitter_gettable_ctx_params }, + { OSSL_FUNC_RAND_GET_CTX_PARAMS, (void(*)(void))jitter_get_ctx_params }, + { OSSL_FUNC_RAND_VERIFY_ZEROIZATION, + (void(*)(void))jitter_verify_zeroization }, + { OSSL_FUNC_RAND_GET_SEED, (void(*)(void))jitter_get_seed }, + { OSSL_FUNC_RAND_CLEAR_SEED, (void(*)(void))jitter_clear_seed }, + OSSL_DISPATCH_END +}; +#else +NON_EMPTY_TRANSLATION_UNIT +#endif diff --git a/providers/implementations/rands/seeding/rand_unix.c b/providers/implementations/rands/seeding/rand_unix.c index 9a936d800d..41b0111092 100644 --- a/providers/implementations/rands/seeding/rand_unix.c +++ b/providers/implementations/rands/seeding/rand_unix.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -95,7 +95,6 @@ static uint64_t get_time_stamp(void); /* none means none. this simplifies the following logic */ # undef OPENSSL_RAND_SEED_OS # undef OPENSSL_RAND_SEED_GETRANDOM -# undef OPENSSL_RAND_SEED_LIBRANDOM # undef OPENSSL_RAND_SEED_DEVRANDOM # undef OPENSSL_RAND_SEED_RDTSC # undef OPENSSL_RAND_SEED_RDCPU @@ -207,10 +206,6 @@ void ossl_rand_pool_keep_random_devices_open(int keep) # define OPENSSL_RAND_SEED_DEVRANDOM # endif -# if defined(OPENSSL_RAND_SEED_LIBRANDOM) -# error "librandom not (yet) supported" -# endif - # if (defined(__FreeBSD__) || defined(__NetBSD__)) && defined(KERN_ARND) /* * sysctl_random(): Use sysctl() to read a random number from the kernel @@ -659,12 +654,6 @@ size_t ossl_pool_acquire_entropy(RAND_POOL *pool) return entropy_available; # endif -# if defined(OPENSSL_RAND_SEED_LIBRANDOM) - { - /* Not yet implemented. */ - } -# endif - # if defined(OPENSSL_RAND_SEED_DEVRANDOM) if (wait_random_seeded()) { size_t bytes_needed; diff --git a/providers/implementations/rands/seeding/rand_vxworks.c b/providers/implementations/rands/seeding/rand_vxworks.c index a28fbd7997..64acf6903f 100644 --- a/providers/implementations/rands/seeding/rand_vxworks.c +++ b/providers/implementations/rands/seeding/rand_vxworks.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -105,8 +105,7 @@ size_t ossl_pool_acquire_entropy(RAND_POOL *pool) size_t bytes_needed; bytes_needed = ossl_rand_pool_bytes_needed(pool, 1 /*entropy_factor*/); - if (bytes_needed > 0) - { + if (bytes_needed > 0) { int retryCount = 0; STATUS result = ERROR; unsigned char *buffer; diff --git a/providers/implementations/rands/test_rng.c b/providers/implementations/rands/test_rng.c index 57b36469ca..b1422efe7c 100644 --- a/providers/implementations/rands/test_rng.c +++ b/providers/implementations/rands/test_rng.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -16,6 +16,7 @@ #include #include #include +#include "prov/securitycheck.h" #include "prov/providercommon.h" #include "prov/provider_ctx.h" #include "prov/provider_util.h" @@ -196,8 +197,14 @@ static int test_rng_get_ctx_params(void *vtest, OSSL_PARAM params[]) return 0; p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_GENERATE); - if (p != NULL && OSSL_PARAM_set_uint(p, t->generate)) + if (p != NULL && !OSSL_PARAM_set_uint(p, t->generate)) return 0; + +#ifdef FIPS_MODULE + p = OSSL_PARAM_locate(params, OSSL_RAND_PARAM_FIPS_APPROVED_INDICATOR); + if (p != NULL && !OSSL_PARAM_set_int(p, 0)) + return 0; +#endif /* FIPS_MODULE */ return 1; } @@ -209,6 +216,7 @@ static const OSSL_PARAM *test_rng_gettable_ctx_params(ossl_unused void *vtest, OSSL_PARAM_uint(OSSL_RAND_PARAM_STRENGTH, NULL), OSSL_PARAM_size_t(OSSL_RAND_PARAM_MAX_REQUEST, NULL), OSSL_PARAM_uint(OSSL_RAND_PARAM_GENERATE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; return known_gettable_ctx_params; diff --git a/providers/implementations/signature/dsa_sig.c b/providers/implementations/signature/dsa_sig.c index b89a0f6836..eb28c595b7 100644 --- a/providers/implementations/signature/dsa_sig.c +++ b/providers/implementations/signature/dsa_sig.c @@ -1,5 +1,5 @@ /* - * Copyright 2019-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2019-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -30,14 +30,18 @@ #include "prov/implementations.h" #include "prov/provider_ctx.h" #include "prov/securitycheck.h" -#include "crypto/dsa.h" #include "prov/der_dsa.h" +#include "crypto/dsa.h" static OSSL_FUNC_signature_newctx_fn dsa_newctx; static OSSL_FUNC_signature_sign_init_fn dsa_sign_init; static OSSL_FUNC_signature_verify_init_fn dsa_verify_init; static OSSL_FUNC_signature_sign_fn dsa_sign; +static OSSL_FUNC_signature_sign_message_update_fn dsa_signverify_message_update; +static OSSL_FUNC_signature_sign_message_final_fn dsa_sign_message_final; static OSSL_FUNC_signature_verify_fn dsa_verify; +static OSSL_FUNC_signature_verify_message_update_fn dsa_signverify_message_update; +static OSSL_FUNC_signature_verify_message_final_fn dsa_verify_message_final; static OSSL_FUNC_signature_digest_sign_init_fn dsa_digest_sign_init; static OSSL_FUNC_signature_digest_sign_update_fn dsa_digest_signverify_update; static OSSL_FUNC_signature_digest_sign_final_fn dsa_digest_sign_final; @@ -46,6 +50,7 @@ static OSSL_FUNC_signature_digest_verify_update_fn dsa_digest_signverify_update; static OSSL_FUNC_signature_digest_verify_final_fn dsa_digest_verify_final; static OSSL_FUNC_signature_freectx_fn dsa_freectx; static OSSL_FUNC_signature_dupctx_fn dsa_dupctx; +static OSSL_FUNC_signature_query_key_types_fn dsa_sigalg_query_key_types; static OSSL_FUNC_signature_get_ctx_params_fn dsa_get_ctx_params; static OSSL_FUNC_signature_gettable_ctx_params_fn dsa_gettable_ctx_params; static OSSL_FUNC_signature_set_ctx_params_fn dsa_set_ctx_params; @@ -54,6 +59,8 @@ static OSSL_FUNC_signature_get_ctx_md_params_fn dsa_get_ctx_md_params; static OSSL_FUNC_signature_gettable_ctx_md_params_fn dsa_gettable_ctx_md_params; static OSSL_FUNC_signature_set_ctx_md_params_fn dsa_set_ctx_md_params; static OSSL_FUNC_signature_settable_ctx_md_params_fn dsa_settable_ctx_md_params; +static OSSL_FUNC_signature_set_ctx_params_fn dsa_sigalg_set_ctx_params; +static OSSL_FUNC_signature_settable_ctx_params_fn dsa_sigalg_settable_ctx_params; /* * What's passed as an actual key is defined by the KEYMGMT interface. @@ -65,7 +72,19 @@ typedef struct { OSSL_LIB_CTX *libctx; char *propq; DSA *dsa; + /* |operation| reuses EVP's operation bitfield */ + int operation; + /* + * Flag to determine if a full sigalg is run (1) or if a composable + * signature algorithm is run (0). + * + * When a full sigalg is run (1), this currently affects the following + * other flags, which are to remain untouched after their initialization: + * + * - flag_allow_md (initialized to 0) + */ + unsigned int flag_sigalg : 1; /* * Flag to determine if the hash function can be changed (1) or not (0) * Because it's dangerous to change during a DigestSign or DigestVerify @@ -77,24 +96,32 @@ typedef struct { /* If this is set to 1 then the generated k is not random */ unsigned int nonce_type; - char mdname[OSSL_MAX_NAME_SIZE]; - /* The Algorithm Identifier of the combined signature algorithm */ unsigned char aid_buf[OSSL_MAX_ALGORITHM_ID_SIZE]; - unsigned char *aid; size_t aid_len; /* main digest */ + char mdname[OSSL_MAX_NAME_SIZE]; EVP_MD *md; EVP_MD_CTX *mdctx; - int operation; -} PROV_DSA_CTX; + /* Signature, for verification */ + unsigned char *sig; + size_t siglen; + + OSSL_FIPS_IND_DECLARE +} PROV_DSA_CTX; static size_t dsa_get_md_size(const PROV_DSA_CTX *pdsactx) { - if (pdsactx->md != NULL) - return EVP_MD_get_size(pdsactx->md); + int md_size; + + if (pdsactx->md != NULL) { + md_size = EVP_MD_get_size(pdsactx->md); + if (md_size <= 0) + return 0; + return (size_t)md_size; + } return 0; } @@ -111,6 +138,7 @@ static void *dsa_newctx(void *provctx, const char *propq) pdsactx->libctx = PROV_LIBCTX_OF(provctx); pdsactx->flag_allow_md = 1; + OSSL_FIPS_IND_INIT(pdsactx) if (propq != NULL && (pdsactx->propq = OPENSSL_strdup(propq)) == NULL) { OPENSSL_free(pdsactx); pdsactx = NULL; @@ -119,39 +147,61 @@ static void *dsa_newctx(void *provctx, const char *propq) } static int dsa_setup_md(PROV_DSA_CTX *ctx, - const char *mdname, const char *mdprops) + const char *mdname, const char *mdprops, + const char *desc) { + EVP_MD *md = NULL; + if (mdprops == NULL) mdprops = ctx->propq; if (mdname != NULL) { - int sha1_allowed = (ctx->operation != EVP_PKEY_OP_SIGN); WPACKET pkt; - EVP_MD *md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); - int md_nid = ossl_digest_get_approved_nid_with_sha1(ctx->libctx, md, - sha1_allowed); + int md_nid; size_t mdname_len = strlen(mdname); + unsigned char *aid = NULL; + + md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); + md_nid = ossl_digest_get_approved_nid(md); if (md == NULL || md_nid < 0) { if (md == NULL) ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, "%s could not be fetched", mdname); - if (md_nid < 0) + if (md_nid == NID_undef) ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, "digest=%s", mdname); if (mdname_len >= sizeof(ctx->mdname)) ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, "%s exceeds name buffer length", mdname); - EVP_MD_free(md); - return 0; + goto err; + } + /* XOF digests don't work */ + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + goto err; + } +#ifdef FIPS_MODULE + { + int sha1_allowed + = ((ctx->operation + & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG)) == 0); + + if (!ossl_fips_ind_digest_sign_check(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE1, + ctx->libctx, + md_nid, sha1_allowed, desc, + ossl_fips_config_signature_digest_check)) + goto err; } +#endif if (!ctx->flag_allow_md) { - if (ctx->mdname[0] != '\0' && !EVP_MD_is_a(md, ctx->mdname)) { + if (ctx->mdname[0] != '\0' + && !EVP_MD_is_a(md, ctx->mdname)) { ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, "digest %s != %s", mdname, ctx->mdname); - EVP_MD_free(md); - return 0; + goto err; } EVP_MD_free(md); return 1; @@ -173,19 +223,58 @@ static int dsa_setup_md(PROV_DSA_CTX *ctx, md_nid) && WPACKET_finish(&pkt)) { WPACKET_get_total_written(&pkt, &ctx->aid_len); - ctx->aid = WPACKET_get_curr(&pkt); + aid = WPACKET_get_curr(&pkt); } WPACKET_cleanup(&pkt); + if (aid != NULL && ctx->aid_len != 0) + memmove(ctx->aid_buf, aid, ctx->aid_len); ctx->mdctx = NULL; ctx->md = md; OPENSSL_strlcpy(ctx->mdname, mdname, sizeof(ctx->mdname)); } + + return 1; + err: + EVP_MD_free(md); + return 0; +} + +#ifdef FIPS_MODULE + +static int dsa_sign_check_approved(PROV_DSA_CTX *ctx, int signing, + const char *desc) +{ + /* DSA Signing is not approved in FIPS 140-3 */ + if (signing + && !OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE2, + ctx->libctx, desc, "DSA", + ossl_fips_config_dsa_sign_disallowed)) + return 0; return 1; } -static int dsa_signverify_init(void *vpdsactx, void *vdsa, - const OSSL_PARAM params[], int operation) +static int dsa_check_key(PROV_DSA_CTX *ctx, int sign, const char *desc) +{ + int approved = ossl_dsa_check_key(ctx->dsa, sign); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE0, + ctx->libctx, desc, "DSA Key", + ossl_fips_config_signature_digest_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + } + return 1; +} +#endif + +static int +dsa_signverify_init(void *vpdsactx, void *vdsa, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], int operation, + const char *desc) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; @@ -199,11 +288,6 @@ static int dsa_signverify_init(void *vpdsactx, void *vdsa, } if (vdsa != NULL) { - if (!ossl_dsa_check_key(pdsactx->libctx, vdsa, - operation == EVP_PKEY_OP_SIGN)) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); - return 0; - } if (!DSA_up_ref(vdsa)) return 0; DSA_free(pdsactx->dsa); @@ -212,25 +296,37 @@ static int dsa_signverify_init(void *vpdsactx, void *vdsa, pdsactx->operation = operation; - if (!dsa_set_ctx_params(pdsactx, params)) + OSSL_FIPS_IND_SET_APPROVED(pdsactx) + if (!set_ctx_params(pdsactx, params)) return 0; +#ifdef FIPS_MODULE + { + int operation_is_sign + = (operation & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG)) != 0; + if (!dsa_sign_check_approved(pdsactx, operation_is_sign, desc)) + return 0; + if (!dsa_check_key(pdsactx, operation_is_sign, desc)) + return 0; + } +#endif return 1; } static int dsa_sign_init(void *vpdsactx, void *vdsa, const OSSL_PARAM params[]) { - return dsa_signverify_init(vpdsactx, vdsa, params, EVP_PKEY_OP_SIGN); + return dsa_signverify_init(vpdsactx, vdsa, dsa_set_ctx_params, params, + EVP_PKEY_OP_SIGN, "DSA Sign Init"); } -static int dsa_verify_init(void *vpdsactx, void *vdsa, - const OSSL_PARAM params[]) -{ - return dsa_signverify_init(vpdsactx, vdsa, params, EVP_PKEY_OP_VERIFY); -} - -static int dsa_sign(void *vpdsactx, unsigned char *sig, size_t *siglen, - size_t sigsize, const unsigned char *tbs, size_t tbslen) +/* + * Sign tbs without digesting it first. This is suitable for "primitive" + * signing and signing the digest of a message, i.e. should be used with + * implementations of the keytype related algorithms. + */ +static int dsa_sign_directly(void *vpdsactx, + unsigned char *sig, size_t *siglen, size_t sigsize, + const unsigned char *tbs, size_t tbslen) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; int ret; @@ -241,12 +337,17 @@ static int dsa_sign(void *vpdsactx, unsigned char *sig, size_t *siglen, if (!ossl_prov_is_running()) return 0; +#ifdef FIPS_MODULE + if (!dsa_sign_check_approved(pdsactx, 1, "Sign")) + return 0; +#endif + if (sig == NULL) { *siglen = dsasize; return 1; } - if (sigsize < (size_t)dsasize) + if (sigsize < dsasize) return 0; if (mdsize != 0 && tbslen != mdsize) @@ -262,8 +363,79 @@ static int dsa_sign(void *vpdsactx, unsigned char *sig, size_t *siglen, return 1; } -static int dsa_verify(void *vpdsactx, const unsigned char *sig, size_t siglen, - const unsigned char *tbs, size_t tbslen) +static int dsa_signverify_message_update(void *vpdsactx, + const unsigned char *data, + size_t datalen) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + + if (pdsactx == NULL) + return 0; + + return EVP_DigestUpdate(pdsactx->mdctx, data, datalen); +} + +static int dsa_sign_message_final(void *vpdsactx, unsigned char *sig, + size_t *siglen, size_t sigsize) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; + + if (!ossl_prov_is_running() || pdsactx == NULL || pdsactx->mdctx == NULL) + return 0; + /* + * If sig is NULL then we're just finding out the sig size. Other fields + * are ignored. Defer to dsa_sign. + */ + if (sig != NULL) { + /* + * When this function is used through dsa_digest_sign_final(), + * there is the possibility that some externally provided digests + * exceed EVP_MAX_MD_SIZE. We should probably handle that + * somehow but that problem is much larger than just in DSA. + */ + if (!EVP_DigestFinal_ex(pdsactx->mdctx, digest, &dlen)) + return 0; + } + + return dsa_sign_directly(vpdsactx, sig, siglen, sigsize, digest, dlen); +} + +/* + * If signing a message, digest tbs and sign the result. + * Otherwise, sign tbs directly. + */ +static int dsa_sign(void *vpdsactx, unsigned char *sig, size_t *siglen, + size_t sigsize, const unsigned char *tbs, size_t tbslen) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + + if (pdsactx->operation == EVP_PKEY_OP_SIGNMSG) { + /* + * If |sig| is NULL, the caller is only looking for the sig length. + * DO NOT update the input in this case. + */ + if (sig == NULL) + return dsa_sign_message_final(pdsactx, sig, siglen, sigsize); + + if (dsa_signverify_message_update(pdsactx, tbs, tbslen) <= 0) + return 0; + return dsa_sign_message_final(pdsactx, sig, siglen, sigsize); + } + return dsa_sign_directly(pdsactx, sig, siglen, sigsize, tbs, tbslen); +} + +static int dsa_verify_init(void *vpdsactx, void *vdsa, + const OSSL_PARAM params[]) +{ + return dsa_signverify_init(vpdsactx, vdsa, dsa_set_ctx_params, params, + EVP_PKEY_OP_VERIFY, "DSA Verify Init"); +} + +static int dsa_verify_directly(void *vpdsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; size_t mdsize = dsa_get_md_size(pdsactx); @@ -274,19 +446,81 @@ static int dsa_verify(void *vpdsactx, const unsigned char *sig, size_t siglen, return DSA_verify(0, tbs, tbslen, sig, siglen, pdsactx->dsa); } +static int dsa_verify_set_sig(void *vpdsactx, + const unsigned char *sig, size_t siglen) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + OSSL_PARAM params[2]; + + params[0] = + OSSL_PARAM_construct_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, + (unsigned char *)sig, siglen); + params[1] = OSSL_PARAM_construct_end(); + return dsa_sigalg_set_ctx_params(pdsactx, params); +} + +static int dsa_verify_message_final(void *vpdsactx) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; + + if (!ossl_prov_is_running()) + return 0; + + if (pdsactx == NULL || pdsactx->mdctx == NULL) + return 0; + + /* + * The digests used here are all known (see dsa_get_md_nid()), so they + * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. + */ + if (!EVP_DigestFinal_ex(pdsactx->mdctx, digest, &dlen)) + return 0; + + return dsa_verify_directly(vpdsactx, pdsactx->sig, pdsactx->siglen, + digest, dlen); +} + +/* + * If verifying a message, digest tbs and verify the result. + * Otherwise, verify tbs directly. + */ +static int dsa_verify(void *vpdsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + + if (pdsactx->operation == EVP_PKEY_OP_VERIFYMSG) { + if (dsa_verify_set_sig(pdsactx, sig, siglen) <= 0) + return 0; + if (dsa_signverify_message_update(pdsactx, tbs, tbslen) <= 0) + return 0; + return dsa_verify_message_final(pdsactx); + } + return dsa_verify_directly(pdsactx, sig, siglen, tbs, tbslen); +} + +/* DigestSign/DigestVerify wrappers */ + static int dsa_digest_signverify_init(void *vpdsactx, const char *mdname, void *vdsa, const OSSL_PARAM params[], - int operation) + int operation, const char *desc) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; if (!ossl_prov_is_running()) return 0; - if (!dsa_signverify_init(vpdsactx, vdsa, params, operation)) + if (!dsa_signverify_init(vpdsactx, vdsa, dsa_set_ctx_params, params, + operation, desc)) return 0; - if (!dsa_setup_md(pdsactx, mdname, NULL)) + if (mdname != NULL + /* was dsa_setup_md already called in dsa_signverify_init()? */ + && (mdname[0] == '\0' || OPENSSL_strcasecmp(pdsactx->mdname, mdname) != 0) + && !dsa_setup_md(pdsactx, mdname, NULL, desc)) return 0; pdsactx->flag_allow_md = 0; @@ -312,90 +546,79 @@ static int dsa_digest_sign_init(void *vpdsactx, const char *mdname, void *vdsa, const OSSL_PARAM params[]) { return dsa_digest_signverify_init(vpdsactx, mdname, vdsa, params, - EVP_PKEY_OP_SIGN); + EVP_PKEY_OP_SIGNMSG, + "DSA Digest Sign Init"); } -static int dsa_digest_verify_init(void *vpdsactx, const char *mdname, - void *vdsa, const OSSL_PARAM params[]) -{ - return dsa_digest_signverify_init(vpdsactx, mdname, vdsa, params, - EVP_PKEY_OP_VERIFY); -} - -int dsa_digest_signverify_update(void *vpdsactx, const unsigned char *data, - size_t datalen) +static int dsa_digest_signverify_update(void *vpdsactx, const unsigned char *data, + size_t datalen) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; - if (pdsactx == NULL || pdsactx->mdctx == NULL) + if (pdsactx == NULL) + return 0; + /* Sigalg implementations shouldn't do digest_sign */ + if (pdsactx->flag_sigalg) return 0; - return EVP_DigestUpdate(pdsactx->mdctx, data, datalen); + return dsa_signverify_message_update(vpdsactx, data, datalen); } -int dsa_digest_sign_final(void *vpdsactx, unsigned char *sig, size_t *siglen, - size_t sigsize) +static int dsa_digest_sign_final(void *vpdsactx, unsigned char *sig, + size_t *siglen, size_t sigsize) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; + int ok = 0; - if (!ossl_prov_is_running() || pdsactx == NULL || pdsactx->mdctx == NULL) + if (pdsactx == NULL) + return 0; + /* Sigalg implementations shouldn't do digest_sign */ + if (pdsactx->flag_sigalg) return 0; - /* - * If sig is NULL then we're just finding out the sig size. Other fields - * are ignored. Defer to dsa_sign. - */ - if (sig != NULL) { - /* - * There is the possibility that some externally provided - * digests exceed EVP_MAX_MD_SIZE. We should probably handle that somehow - - * but that problem is much larger than just in DSA. - */ - if (!EVP_DigestFinal_ex(pdsactx->mdctx, digest, &dlen)) - return 0; - } + ok = dsa_sign_message_final(pdsactx, sig, siglen, sigsize); pdsactx->flag_allow_md = 1; - return dsa_sign(vpdsactx, sig, siglen, sigsize, digest, (size_t)dlen); + return ok; } +static int dsa_digest_verify_init(void *vpdsactx, const char *mdname, + void *vdsa, const OSSL_PARAM params[]) +{ + return dsa_digest_signverify_init(vpdsactx, mdname, vdsa, params, + EVP_PKEY_OP_VERIFYMSG, + "DSA Digest Verify Init"); +} int dsa_digest_verify_final(void *vpdsactx, const unsigned char *sig, size_t siglen) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; + int ok = 0; - if (!ossl_prov_is_running() || pdsactx == NULL || pdsactx->mdctx == NULL) + if (pdsactx == NULL) return 0; - - /* - * There is the possibility that some externally provided - * digests exceed EVP_MAX_MD_SIZE. We should probably handle that somehow - - * but that problem is much larger than just in DSA. - */ - if (!EVP_DigestFinal_ex(pdsactx->mdctx, digest, &dlen)) + /* Sigalg implementations shouldn't do digest_verify */ + if (pdsactx->flag_sigalg) return 0; + if (dsa_verify_set_sig(pdsactx, sig, siglen)) + ok = dsa_verify_message_final(vpdsactx); + pdsactx->flag_allow_md = 1; - return dsa_verify(vpdsactx, sig, siglen, digest, (size_t)dlen); + return ok; } static void dsa_freectx(void *vpdsactx) { PROV_DSA_CTX *ctx = (PROV_DSA_CTX *)vpdsactx; - OPENSSL_free(ctx->propq); EVP_MD_CTX_free(ctx->mdctx); EVP_MD_free(ctx->md); - ctx->propq = NULL; - ctx->mdctx = NULL; - ctx->md = NULL; + OPENSSL_free(ctx->sig); + OPENSSL_free(ctx->propq); DSA_free(ctx->dsa); OPENSSL_free(ctx); } @@ -414,8 +637,6 @@ static void *dsa_dupctx(void *vpdsactx) *dstctx = *srcctx; dstctx->dsa = NULL; - dstctx->md = NULL; - dstctx->mdctx = NULL; dstctx->propq = NULL; if (srcctx->dsa != NULL && !DSA_up_ref(srcctx->dsa)) @@ -432,6 +653,7 @@ static void *dsa_dupctx(void *vpdsactx) || !EVP_MD_CTX_copy_ex(dstctx->mdctx, srcctx->mdctx)) goto err; } + if (srcctx->propq != NULL) { dstctx->propq = OPENSSL_strdup(srcctx->propq); if (dstctx->propq == NULL) @@ -454,7 +676,9 @@ static int dsa_get_ctx_params(void *vpdsactx, OSSL_PARAM *params) p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_ALGORITHM_ID); if (p != NULL - && !OSSL_PARAM_set_octet_string(p, pdsactx->aid, pdsactx->aid_len)) + && !OSSL_PARAM_set_octet_string(p, + pdsactx->aid_len == 0 ? NULL : pdsactx->aid_buf, + pdsactx->aid_len)) return 0; p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_DIGEST); @@ -464,6 +688,8 @@ static int dsa_get_ctx_params(void *vpdsactx, OSSL_PARAM *params) p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_NONCE_TYPE); if (p != NULL && !OSSL_PARAM_set_uint(p, pdsactx->nonce_type)) return 0; + if (!OSSL_FIPS_IND_GET_CTX_PARAM(pdsactx, params)) + return 0; return 1; } @@ -472,6 +698,7 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_octet_string(OSSL_SIGNATURE_PARAM_ALGORITHM_ID, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_DIGEST, NULL, 0), OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -481,7 +708,8 @@ static const OSSL_PARAM *dsa_gettable_ctx_params(ossl_unused void *ctx, return known_gettable_ctx_params; } -static int dsa_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) +/* The common params for dsa_set_ctx_params and dsa_sigalg_set_ctx_params */ +static int dsa_common_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) { PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; const OSSL_PARAM *p; @@ -491,6 +719,42 @@ static int dsa_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pdsactx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pdsactx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(pdsactx, OSSL_FIPS_IND_SETTABLE2, params, + OSSL_SIGNATURE_PARAM_FIPS_SIGN_CHECK)) + return 0; + + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_NONCE_TYPE); + if (p != NULL + && !OSSL_PARAM_get_uint(p, &pdsactx->nonce_type)) + return 0; + return 1; +} + +#define DSA_COMMON_SETTABLE_CTX_PARAMS \ + OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), \ + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK) \ + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK) \ + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_SIGN_CHECK) \ + OSSL_PARAM_END + +static int dsa_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + const OSSL_PARAM *p; + int ret; + + if ((ret = dsa_common_set_ctx_params(pdsactx, params)) <= 0) + return ret; + + if (params == NULL) + return 1; + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_DIGEST); if (p != NULL) { char mdname[OSSL_MAX_NAME_SIZE] = "", *pmdname = mdname; @@ -504,22 +768,16 @@ static int dsa_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) if (propsp != NULL && !OSSL_PARAM_get_utf8_string(propsp, &pmdprops, sizeof(mdprops))) return 0; - if (!dsa_setup_md(pdsactx, mdname, mdprops)) + if (!dsa_setup_md(pdsactx, mdname, mdprops, "DSA Set Ctx")) return 0; } - p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_NONCE_TYPE); - if (p != NULL - && !OSSL_PARAM_get_uint(p, &pdsactx->nonce_type)) - return 0; - return 1; } static const OSSL_PARAM settable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_PROPERTIES, NULL, 0), - OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), - OSSL_PARAM_END + DSA_COMMON_SETTABLE_CTX_PARAMS }; static const OSSL_PARAM settable_ctx_params_no_digest[] = { @@ -612,3 +870,210 @@ const OSSL_DISPATCH ossl_dsa_signature_functions[] = { (void (*)(void))dsa_settable_ctx_md_params }, OSSL_DISPATCH_END }; + +/* ------------------------------------------------------------------ */ + +/* + * So called sigalgs (composite DSA+hash) implemented below. They + * are pretty much hard coded. + */ + +static OSSL_FUNC_signature_query_key_types_fn dsa_sigalg_query_key_types; +static OSSL_FUNC_signature_settable_ctx_params_fn dsa_sigalg_settable_ctx_params; +static OSSL_FUNC_signature_set_ctx_params_fn dsa_sigalg_set_ctx_params; + +/* + * dsa_sigalg_signverify_init() is almost like dsa_digest_signverify_init(), + * just doesn't allow fetching an MD from whatever the user chooses. + */ +static int dsa_sigalg_signverify_init(void *vpdsactx, void *vdsa, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], + const char *mdname, + int operation, const char *desc) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + + if (!ossl_prov_is_running()) + return 0; + + if (!dsa_signverify_init(vpdsactx, vdsa, set_ctx_params, params, operation, + desc)) + return 0; + + if (!dsa_setup_md(pdsactx, mdname, NULL, desc)) + return 0; + + pdsactx->flag_sigalg = 1; + pdsactx->flag_allow_md = 0; + + if (pdsactx->mdctx == NULL) { + pdsactx->mdctx = EVP_MD_CTX_new(); + if (pdsactx->mdctx == NULL) + goto error; + } + + if (!EVP_DigestInit_ex2(pdsactx->mdctx, pdsactx->md, params)) + goto error; + + return 1; + + error: + EVP_MD_CTX_free(pdsactx->mdctx); + pdsactx->mdctx = NULL; + return 0; +} + +static const char **dsa_sigalg_query_key_types(void) +{ + static const char *keytypes[] = { "DSA", NULL }; + + return keytypes; +} + +static const OSSL_PARAM settable_sigalg_ctx_params[] = { + OSSL_PARAM_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, NULL, 0), + DSA_COMMON_SETTABLE_CTX_PARAMS +}; + +static const OSSL_PARAM *dsa_sigalg_settable_ctx_params(void *vpdsactx, + ossl_unused void *provctx) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + + if (pdsactx != NULL && pdsactx->operation == EVP_PKEY_OP_VERIFYMSG) + return settable_sigalg_ctx_params; + return NULL; +} + +static int dsa_sigalg_set_ctx_params(void *vpdsactx, const OSSL_PARAM params[]) +{ + PROV_DSA_CTX *pdsactx = (PROV_DSA_CTX *)vpdsactx; + const OSSL_PARAM *p; + int ret; + + if ((ret = dsa_common_set_ctx_params(pdsactx, params)) <= 0) + return ret; + + if (params == NULL) + return 1; + + if (pdsactx->operation == EVP_PKEY_OP_VERIFYMSG) { + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_SIGNATURE); + if (p != NULL) { + OPENSSL_free(pdsactx->sig); + pdsactx->sig = NULL; + pdsactx->siglen = 0; + if (!OSSL_PARAM_get_octet_string(p, (void **)&pdsactx->sig, + 0, &pdsactx->siglen)) + return 0; + } + } + return 1; +} + +#define IMPL_DSA_SIGALG(md, MD) \ + static OSSL_FUNC_signature_sign_init_fn dsa_##md##_sign_init; \ + static OSSL_FUNC_signature_sign_message_init_fn \ + dsa_##md##_sign_message_init; \ + static OSSL_FUNC_signature_verify_init_fn dsa_##md##_verify_init; \ + static OSSL_FUNC_signature_verify_message_init_fn \ + dsa_##md##_verify_message_init; \ + \ + static int \ + dsa_##md##_sign_init(void *vpdsactx, void *vdsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "DSA-" #MD " Sign Init"; \ + \ + return dsa_sigalg_signverify_init(vpdsactx, vdsa, \ + dsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGN, \ + desc); \ + } \ + \ + static int \ + dsa_##md##_sign_message_init(void *vpdsactx, void *vdsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "DSA-" #MD " Sign Message Init"; \ + \ + return dsa_sigalg_signverify_init(vpdsactx, vdsa, \ + dsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGNMSG, \ + desc); \ + } \ + \ + static int \ + dsa_##md##_verify_init(void *vpdsactx, void *vdsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "DSA-" #MD " Verify Init"; \ + \ + return dsa_sigalg_signverify_init(vpdsactx, vdsa, \ + dsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFY, \ + desc); \ + } \ + \ + static int \ + dsa_##md##_verify_message_init(void *vpdsactx, void *vdsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "DSA-" #MD " Verify Message Init"; \ + \ + return dsa_sigalg_signverify_init(vpdsactx, vdsa, \ + dsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFYMSG, \ + desc); \ + } \ + \ + const OSSL_DISPATCH ossl_dsa_##md##_signature_functions[] = { \ + { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))dsa_newctx }, \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))dsa_##md##_sign_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN, (void (*)(void))dsa_sign }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT, \ + (void (*)(void))dsa_##md##_sign_message_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_UPDATE, \ + (void (*)(void))dsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_FINAL, \ + (void (*)(void))dsa_sign_message_final }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))dsa_##md##_verify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY, \ + (void (*)(void))dsa_verify }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT, \ + (void (*)(void))dsa_##md##_verify_message_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_UPDATE, \ + (void (*)(void))dsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_FINAL, \ + (void (*)(void))dsa_verify_message_final }, \ + { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))dsa_freectx }, \ + { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))dsa_dupctx }, \ + { OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES, \ + (void (*)(void))dsa_sigalg_query_key_types }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))dsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))dsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))dsa_sigalg_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))dsa_sigalg_settable_ctx_params }, \ + OSSL_DISPATCH_END \ + } + +IMPL_DSA_SIGALG(sha1, SHA1); +IMPL_DSA_SIGALG(sha224, SHA2-224); +IMPL_DSA_SIGALG(sha256, SHA2-256); +IMPL_DSA_SIGALG(sha384, SHA2-384); +IMPL_DSA_SIGALG(sha512, SHA2-512); +IMPL_DSA_SIGALG(sha3_224, SHA3-224); +IMPL_DSA_SIGALG(sha3_256, SHA3-256); +IMPL_DSA_SIGALG(sha3_384, SHA3-384); +IMPL_DSA_SIGALG(sha3_512, SHA3-512); diff --git a/providers/implementations/signature/ecdsa_sig.c b/providers/implementations/signature/ecdsa_sig.c index fe65ed8dc6..72be2bcb62 100644 --- a/providers/implementations/signature/ecdsa_sig.c +++ b/providers/implementations/signature/ecdsa_sig.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -30,14 +30,18 @@ #include "prov/implementations.h" #include "prov/provider_ctx.h" #include "prov/securitycheck.h" -#include "crypto/ec.h" #include "prov/der_ec.h" +#include "crypto/ec.h" static OSSL_FUNC_signature_newctx_fn ecdsa_newctx; static OSSL_FUNC_signature_sign_init_fn ecdsa_sign_init; static OSSL_FUNC_signature_verify_init_fn ecdsa_verify_init; static OSSL_FUNC_signature_sign_fn ecdsa_sign; +static OSSL_FUNC_signature_sign_message_update_fn ecdsa_signverify_message_update; +static OSSL_FUNC_signature_sign_message_final_fn ecdsa_sign_message_final; static OSSL_FUNC_signature_verify_fn ecdsa_verify; +static OSSL_FUNC_signature_verify_message_update_fn ecdsa_signverify_message_update; +static OSSL_FUNC_signature_verify_message_final_fn ecdsa_verify_message_final; static OSSL_FUNC_signature_digest_sign_init_fn ecdsa_digest_sign_init; static OSSL_FUNC_signature_digest_sign_update_fn ecdsa_digest_signverify_update; static OSSL_FUNC_signature_digest_sign_final_fn ecdsa_digest_sign_final; @@ -46,6 +50,7 @@ static OSSL_FUNC_signature_digest_verify_update_fn ecdsa_digest_signverify_updat static OSSL_FUNC_signature_digest_verify_final_fn ecdsa_digest_verify_final; static OSSL_FUNC_signature_freectx_fn ecdsa_freectx; static OSSL_FUNC_signature_dupctx_fn ecdsa_dupctx; +static OSSL_FUNC_signature_query_key_types_fn ecdsa_sigalg_query_key_types; static OSSL_FUNC_signature_get_ctx_params_fn ecdsa_get_ctx_params; static OSSL_FUNC_signature_gettable_ctx_params_fn ecdsa_gettable_ctx_params; static OSSL_FUNC_signature_set_ctx_params_fn ecdsa_set_ctx_params; @@ -54,6 +59,8 @@ static OSSL_FUNC_signature_get_ctx_md_params_fn ecdsa_get_ctx_md_params; static OSSL_FUNC_signature_gettable_ctx_md_params_fn ecdsa_gettable_ctx_md_params; static OSSL_FUNC_signature_set_ctx_md_params_fn ecdsa_set_ctx_md_params; static OSSL_FUNC_signature_settable_ctx_md_params_fn ecdsa_settable_ctx_md_params; +static OSSL_FUNC_signature_set_ctx_params_fn ecdsa_sigalg_set_ctx_params; +static OSSL_FUNC_signature_settable_ctx_params_fn ecdsa_sigalg_settable_ctx_params; /* * What's passed as an actual key is defined by the KEYMGMT interface. @@ -65,8 +72,19 @@ typedef struct { OSSL_LIB_CTX *libctx; char *propq; EC_KEY *ec; - char mdname[OSSL_MAX_NAME_SIZE]; + /* |operation| reuses EVP's operation bitfield */ + int operation; + /* + * Flag to determine if a full sigalg is run (1) or if a composable + * signature algorithm is run (0). + * + * When a full sigalg is run (1), this currently affects the following + * other flags, which are to remain untouched after their initialization: + * + * - flag_allow_md (initialized to 0) + */ + unsigned int flag_sigalg : 1; /* * Flag to determine if the hash function can be changed (1) or not (0) * Because it's dangerous to change during a DigestSign or DigestVerify @@ -77,13 +95,18 @@ typedef struct { /* The Algorithm Identifier of the combined signature algorithm */ unsigned char aid_buf[OSSL_MAX_ALGORITHM_ID_SIZE]; - unsigned char *aid; size_t aid_len; - size_t mdsize; - int operation; + /* main digest */ + char mdname[OSSL_MAX_NAME_SIZE]; EVP_MD *md; EVP_MD_CTX *mdctx; + size_t mdsize; + + /* Signature, for verification */ + unsigned char *sig; + size_t siglen; + /* * Internally used to cache the results of calling the EC group * sign_setup() methods which are then passed to the sign operation. @@ -102,9 +125,18 @@ typedef struct { * valid - but for this mode of operation it forces a failure instead. */ unsigned int kattest; +#endif +#ifdef FIPS_MODULE + /* + * FIPS 140-3 IG 2.4.B mandates that verification based on a digest of a + * message is not permitted. However, signing based on a digest is still + * permitted. + */ + int verify_message; #endif /* If this is set then the generated k is not random */ unsigned int nonce_type; + OSSL_FIPS_IND_DECLARE } PROV_ECDSA_CTX; static void *ecdsa_newctx(void *provctx, const char *propq) @@ -118,7 +150,11 @@ static void *ecdsa_newctx(void *provctx, const char *propq) if (ctx == NULL) return NULL; + OSSL_FIPS_IND_INIT(ctx) ctx->flag_allow_md = 1; +#ifdef FIPS_MODULE + ctx->verify_message = 1; +#endif ctx->libctx = PROV_LIBCTX_OF(provctx); if (propq != NULL && (ctx->propq = OPENSSL_strdup(propq)) == NULL) { OPENSSL_free(ctx); @@ -127,11 +163,108 @@ static void *ecdsa_newctx(void *provctx, const char *propq) return ctx; } -static int ecdsa_signverify_init(void *vctx, void *ec, - const OSSL_PARAM params[], int operation) +static int ecdsa_setup_md(PROV_ECDSA_CTX *ctx, + const char *mdname, const char *mdprops, + const char *desc) { - PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + EVP_MD *md = NULL; + size_t mdname_len; + int md_nid, md_size; + WPACKET pkt; + unsigned char *aid = NULL; + + if (mdname == NULL) + return 1; + + mdname_len = strlen(mdname); + if (mdname_len >= sizeof(ctx->mdname)) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "%s exceeds name buffer length", mdname); + return 0; + } + if (mdprops == NULL) + mdprops = ctx->propq; + md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); + if (md == NULL) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "%s could not be fetched", mdname); + return 0; + } + md_size = EVP_MD_get_size(md); + if (md_size <= 0) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "%s has invalid md size %d", mdname, md_size); + goto err; + } + md_nid = ossl_digest_get_approved_nid(md); + if (md_nid == NID_undef) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, + "digest=%s", mdname); + goto err; + } + /* XOF digests don't work */ + if (EVP_MD_xof(md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + goto err; + } + +#ifdef FIPS_MODULE + { + int sha1_allowed + = ((ctx->operation + & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG)) == 0); + + if (!ossl_fips_ind_digest_sign_check(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE1, + ctx->libctx, + md_nid, sha1_allowed, desc, + ossl_fips_config_signature_digest_check)) + goto err; + } +#endif + + if (!ctx->flag_allow_md) { + if (ctx->mdname[0] != '\0' && !EVP_MD_is_a(md, ctx->mdname)) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, + "digest %s != %s", mdname, ctx->mdname); + goto err; + } + EVP_MD_free(md); + return 1; + } + + EVP_MD_CTX_free(ctx->mdctx); + EVP_MD_free(ctx->md); + + ctx->aid_len = 0; + if (WPACKET_init_der(&pkt, ctx->aid_buf, sizeof(ctx->aid_buf)) + && ossl_DER_w_algorithmIdentifier_ECDSA_with_MD(&pkt, -1, ctx->ec, + md_nid) + && WPACKET_finish(&pkt)) { + WPACKET_get_total_written(&pkt, &ctx->aid_len); + aid = WPACKET_get_curr(&pkt); + } + WPACKET_cleanup(&pkt); + if (aid != NULL && ctx->aid_len != 0) + memmove(ctx->aid_buf, aid, ctx->aid_len); + + ctx->mdctx = NULL; + ctx->md = md; + ctx->mdsize = (size_t)md_size; + OPENSSL_strlcpy(ctx->mdname, mdname, sizeof(ctx->mdname)); + return 1; + err: + EVP_MD_free(md); + return 0; +} + +static int +ecdsa_signverify_init(PROV_ECDSA_CTX *ctx, void *ec, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], int operation, + const char *desc) +{ if (!ossl_prov_is_running() || ctx == NULL) return 0; @@ -142,8 +275,6 @@ static int ecdsa_signverify_init(void *vctx, void *ec, } if (ec != NULL) { - if (!ossl_ec_check_key(ctx->libctx, ec, operation == EVP_PKEY_OP_SIGN)) - return 0; if (!EC_KEY_up_ref(ec)) return 0; EC_KEY_free(ctx->ec); @@ -152,24 +283,38 @@ static int ecdsa_signverify_init(void *vctx, void *ec, ctx->operation = operation; - if (!ecdsa_set_ctx_params(ctx, params)) + OSSL_FIPS_IND_SET_APPROVED(ctx) + if (!set_ctx_params(ctx, params)) return 0; - +#ifdef FIPS_MODULE + if (!ossl_fips_ind_ec_key_check(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE0, ctx->libctx, + EC_KEY_get0_group(ctx->ec), desc, + (operation & (EVP_PKEY_OP_SIGN + | EVP_PKEY_OP_SIGNMSG)) != 0)) + return 0; +#endif return 1; } static int ecdsa_sign_init(void *vctx, void *ec, const OSSL_PARAM params[]) { - return ecdsa_signverify_init(vctx, ec, params, EVP_PKEY_OP_SIGN); -} + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; -static int ecdsa_verify_init(void *vctx, void *ec, const OSSL_PARAM params[]) -{ - return ecdsa_signverify_init(vctx, ec, params, EVP_PKEY_OP_VERIFY); +#ifdef FIPS_MODULE + ctx->verify_message = 1; +#endif + return ecdsa_signverify_init(ctx, ec, ecdsa_set_ctx_params, params, + EVP_PKEY_OP_SIGN, "ECDSA Sign Init"); } -static int ecdsa_sign(void *vctx, unsigned char *sig, size_t *siglen, - size_t sigsize, const unsigned char *tbs, size_t tbslen) +/* + * Sign tbs without digesting it first. This is suitable for "primitive" + * signing and signing the digest of a message. + */ +static int ecdsa_sign_directly(void *vctx, + unsigned char *sig, size_t *siglen, size_t sigsize, + const unsigned char *tbs, size_t tbslen) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; int ret; @@ -196,9 +341,13 @@ static int ecdsa_sign(void *vctx, unsigned char *sig, size_t *siglen, return 0; if (ctx->nonce_type != 0) { + const char *mdname = NULL; + + if (ctx->mdname[0] != '\0') + mdname = ctx->mdname; ret = ossl_ecdsa_deterministic_sign(tbs, tbslen, sig, &sltmp, ctx->ec, ctx->nonce_type, - ctx->mdname, + mdname, ctx->libctx, ctx->propq); } else { ret = ECDSA_sign_ex(0, tbs, tbslen, sig, &sltmp, ctx->kinv, ctx->r, @@ -211,94 +360,161 @@ static int ecdsa_sign(void *vctx, unsigned char *sig, size_t *siglen, return 1; } -static int ecdsa_verify(void *vctx, const unsigned char *sig, size_t siglen, - const unsigned char *tbs, size_t tbslen) +static int ecdsa_signverify_message_update(void *vctx, + const unsigned char *data, + size_t datalen) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - if (!ossl_prov_is_running() || (ctx->mdsize != 0 && tbslen != ctx->mdsize)) + if (ctx == NULL) return 0; - return ECDSA_verify(0, tbs, tbslen, sig, siglen, ctx->ec); + return EVP_DigestUpdate(ctx->mdctx, data, datalen); } -static int ecdsa_setup_md(PROV_ECDSA_CTX *ctx, const char *mdname, - const char *mdprops) +static int ecdsa_sign_message_final(void *vctx, unsigned char *sig, + size_t *siglen, size_t sigsize) { - EVP_MD *md = NULL; - size_t mdname_len; - int md_nid, sha1_allowed; - WPACKET pkt; - - if (mdname == NULL) - return 1; + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; - mdname_len = strlen(mdname); - if (mdname_len >= sizeof(ctx->mdname)) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, - "%s exceeds name buffer length", mdname); + if (!ossl_prov_is_running() || ctx == NULL) return 0; - } - if (mdprops == NULL) - mdprops = ctx->propq; - md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); - if (md == NULL) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, - "%s could not be fetched", mdname); + if (ctx->mdctx == NULL) return 0; - } - sha1_allowed = (ctx->operation != EVP_PKEY_OP_SIGN); - md_nid = ossl_digest_get_approved_nid_with_sha1(ctx->libctx, md, - sha1_allowed); - if (md_nid < 0) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, - "digest=%s", mdname); - EVP_MD_free(md); + /* + * If sig is NULL then we're just finding out the sig size. Other fields + * are ignored. Defer to ecdsa_sign. + */ + if (sig != NULL + && !EVP_DigestFinal_ex(ctx->mdctx, digest, &dlen)) return 0; - } + return ecdsa_sign_directly(vctx, sig, siglen, sigsize, digest, dlen); +} - if (!ctx->flag_allow_md) { - if (ctx->mdname[0] != '\0' && !EVP_MD_is_a(md, ctx->mdname)) { - ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, - "digest %s != %s", mdname, ctx->mdname); - EVP_MD_free(md); +/* + * If signing a message, digest tbs and sign the result. + * Otherwise, sign tbs directly. + */ +static int ecdsa_sign(void *vctx, unsigned char *sig, size_t *siglen, + size_t sigsize, const unsigned char *tbs, size_t tbslen) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + + if (ctx->operation == EVP_PKEY_OP_SIGNMSG) { + /* + * If |sig| is NULL, the caller is only looking for the sig length. + * DO NOT update the input in this case. + */ + if (sig == NULL) + return ecdsa_sign_message_final(ctx, sig, siglen, sigsize); + + if (ecdsa_signverify_message_update(ctx, tbs, tbslen) <= 0) return 0; - } - EVP_MD_free(md); - return 1; + return ecdsa_sign_message_final(ctx, sig, siglen, sigsize); } + return ecdsa_sign_directly(ctx, sig, siglen, sigsize, tbs, tbslen); +} - EVP_MD_CTX_free(ctx->mdctx); - EVP_MD_free(ctx->md); +static int ecdsa_verify_init(void *vctx, void *ec, const OSSL_PARAM params[]) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - ctx->aid_len = 0; - if (WPACKET_init_der(&pkt, ctx->aid_buf, sizeof(ctx->aid_buf)) - && ossl_DER_w_algorithmIdentifier_ECDSA_with_MD(&pkt, -1, ctx->ec, - md_nid) - && WPACKET_finish(&pkt)) { - WPACKET_get_total_written(&pkt, &ctx->aid_len); - ctx->aid = WPACKET_get_curr(&pkt); - } - WPACKET_cleanup(&pkt); - ctx->mdctx = NULL; - ctx->md = md; - ctx->mdsize = EVP_MD_get_size(ctx->md); - OPENSSL_strlcpy(ctx->mdname, mdname, sizeof(ctx->mdname)); +#ifdef FIPS_MODULE + ctx->verify_message = 0; +#endif + return ecdsa_signverify_init(ctx, ec, ecdsa_set_ctx_params, params, + EVP_PKEY_OP_VERIFY, "ECDSA Verify Init"); +} - return 1; +static int ecdsa_verify_directly(void *vctx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + + if (!ossl_prov_is_running() || (ctx->mdsize != 0 && tbslen != ctx->mdsize)) + return 0; + + return ECDSA_verify(0, tbs, tbslen, sig, siglen, ctx->ec); } +static int ecdsa_verify_set_sig(void *vctx, + const unsigned char *sig, size_t siglen) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + OSSL_PARAM params[2]; + + params[0] = + OSSL_PARAM_construct_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, + (unsigned char *)sig, siglen); + params[1] = OSSL_PARAM_construct_end(); + return ecdsa_sigalg_set_ctx_params(ctx, params); +} + +static int ecdsa_verify_message_final(void *vctx) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; + + if (!ossl_prov_is_running() || ctx == NULL || ctx->mdctx == NULL) + return 0; + + /* + * The digests used here are all known (see ecdsa_get_md_nid()), so they + * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. + */ + if (!EVP_DigestFinal_ex(ctx->mdctx, digest, &dlen)) + return 0; + + return ecdsa_verify_directly(vctx, ctx->sig, ctx->siglen, + digest, dlen); +} + +/* + * If verifying a message, digest tbs and verify the result. + * Otherwise, verify tbs directly. + */ +static int ecdsa_verify(void *vctx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + + if (ctx->operation == EVP_PKEY_OP_VERIFYMSG) { + if (ecdsa_verify_set_sig(ctx, sig, siglen) <= 0) + return 0; + if (ecdsa_signverify_message_update(ctx, tbs, tbslen) <= 0) + return 0; + return ecdsa_verify_message_final(ctx); + } + return ecdsa_verify_directly(ctx, sig, siglen, tbs, tbslen); +} + +/* DigestSign/DigestVerify wrappers */ + static int ecdsa_digest_signverify_init(void *vctx, const char *mdname, void *ec, const OSSL_PARAM params[], - int operation) + int operation, const char *desc) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; if (!ossl_prov_is_running()) return 0; - if (!ecdsa_signverify_init(vctx, ec, params, operation) - || !ecdsa_setup_md(ctx, mdname, NULL)) +#ifdef FIPS_MODULE + ctx->verify_message = 1; +#endif + if (!ecdsa_signverify_init(vctx, ec, ecdsa_set_ctx_params, params, + operation, desc)) + return 0; + + if (mdname != NULL + /* was ecdsa_setup_md already called in ecdsa_signverify_init()? */ + && (mdname[0] == '\0' || OPENSSL_strcasecmp(ctx->mdname, mdname) != 0) + && !ecdsa_setup_md(ctx, mdname, NULL, desc)) return 0; ctx->flag_allow_md = 0; @@ -322,75 +538,80 @@ static int ecdsa_digest_sign_init(void *vctx, const char *mdname, void *ec, const OSSL_PARAM params[]) { return ecdsa_digest_signverify_init(vctx, mdname, ec, params, - EVP_PKEY_OP_SIGN); -} - -static int ecdsa_digest_verify_init(void *vctx, const char *mdname, void *ec, - const OSSL_PARAM params[]) -{ - return ecdsa_digest_signverify_init(vctx, mdname, ec, params, - EVP_PKEY_OP_VERIFY); + EVP_PKEY_OP_SIGNMSG, + "ECDSA Digest Sign Init"); } -int ecdsa_digest_signverify_update(void *vctx, const unsigned char *data, - size_t datalen) +static int ecdsa_digest_signverify_update(void *vctx, const unsigned char *data, + size_t datalen) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; if (ctx == NULL || ctx->mdctx == NULL) return 0; + /* Sigalg implementations shouldn't do digest_sign */ + if (ctx->flag_sigalg) + return 0; - return EVP_DigestUpdate(ctx->mdctx, data, datalen); + return ecdsa_signverify_message_update(vctx, data, datalen); } int ecdsa_digest_sign_final(void *vctx, unsigned char *sig, size_t *siglen, size_t sigsize) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; + int ok = 0; - if (!ossl_prov_is_running() || ctx == NULL || ctx->mdctx == NULL) + if (ctx == NULL) return 0; - - /* - * If sig is NULL then we're just finding out the sig size. Other fields - * are ignored. Defer to ecdsa_sign. - */ - if (sig != NULL - && !EVP_DigestFinal_ex(ctx->mdctx, digest, &dlen)) + /* Sigalg implementations shouldn't do digest_sign */ + if (ctx->flag_sigalg) return 0; + + ok = ecdsa_sign_message_final(ctx, sig, siglen, sigsize); + ctx->flag_allow_md = 1; - return ecdsa_sign(vctx, sig, siglen, sigsize, digest, (size_t)dlen); + + return ok; +} + +static int ecdsa_digest_verify_init(void *vctx, const char *mdname, void *ec, + const OSSL_PARAM params[]) +{ + return ecdsa_digest_signverify_init(vctx, mdname, ec, params, + EVP_PKEY_OP_VERIFYMSG, + "ECDSA Digest Verify Init"); } int ecdsa_digest_verify_final(void *vctx, const unsigned char *sig, size_t siglen) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; + int ok = 0; if (!ossl_prov_is_running() || ctx == NULL || ctx->mdctx == NULL) return 0; - if (!EVP_DigestFinal_ex(ctx->mdctx, digest, &dlen)) + /* Sigalg implementations shouldn't do digest_verify */ + if (ctx->flag_sigalg) return 0; + + if (ecdsa_verify_set_sig(ctx, sig, siglen)) + ok = ecdsa_verify_message_final(ctx); + ctx->flag_allow_md = 1; - return ecdsa_verify(ctx, sig, siglen, digest, (size_t)dlen); + + return ok; } static void ecdsa_freectx(void *vctx) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - OPENSSL_free(ctx->propq); EVP_MD_CTX_free(ctx->mdctx); EVP_MD_free(ctx->md); - ctx->propq = NULL; - ctx->mdctx = NULL; - ctx->md = NULL; - ctx->mdsize = 0; + OPENSSL_free(ctx->propq); + OPENSSL_free(ctx->sig); EC_KEY_free(ctx->ec); BN_clear_free(ctx->kinv); BN_clear_free(ctx->r); @@ -411,8 +632,6 @@ static void *ecdsa_dupctx(void *vctx) *dstctx = *srcctx; dstctx->ec = NULL; - dstctx->md = NULL; - dstctx->mdctx = NULL; dstctx->propq = NULL; if (srcctx->ec != NULL && !EC_KEY_up_ref(srcctx->ec)) @@ -454,7 +673,9 @@ static int ecdsa_get_ctx_params(void *vctx, OSSL_PARAM *params) return 0; p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_ALGORITHM_ID); - if (p != NULL && !OSSL_PARAM_set_octet_string(p, ctx->aid, ctx->aid_len)) + if (p != NULL && !OSSL_PARAM_set_octet_string(p, + ctx->aid_len == 0 ? NULL : ctx->aid_buf, + ctx->aid_len)) return 0; p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_DIGEST_SIZE); @@ -471,6 +692,14 @@ static int ecdsa_get_ctx_params(void *vctx, OSSL_PARAM *params) if (p != NULL && !OSSL_PARAM_set_uint(p, ctx->nonce_type)) return 0; +#ifdef FIPS_MODULE + p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE); + if (p != NULL && !OSSL_PARAM_set_uint(p, ctx->verify_message)) + return 0; +#endif + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(ctx, params)) + return 0; return 1; } @@ -479,6 +708,10 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_size_t(OSSL_SIGNATURE_PARAM_DIGEST_SIZE, NULL), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_DIGEST, NULL, 0), OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), +#ifdef FIPS_MODULE + OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE, NULL), +#endif + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -488,23 +721,57 @@ static const OSSL_PARAM *ecdsa_gettable_ctx_params(ossl_unused void *vctx, return known_gettable_ctx_params; } -static int ecdsa_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +/* The common params for ecdsa_set_ctx_params and ecdsa_sigalg_set_ctx_params */ +static int ecdsa_common_set_ctx_params(void *vctx, const OSSL_PARAM params[]) { PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; const OSSL_PARAM *p; - size_t mdsize = 0; if (ctx == NULL) return 0; if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK)) + return 0; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(ctx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK)) + return 0; + #if !defined(OPENSSL_NO_ACVP_TESTS) p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_KAT); if (p != NULL && !OSSL_PARAM_get_uint(p, &ctx->kattest)) return 0; #endif + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_NONCE_TYPE); + if (p != NULL + && !OSSL_PARAM_get_uint(p, &ctx->nonce_type)) + return 0; + return 1; +} + +#define ECDSA_COMMON_SETTABLE_CTX_PARAMS \ + OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_KAT, NULL), \ + OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), \ + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK) \ + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK) \ + OSSL_PARAM_END + +static int ecdsa_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + const OSSL_PARAM *p; + size_t mdsize = 0; + int ret; + + if ((ret = ecdsa_common_set_ctx_params(ctx, params)) <= 0) + return ret; + + if (params == NULL) + return 1; + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_DIGEST); if (p != NULL) { char mdname[OSSL_MAX_NAME_SIZE] = "", *pmdname = mdname; @@ -518,7 +785,7 @@ static int ecdsa_set_ctx_params(void *vctx, const OSSL_PARAM params[]) if (propsp != NULL && !OSSL_PARAM_get_utf8_string(propsp, &pmdprops, sizeof(mdprops))) return 0; - if (!ecdsa_setup_md(ctx, mdname, mdprops)) + if (!ecdsa_setup_md(ctx, mdname, mdprops, "ECDSA Set Ctx")) return 0; } @@ -529,11 +796,6 @@ static int ecdsa_set_ctx_params(void *vctx, const OSSL_PARAM params[]) return 0; ctx->mdsize = mdsize; } - p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_NONCE_TYPE); - if (p != NULL - && !OSSL_PARAM_get_uint(p, &ctx->nonce_type)) - return 0; - return 1; } @@ -541,23 +803,12 @@ static const OSSL_PARAM settable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_DIGEST, NULL, 0), OSSL_PARAM_size_t(OSSL_SIGNATURE_PARAM_DIGEST_SIZE, NULL), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_PROPERTIES, NULL, 0), - OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_KAT, NULL), - OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_NONCE_TYPE, NULL), - OSSL_PARAM_END -}; - -static const OSSL_PARAM settable_ctx_params_no_digest[] = { - OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_KAT, NULL), - OSSL_PARAM_END + ECDSA_COMMON_SETTABLE_CTX_PARAMS }; static const OSSL_PARAM *ecdsa_settable_ctx_params(void *vctx, ossl_unused void *provctx) { - PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; - - if (ctx != NULL && !ctx->flag_allow_md) - return settable_ctx_params_no_digest; return settable_ctx_params; } @@ -637,3 +888,210 @@ const OSSL_DISPATCH ossl_ecdsa_signature_functions[] = { (void (*)(void))ecdsa_settable_ctx_md_params }, OSSL_DISPATCH_END }; + +/* ------------------------------------------------------------------ */ + +/* + * So called sigalgs (composite ECDSA+hash) implemented below. They + * are pretty much hard coded. + */ + +static OSSL_FUNC_signature_query_key_types_fn ecdsa_sigalg_query_key_types; +static OSSL_FUNC_signature_settable_ctx_params_fn ecdsa_sigalg_settable_ctx_params; +static OSSL_FUNC_signature_set_ctx_params_fn ecdsa_sigalg_set_ctx_params; + +/* + * ecdsa_sigalg_signverify_init() is almost like ecdsa_digest_signverify_init(), + * just doesn't allow fetching an MD from whatever the user chooses. + */ +static int ecdsa_sigalg_signverify_init(void *vctx, void *vec, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], + const char *mdname, + int operation, const char *desc) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + + if (!ossl_prov_is_running()) + return 0; + + if (!ecdsa_signverify_init(vctx, vec, set_ctx_params, params, operation, + desc)) + return 0; + + if (!ecdsa_setup_md(ctx, mdname, NULL, desc)) + return 0; + + ctx->flag_sigalg = 1; + ctx->flag_allow_md = 0; + + if (ctx->mdctx == NULL) { + ctx->mdctx = EVP_MD_CTX_new(); + if (ctx->mdctx == NULL) + goto error; + } + + if (!EVP_DigestInit_ex2(ctx->mdctx, ctx->md, params)) + goto error; + + return 1; + + error: + EVP_MD_CTX_free(ctx->mdctx); + ctx->mdctx = NULL; + return 0; +} + +static const char **ecdsa_sigalg_query_key_types(void) +{ + static const char *keytypes[] = { "EC", NULL }; + + return keytypes; +} + +static const OSSL_PARAM settable_sigalg_ctx_params[] = { + OSSL_PARAM_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, NULL, 0), + ECDSA_COMMON_SETTABLE_CTX_PARAMS +}; + +static const OSSL_PARAM *ecdsa_sigalg_settable_ctx_params(void *vctx, + ossl_unused void *provctx) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + + if (ctx != NULL && ctx->operation == EVP_PKEY_OP_VERIFYMSG) + return settable_sigalg_ctx_params; + return NULL; +} + +static int ecdsa_sigalg_set_ctx_params(void *vctx, const OSSL_PARAM params[]) +{ + PROV_ECDSA_CTX *ctx = (PROV_ECDSA_CTX *)vctx; + const OSSL_PARAM *p; + int ret; + + if ((ret = ecdsa_common_set_ctx_params(ctx, params)) <= 0) + return ret; + + if (params == NULL) + return 1; + + if (ctx->operation == EVP_PKEY_OP_VERIFYMSG) { + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_SIGNATURE); + if (p != NULL) { + OPENSSL_free(ctx->sig); + ctx->sig = NULL; + ctx->siglen = 0; + if (!OSSL_PARAM_get_octet_string(p, (void **)&ctx->sig, + 0, &ctx->siglen)) + return 0; + } + } + return 1; +} + +#define IMPL_ECDSA_SIGALG(md, MD) \ + static OSSL_FUNC_signature_sign_init_fn ecdsa_##md##_sign_init; \ + static OSSL_FUNC_signature_sign_message_init_fn \ + ecdsa_##md##_sign_message_init; \ + static OSSL_FUNC_signature_verify_init_fn ecdsa_##md##_verify_init; \ + static OSSL_FUNC_signature_verify_message_init_fn \ + ecdsa_##md##_verify_message_init; \ + \ + static int \ + ecdsa_##md##_sign_init(void *vctx, void *vec, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "ECDSA-" #MD " Sign Init"; \ + \ + return ecdsa_sigalg_signverify_init(vctx, vec, \ + ecdsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGN, \ + desc); \ + } \ + \ + static int \ + ecdsa_##md##_sign_message_init(void *vctx, void *vec, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "ECDSA-" #MD " Sign Message Init"; \ + \ + return ecdsa_sigalg_signverify_init(vctx, vec, \ + ecdsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGNMSG, \ + desc); \ + } \ + \ + static int \ + ecdsa_##md##_verify_init(void *vctx, void *vec, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "ECDSA-" #MD " Verify Init"; \ + \ + return ecdsa_sigalg_signverify_init(vctx, vec, \ + ecdsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFY, \ + desc); \ + } \ + \ + static int \ + ecdsa_##md##_verify_message_init(void *vctx, void *vec, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "ECDSA-" #MD " Verify Message Init"; \ + \ + return ecdsa_sigalg_signverify_init(vctx, vec, \ + ecdsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFYMSG, \ + desc); \ + } \ + \ + const OSSL_DISPATCH ossl_ecdsa_##md##_signature_functions[] = { \ + { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))ecdsa_newctx }, \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))ecdsa_##md##_sign_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN, (void (*)(void))ecdsa_sign }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT, \ + (void (*)(void))ecdsa_##md##_sign_message_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_UPDATE, \ + (void (*)(void))ecdsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_FINAL, \ + (void (*)(void))ecdsa_sign_message_final }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))ecdsa_##md##_verify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY, \ + (void (*)(void))ecdsa_verify }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT, \ + (void (*)(void))ecdsa_##md##_verify_message_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_UPDATE, \ + (void (*)(void))ecdsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_FINAL, \ + (void (*)(void))ecdsa_verify_message_final }, \ + { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))ecdsa_freectx }, \ + { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))ecdsa_dupctx }, \ + { OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES, \ + (void (*)(void))ecdsa_sigalg_query_key_types }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))ecdsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))ecdsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))ecdsa_sigalg_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))ecdsa_sigalg_settable_ctx_params }, \ + OSSL_DISPATCH_END \ + } + +IMPL_ECDSA_SIGALG(sha1, SHA1); +IMPL_ECDSA_SIGALG(sha224, SHA2-224); +IMPL_ECDSA_SIGALG(sha256, SHA2-256); +IMPL_ECDSA_SIGALG(sha384, SHA2-384); +IMPL_ECDSA_SIGALG(sha512, SHA2-512); +IMPL_ECDSA_SIGALG(sha3_224, SHA3-224); +IMPL_ECDSA_SIGALG(sha3_256, SHA3-256); +IMPL_ECDSA_SIGALG(sha3_384, SHA3-384); +IMPL_ECDSA_SIGALG(sha3_512, SHA3-512); diff --git a/providers/implementations/signature/eddsa_sig.c b/providers/implementations/signature/eddsa_sig.c index 8594af39e1..e6689911c8 100644 --- a/providers/implementations/signature/eddsa_sig.c +++ b/providers/implementations/signature/eddsa_sig.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -18,6 +18,7 @@ #include "internal/sizes.h" #include "prov/providercommon.h" #include "prov/implementations.h" +#include "prov/securitycheck.h" #include "prov/provider_ctx.h" #include "prov/der_ecx.h" #include "crypto/ecx.h" @@ -62,17 +63,30 @@ enum ID_EdDSA_INSTANCE { #define EDDSA_PREHASH_OUTPUT_LEN 64 static OSSL_FUNC_signature_newctx_fn eddsa_newctx; -static OSSL_FUNC_signature_digest_sign_init_fn eddsa_digest_signverify_init; +static OSSL_FUNC_signature_sign_message_init_fn ed25519_signverify_message_init; +static OSSL_FUNC_signature_sign_message_init_fn ed25519ph_signverify_message_init; +static OSSL_FUNC_signature_sign_message_init_fn ed25519ctx_signverify_message_init; +static OSSL_FUNC_signature_sign_message_init_fn ed448_signverify_message_init; +static OSSL_FUNC_signature_sign_message_init_fn ed448ph_signverify_message_init; +static OSSL_FUNC_signature_sign_fn ed25519_sign; +static OSSL_FUNC_signature_sign_fn ed448_sign; +static OSSL_FUNC_signature_verify_fn ed25519_verify; +static OSSL_FUNC_signature_verify_fn ed448_verify; +static OSSL_FUNC_signature_digest_sign_init_fn ed25519_digest_signverify_init; +static OSSL_FUNC_signature_digest_sign_init_fn ed448_digest_signverify_init; static OSSL_FUNC_signature_digest_sign_fn ed25519_digest_sign; static OSSL_FUNC_signature_digest_sign_fn ed448_digest_sign; static OSSL_FUNC_signature_digest_verify_fn ed25519_digest_verify; static OSSL_FUNC_signature_digest_verify_fn ed448_digest_verify; static OSSL_FUNC_signature_freectx_fn eddsa_freectx; static OSSL_FUNC_signature_dupctx_fn eddsa_dupctx; +static OSSL_FUNC_signature_query_key_types_fn ed25519_sigalg_query_key_types; +static OSSL_FUNC_signature_query_key_types_fn ed448_sigalg_query_key_types; static OSSL_FUNC_signature_get_ctx_params_fn eddsa_get_ctx_params; static OSSL_FUNC_signature_gettable_ctx_params_fn eddsa_gettable_ctx_params; static OSSL_FUNC_signature_set_ctx_params_fn eddsa_set_ctx_params; static OSSL_FUNC_signature_settable_ctx_params_fn eddsa_settable_ctx_params; +static OSSL_FUNC_signature_settable_ctx_params_fn eddsa_settable_variant_ctx_params; /* there are five EdDSA instances: @@ -127,11 +141,14 @@ typedef struct { /* The Algorithm Identifier of the signature algorithm */ unsigned char aid_buf[OSSL_MAX_ALGORITHM_ID_SIZE]; - unsigned char *aid; size_t aid_len; /* id indicating the EdDSA instance */ int instance_id; + /* indicates that instance_id and associated flags are preset / hardcoded */ + unsigned int instance_id_preset_flag : 1; + /* for ph instances, this indicates whether the caller is expected to prehash */ + unsigned int prehash_by_caller_flag : 1; unsigned int dom2_flag : 1; unsigned int prehash_flag : 1; @@ -160,26 +177,68 @@ static void *eddsa_newctx(void *provctx, const char *propq_unused) return peddsactx; } -static int eddsa_digest_signverify_init(void *vpeddsactx, const char *mdname, - void *vedkey, - const OSSL_PARAM params[]) +static int eddsa_setup_instance(void *vpeddsactx, int instance_id, + unsigned int instance_id_preset, + unsigned int prehash_by_caller) +{ + PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; + + switch (instance_id) { + case ID_Ed25519: + if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) + return 0; + peddsactx->dom2_flag = 0; + peddsactx->prehash_flag = 0; + peddsactx->context_string_flag = 0; + break; + case ID_Ed25519ctx: + if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) + return 0; + peddsactx->dom2_flag = 1; + peddsactx->prehash_flag = 0; + peddsactx->context_string_flag = 1; + break; + case ID_Ed25519ph: + if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) + return 0; + peddsactx->dom2_flag = 1; + peddsactx->prehash_flag = 1; + peddsactx->context_string_flag = 0; + break; + case ID_Ed448: + if (peddsactx->key->type != ECX_KEY_TYPE_ED448) + return 0; + peddsactx->prehash_flag = 0; + peddsactx->context_string_flag = 0; + break; + case ID_Ed448ph: + if (peddsactx->key->type != ECX_KEY_TYPE_ED448) + return 0; + peddsactx->prehash_flag = 1; + peddsactx->context_string_flag = 0; + break; + default: + /* we did not recognize the instance */ + return 0; + } + peddsactx->instance_id = instance_id; + peddsactx->instance_id_preset_flag = instance_id_preset; + peddsactx->prehash_by_caller_flag = prehash_by_caller; + return 1; +} + +static int eddsa_signverify_init(void *vpeddsactx, void *vedkey) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; ECX_KEY *edkey = (ECX_KEY *)vedkey; WPACKET pkt; int ret; + unsigned char *aid = NULL; if (!ossl_prov_is_running()) return 0; - if (mdname != NULL && mdname[0] != '\0') { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST); - return 0; - } - if (edkey == NULL) { - if (peddsactx->key != NULL) - return eddsa_set_ctx_params(peddsactx, params); ERR_raise(ERR_LIB_PROV, PROV_R_NO_KEY_SET); return 0; } @@ -189,11 +248,14 @@ static int eddsa_digest_signverify_init(void *vpeddsactx, const char *mdname, return 0; } + peddsactx->instance_id_preset_flag = 0; peddsactx->dom2_flag = 0; peddsactx->prehash_flag = 0; peddsactx->context_string_flag = 0; peddsactx->context_string_len = 0; + peddsactx->key = edkey; + /* * We do not care about DER writing errors. * All it really means is that for some reason, there's no @@ -206,34 +268,118 @@ static int eddsa_digest_signverify_init(void *vpeddsactx, const char *mdname, switch (edkey->type) { case ECX_KEY_TYPE_ED25519: ret = ret && ossl_DER_w_algorithmIdentifier_ED25519(&pkt, -1, edkey); - peddsactx->instance_id = ID_Ed25519; break; case ECX_KEY_TYPE_ED448: ret = ret && ossl_DER_w_algorithmIdentifier_ED448(&pkt, -1, edkey); - peddsactx->instance_id = ID_Ed448; break; default: /* Should never happen */ ERR_raise(ERR_LIB_PROV, ERR_R_INTERNAL_ERROR); ossl_ecx_key_free(edkey); + peddsactx->key = NULL; return 0; } if (ret && WPACKET_finish(&pkt)) { WPACKET_get_total_written(&pkt, &peddsactx->aid_len); - peddsactx->aid = WPACKET_get_curr(&pkt); + aid = WPACKET_get_curr(&pkt); } WPACKET_cleanup(&pkt); + if (aid != NULL && peddsactx->aid_len != 0) + memmove(peddsactx->aid_buf, aid, peddsactx->aid_len); - peddsactx->key = edkey; + return 1; +} - if (!eddsa_set_ctx_params(peddsactx, params)) - return 0; +static int ed25519_signverify_message_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519, 1, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} - return 1; +static int ed25519ph_signverify_message_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519ph, 1, 0) + && eddsa_set_ctx_params(vpeddsactx, params); } -int ed25519_digest_sign(void *vpeddsactx, unsigned char *sigret, - size_t *siglen, size_t sigsize, +static int ed25519ph_signverify_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519ph, 1, 1) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +/* + * This supports using ED25519 with EVP_PKEY_{sign,verify}_init_ex() and + * EVP_PKEY_{sign,verify}_init_ex2(), under the condition that the caller + * explicitly sets the Ed25519ph instance (this is verified by ed25519_sign() + * and ed25519_verify()) + */ +static int ed25519_signverify_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519, 0, 1) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed25519ctx_signverify_message_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519ctx, 1, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed448_signverify_message_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed448, 1, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed448ph_signverify_message_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed448ph, 1, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed448ph_signverify_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed448ph, 1, 1) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +/* + * This supports using ED448 with EVP_PKEY_{sign,verify}_init_ex() and + * EVP_PKEY_{sign,verify}_init_ex2(), under the condition that the caller + * explicitly sets the Ed448ph instance (this is verified by ed448_sign() + * and ed448_verify()) + */ +static int ed448_signverify_init(void *vpeddsactx, void *vedkey, + const OSSL_PARAM params[]) +{ + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed448, 0, 1) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +/* + * This is used directly for OSSL_FUNC_SIGNATURE_SIGN and indirectly + * for OSSL_FUNC_SIGNATURE_DIGEST_SIGN + */ +static int ed25519_sign(void *vpeddsactx, + unsigned char *sigret, size_t *siglen, size_t sigsize, const unsigned char *tbs, size_t tbslen) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; @@ -257,12 +403,17 @@ int ed25519_digest_sign(void *vpeddsactx, unsigned char *sigret, return 0; } #ifdef S390X_EC_ASM - /* s390x_ed25519_digestsign() does not yet support dom2 or context-strings. - fall back to non-accelerated sign if those options are set. */ + /* + * s390x_ed25519_digestsign() does not yet support dom2 or context-strings. + * fall back to non-accelerated sign if those options are set, or pre-hasing + * is provided. + */ if (S390X_CAN_SIGN(ED25519) && !peddsactx->dom2_flag && !peddsactx->context_string_flag - && peddsactx->context_string_len == 0) { + && peddsactx->context_string_len == 0 + && !peddsactx->prehash_flag + && !peddsactx->prehash_by_caller_flag) { if (s390x_ed25519_digestsign(edkey, sigret, tbs, tbslen) == 0) { ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SIGN); return 0; @@ -273,11 +424,24 @@ int ed25519_digest_sign(void *vpeddsactx, unsigned char *sigret, #endif /* S390X_EC_ASM */ if (peddsactx->prehash_flag) { - if (!EVP_Q_digest(peddsactx->libctx, SN_sha512, NULL, tbs, tbslen, md, &mdlen) - || mdlen != EDDSA_PREHASH_OUTPUT_LEN) + if (!peddsactx->prehash_by_caller_flag) { + if (!EVP_Q_digest(peddsactx->libctx, SN_sha512, NULL, + tbs, tbslen, md, &mdlen) + || mdlen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_PREHASHED_DIGEST_LENGTH); + return 0; + } + tbs = md; + tbslen = mdlen; + } else if (tbslen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); return 0; - tbs = md; - tbslen = mdlen; + } + } else if (peddsactx->prehash_by_caller_flag) { + /* The caller is supposed to set up a ph instance! */ + ERR_raise(ERR_LIB_PROV, + PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION); + return 0; } if (ossl_ed25519_sign(sigret, tbs, tbslen, edkey->pubkey, edkey->privkey, @@ -318,8 +482,12 @@ static int ed448_shake256(OSSL_LIB_CTX *libctx, return ret; } -int ed448_digest_sign(void *vpeddsactx, unsigned char *sigret, - size_t *siglen, size_t sigsize, +/* + * This is used directly for OSSL_FUNC_SIGNATURE_SIGN and indirectly + * for OSSL_FUNC_SIGNATURE_DIGEST_SIGN + */ +static int ed448_sign(void *vpeddsactx, + unsigned char *sigret, size_t *siglen, size_t sigsize, const unsigned char *tbs, size_t tbslen) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; @@ -343,11 +511,15 @@ int ed448_digest_sign(void *vpeddsactx, unsigned char *sigret, return 0; } #ifdef S390X_EC_ASM - /* s390x_ed448_digestsign() does not yet support context-strings or pre-hashing. - fall back to non-accelerated sign if a context-string or pre-hasing is provided. */ + /* + * s390x_ed448_digestsign() does not yet support context-strings or + * pre-hashing. Fall back to non-accelerated sign if a context-string or + * pre-hasing is provided. + */ if (S390X_CAN_SIGN(ED448) && peddsactx->context_string_len == 0 - && peddsactx->prehash_flag == 0) { + && !peddsactx->prehash_flag + && !peddsactx->prehash_by_caller_flag) { if (s390x_ed448_digestsign(edkey, sigret, tbs, tbslen) == 0) { ERR_raise(ERR_LIB_PROV, PROV_R_FAILED_TO_SIGN); return 0; @@ -358,10 +530,20 @@ int ed448_digest_sign(void *vpeddsactx, unsigned char *sigret, #endif /* S390X_EC_ASM */ if (peddsactx->prehash_flag) { - if (!ed448_shake256(peddsactx->libctx, NULL, tbs, tbslen, md, mdlen)) + if (!peddsactx->prehash_by_caller_flag) { + if (!ed448_shake256(peddsactx->libctx, NULL, tbs, tbslen, md, mdlen)) + return 0; + tbs = md; + tbslen = mdlen; + } else if (tbslen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); return 0; - tbs = md; - tbslen = mdlen; + } + } else if (peddsactx->prehash_by_caller_flag) { + /* The caller is supposed to set up a ph instance! */ + ERR_raise(ERR_LIB_PROV, + PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION); + return 0; } if (ossl_ed448_sign(peddsactx->libctx, sigret, tbs, tbslen, @@ -375,9 +557,13 @@ int ed448_digest_sign(void *vpeddsactx, unsigned char *sigret, return 1; } -int ed25519_digest_verify(void *vpeddsactx, const unsigned char *sig, - size_t siglen, const unsigned char *tbs, - size_t tbslen) +/* + * This is used directly for OSSL_FUNC_SIGNATURE_VERIFY and indirectly + * for OSSL_FUNC_SIGNATURE_DIGEST_VERIFY + */ +static int ed25519_verify(void *vpeddsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; const ECX_KEY *edkey = peddsactx->key; @@ -388,22 +574,39 @@ int ed25519_digest_verify(void *vpeddsactx, const unsigned char *sig, return 0; #ifdef S390X_EC_ASM - /* s390x_ed25519_digestverify() does not yet support dom2 or context-strings. - fall back to non-accelerated verify if those options are set. */ + /* + * s390x_ed25519_digestverify() does not yet support dom2 or context-strings. + * fall back to non-accelerated verify if those options are set, or + * pre-hasing is provided. + */ if (S390X_CAN_SIGN(ED25519) && !peddsactx->dom2_flag && !peddsactx->context_string_flag - && peddsactx->context_string_len == 0) { + && peddsactx->context_string_len == 0 + && !peddsactx->prehash_flag + && !peddsactx->prehash_by_caller_flag) return s390x_ed25519_digestverify(edkey, sig, tbs, tbslen); - } #endif /* S390X_EC_ASM */ if (peddsactx->prehash_flag) { - if (!EVP_Q_digest(peddsactx->libctx, SN_sha512, NULL, tbs, tbslen, md, &mdlen) - || mdlen != EDDSA_PREHASH_OUTPUT_LEN) + if (!peddsactx->prehash_by_caller_flag) { + if (!EVP_Q_digest(peddsactx->libctx, SN_sha512, NULL, + tbs, tbslen, md, &mdlen) + || mdlen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_PREHASHED_DIGEST_LENGTH); + return 0; + } + tbs = md; + tbslen = mdlen; + } else if (tbslen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); return 0; - tbs = md; - tbslen = mdlen; + } + } else if (peddsactx->prehash_by_caller_flag) { + /* The caller is supposed to set up a ph instance! */ + ERR_raise(ERR_LIB_PROV, + PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION); + return 0; } return ossl_ed25519_verify(tbs, tbslen, sig, edkey->pubkey, @@ -412,9 +615,13 @@ int ed25519_digest_verify(void *vpeddsactx, const unsigned char *sig, peddsactx->libctx, edkey->propq); } -int ed448_digest_verify(void *vpeddsactx, const unsigned char *sig, - size_t siglen, const unsigned char *tbs, - size_t tbslen) +/* + * This is used directly for OSSL_FUNC_SIGNATURE_VERIFY and indirectly + * for OSSL_FUNC_SIGNATURE_DIGEST_VERIFY + */ +static int ed448_verify(void *vpeddsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; const ECX_KEY *edkey = peddsactx->key; @@ -425,20 +632,33 @@ int ed448_digest_verify(void *vpeddsactx, const unsigned char *sig, return 0; #ifdef S390X_EC_ASM - /* s390x_ed448_digestverify() does not yet support context-strings or pre-hashing. - fall back to non-accelerated verify if a context-string or pre-hasing is provided. */ + /* + * s390x_ed448_digestverify() does not yet support context-strings or + * pre-hashing. Fall back to non-accelerated verify if a context-string or + * pre-hasing is provided. + */ if (S390X_CAN_SIGN(ED448) && peddsactx->context_string_len == 0 - && peddsactx->prehash_flag == 0) { + && !peddsactx->prehash_flag + && !peddsactx->prehash_by_caller_flag) return s390x_ed448_digestverify(edkey, sig, tbs, tbslen); - } #endif /* S390X_EC_ASM */ if (peddsactx->prehash_flag) { - if (!ed448_shake256(peddsactx->libctx, NULL, tbs, tbslen, md, mdlen)) + if (!peddsactx->prehash_by_caller_flag) { + if (!ed448_shake256(peddsactx->libctx, NULL, tbs, tbslen, md, mdlen)) + return 0; + tbs = md; + tbslen = mdlen; + } else if (tbslen != EDDSA_PREHASH_OUTPUT_LEN) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_DIGEST_LENGTH); return 0; - tbs = md; - tbslen = mdlen; + } + } else if (peddsactx->prehash_by_caller_flag) { + /* The caller is supposed to set up a ph instance! */ + ERR_raise(ERR_LIB_PROV, + PROV_R_INVALID_EDDSA_INSTANCE_FOR_ATTEMPTED_OPERATION); + return 0; } return ossl_ed448_verify(peddsactx->libctx, tbs, tbslen, sig, edkey->pubkey, @@ -446,6 +666,76 @@ int ed448_digest_verify(void *vpeddsactx, const unsigned char *sig, peddsactx->prehash_flag, edkey->propq); } +/* All digest_{sign,verify} are simple wrappers around the functions above */ + +static int ed25519_digest_signverify_init(void *vpeddsactx, const char *mdname, + void *vedkey, + const OSSL_PARAM params[]) +{ + PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; + + if (mdname != NULL && mdname[0] != '\0') { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "Explicit digest not allowed with EdDSA operations"); + return 0; + } + + if (vedkey == NULL && peddsactx->key != NULL) + return eddsa_set_ctx_params(peddsactx, params); + + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed25519, 0, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed25519_digest_sign(void *vpeddsactx, + unsigned char *sigret, size_t *siglen, size_t sigsize, + const unsigned char *tbs, size_t tbslen) +{ + return ed25519_sign(vpeddsactx, sigret, siglen, sigsize, tbs, tbslen); +} + +static int ed25519_digest_verify(void *vpeddsactx, + const unsigned char *sigret, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + return ed25519_verify(vpeddsactx, sigret, siglen, tbs, tbslen); +} + +static int ed448_digest_signverify_init(void *vpeddsactx, const char *mdname, + void *vedkey, + const OSSL_PARAM params[]) +{ + PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; + + if (mdname != NULL && mdname[0] != '\0') { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "Explicit digest not allowed with EdDSA operations"); + return 0; + } + + if (vedkey == NULL && peddsactx->key != NULL) + return eddsa_set_ctx_params(peddsactx, params); + + return eddsa_signverify_init(vpeddsactx, vedkey) + && eddsa_setup_instance(vpeddsactx, ID_Ed448, 0, 0) + && eddsa_set_ctx_params(vpeddsactx, params); +} + +static int ed448_digest_sign(void *vpeddsactx, + unsigned char *sigret, size_t *siglen, size_t sigsize, + const unsigned char *tbs, size_t tbslen) +{ + return ed448_sign(vpeddsactx, sigret, siglen, sigsize, tbs, tbslen); +} + +static int ed448_digest_verify(void *vpeddsactx, + const unsigned char *sigret, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + return ed448_verify(vpeddsactx, sigret, siglen, tbs, tbslen); +} + static void eddsa_freectx(void *vpeddsactx) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; @@ -482,6 +772,22 @@ static void *eddsa_dupctx(void *vpeddsactx) return NULL; } +static const char **ed25519_sigalg_query_key_types(void) +{ + static const char *keytypes[] = { "ED25519", NULL }; + + return keytypes; +} + +static const char **ed448_sigalg_query_key_types(void) +{ + static const char *keytypes[] = { "ED448", NULL }; + + return keytypes; +} + + + static int eddsa_get_ctx_params(void *vpeddsactx, OSSL_PARAM *params) { PROV_EDDSA_CTX *peddsactx = (PROV_EDDSA_CTX *)vpeddsactx; @@ -491,8 +797,10 @@ static int eddsa_get_ctx_params(void *vpeddsactx, OSSL_PARAM *params) return 0; p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_ALGORITHM_ID); - if (p != NULL && !OSSL_PARAM_set_octet_string(p, peddsactx->aid, - peddsactx->aid_len)) + if (p != NULL + && !OSSL_PARAM_set_octet_string(p, + peddsactx->aid_len == 0 ? NULL : peddsactx->aid_buf, + peddsactx->aid_len)) return 0; return 1; @@ -526,37 +834,38 @@ static int eddsa_set_ctx_params(void *vpeddsactx, const OSSL_PARAM params[]) char instance_name[OSSL_MAX_NAME_SIZE] = ""; char *pinstance_name = instance_name; + if (peddsactx->instance_id_preset_flag) { + /* When the instance is preset, the caller must no try to set it */ + ERR_raise_data(ERR_LIB_PROV, PROV_R_NO_INSTANCE_ALLOWED, + "the EdDSA instance is preset, you may not try to specify it", + NULL); + return 0; + } + if (!OSSL_PARAM_get_utf8_string(p, &pinstance_name, sizeof(instance_name))) return 0; + /* + * When setting the new instance, we're careful not to change the + * prehash_by_caller flag, as that's always preset by the init + * functions. The sign functions will determine if the instance + * matches this flag. + */ if (OPENSSL_strcasecmp(pinstance_name, SN_Ed25519) == 0) { - peddsactx->instance_id = ID_Ed25519; - if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) return 0; - peddsactx->dom2_flag = 0; - peddsactx->prehash_flag = 0; - peddsactx->context_string_flag = 0; + eddsa_setup_instance(peddsactx, ID_Ed25519, 0, + peddsactx->prehash_by_caller_flag); } else if (OPENSSL_strcasecmp(pinstance_name, SN_Ed25519ctx) == 0) { - peddsactx->instance_id = ID_Ed25519ctx; - if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) return 0; - peddsactx->dom2_flag = 1; - peddsactx->prehash_flag = 0; - peddsactx->context_string_flag = 1; + eddsa_setup_instance(peddsactx, ID_Ed25519ctx, 0, + peddsactx->prehash_by_caller_flag); } else if (OPENSSL_strcasecmp(pinstance_name, SN_Ed25519ph) == 0) { - peddsactx->instance_id = ID_Ed25519ph; - if (peddsactx->key->type != ECX_KEY_TYPE_ED25519) return 0; - peddsactx->dom2_flag = 1; - peddsactx->prehash_flag = 1; - peddsactx->context_string_flag = 0; + eddsa_setup_instance(peddsactx, ID_Ed25519ph, 0, + peddsactx->prehash_by_caller_flag); } else if (OPENSSL_strcasecmp(pinstance_name, SN_Ed448) == 0) { - peddsactx->instance_id = ID_Ed448; - if (peddsactx->key->type != ECX_KEY_TYPE_ED448) return 0; - peddsactx->prehash_flag = 0; - peddsactx->context_string_flag = 0; + eddsa_setup_instance(peddsactx, ID_Ed448, 0, + peddsactx->prehash_by_caller_flag); } else if (OPENSSL_strcasecmp(pinstance_name, SN_Ed448ph) == 0) { - peddsactx->instance_id = ID_Ed448ph; - if (peddsactx->key->type != ECX_KEY_TYPE_ED448) return 0; - peddsactx->prehash_flag = 1; - peddsactx->context_string_flag = 0; + eddsa_setup_instance(peddsactx, ID_Ed448ph, 0, + peddsactx->prehash_by_caller_flag); } else { /* we did not recognize the instance */ return 0; @@ -589,47 +898,149 @@ static const OSSL_PARAM *eddsa_settable_ctx_params(ossl_unused void *vpeddsactx, return settable_ctx_params; } -const OSSL_DISPATCH ossl_ed25519_signature_functions[] = { - { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))eddsa_newctx }, - { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT, - (void (*)(void))eddsa_digest_signverify_init }, - { OSSL_FUNC_SIGNATURE_DIGEST_SIGN, - (void (*)(void))ed25519_digest_sign }, - { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_INIT, - (void (*)(void))eddsa_digest_signverify_init }, - { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY, - (void (*)(void))ed25519_digest_verify }, - { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))eddsa_freectx }, - { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))eddsa_dupctx }, - { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, (void (*)(void))eddsa_get_ctx_params }, - { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, - (void (*)(void))eddsa_gettable_ctx_params }, - { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, (void (*)(void))eddsa_set_ctx_params }, - { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, - (void (*)(void))eddsa_settable_ctx_params }, - OSSL_DISPATCH_END +static const OSSL_PARAM settable_variant_ctx_params[] = { + OSSL_PARAM_octet_string(OSSL_SIGNATURE_PARAM_CONTEXT_STRING, NULL, 0), + OSSL_PARAM_END }; -const OSSL_DISPATCH ossl_ed448_signature_functions[] = { - { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))eddsa_newctx }, - { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT, - (void (*)(void))eddsa_digest_signverify_init }, - { OSSL_FUNC_SIGNATURE_DIGEST_SIGN, - (void (*)(void))ed448_digest_sign }, - { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_INIT, - (void (*)(void))eddsa_digest_signverify_init }, - { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY, - (void (*)(void))ed448_digest_verify }, - { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))eddsa_freectx }, - { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))eddsa_dupctx }, - { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, (void (*)(void))eddsa_get_ctx_params }, - { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, - (void (*)(void))eddsa_gettable_ctx_params }, - { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, (void (*)(void))eddsa_set_ctx_params }, - { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, - (void (*)(void))eddsa_settable_ctx_params }, +static const OSSL_PARAM * +eddsa_settable_variant_ctx_params(ossl_unused void *vpeddsactx, + ossl_unused void *provctx) +{ + return settable_variant_ctx_params; +} + +/* + * Ed25519 can be used with: + * - EVP_PKEY_sign_init_ex2() [ instance and prehash assumed done by caller ] + * - EVP_PKEY_verify_init_ex2() [ instance and prehash assumed done by caller ] + * - EVP_PKEY_sign_message_init() + * - EVP_PKEY_verify_message_init() + * - EVP_DigestSignInit_ex() + * - EVP_DigestVerifyInit_ex() + * Ed25519ph can be used with: + * - EVP_PKEY_sign_init_ex2() [ prehash assumed done by caller ] + * - EVP_PKEY_verify_init_ex2() [ prehash assumed done by caller ] + * - EVP_PKEY_sign_message_init() + * - EVP_PKEY_verify_message_init() + * Ed25519ctx can be used with: + * - EVP_PKEY_sign_message_init() + * - EVP_PKEY_verify_message_init() + * Ed448 can be used with: + * - EVP_PKEY_sign_init_ex2() [ instance and prehash assumed done by caller ] + * - EVP_PKEY_verify_init_ex2() [ instance and prehash assumed done by caller ] + * - EVP_PKEY_sign_message_init() + * - EVP_PKEY_verify_message_init() + * - EVP_DigestSignInit_ex() + * - EVP_DigestVerifyInit_ex() + * Ed448ph can be used with: + * - EVP_PKEY_sign_init_ex2() [ prehash assumed done by caller ] + * - EVP_PKEY_verify_init_ex2() [ prehash assumed done by caller ] + * - EVP_PKEY_sign_message_init() + * - EVP_PKEY_verify_message_init() + */ + +#define ed25519_DISPATCH_END \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))ed25519_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))ed25519_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT, \ + (void (*)(void))ed25519_digest_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_SIGN, \ + (void (*)(void))ed25519_digest_sign }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_INIT, \ + (void (*)(void))ed25519_digest_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY, \ + (void (*)(void))ed25519_digest_verify }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))eddsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))eddsa_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_settable_ctx_params }, \ OSSL_DISPATCH_END -}; + +#define eddsa_variant_DISPATCH_END(v) \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))v##_signverify_message_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))v##_signverify_message_init }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))eddsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))eddsa_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_settable_variant_ctx_params }, \ + OSSL_DISPATCH_END + +#define ed25519ph_DISPATCH_END \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))ed25519ph_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))ed25519ph_signverify_init }, \ + eddsa_variant_DISPATCH_END(ed25519ph) + +#define ed25519ctx_DISPATCH_END eddsa_variant_DISPATCH_END(ed25519ctx) + +#define ed448_DISPATCH_END \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))ed448_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))ed448_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT, \ + (void (*)(void))ed448_digest_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_SIGN, \ + (void (*)(void))ed448_digest_sign }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_INIT, \ + (void (*)(void))ed448_digest_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY, \ + (void (*)(void))ed448_digest_verify }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))eddsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))eddsa_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))eddsa_settable_ctx_params }, \ + OSSL_DISPATCH_END + +#define ed448ph_DISPATCH_END \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))ed448ph_signverify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))ed448ph_signverify_init }, \ + eddsa_variant_DISPATCH_END(ed448ph) + +/* vn = variant name, bn = base name */ +#define IMPL_EDDSA_DISPATCH(vn,bn) \ + const OSSL_DISPATCH ossl_##vn##_signature_functions[] = { \ + { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))eddsa_newctx }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT, \ + (void (*)(void))vn##_signverify_message_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN, \ + (void (*)(void))bn##_sign }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT, \ + (void (*)(void))vn##_signverify_message_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY, \ + (void (*)(void))bn##_verify }, \ + { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))eddsa_freectx }, \ + { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))eddsa_dupctx }, \ + { OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES, \ + (void (*)(void))bn##_sigalg_query_key_types }, \ + vn##_DISPATCH_END \ + } + +IMPL_EDDSA_DISPATCH(ed25519,ed25519); +IMPL_EDDSA_DISPATCH(ed25519ph,ed25519); +IMPL_EDDSA_DISPATCH(ed25519ctx,ed25519); +IMPL_EDDSA_DISPATCH(ed448,ed448); +IMPL_EDDSA_DISPATCH(ed448ph,ed448); #ifdef S390X_EC_ASM diff --git a/providers/implementations/signature/rsa_sig.c b/providers/implementations/signature/rsa_sig.c index f98fb61ce3..d11b8dc345 100644 --- a/providers/implementations/signature/rsa_sig.c +++ b/providers/implementations/signature/rsa_sig.c @@ -18,6 +18,7 @@ #include #include #include +#include #include #include #include @@ -39,16 +40,21 @@ static OSSL_FUNC_signature_sign_init_fn rsa_sign_init; static OSSL_FUNC_signature_verify_init_fn rsa_verify_init; static OSSL_FUNC_signature_verify_recover_init_fn rsa_verify_recover_init; static OSSL_FUNC_signature_sign_fn rsa_sign; +static OSSL_FUNC_signature_sign_message_update_fn rsa_signverify_message_update; +static OSSL_FUNC_signature_sign_message_final_fn rsa_sign_message_final; static OSSL_FUNC_signature_verify_fn rsa_verify; static OSSL_FUNC_signature_verify_recover_fn rsa_verify_recover; +static OSSL_FUNC_signature_verify_message_update_fn rsa_signverify_message_update; +static OSSL_FUNC_signature_verify_message_final_fn rsa_verify_message_final; static OSSL_FUNC_signature_digest_sign_init_fn rsa_digest_sign_init; -static OSSL_FUNC_signature_digest_sign_update_fn rsa_digest_signverify_update; +static OSSL_FUNC_signature_digest_sign_update_fn rsa_digest_sign_update; static OSSL_FUNC_signature_digest_sign_final_fn rsa_digest_sign_final; static OSSL_FUNC_signature_digest_verify_init_fn rsa_digest_verify_init; -static OSSL_FUNC_signature_digest_verify_update_fn rsa_digest_signverify_update; +static OSSL_FUNC_signature_digest_verify_update_fn rsa_digest_verify_update; static OSSL_FUNC_signature_digest_verify_final_fn rsa_digest_verify_final; static OSSL_FUNC_signature_freectx_fn rsa_freectx; static OSSL_FUNC_signature_dupctx_fn rsa_dupctx; +static OSSL_FUNC_signature_query_key_types_fn rsa_sigalg_query_key_types; static OSSL_FUNC_signature_get_ctx_params_fn rsa_get_ctx_params; static OSSL_FUNC_signature_gettable_ctx_params_fn rsa_gettable_ctx_params; static OSSL_FUNC_signature_set_ctx_params_fn rsa_set_ctx_params; @@ -57,6 +63,8 @@ static OSSL_FUNC_signature_get_ctx_md_params_fn rsa_get_ctx_md_params; static OSSL_FUNC_signature_gettable_ctx_md_params_fn rsa_gettable_ctx_md_params; static OSSL_FUNC_signature_set_ctx_md_params_fn rsa_set_ctx_md_params; static OSSL_FUNC_signature_settable_ctx_md_params_fn rsa_settable_ctx_md_params; +static OSSL_FUNC_signature_set_ctx_params_fn rsa_sigalg_set_ctx_params; +static OSSL_FUNC_signature_settable_ctx_params_fn rsa_sigalg_settable_ctx_params; static OSSL_ITEM padding_item[] = { { RSA_PKCS1_PADDING, OSSL_PKEY_RSA_PAD_MODE_PKCSV15 }, @@ -78,14 +86,40 @@ typedef struct { RSA *rsa; int operation; + /* + * Flag to determine if a full sigalg is run (1) or if a composable + * signature algorithm is run (0). + * + * When a full sigalg is run (1), this currently affects the following + * other flags, which are to remain untouched after their initialization: + * + * - flag_allow_md (initialized to 0) + */ + unsigned int flag_sigalg : 1; /* * Flag to determine if the hash function can be changed (1) or not (0) * Because it's dangerous to change during a DigestSign or DigestVerify * operation, this flag is cleared by their Init function, and set again * by their Final function. + * Implementations of full sigalgs (such as RSA-SHA256) hard-code this + * flag to not allow changes (0). */ unsigned int flag_allow_md : 1; unsigned int mgf1_md_set : 1; + /* + * Flags to say what are the possible next external calls in what + * consitutes the life cycle of an algorithm. The relevant calls are: + * - init + * - update + * - final + * - oneshot + * All other external calls are regarded as utilitarian and are allowed + * at any time (they may be affected by other flags, like flag_allow_md, + * though). + */ + unsigned int flag_allow_update : 1; + unsigned int flag_allow_final : 1; + unsigned int flag_allow_oneshot : 1; /* main digest */ EVP_MD *md; @@ -104,9 +138,23 @@ typedef struct { /* Minimum salt length or -1 if no PSS parameter restriction */ int min_saltlen; + /* Signature, for verification */ + unsigned char *sig; + size_t siglen; + +#ifdef FIPS_MODULE + /* + * FIPS 140-3 IG 2.4.B mandates that verification based on a digest of a + * message is not permitted. However, signing based on a digest is still + * permitted. + */ + int verify_message; +#endif + /* Temp buffer */ unsigned char *tbuf; + OSSL_FIPS_IND_DECLARE } PROV_RSA_CTX; /* True if PSS parameters are restricted */ @@ -114,8 +162,14 @@ typedef struct { static size_t rsa_get_md_size(const PROV_RSA_CTX *prsactx) { - if (prsactx->md != NULL) - return EVP_MD_get_size(prsactx->md); + int md_size; + + if (prsactx->md != NULL) { + md_size = EVP_MD_get_size(prsactx->md); + if (md_size <= 0) + return 0; + return md_size; + } return 0; } @@ -124,29 +178,29 @@ static int rsa_check_padding(const PROV_RSA_CTX *prsactx, int mdnid) { switch (prsactx->pad_mode) { - case RSA_NO_PADDING: - if (mdname != NULL || mdnid != NID_undef) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_PADDING_MODE); - return 0; - } - break; - case RSA_X931_PADDING: - if (RSA_X931_hash_id(mdnid) == -1) { - ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_X931_DIGEST); + case RSA_NO_PADDING: + if (mdname != NULL || mdnid != NID_undef) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_PADDING_MODE); + return 0; + } + break; + case RSA_X931_PADDING: + if (RSA_X931_hash_id(mdnid) == -1) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_X931_DIGEST); + return 0; + } + break; + case RSA_PKCS1_PSS_PADDING: + if (rsa_pss_restricted(prsactx)) + if ((mdname != NULL && !EVP_MD_is_a(prsactx->md, mdname)) + || (mgf1_mdname != NULL + && !EVP_MD_is_a(prsactx->mgf1_md, mgf1_mdname))) { + ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); return 0; } - break; - case RSA_PKCS1_PSS_PADDING: - if (rsa_pss_restricted(prsactx)) - if ((mdname != NULL && !EVP_MD_is_a(prsactx->md, mdname)) - || (mgf1_mdname != NULL - && !EVP_MD_is_a(prsactx->mgf1_md, mgf1_mdname))) { - ERR_raise(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED); - return 0; - } - break; - default: - break; + break; + default: + break; } return 1; @@ -185,8 +239,12 @@ static void *rsa_newctx(void *provctx, const char *propq) return NULL; } + OSSL_FIPS_IND_INIT(prsactx) prsactx->libctx = PROV_LIBCTX_OF(provctx); prsactx->flag_allow_md = 1; +#ifdef FIPS_MODULE + prsactx->verify_message = 1; +#endif prsactx->propq = propq_copy; /* Maximum up to digest length for sign, auto for verify */ prsactx->saltlen = RSA_PSS_SALTLEN_AUTO_DIGEST_MAX; @@ -310,41 +368,68 @@ static unsigned char *rsa_generate_signature_aid(PROV_RSA_CTX *ctx, } static int rsa_setup_md(PROV_RSA_CTX *ctx, const char *mdname, - const char *mdprops) + const char *mdprops, const char *desc) { + EVP_MD *md = NULL; + if (mdprops == NULL) mdprops = ctx->propq; if (mdname != NULL) { - EVP_MD *md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); - int sha1_allowed = (ctx->operation != EVP_PKEY_OP_SIGN); - int md_nid = ossl_digest_rsa_sign_get_md_nid(ctx->libctx, md, - sha1_allowed); + int md_nid; size_t mdname_len = strlen(mdname); - if (md == NULL - || md_nid <= 0 - || !rsa_check_padding(ctx, mdname, NULL, md_nid) - || mdname_len >= sizeof(ctx->mdname)) { - if (md == NULL) - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, - "%s could not be fetched", mdname); - if (md_nid <= 0) - ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, - "digest=%s", mdname); - if (mdname_len >= sizeof(ctx->mdname)) - ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, - "%s exceeds name buffer length", mdname); - EVP_MD_free(md); - return 0; + md = EVP_MD_fetch(ctx->libctx, mdname, mdprops); + + if (md == NULL) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "%s could not be fetched", mdname); + goto err; + } + md_nid = ossl_digest_rsa_sign_get_md_nid(md); + if (md_nid == NID_undef) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, + "digest=%s", mdname); + goto err; + } + /* + * XOF digests are not allowed except for RSA PSS. + * We don't support XOF digests with RSA PSS (yet), so just fail. + * When we do support them, uncomment the second clause. + */ + if (EVP_MD_xof(md) + /* && ctx->pad_mode != RSA_PKCS1_PSS_PADDING */) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + goto err; + } +#ifdef FIPS_MODULE + { + int sha1_allowed + = ((ctx->operation + & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG)) == 0); + + if (!ossl_fips_ind_digest_sign_check(OSSL_FIPS_IND_GET(ctx), + OSSL_FIPS_IND_SETTABLE1, + ctx->libctx, + md_nid, sha1_allowed, desc, + ossl_fips_config_signature_digest_check)) + goto err; + } +#endif + + if (!rsa_check_padding(ctx, mdname, NULL, md_nid)) + goto err; + if (mdname_len >= sizeof(ctx->mdname)) { + ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_DIGEST, + "%s exceeds name buffer length", mdname); + goto err; } if (!ctx->flag_allow_md) { if (ctx->mdname[0] != '\0' && !EVP_MD_is_a(md, ctx->mdname)) { ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, "digest %s != %s", mdname, ctx->mdname); - EVP_MD_free(md); - return 0; + goto err; } EVP_MD_free(md); return 1; @@ -352,8 +437,7 @@ static int rsa_setup_md(PROV_RSA_CTX *ctx, const char *mdname, if (!ctx->mgf1_md_set) { if (!EVP_MD_up_ref(md)) { - EVP_MD_free(md); - return 0; + goto err; } EVP_MD_free(ctx->mgf1_md); ctx->mgf1_md = md; @@ -371,6 +455,9 @@ static int rsa_setup_md(PROV_RSA_CTX *ctx, const char *mdname, } return 1; +err: + EVP_MD_free(md); + return 0; } static int rsa_setup_mgf1_md(PROV_RSA_CTX *ctx, const char *mdname, @@ -389,7 +476,7 @@ static int rsa_setup_mgf1_md(PROV_RSA_CTX *ctx, const char *mdname, return 0; } /* The default for mgf1 is SHA1 - so allow SHA1 */ - if ((mdnid = ossl_digest_rsa_sign_get_md_nid(ctx->libctx, md, 1)) <= 0 + if ((mdnid = ossl_digest_rsa_sign_get_md_nid(md)) <= 0 || !rsa_check_padding(ctx, NULL, mdname, mdnid)) { if (mdnid <= 0) ERR_raise_data(ERR_LIB_PROV, PROV_R_DIGEST_NOT_ALLOWED, @@ -412,10 +499,13 @@ static int rsa_setup_mgf1_md(PROV_RSA_CTX *ctx, const char *mdname, return 1; } -static int rsa_signverify_init(void *vprsactx, void *vrsa, - const OSSL_PARAM params[], int operation) +static int +rsa_signverify_init(PROV_RSA_CTX *prsactx, void *vrsa, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], int operation, + const char *desc) { - PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + int protect; if (!ossl_prov_is_running() || prsactx == NULL) return 0; @@ -426,16 +516,18 @@ static int rsa_signverify_init(void *vprsactx, void *vrsa, } if (vrsa != NULL) { - if (!ossl_rsa_check_key(prsactx->libctx, vrsa, operation)) - return 0; - if (!RSA_up_ref(vrsa)) return 0; RSA_free(prsactx->rsa); prsactx->rsa = vrsa; } + if (!ossl_rsa_key_op_get_protect(prsactx->rsa, operation, &protect)) + return 0; prsactx->operation = operation; + prsactx->flag_allow_update = 1; + prsactx->flag_allow_final = 1; + prsactx->flag_allow_oneshot = 1; /* Maximize up to digest length for sign, auto for verify */ prsactx->saltlen = RSA_PSS_SALTLEN_AUTO_DIGEST_MAX; @@ -491,7 +583,7 @@ static int rsa_signverify_init(void *vprsactx, void *vrsa, /* call rsa_setup_mgf1_md before rsa_setup_md to avoid duplication */ if (!rsa_setup_mgf1_md(prsactx, mgf1mdname, prsactx->propq) - || !rsa_setup_md(prsactx, mdname, prsactx->propq) + || !rsa_setup_md(prsactx, mdname, prsactx->propq, desc) || !rsa_check_parameters(prsactx, min_saltlen)) return 0; } @@ -503,9 +595,15 @@ static int rsa_signverify_init(void *vprsactx, void *vrsa, return 0; } - if (!rsa_set_ctx_params(prsactx, params)) + OSSL_FIPS_IND_SET_APPROVED(prsactx) + if (!set_ctx_params(prsactx, params)) return 0; - +#ifdef FIPS_MODULE + if (!ossl_fips_ind_rsa_key_check(OSSL_FIPS_IND_GET(prsactx), + OSSL_FIPS_IND_SETTABLE0, prsactx->libctx, + prsactx->rsa, desc, protect)) + return 0; +#endif return 1; } @@ -531,17 +629,54 @@ static void free_tbuf(PROV_RSA_CTX *ctx) ctx->tbuf = NULL; } -static int rsa_sign_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) +#ifdef FIPS_MODULE +static int rsa_pss_saltlen_check_passed(PROV_RSA_CTX *ctx, const char *algoname, int saltlen) { - if (!ossl_prov_is_running()) - return 0; - return rsa_signverify_init(vprsactx, vrsa, params, EVP_PKEY_OP_SIGN); + int mdsize = rsa_get_md_size(ctx); + /* + * Perform the check if the salt length is compliant to FIPS 186-5. + * + * According to FIPS 186-5 5.4 (g), the salt length shall be between zero + * and the output block length of the digest function (inclusive). + */ + int approved = (saltlen >= 0 && saltlen <= mdsize); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE3, + ctx->libctx, + algoname, "PSS Salt Length", + ossl_fips_config_rsa_pss_saltlen_check)) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_SALT_LENGTH); + return 0; + } + } + + return 1; } +#endif -static int rsa_sign(void *vprsactx, unsigned char *sig, size_t *siglen, - size_t sigsize, const unsigned char *tbs, size_t tbslen) +static int rsa_sign_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + +#ifdef FIPS_MODULE + if (prsactx != NULL) + prsactx->verify_message = 1; +#endif + + return rsa_signverify_init(prsactx, vrsa, rsa_set_ctx_params, params, + EVP_PKEY_OP_SIGN, "RSA Sign Init"); +} + +/* + * Sign tbs without digesting it first. This is suitable for "primitive" + * signing and signing the digest of a message, i.e. should be used with + * implementations of the keytype related algorithms. + */ +static int rsa_sign_directly(PROV_RSA_CTX *prsactx, + unsigned char *sig, size_t *siglen, size_t sigsize, + const unsigned char *tbs, size_t tbslen) +{ int ret; size_t rsasize = RSA_size(prsactx->rsa); size_t mdsize = rsa_get_md_size(prsactx); @@ -604,7 +739,6 @@ static int rsa_sign(void *vprsactx, unsigned char *sig, size_t *siglen, sig, prsactx->rsa, RSA_X931_PADDING); clean_tbuf(prsactx); break; - case RSA_PKCS1_PADDING: { unsigned int sltmp; @@ -620,46 +754,55 @@ static int rsa_sign(void *vprsactx, unsigned char *sig, size_t *siglen, break; case RSA_PKCS1_PSS_PADDING: - /* Check PSS restrictions */ - if (rsa_pss_restricted(prsactx)) { - switch (prsactx->saltlen) { - case RSA_PSS_SALTLEN_DIGEST: - if (prsactx->min_saltlen > EVP_MD_get_size(prsactx->md)) { - ERR_raise_data(ERR_LIB_PROV, - PROV_R_PSS_SALTLEN_TOO_SMALL, - "minimum salt length set to %d, " - "but the digest only gives %d", - prsactx->min_saltlen, - EVP_MD_get_size(prsactx->md)); - return 0; - } - /* FALLTHRU */ - default: - if (prsactx->saltlen >= 0 - && prsactx->saltlen < prsactx->min_saltlen) { - ERR_raise_data(ERR_LIB_PROV, - PROV_R_PSS_SALTLEN_TOO_SMALL, - "minimum salt length set to %d, but the" - "actual salt length is only set to %d", - prsactx->min_saltlen, - prsactx->saltlen); - return 0; + { + int saltlen; + + /* Check PSS restrictions */ + if (rsa_pss_restricted(prsactx)) { + switch (prsactx->saltlen) { + case RSA_PSS_SALTLEN_DIGEST: + if (prsactx->min_saltlen > EVP_MD_get_size(prsactx->md)) { + ERR_raise_data(ERR_LIB_PROV, + PROV_R_PSS_SALTLEN_TOO_SMALL, + "minimum salt length set to %d, " + "but the digest only gives %d", + prsactx->min_saltlen, + EVP_MD_get_size(prsactx->md)); + return 0; + } + /* FALLTHRU */ + default: + if (prsactx->saltlen >= 0 + && prsactx->saltlen < prsactx->min_saltlen) { + ERR_raise_data(ERR_LIB_PROV, + PROV_R_PSS_SALTLEN_TOO_SMALL, + "minimum salt length set to %d, but the" + "actual salt length is only set to %d", + prsactx->min_saltlen, + prsactx->saltlen); + return 0; + } + break; } - break; } + if (!setup_tbuf(prsactx)) + return 0; + saltlen = prsactx->saltlen; + if (!ossl_rsa_padding_add_PKCS1_PSS_mgf1(prsactx->rsa, + prsactx->tbuf, tbs, + prsactx->md, prsactx->mgf1_md, + &saltlen)) { + ERR_raise(ERR_LIB_PROV, ERR_R_RSA_LIB); + return 0; + } +#ifdef FIPS_MODULE + if (!rsa_pss_saltlen_check_passed(prsactx, "RSA Sign", saltlen)) + return 0; +#endif + ret = RSA_private_encrypt(RSA_size(prsactx->rsa), prsactx->tbuf, + sig, prsactx->rsa, RSA_NO_PADDING); + clean_tbuf(prsactx); } - if (!setup_tbuf(prsactx)) - return 0; - if (!RSA_padding_add_PKCS1_PSS_mgf1(prsactx->rsa, - prsactx->tbuf, tbs, - prsactx->md, prsactx->mgf1_md, - prsactx->saltlen)) { - ERR_raise(ERR_LIB_PROV, ERR_R_RSA_LIB); - return 0; - } - ret = RSA_private_encrypt(RSA_size(prsactx->rsa), prsactx->tbuf, - sig, prsactx->rsa, RSA_NO_PADDING); - clean_tbuf(prsactx); break; default: @@ -684,21 +827,112 @@ static int rsa_sign(void *vprsactx, unsigned char *sig, size_t *siglen, return 1; } +static int rsa_signverify_message_update(void *vprsactx, + const unsigned char *data, + size_t datalen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (prsactx == NULL || prsactx->mdctx == NULL) + return 0; + + if (!prsactx->flag_allow_update) { + ERR_raise(ERR_LIB_PROV, PROV_R_UPDATE_CALL_OUT_OF_ORDER); + return 0; + } + prsactx->flag_allow_oneshot = 0; + + return EVP_DigestUpdate(prsactx->mdctx, data, datalen); +} + +static int rsa_sign_message_final(void *vprsactx, unsigned char *sig, + size_t *siglen, size_t sigsize) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; + + if (!ossl_prov_is_running() || prsactx == NULL) + return 0; + if (prsactx->mdctx == NULL) + return 0; + if (!prsactx->flag_allow_final) { + ERR_raise(ERR_LIB_PROV, PROV_R_FINAL_CALL_OUT_OF_ORDER); + return 0; + } + + /* + * If sig is NULL then we're just finding out the sig size. Other fields + * are ignored. Defer to rsa_sign. + */ + if (sig != NULL) { + /* + * The digests used here are all known (see rsa_get_md_nid()), so they + * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. + */ + if (!EVP_DigestFinal_ex(prsactx->mdctx, digest, &dlen)) + return 0; + + prsactx->flag_allow_update = 0; + prsactx->flag_allow_oneshot = 0; + prsactx->flag_allow_final = 0; + } + + return rsa_sign_directly(prsactx, sig, siglen, sigsize, digest, dlen); +} + +/* + * If signing a message, digest tbs and sign the result. + * Otherwise, sign tbs directly. + */ +static int rsa_sign(void *vprsactx, unsigned char *sig, size_t *siglen, + size_t sigsize, const unsigned char *tbs, size_t tbslen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (!ossl_prov_is_running() || prsactx == NULL) + return 0; + if (!prsactx->flag_allow_oneshot) { + ERR_raise(ERR_LIB_PROV, PROV_R_ONESHOT_CALL_OUT_OF_ORDER); + return 0; + } + + if (prsactx->operation == EVP_PKEY_OP_SIGNMSG) { + /* + * If |sig| is NULL, the caller is only looking for the sig length. + * DO NOT update the input in this case. + */ + if (sig == NULL) + return rsa_sign_message_final(prsactx, sig, siglen, sigsize); + + return rsa_signverify_message_update(prsactx, tbs, tbslen) + && rsa_sign_message_final(prsactx, sig, siglen, sigsize); + } + return rsa_sign_directly(prsactx, sig, siglen, sigsize, tbs, tbslen); +} + static int rsa_verify_recover_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - if (!ossl_prov_is_running()) - return 0; - return rsa_signverify_init(vprsactx, vrsa, params, - EVP_PKEY_OP_VERIFYRECOVER); + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + +#ifdef FIPS_MODULE + if (prsactx != NULL) + prsactx->verify_message = 0; +#endif + + return rsa_signverify_init(prsactx, vrsa, rsa_set_ctx_params, params, + EVP_PKEY_OP_VERIFYRECOVER, "RSA VerifyRecover Init"); } +/* + * There is no message variant of verify recover, so no need for + * 'rsa_verify_recover_directly', just use this function, er, directly. + */ static int rsa_verify_recover(void *vprsactx, - unsigned char *rout, - size_t *routlen, + unsigned char *rout, size_t *routlen, size_t routsize, - const unsigned char *sig, - size_t siglen) + const unsigned char *sig, size_t siglen) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; int ret; @@ -780,15 +1014,21 @@ static int rsa_verify_recover(void *vprsactx, static int rsa_verify_init(void *vprsactx, void *vrsa, const OSSL_PARAM params[]) { - if (!ossl_prov_is_running()) - return 0; - return rsa_signverify_init(vprsactx, vrsa, params, EVP_PKEY_OP_VERIFY); + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + +#ifdef FIPS_MODULE + if (prsactx != NULL) + prsactx->verify_message = 0; +#endif + + return rsa_signverify_init(prsactx, vrsa, rsa_set_ctx_params, params, + EVP_PKEY_OP_VERIFY, "RSA Verify Init"); } -static int rsa_verify(void *vprsactx, const unsigned char *sig, size_t siglen, - const unsigned char *tbs, size_t tbslen) +static int rsa_verify_directly(PROV_RSA_CTX *prsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) { - PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; size_t rslen; if (!ossl_prov_is_running()) @@ -812,6 +1052,7 @@ static int rsa_verify(void *vprsactx, const unsigned char *sig, size_t siglen, case RSA_PKCS1_PSS_PADDING: { int ret; + int saltlen; size_t mdsize; /* @@ -834,14 +1075,19 @@ static int rsa_verify(void *vprsactx, const unsigned char *sig, size_t siglen, ERR_raise(ERR_LIB_PROV, ERR_R_RSA_LIB); return 0; } - ret = RSA_verify_PKCS1_PSS_mgf1(prsactx->rsa, tbs, - prsactx->md, prsactx->mgf1_md, - prsactx->tbuf, - prsactx->saltlen); + saltlen = prsactx->saltlen; + ret = ossl_rsa_verify_PKCS1_PSS_mgf1(prsactx->rsa, tbs, + prsactx->md, prsactx->mgf1_md, + prsactx->tbuf, + &saltlen); if (ret <= 0) { ERR_raise(ERR_LIB_PROV, ERR_R_RSA_LIB); return 0; } +#ifdef FIPS_MODULE + if (!rsa_pss_saltlen_check_passed(prsactx, "RSA Verify", saltlen)) + return 0; +#endif return 1; } default: @@ -869,22 +1115,94 @@ static int rsa_verify(void *vprsactx, const unsigned char *sig, size_t siglen, return 1; } +static int rsa_verify_set_sig(void *vprsactx, + const unsigned char *sig, size_t siglen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + OSSL_PARAM params[2]; + + params[0] = + OSSL_PARAM_construct_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, + (unsigned char *)sig, siglen); + params[1] = OSSL_PARAM_construct_end(); + return rsa_sigalg_set_ctx_params(prsactx, params); +} + +static int rsa_verify_message_final(void *vprsactx) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + unsigned char digest[EVP_MAX_MD_SIZE]; + unsigned int dlen = 0; + + if (!ossl_prov_is_running() || prsactx == NULL) + return 0; + if (prsactx->mdctx == NULL) + return 0; + if (!prsactx->flag_allow_final) { + ERR_raise(ERR_LIB_PROV, PROV_R_FINAL_CALL_OUT_OF_ORDER); + return 0; + } + + /* + * The digests used here are all known (see rsa_get_md_nid()), so they + * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. + */ + if (!EVP_DigestFinal_ex(prsactx->mdctx, digest, &dlen)) + return 0; + + prsactx->flag_allow_update = 0; + prsactx->flag_allow_final = 0; + prsactx->flag_allow_oneshot = 0; + + return rsa_verify_directly(prsactx, prsactx->sig, prsactx->siglen, + digest, dlen); +} + +/* + * If verifying a message, digest tbs and verify the result. + * Otherwise, verify tbs directly. + */ +static int rsa_verify(void *vprsactx, + const unsigned char *sig, size_t siglen, + const unsigned char *tbs, size_t tbslen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (!ossl_prov_is_running() || prsactx == NULL) + return 0; + if (!prsactx->flag_allow_oneshot) { + ERR_raise(ERR_LIB_PROV, PROV_R_ONESHOT_CALL_OUT_OF_ORDER); + return 0; + } + + if (prsactx->operation == EVP_PKEY_OP_VERIFYMSG) + return rsa_verify_set_sig(prsactx, sig, siglen) + && rsa_signverify_message_update(prsactx, tbs, tbslen) + && rsa_verify_message_final(prsactx); + return rsa_verify_directly(prsactx, sig, siglen, tbs, tbslen); +} + +/* DigestSign/DigestVerify wrappers */ + static int rsa_digest_signverify_init(void *vprsactx, const char *mdname, void *vrsa, const OSSL_PARAM params[], - int operation) + int operation, const char *desc) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; - if (!ossl_prov_is_running()) - return 0; +#ifdef FIPS_MODULE + if (prsactx != NULL) + prsactx->verify_message = 1; +#endif - if (!rsa_signverify_init(vprsactx, vrsa, params, operation)) + if (!rsa_signverify_init(prsactx, vrsa, rsa_set_ctx_params, params, + operation, desc)) return 0; if (mdname != NULL /* was rsa_setup_md already called in rsa_signverify_init()? */ && (mdname[0] == '\0' || OPENSSL_strcasecmp(prsactx->mdname, mdname) != 0) - && !rsa_setup_md(prsactx, mdname, prsactx->propq)) + && !rsa_setup_md(prsactx, mdname, prsactx->propq, desc)) return 0; prsactx->flag_allow_md = 0; @@ -906,53 +1224,48 @@ static int rsa_digest_signverify_init(void *vprsactx, const char *mdname, return 0; } -static int rsa_digest_signverify_update(void *vprsactx, - const unsigned char *data, - size_t datalen) -{ - PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; - - if (prsactx == NULL || prsactx->mdctx == NULL) - return 0; - - return EVP_DigestUpdate(prsactx->mdctx, data, datalen); -} - static int rsa_digest_sign_init(void *vprsactx, const char *mdname, void *vrsa, const OSSL_PARAM params[]) { if (!ossl_prov_is_running()) return 0; return rsa_digest_signverify_init(vprsactx, mdname, vrsa, - params, EVP_PKEY_OP_SIGN); + params, EVP_PKEY_OP_SIGNMSG, + "RSA Digest Sign Init"); +} + +static int rsa_digest_sign_update(void *vprsactx, const unsigned char *data, + size_t datalen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (prsactx == NULL) + return 0; + /* Sigalg implementations shouldn't do digest_sign */ + if (prsactx->flag_sigalg) + return 0; + + return rsa_signverify_message_update(prsactx, data, datalen); } static int rsa_digest_sign_final(void *vprsactx, unsigned char *sig, size_t *siglen, size_t sigsize) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; + int ok = 0; - if (!ossl_prov_is_running() || prsactx == NULL) + if (prsactx == NULL) return 0; - prsactx->flag_allow_md = 1; - if (prsactx->mdctx == NULL) + /* Sigalg implementations shouldn't do digest_sign */ + if (prsactx->flag_sigalg) return 0; - /* - * If sig is NULL then we're just finding out the sig size. Other fields - * are ignored. Defer to rsa_sign. - */ - if (sig != NULL) { - /* - * The digests used here are all known (see rsa_get_md_nid()), so they - * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. - */ - if (!EVP_DigestFinal_ex(prsactx->mdctx, digest, &dlen)) - return 0; - } - return rsa_sign(vprsactx, sig, siglen, sigsize, digest, (size_t)dlen); + if (rsa_sign_message_final(prsactx, sig, siglen, sigsize)) + ok = 1; + + prsactx->flag_allow_md = 1; + + return ok; } static int rsa_digest_verify_init(void *vprsactx, const char *mdname, @@ -961,33 +1274,43 @@ static int rsa_digest_verify_init(void *vprsactx, const char *mdname, if (!ossl_prov_is_running()) return 0; return rsa_digest_signverify_init(vprsactx, mdname, vrsa, - params, EVP_PKEY_OP_VERIFY); + params, EVP_PKEY_OP_VERIFYMSG, + "RSA Digest Verify Init"); } -int rsa_digest_verify_final(void *vprsactx, const unsigned char *sig, - size_t siglen) +static int rsa_digest_verify_update(void *vprsactx, const unsigned char *data, + size_t datalen) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; - unsigned char digest[EVP_MAX_MD_SIZE]; - unsigned int dlen = 0; - if (!ossl_prov_is_running()) + if (prsactx == NULL) + return 0; + /* Sigalg implementations shouldn't do digest_sign */ + if (prsactx->flag_sigalg) return 0; + return rsa_signverify_message_update(prsactx, data, datalen); +} + +int rsa_digest_verify_final(void *vprsactx, const unsigned char *sig, + size_t siglen) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + int ok = 0; + if (prsactx == NULL) return 0; - prsactx->flag_allow_md = 1; - if (prsactx->mdctx == NULL) + /* Sigalg implementations shouldn't do digest_verify */ + if (prsactx->flag_sigalg) return 0; - /* - * The digests used here are all known (see rsa_get_md_nid()), so they - * should not exceed the internal buffer size of EVP_MAX_MD_SIZE. - */ - if (!EVP_DigestFinal_ex(prsactx->mdctx, digest, &dlen)) - return 0; + if (rsa_verify_set_sig(prsactx, sig, siglen) + && rsa_verify_message_final(vprsactx)) + ok = 1; + + prsactx->flag_allow_md = 1; - return rsa_verify(vprsactx, sig, siglen, digest, (size_t)dlen); + return ok; } static void rsa_freectx(void *vprsactx) @@ -1000,6 +1323,7 @@ static void rsa_freectx(void *vprsactx) EVP_MD_CTX_free(prsactx->mdctx); EVP_MD_free(prsactx->md); EVP_MD_free(prsactx->mgf1_md); + OPENSSL_free(prsactx->sig); OPENSSL_free(prsactx->propq); free_tbuf(prsactx); RSA_free(prsactx->rsa); @@ -1156,6 +1480,14 @@ static int rsa_get_ctx_params(void *vprsactx, OSSL_PARAM *params) } } +#ifdef FIPS_MODULE + p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE); + if (p != NULL && !OSSL_PARAM_set_uint(p, prsactx->verify_message)) + return 0; +#endif + + if (!OSSL_FIPS_IND_GET_CTX_PARAM(prsactx, params)) + return 0; return 1; } @@ -1165,6 +1497,10 @@ static const OSSL_PARAM known_gettable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_MGF1_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_PSS_SALTLEN, NULL, 0), +#ifdef FIPS_MODULE + OSSL_PARAM_uint(OSSL_SIGNATURE_PARAM_FIPS_VERIFY_MESSAGE, NULL), +#endif + OSSL_FIPS_IND_GETTABLE_CTX_PARAM() OSSL_PARAM_END }; @@ -1174,6 +1510,25 @@ static const OSSL_PARAM *rsa_gettable_ctx_params(ossl_unused void *vprsactx, return known_gettable_ctx_params; } +#ifdef FIPS_MODULE +static int rsa_x931_padding_allowed(PROV_RSA_CTX *ctx) +{ + int approved = ((ctx->operation & EVP_PKEY_OP_SIGN) == 0); + + if (!approved) { + if (!OSSL_FIPS_IND_ON_UNAPPROVED(ctx, OSSL_FIPS_IND_SETTABLE2, + ctx->libctx, + "RSA Sign set ctx", "X931 Padding", + ossl_fips_config_rsa_sign_x931_disallowed)) { + ERR_raise(ERR_LIB_PROV, + PROV_R_ILLEGAL_OR_UNSUPPORTED_PADDING_MODE); + return 0; + } + } + return 1; +} +#endif + static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) { PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; @@ -1190,6 +1545,22 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) if (params == NULL) return 1; + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE0, params, + OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK)) + return 0; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE1, params, + OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK)) + return 0; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE2, params, + OSSL_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK)) + return 0; + + if (!OSSL_FIPS_IND_SET_CTX_PARAM(prsactx, OSSL_FIPS_IND_SETTABLE3, params, + OSSL_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK)) + return 0; + pad_mode = prsactx->pad_mode; saltlen = prsactx->saltlen; @@ -1249,7 +1620,8 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) goto bad_pad; case RSA_PKCS1_PSS_PADDING: if ((prsactx->operation - & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_VERIFY)) == 0) { + & (EVP_PKEY_OP_SIGN | EVP_PKEY_OP_SIGNMSG + | EVP_PKEY_OP_VERIFY | EVP_PKEY_OP_VERIFYMSG)) == 0) { err_extra_text = "PSS padding only allowed for sign and verify operations"; goto bad_pad; @@ -1262,6 +1634,16 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) err_extra_text = "No padding not allowed with RSA-PSS"; goto cont; case RSA_X931_PADDING: +#ifdef FIPS_MODULE + /* X9.31 only allows sizes of 1024 + 256 * s (bits) */ + if ((RSA_bits(prsactx->rsa) & 0xFF) != 0) { + ERR_raise(ERR_LIB_PROV, PROV_R_INVALID_KEY_LENGTH); + return 0; + } + /* RSA Signing with X9.31 padding is not allowed in FIPS 140-3 */ + if (!rsa_x931_padding_allowed(prsactx)) + return 0; +#endif err_extra_text = "X.931 padding not allowed with RSA-PSS"; cont: if (RSA_test_flags(prsactx->rsa, @@ -1325,7 +1707,8 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) switch (saltlen) { case RSA_PSS_SALTLEN_AUTO: case RSA_PSS_SALTLEN_AUTO_DIGEST_MAX: - if (prsactx->operation == EVP_PKEY_OP_VERIFY) { + if ((prsactx->operation + & (EVP_PKEY_OP_VERIFY | EVP_PKEY_OP_VERIFYMSG)) == 0) { ERR_raise_data(ERR_LIB_PROV, PROV_R_INVALID_SALT_LENGTH, "Cannot use autodetected salt length"); return 0; @@ -1390,7 +1773,7 @@ static int rsa_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) return 0; if (pmdname != NULL) { - if (!rsa_setup_md(prsactx, pmdname, pmdprops)) + if (!rsa_setup_md(prsactx, pmdname, pmdprops, "RSA Sign Set Ctx")) return 0; } else { if (!rsa_check_padding(prsactx, NULL, NULL, prsactx->mdnid)) @@ -1406,6 +1789,10 @@ static const OSSL_PARAM settable_ctx_params[] = { OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_MGF1_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_MGF1_PROPERTIES, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_PSS_SALTLEN, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK) OSSL_PARAM_END }; @@ -1414,6 +1801,10 @@ static const OSSL_PARAM settable_ctx_params_no_digest[] = { OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_MGF1_DIGEST, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_MGF1_PROPERTIES, NULL, 0), OSSL_PARAM_utf8_string(OSSL_SIGNATURE_PARAM_PSS_SALTLEN, NULL, 0), + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_KEY_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_DIGEST_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_RSA_PSS_SALTLEN_CHECK) + OSSL_FIPS_IND_SETTABLE_CTX_PARAM(OSSL_SIGNATURE_PARAM_FIPS_SIGN_X931_PAD_CHECK) OSSL_PARAM_END }; @@ -1480,13 +1871,13 @@ const OSSL_DISPATCH ossl_rsa_signature_functions[] = { { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_INIT, (void (*)(void))rsa_digest_sign_init }, { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_UPDATE, - (void (*)(void))rsa_digest_signverify_update }, + (void (*)(void))rsa_digest_sign_update }, { OSSL_FUNC_SIGNATURE_DIGEST_SIGN_FINAL, (void (*)(void))rsa_digest_sign_final }, { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_INIT, (void (*)(void))rsa_digest_verify_init }, { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_UPDATE, - (void (*)(void))rsa_digest_signverify_update }, + (void (*)(void))rsa_digest_verify_update }, { OSSL_FUNC_SIGNATURE_DIGEST_VERIFY_FINAL, (void (*)(void))rsa_digest_verify_final }, { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))rsa_freectx }, @@ -1507,3 +1898,250 @@ const OSSL_DISPATCH ossl_rsa_signature_functions[] = { (void (*)(void))rsa_settable_ctx_md_params }, OSSL_DISPATCH_END }; + +/* ------------------------------------------------------------------ */ + +/* + * So called sigalgs (composite RSA+hash) implemented below. They + * are pretty much hard coded, and rely on the hash implementation + * being available as per what OPENSSL_NO_ macros allow. + */ + +static OSSL_FUNC_signature_query_key_types_fn rsa_sigalg_query_key_types; +static OSSL_FUNC_signature_settable_ctx_params_fn rsa_sigalg_settable_ctx_params; +static OSSL_FUNC_signature_set_ctx_params_fn rsa_sigalg_set_ctx_params; + +/* + * rsa_sigalg_signverify_init() is almost like rsa_digest_signverify_init(), + * just doesn't allow fetching an MD from whatever the user chooses. + */ +static int rsa_sigalg_signverify_init(void *vprsactx, void *vrsa, + OSSL_FUNC_signature_set_ctx_params_fn *set_ctx_params, + const OSSL_PARAM params[], + const char *mdname, + int operation, int pad_mode, + const char *desc) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (!ossl_prov_is_running()) + return 0; + + if (!rsa_signverify_init(prsactx, vrsa, set_ctx_params, params, operation, + desc)) + return 0; + + /* PSS is currently not supported as a sigalg */ + if (prsactx->pad_mode == RSA_PKCS1_PSS_PADDING) { + ERR_raise(ERR_LIB_RSA, PROV_R_OPERATION_NOT_SUPPORTED_FOR_THIS_KEYTYPE); + return 0; + } + + if (!rsa_setup_md(prsactx, mdname, NULL, desc)) + return 0; + + prsactx->pad_mode = pad_mode; + prsactx->flag_sigalg = 1; + prsactx->flag_allow_md = 0; + + if (prsactx->mdctx == NULL) { + prsactx->mdctx = EVP_MD_CTX_new(); + if (prsactx->mdctx == NULL) + goto error; + } + + if (!EVP_DigestInit_ex2(prsactx->mdctx, prsactx->md, params)) + goto error; + + return 1; + + error: + EVP_MD_CTX_free(prsactx->mdctx); + prsactx->mdctx = NULL; + return 0; +} + +static const char **rsa_sigalg_query_key_types(void) +{ + static const char *keytypes[] = { "RSA", NULL }; + + return keytypes; +} + +static const OSSL_PARAM settable_sigalg_ctx_params[] = { + OSSL_PARAM_octet_string(OSSL_SIGNATURE_PARAM_SIGNATURE, NULL, 0), + OSSL_PARAM_END +}; + +static const OSSL_PARAM *rsa_sigalg_settable_ctx_params(void *vprsactx, + ossl_unused void *provctx) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + + if (prsactx != NULL && prsactx->operation == EVP_PKEY_OP_VERIFYMSG) + return settable_sigalg_ctx_params; + return NULL; +} + +static int rsa_sigalg_set_ctx_params(void *vprsactx, const OSSL_PARAM params[]) +{ + PROV_RSA_CTX *prsactx = (PROV_RSA_CTX *)vprsactx; + const OSSL_PARAM *p; + + if (prsactx == NULL) + return 0; + if (params == NULL) + return 1; + + if (prsactx->operation == EVP_PKEY_OP_VERIFYMSG) { + p = OSSL_PARAM_locate_const(params, OSSL_SIGNATURE_PARAM_SIGNATURE); + if (p != NULL) { + OPENSSL_free(prsactx->sig); + prsactx->sig = NULL; + prsactx->siglen = 0; + if (!OSSL_PARAM_get_octet_string(p, (void **)&prsactx->sig, + 0, &prsactx->siglen)) + return 0; + } + return 1; + } + + /* Wrong operation */ + return 0; +} + +#define IMPL_RSA_SIGALG(md, MD) \ + static OSSL_FUNC_signature_sign_init_fn rsa_##md##_sign_init; \ + static OSSL_FUNC_signature_sign_message_init_fn \ + rsa_##md##_sign_message_init; \ + static OSSL_FUNC_signature_verify_init_fn rsa_##md##_verify_init; \ + static OSSL_FUNC_signature_verify_message_init_fn \ + rsa_##md##_verify_message_init; \ + \ + static int \ + rsa_##md##_sign_init(void *vprsactx, void *vrsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "RSA Sigalg Sign Init"; \ + \ + return rsa_sigalg_signverify_init(vprsactx, vrsa, \ + rsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGN, \ + RSA_PKCS1_PADDING, \ + desc); \ + } \ + \ + static int \ + rsa_##md##_sign_message_init(void *vprsactx, void *vrsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "RSA Sigalg Sign Message Init"; \ + \ + return rsa_sigalg_signverify_init(vprsactx, vrsa, \ + rsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_SIGNMSG, \ + RSA_PKCS1_PADDING, \ + desc); \ + } \ + \ + static int \ + rsa_##md##_verify_init(void *vprsactx, void *vrsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "RSA Sigalg Verify Init"; \ + \ + return rsa_sigalg_signverify_init(vprsactx, vrsa, \ + rsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFY, \ + RSA_PKCS1_PADDING, \ + desc); \ + } \ + \ + static int \ + rsa_##md##_verify_recover_init(void *vprsactx, void *vrsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "RSA Sigalg Verify Recover Init"; \ + \ + return rsa_sigalg_signverify_init(vprsactx, vrsa, \ + rsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFYRECOVER, \ + RSA_PKCS1_PADDING, \ + desc); \ + } \ + \ + static int \ + rsa_##md##_verify_message_init(void *vprsactx, void *vrsa, \ + const OSSL_PARAM params[]) \ + { \ + static const char desc[] = "RSA Sigalg Verify Message Init"; \ + \ + return rsa_sigalg_signverify_init(vprsactx, vrsa, \ + rsa_sigalg_set_ctx_params, \ + params, #MD, \ + EVP_PKEY_OP_VERIFYMSG, \ + RSA_PKCS1_PADDING, \ + desc); \ + } \ + \ + const OSSL_DISPATCH ossl_rsa_##md##_signature_functions[] = { \ + { OSSL_FUNC_SIGNATURE_NEWCTX, (void (*)(void))rsa_newctx }, \ + { OSSL_FUNC_SIGNATURE_SIGN_INIT, \ + (void (*)(void))rsa_##md##_sign_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN, (void (*)(void))rsa_sign }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_INIT, \ + (void (*)(void))rsa_##md##_sign_message_init }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_UPDATE, \ + (void (*)(void))rsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_SIGN_MESSAGE_FINAL, \ + (void (*)(void))rsa_sign_message_final }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_INIT, \ + (void (*)(void))rsa_##md##_verify_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY, \ + (void (*)(void))rsa_verify }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_INIT, \ + (void (*)(void))rsa_##md##_verify_message_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_UPDATE, \ + (void (*)(void))rsa_signverify_message_update }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_MESSAGE_FINAL, \ + (void (*)(void))rsa_verify_message_final }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_RECOVER_INIT, \ + (void (*)(void))rsa_##md##_verify_recover_init }, \ + { OSSL_FUNC_SIGNATURE_VERIFY_RECOVER, \ + (void (*)(void))rsa_verify_recover }, \ + { OSSL_FUNC_SIGNATURE_FREECTX, (void (*)(void))rsa_freectx }, \ + { OSSL_FUNC_SIGNATURE_DUPCTX, (void (*)(void))rsa_dupctx }, \ + { OSSL_FUNC_SIGNATURE_QUERY_KEY_TYPES, \ + (void (*)(void))rsa_sigalg_query_key_types }, \ + { OSSL_FUNC_SIGNATURE_GET_CTX_PARAMS, \ + (void (*)(void))rsa_get_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_GETTABLE_CTX_PARAMS, \ + (void (*)(void))rsa_gettable_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SET_CTX_PARAMS, \ + (void (*)(void))rsa_sigalg_set_ctx_params }, \ + { OSSL_FUNC_SIGNATURE_SETTABLE_CTX_PARAMS, \ + (void (*)(void))rsa_sigalg_settable_ctx_params }, \ + OSSL_DISPATCH_END \ + } + +#if !defined(OPENSSL_NO_RMD160) && !defined(FIPS_MODULE) +IMPL_RSA_SIGALG(ripemd160, RIPEMD160); +#endif +IMPL_RSA_SIGALG(sha1, SHA1); +IMPL_RSA_SIGALG(sha224, SHA2-224); +IMPL_RSA_SIGALG(sha256, SHA2-256); +IMPL_RSA_SIGALG(sha384, SHA2-384); +IMPL_RSA_SIGALG(sha512, SHA2-512); +IMPL_RSA_SIGALG(sha512_224, SHA2-512/224); +IMPL_RSA_SIGALG(sha512_256, SHA2-512/256); +IMPL_RSA_SIGALG(sha3_224, SHA3-224); +IMPL_RSA_SIGALG(sha3_256, SHA3-256); +IMPL_RSA_SIGALG(sha3_384, SHA3-384); +IMPL_RSA_SIGALG(sha3_512, SHA3-512); +#if !defined(OPENSSL_NO_SM3) && !defined(FIPS_MODULE) +IMPL_RSA_SIGALG(sm3, SM3); +#endif diff --git a/providers/implementations/signature/sm2_sig.c b/providers/implementations/signature/sm2_sig.c index 479e4eebe8..fa7dcefaa3 100644 --- a/providers/implementations/signature/sm2_sig.c +++ b/providers/implementations/signature/sm2_sig.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -77,7 +77,6 @@ typedef struct { /* The Algorithm Identifier of the combined signature algorithm */ unsigned char aid_buf[OSSL_MAX_ALGORITHM_ID_SIZE]; - unsigned char *aid; size_t aid_len; /* main digest */ @@ -98,6 +97,12 @@ static int sm2sig_set_mdname(PROV_SM2_CTX *psm2ctx, const char *mdname) if (psm2ctx->md == NULL) return 0; + /* XOF digests don't work */ + if (EVP_MD_xof(psm2ctx->md)) { + ERR_raise(ERR_LIB_PROV, PROV_R_XOF_DIGESTS_NOT_ALLOWED); + return 0; + } + if (mdname == NULL) return 1; @@ -207,6 +212,7 @@ static int sm2sig_digest_signverify_init(void *vpsm2ctx, const char *mdname, int md_nid; WPACKET pkt; int ret = 0; + unsigned char *aid = NULL; if (!sm2sig_signature_init(vpsm2ctx, ec, params) || !sm2sig_set_mdname(ctx, mdname)) @@ -232,9 +238,11 @@ static int sm2sig_digest_signverify_init(void *vpsm2ctx, const char *mdname, && ossl_DER_w_algorithmIdentifier_SM2_with_MD(&pkt, -1, ctx->ec, md_nid) && WPACKET_finish(&pkt)) { WPACKET_get_total_written(&pkt, &ctx->aid_len); - ctx->aid = WPACKET_get_curr(&pkt); + aid = WPACKET_get_curr(&pkt); } WPACKET_cleanup(&pkt); + if (aid != NULL && ctx->aid_len != 0) + memmove(ctx->aid_buf, aid, ctx->aid_len); if (!EVP_DigestInit_ex2(ctx->mdctx, ctx->md, params)) goto error; @@ -310,10 +318,13 @@ int sm2sig_digest_verify_final(void *vpsm2ctx, const unsigned char *sig, PROV_SM2_CTX *psm2ctx = (PROV_SM2_CTX *)vpsm2ctx; unsigned char digest[EVP_MAX_MD_SIZE]; unsigned int dlen = 0; + int md_size; + + if (psm2ctx == NULL || psm2ctx->mdctx == NULL) + return 0; - if (psm2ctx == NULL - || psm2ctx->mdctx == NULL - || EVP_MD_get_size(psm2ctx->md) > (int)sizeof(digest)) + md_size = EVP_MD_get_size(psm2ctx->md); + if (md_size <= 0 || md_size > (int)sizeof(digest)) return 0; if (!(sm2sig_compute_z_digest(psm2ctx) @@ -395,7 +406,9 @@ static int sm2sig_get_ctx_params(void *vpsm2ctx, OSSL_PARAM *params) p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_ALGORITHM_ID); if (p != NULL - && !OSSL_PARAM_set_octet_string(p, psm2ctx->aid, psm2ctx->aid_len)) + && !OSSL_PARAM_set_octet_string(p, + psm2ctx->aid_len == 0 ? NULL : psm2ctx->aid_buf, + psm2ctx->aid_len)) return 0; p = OSSL_PARAM_locate(params, OSSL_SIGNATURE_PARAM_DIGEST_SIZE); diff --git a/providers/implementations/storemgmt/file_store.c b/providers/implementations/storemgmt/file_store.c index 171c74d581..d87cbfa189 100644 --- a/providers/implementations/storemgmt/file_store.c +++ b/providers/implementations/storemgmt/file_store.c @@ -1,5 +1,5 @@ /* - * Copyright 2020-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2020-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -234,7 +234,7 @@ static void *file_open(void *provctx, const char *uri) #ifdef _WIN32 /* Windows "file:" URIs with a drive letter start with a '/' */ if (p[0] == '/' && p[2] == ':' && p[3] == '/') { - char c = tolower(p[1]); + char c = tolower((unsigned char)p[1]); if (c >= 'a' && c <= 'z') { p++; diff --git a/ssl/build.info b/ssl/build.info index de28a0700a..adfc966379 100644 --- a/ssl/build.info +++ b/ssl/build.info @@ -32,5 +32,5 @@ IF[{- !$disabled{'deprecated-3.0'} -}] ENDIF IF[{- !$disabled{quic} -}] - SOURCE[../libssl]=priority_queue.c event_queue.c + SOURCE[../libssl]=priority_queue.c ENDIF diff --git a/ssl/d1_lib.c b/ssl/d1_lib.c index 1ac0975d0a..d055f06b39 100644 --- a/ssl/d1_lib.c +++ b/ssl/d1_lib.c @@ -1,5 +1,5 @@ /* - * Copyright 2005-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2005-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -29,7 +29,7 @@ const SSL3_ENC_METHOD DTLSv1_enc_data = { TLS_MD_SERVER_FINISH_CONST, TLS_MD_SERVER_FINISH_CONST_SIZE, tls1_alert_code, tls1_export_keying_material, - SSL_ENC_FLAG_DTLS | SSL_ENC_FLAG_EXPLICIT_IV, + SSL_ENC_FLAG_DTLS, dtls1_set_handshake_header, dtls1_close_construct_packet, dtls1_handshake_write @@ -44,7 +44,7 @@ const SSL3_ENC_METHOD DTLSv1_2_enc_data = { TLS_MD_SERVER_FINISH_CONST, TLS_MD_SERVER_FINISH_CONST_SIZE, tls1_alert_code, tls1_export_keying_material, - SSL_ENC_FLAG_DTLS | SSL_ENC_FLAG_EXPLICIT_IV | SSL_ENC_FLAG_SIGALGS + SSL_ENC_FLAG_DTLS | SSL_ENC_FLAG_SIGALGS | SSL_ENC_FLAG_SHA256_PRF | SSL_ENC_FLAG_TLS1_2_CIPHERS, dtls1_set_handshake_header, dtls1_close_construct_packet, diff --git a/ssl/event_queue.c b/ssl/event_queue.c deleted file mode 100644 index 20f4020db5..0000000000 --- a/ssl/event_queue.c +++ /dev/null @@ -1,196 +0,0 @@ -/* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. - * - * Licensed under the Apache License 2.0 (the "License"). You may not use - * this file except in compliance with the License. You can obtain a copy - * in the file LICENSE in the source distribution or at - * https://www.openssl.org/source/license.html - */ - -#include -#include "internal/event_queue.h" -#include "ssl_local.h" - -struct ossl_event_queue_st { - PRIORITY_QUEUE_OF(OSSL_EVENT) *timed_events; - PRIORITY_QUEUE_OF(OSSL_EVENT) *now_events; -}; - -static int event_compare_times(const OSSL_EVENT *a, const OSSL_EVENT *b) -{ - return ossl_time_compare(a->when, b->when); -} - -static int event_compare_priority(const OSSL_EVENT *a, const OSSL_EVENT *b) -{ - if (a->priority > b->priority) - return -1; - if (a->priority < b->priority) - return 1; - return 0; -} - -OSSL_EVENT_QUEUE *ossl_event_queue_new(void) -{ - OSSL_EVENT_QUEUE *r = OPENSSL_malloc(sizeof(*r)); - - if (r != NULL) { - r->timed_events = ossl_pqueue_OSSL_EVENT_new(&event_compare_times); - r->now_events = ossl_pqueue_OSSL_EVENT_new(&event_compare_priority); - if (r->timed_events == NULL || r->now_events == NULL) { - ossl_event_queue_free(r); - return NULL; - } - } - return r; -} - -void ossl_event_free(OSSL_EVENT *event) -{ - if (event != NULL) { - if (event->flag_dynamic) - OPENSSL_free(event); - else - event->queue = NULL; - } -} - -static void event_queue_free(PRIORITY_QUEUE_OF(OSSL_EVENT) *queue) -{ - OSSL_EVENT *e; - - if (queue != NULL) { - while ((e = ossl_pqueue_OSSL_EVENT_pop(queue)) != NULL) - ossl_event_free(e); - ossl_pqueue_OSSL_EVENT_free(queue); - } -} - -void ossl_event_queue_free(OSSL_EVENT_QUEUE *queue) -{ - if (queue != NULL) { - event_queue_free(queue->now_events); - event_queue_free(queue->timed_events); - OPENSSL_free(queue); - } -} - -static ossl_inline -int event_queue_add(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event) -{ - PRIORITY_QUEUE_OF(OSSL_EVENT) *pq = - ossl_time_compare(event->when, ossl_time_now()) <= 0 - ? queue->now_events - : queue->timed_events; - - if (ossl_pqueue_OSSL_EVENT_push(pq, event, &event->ref)) { - event->queue = pq; - return 1; - } - return 0; -} - -static ossl_inline -void ossl_event_set(OSSL_EVENT *event, uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size) -{ - event->type = type; - event->priority = priority; - event->when = when; - event->ctx = ctx; - event->payload = payload; - event->payload_size = payload_size; -} - -OSSL_EVENT *ossl_event_queue_add_new(OSSL_EVENT_QUEUE *queue, - uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size) -{ - OSSL_EVENT *e = OPENSSL_malloc(sizeof(*e)); - - if (e == NULL || queue == NULL) { - OPENSSL_free(e); - return NULL; - } - - ossl_event_set(e, type, priority, when, ctx, payload, payload_size); - e->flag_dynamic = 1; - if (event_queue_add(queue, e)) - return e; - OPENSSL_free(e); - return NULL; -} - -int ossl_event_queue_add(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event, - uint32_t type, uint32_t priority, - OSSL_TIME when, void *ctx, - void *payload, size_t payload_size) -{ - if (event == NULL || queue == NULL) - return 0; - ossl_event_set(event, type, priority, when, ctx, payload, payload_size); - event->flag_dynamic = 0; - return event_queue_add(queue, event); -} - -int ossl_event_queue_remove(OSSL_EVENT_QUEUE *queue, OSSL_EVENT *event) -{ - if (event != NULL && event->queue != NULL) { - ossl_pqueue_OSSL_EVENT_remove(event->queue, event->ref); - event->queue = NULL; - } - return 1; -} - -OSSL_TIME ossl_event_time_until(const OSSL_EVENT *event) -{ - if (event == NULL) - return ossl_time_infinite(); - return ossl_time_subtract(event->when, ossl_time_now()); -} - -OSSL_TIME ossl_event_queue_time_until_next(const OSSL_EVENT_QUEUE *queue) -{ - if (queue == NULL) - return ossl_time_infinite(); - if (ossl_pqueue_OSSL_EVENT_num(queue->now_events) > 0) - return ossl_time_zero(); - return ossl_event_time_until(ossl_pqueue_OSSL_EVENT_peek(queue->timed_events)); -} - -int ossl_event_queue_postpone_until(OSSL_EVENT_QUEUE *queue, - OSSL_EVENT *event, - OSSL_TIME when) -{ - if (ossl_event_queue_remove(queue, event)) { - event->when = when; - return event_queue_add(queue, event); - } - return 0; -} - -int ossl_event_queue_get1_next_event(OSSL_EVENT_QUEUE *queue, - OSSL_EVENT **event) -{ - OSSL_TIME now = ossl_time_now(); - OSSL_EVENT *e; - - /* Check for expired timer based events and convert them to now events */ - while ((e = ossl_pqueue_OSSL_EVENT_peek(queue->timed_events)) != NULL - && ossl_time_compare(e->when, now) <= 0) { - e = ossl_pqueue_OSSL_EVENT_pop(queue->timed_events); - if (!ossl_pqueue_OSSL_EVENT_push(queue->now_events, e, &e->ref)) { - e->queue = NULL; - return 0; - } - } - - /* - * Get next event from the now queue. - * The pop returns NULL when there is none. - */ - *event = ossl_pqueue_OSSL_EVENT_pop(queue->now_events); - return 1; -} diff --git a/ssl/priority_queue.c b/ssl/priority_queue.c index 5393c532a7..ed1d191f2e 100644 --- a/ssl/priority_queue.c +++ b/ssl/priority_queue.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -46,8 +46,7 @@ struct pq_elem_st { #endif }; -struct ossl_pqueue_st -{ +struct ossl_pqueue_st { struct pq_heap_st *heap; struct pq_elem_st *elements; int (*compare)(const void *, const void *); diff --git a/ssl/quic/quic_cfq.c b/ssl/quic/quic_cfq.c index 9b9999a823..fb96e0c68c 100644 --- a/ssl/quic/quic_cfq.c +++ b/ssl/quic/quic_cfq.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -71,7 +71,7 @@ typedef struct quic_cfq_item_list_st { } QUIC_CFQ_ITEM_LIST; struct quic_cfq_st { - /* + /* * Invariant: A CFQ item is always in exactly one of these lists, never more * or less than one. * diff --git a/ssl/quic/quic_engine.c b/ssl/quic/quic_engine.c index 3bcb5d6810..27488bcb03 100644 --- a/ssl/quic/quic_engine.c +++ b/ssl/quic/quic_engine.c @@ -1,5 +1,5 @@ /* - * Copyright 2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2023-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -131,7 +131,7 @@ static void qeng_tick(QUIC_TICK_RESULT *res, void *arg, uint32_t flags) return; /* Iterate through all ports and service them. */ - LIST_FOREACH(port, port, &qeng->port_list) { + OSSL_LIST_FOREACH(port, port, &qeng->port_list) { QUIC_TICK_RESULT subr = {0}; ossl_quic_port_subtick(port, &subr, flags); diff --git a/ssl/quic/quic_port.c b/ssl/quic/quic_port.c index 96c289f7e7..87c0ac0ca6 100644 --- a/ssl/quic/quic_port.c +++ b/ssl/quic/quic_port.c @@ -220,7 +220,7 @@ static int port_update_poll_desc(QUIC_PORT *port, BIO *net_bio, int for_write) * single pollable currently. In the future, once complete polling * infrastructure has been implemented, this limitation can be removed. * - * For now, just update the descriptor on the the engine's reactor as we are + * For now, just update the descriptor on the engine's reactor as we are * guaranteed to be the only port under it. */ if (for_write) @@ -273,7 +273,7 @@ int ossl_quic_port_set_net_wbio(QUIC_PORT *port, BIO *net_wbio) if (!port_update_poll_desc(port, net_wbio, /*for_write=*/1)) return 0; - LIST_FOREACH(ch, ch, &port->channel_list) + OSSL_LIST_FOREACH(ch, ch, &port->channel_list) ossl_qtx_set_bio(ch->qtx, net_wbio); port->net_wbio = net_wbio; @@ -373,7 +373,7 @@ void ossl_quic_port_subtick(QUIC_PORT *port, QUIC_TICK_RESULT *res, port_rx_pre(port); /* Iterate through all channels and service them. */ - LIST_FOREACH(ch, ch, &port->channel_list) { + OSSL_LIST_FOREACH(ch, ch, &port->channel_list) { QUIC_TICK_RESULT subr = {0}; ossl_quic_channel_subtick(ch, &subr, flags); @@ -603,7 +603,7 @@ void ossl_quic_port_raise_net_error(QUIC_PORT *port, if (triggering_ch != NULL) ossl_quic_channel_raise_net_error(triggering_ch); - LIST_FOREACH(ch, ch, &port->channel_list) + OSSL_LIST_FOREACH(ch, ch, &port->channel_list) if (ch != triggering_ch) ossl_quic_channel_raise_net_error(ch); } diff --git a/ssl/quic/quic_rcidm.c b/ssl/quic/quic_rcidm.c index 77d8cbfcc0..18f7e8096b 100644 --- a/ssl/quic/quic_rcidm.c +++ b/ssl/quic/quic_rcidm.c @@ -310,7 +310,7 @@ void ossl_quic_rcidm_free(QUIC_RCIDM *rcidm) while ((rcid = ossl_pqueue_RCID_pop(rcidm->rcids)) != NULL) OPENSSL_free(rcid); - LIST_FOREACH_DELSAFE(rcid, rnext, retiring, &rcidm->retiring_list) + OSSL_LIST_FOREACH_DELSAFE(rcid, rnext, retiring, &rcidm->retiring_list) OPENSSL_free(rcid); ossl_pqueue_RCID_free(rcidm->rcids); diff --git a/ssl/quic/quic_record_util.c b/ssl/quic/quic_record_util.c index e95a84c39b..d7c3cece88 100644 --- a/ssl/quic/quic_record_util.c +++ b/ssl/quic/quic_record_util.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -29,7 +29,8 @@ int ossl_quic_hkdf_extract(OSSL_LIB_CTX *libctx, int ret = 0; EVP_KDF *kdf = NULL; EVP_KDF_CTX *kctx = NULL; - OSSL_PARAM params[7], *p = params; + OSSL_PARAM params[8], *p = params; + int key_check = 0; int mode = EVP_PKEY_HKDEF_MODE_EXTRACT_ONLY; const char *md_name; @@ -38,6 +39,15 @@ int ossl_quic_hkdf_extract(OSSL_LIB_CTX *libctx, || (kctx = EVP_KDF_CTX_new(kdf)) == NULL) goto err; + /* + * According to RFC 9000, the length of destination connection ID must be + * at least 8 bytes. It means that the length of destination connection ID + * may be less than the minimum length for HKDF required by FIPS provider. + * + * Therefore, we need to set `key-check` to zero to allow using destionation + * connection ID as IKM. + */ + *p++ = OSSL_PARAM_construct_int(OSSL_KDF_PARAM_FIPS_KEY_CHECK, &key_check); *p++ = OSSL_PARAM_construct_int(OSSL_KDF_PARAM_MODE, &mode); *p++ = OSSL_PARAM_construct_utf8_string(OSSL_KDF_PARAM_DIGEST, (char *)md_name, 0); diff --git a/ssl/quic/quic_stream_map.c b/ssl/quic/quic_stream_map.c index c836721f78..64700b09d9 100644 --- a/ssl/quic/quic_stream_map.c +++ b/ssl/quic/quic_stream_map.c @@ -764,7 +764,7 @@ void ossl_quic_stream_map_remove_from_accept_queue(QUIC_STREAM_MAP *qsm, --qsm->num_accept_uni; if ((max_streams_rxfc = qsm_get_max_streams_rxfc(qsm, s)) != NULL) - ossl_quic_rxfc_on_retire(max_streams_rxfc, 1, rtt); + (void)ossl_quic_rxfc_on_retire(max_streams_rxfc, 1, rtt); } size_t ossl_quic_stream_map_get_accept_queue_len(QUIC_STREAM_MAP *qsm, int is_uni) diff --git a/ssl/record/methods/dtls_meth.c b/ssl/record/methods/dtls_meth.c index a5e6c82341..a69629b07b 100644 --- a/ssl/record/methods/dtls_meth.c +++ b/ssl/record/methods/dtls_meth.c @@ -151,7 +151,7 @@ static int dtls_process_record(OSSL_RECORD_LAYER *rl, DTLS_BITMAP *bitmap) if (tmpmd != NULL) { imac_size = EVP_MD_get_size(tmpmd); - if (!ossl_assert(imac_size >= 0 && imac_size <= EVP_MAX_MD_SIZE)) { + if (!ossl_assert(imac_size > 0 && imac_size <= EVP_MAX_MD_SIZE)) { RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); return 0; } diff --git a/ssl/record/methods/recmethod_local.h b/ssl/record/methods/recmethod_local.h index fe9dce1535..364a3a01bb 100644 --- a/ssl/record/methods/recmethod_local.h +++ b/ssl/record/methods/recmethod_local.h @@ -91,8 +91,7 @@ typedef struct tls_rl_record_st { /* Protocol version specific function pointers */ -struct record_functions_st -{ +struct record_functions_st { /* * Returns either OSSL_RECORD_RETURN_SUCCESS, OSSL_RECORD_RETURN_FATAL or * OSSL_RECORD_RETURN_NON_FATAL_ERR if we can keep trying to find an @@ -209,8 +208,7 @@ struct record_functions_st int (*prepare_write_bio)(OSSL_RECORD_LAYER *rl, int type); }; -struct ossl_record_layer_st -{ +struct ossl_record_layer_st { OSSL_LIB_CTX *libctx; const char *propq; int isdtls; @@ -295,6 +293,9 @@ struct ossl_record_layer_st /* cryptographic state */ EVP_CIPHER_CTX *enc_ctx; + /* TLSv1.3 MAC ctx, only used with integrity-only cipher */ + EVP_MAC_CTX *mac_ctx; + /* Explicit IV length */ size_t eivlen; @@ -321,6 +322,7 @@ struct ossl_record_layer_st /* TLSv1.3 record padding */ size_t block_padding; + size_t hs_padding; /* Only used by SSLv3 */ unsigned char mac_secret[EVP_MAX_MD_SIZE]; @@ -333,8 +335,8 @@ struct ossl_record_layer_st int tlstree; /* TLSv1.3 fields */ - /* static IV */ - unsigned char iv[EVP_MAX_IV_LENGTH]; + unsigned char *iv; /* static IV */ + unsigned char *nonce; /* part of static IV followed by sequence number */ int allow_plain_alerts; /* TLS "any" fields */ diff --git a/ssl/record/methods/tls13_meth.c b/ssl/record/methods/tls13_meth.c index d782c327ec..6bbba84d0d 100644 --- a/ssl/record/methods/tls13_meth.c +++ b/ssl/record/methods/tls13_meth.c @@ -24,15 +24,42 @@ static int tls13_set_crypto_state(OSSL_RECORD_LAYER *rl, int level, COMP_METHOD *comp) { EVP_CIPHER_CTX *ciph_ctx; + EVP_MAC_CTX *mac_ctx; + EVP_MAC *mac; + OSSL_PARAM params[2], *p = params; int mode; int enc = (rl->direction == OSSL_RECORD_DIRECTION_WRITE) ? 1 : 0; - if (ivlen > sizeof(rl->iv)) { - ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); + rl->iv = OPENSSL_malloc(ivlen); + if (rl->iv == NULL) return OSSL_RECORD_RETURN_FATAL; - } + + rl->nonce = OPENSSL_malloc(ivlen); + if (rl->nonce == NULL) + return OSSL_RECORD_RETURN_FATAL; + memcpy(rl->iv, iv, ivlen); + /* Integrity only */ + if (EVP_CIPHER_is_a(ciph, "NULL") && mactype == NID_hmac && md != NULL) { + mac = EVP_MAC_fetch(rl->libctx, "HMAC", rl->propq); + if (mac == NULL + || (mac_ctx = rl->mac_ctx = EVP_MAC_CTX_new(mac)) == NULL) { + EVP_MAC_free(mac); + ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); + return OSSL_RECORD_RETURN_FATAL; + } + EVP_MAC_free(mac); + *p++ = OSSL_PARAM_construct_utf8_string(OSSL_MAC_PARAM_DIGEST, + (char *)EVP_MD_name(md), 0); + *p = OSSL_PARAM_construct_end(); + if (!EVP_MAC_init(mac_ctx, key, keylen, params)) { + ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); + return OSSL_RECORD_RETURN_FATAL; + } + goto end; + } + ciph_ctx = rl->enc_ctx = EVP_CIPHER_CTX_new(); if (ciph_ctx == NULL) { ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); @@ -51,7 +78,7 @@ static int tls13_set_crypto_state(OSSL_RECORD_LAYER *rl, int level, ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); return OSSL_RECORD_RETURN_FATAL; } - + end: return OSSL_RECORD_RETURN_SUCCESS; } @@ -59,15 +86,18 @@ static int tls13_cipher(OSSL_RECORD_LAYER *rl, TLS_RL_RECORD *recs, size_t n_recs, int sending, SSL_MAC_BUF *mac, size_t macsize) { - EVP_CIPHER_CTX *ctx; - unsigned char iv[EVP_MAX_IV_LENGTH], recheader[SSL3_RT_HEADER_LENGTH]; - size_t ivlen, offset, loop, hdrlen; + EVP_CIPHER_CTX *enc_ctx; + unsigned char recheader[SSL3_RT_HEADER_LENGTH]; + unsigned char tag[EVP_MAX_MD_SIZE]; + size_t nonce_len, offset, loop, hdrlen, taglen; unsigned char *staticiv; + unsigned char *nonce; unsigned char *seq = rl->sequence; int lenu, lenf; TLS_RL_RECORD *rec = &recs[0]; WPACKET wpkt; const EVP_CIPHER *cipher; + EVP_MAC_CTX *mac_ctx = NULL; int mode; if (n_recs != 1) { @@ -76,15 +106,14 @@ static int tls13_cipher(OSSL_RECORD_LAYER *rl, TLS_RL_RECORD *recs, return 0; } - ctx = rl->enc_ctx; + enc_ctx = rl->enc_ctx; /* enc_ctx is ignored when rl->mac_ctx != NULL */ staticiv = rl->iv; + nonce = rl->nonce; - cipher = EVP_CIPHER_CTX_get0_cipher(ctx); - if (cipher == NULL) { + if (enc_ctx == NULL && rl->mac_ctx == NULL) { RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); return 0; } - mode = EVP_CIPHER_get_mode(cipher); /* * If we're sending an alert and ctx != NULL then we must be forcing @@ -92,13 +121,25 @@ static int tls13_cipher(OSSL_RECORD_LAYER *rl, TLS_RL_RECORD *recs, * plaintext alerts at certain points in the handshake. If we've got this * far then we have already validated that a plaintext alert is ok here. */ - if (ctx == NULL || rec->type == SSL3_RT_ALERT) { + if (rec->type == SSL3_RT_ALERT) { memmove(rec->data, rec->input, rec->length); rec->input = rec->data; return 1; } - ivlen = EVP_CIPHER_CTX_get_iv_length(ctx); + /* For integrity-only ciphers, nonce_len is same as MAC size */ + if (rl->mac_ctx != NULL) { + nonce_len = EVP_MAC_CTX_get_mac_size(rl->mac_ctx); + } else { + int ivlen = EVP_CIPHER_CTX_get_iv_length(enc_ctx); + + if (ivlen < 0) { + /* Should not happen */ + RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + return 0; + } + nonce_len = (size_t)ivlen; + } if (!sending) { /* @@ -110,30 +151,22 @@ static int tls13_cipher(OSSL_RECORD_LAYER *rl, TLS_RL_RECORD *recs, rec->length -= rl->taglen; } - /* Set up IV */ - if (ivlen < SEQ_NUM_SIZE) { + /* Set up nonce: part of static IV followed by sequence number */ + if (nonce_len < SEQ_NUM_SIZE) { /* Should not happen */ RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); return 0; } - offset = ivlen - SEQ_NUM_SIZE; - memcpy(iv, staticiv, offset); + offset = nonce_len - SEQ_NUM_SIZE; + memcpy(nonce, staticiv, offset); for (loop = 0; loop < SEQ_NUM_SIZE; loop++) - iv[offset + loop] = staticiv[offset + loop] ^ seq[loop]; + nonce[offset + loop] = staticiv[offset + loop] ^ seq[loop]; if (!tls_increment_sequence_ctr(rl)) { /* RLAYERfatal already called */ return 0; } - if (EVP_CipherInit_ex(ctx, NULL, NULL, NULL, iv, sending) <= 0 - || (!sending && EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_SET_TAG, - rl->taglen, - rec->data + rec->length) <= 0)) { - RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); - return 0; - } - /* Set up the AAD */ if (!WPACKET_init_static_len(&wpkt, recheader, sizeof(recheader), 0) || !WPACKET_put_bytes_u8(&wpkt, rec->type) @@ -147,24 +180,64 @@ static int tls13_cipher(OSSL_RECORD_LAYER *rl, TLS_RL_RECORD *recs, return 0; } + if (rl->mac_ctx != NULL) { + int ret = 0; + + if ((mac_ctx = EVP_MAC_CTX_dup(rl->mac_ctx)) == NULL + || !EVP_MAC_update(mac_ctx, nonce, nonce_len) + || !EVP_MAC_update(mac_ctx, recheader, sizeof(recheader)) + || !EVP_MAC_update(mac_ctx, rec->input, rec->length) + || !EVP_MAC_final(mac_ctx, tag, &taglen, rl->taglen)) { + RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + goto end_mac; + } + + if (sending) { + memcpy(rec->data + rec->length, tag, rl->taglen); + rec->length += rl->taglen; + } else if (CRYPTO_memcmp(tag, rec->data + rec->length, + rl->taglen) != 0) { + goto end_mac; + } + ret = 1; + end_mac: + EVP_MAC_CTX_free(mac_ctx); + return ret; + } + + cipher = EVP_CIPHER_CTX_get0_cipher(enc_ctx); + if (cipher == NULL) { + RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + return 0; + } + mode = EVP_CIPHER_get_mode(cipher); + + if (EVP_CipherInit_ex(enc_ctx, NULL, NULL, NULL, nonce, sending) <= 0 + || (!sending && EVP_CIPHER_CTX_ctrl(enc_ctx, EVP_CTRL_AEAD_SET_TAG, + rl->taglen, + rec->data + rec->length) <= 0)) { + RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + return 0; + } + /* * For CCM we must explicitly set the total plaintext length before we add * any AAD. */ if ((mode == EVP_CIPH_CCM_MODE - && EVP_CipherUpdate(ctx, NULL, &lenu, NULL, + && EVP_CipherUpdate(enc_ctx, NULL, &lenu, NULL, (unsigned int)rec->length) <= 0) - || EVP_CipherUpdate(ctx, NULL, &lenu, recheader, + || EVP_CipherUpdate(enc_ctx, NULL, &lenu, recheader, sizeof(recheader)) <= 0 - || EVP_CipherUpdate(ctx, rec->data, &lenu, rec->input, + || EVP_CipherUpdate(enc_ctx, rec->data, &lenu, rec->input, (unsigned int)rec->length) <= 0 - || EVP_CipherFinal_ex(ctx, rec->data + lenu, &lenf) <= 0 + || EVP_CipherFinal_ex(enc_ctx, rec->data + lenu, &lenf) <= 0 || (size_t)(lenu + lenf) != rec->length) { return 0; } if (sending) { /* Add the tag */ - if (EVP_CIPHER_CTX_ctrl(ctx, EVP_CTRL_AEAD_GET_TAG, rl->taglen, + if (EVP_CIPHER_CTX_ctrl(enc_ctx, EVP_CTRL_AEAD_GET_TAG, rl->taglen, rec->data + rec->length) <= 0) { RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); return 0; @@ -270,22 +343,51 @@ static int tls13_add_record_padding(OSSL_RECORD_LAYER *rl, size_t padding = 0; size_t max_padding = rl->max_frag_len - rlen; + /* + * We might want to change the "else if" below so that + * library-added padding can still happen even if there + * is an application-layer callback. The reason being + * the application may not be aware that the effectiveness + * of ECH could be damaged if the callback e.g. only + * padded application data. However, doing so would be + * a change that could break some application that has + * a client and server that both know what padding they + * like, and that dislike any other padding. That'd need + * one of those to have been updated though so the + * probability may be low enough that we could change + * the "else if" below to just an "if" and pick the + * larger of the library and callback's idea of padding. + * (Still subject to max_padding though.) + */ if (rl->padding != NULL) { padding = rl->padding(rl->cbarg, thistempl->type, rlen); - } else if (rl->block_padding > 0) { - size_t mask = rl->block_padding - 1; - size_t remainder; - - /* optimize for power of 2 */ - if ((rl->block_padding & mask) == 0) - remainder = rlen & mask; - else - remainder = rlen % rl->block_padding; - /* don't want to add a block of padding if we don't have to */ - if (remainder == 0) - padding = 0; - else - padding = rl->block_padding - remainder; + } else if (rl->block_padding > 0 || rl->hs_padding > 0) { + size_t mask, bp = 0, remainder; + + /* + * pad handshake or alert messages based on |hs_padding| + * but application data based on |block_padding| + */ + if (thistempl->type == SSL3_RT_HANDSHAKE && rl->hs_padding > 0) + bp = rl->hs_padding; + else if (thistempl->type == SSL3_RT_ALERT && rl->hs_padding > 0) + bp = rl->hs_padding; + else if (thistempl->type == SSL3_RT_APPLICATION_DATA + && rl->block_padding > 0) + bp = rl->block_padding; + if (bp > 0) { + mask = bp - 1; + /* optimize for power of 2 */ + if ((bp & mask) == 0) + remainder = rlen & mask; + else + remainder = rlen % bp; + /* don't want to add a block of padding if we don't have to */ + if (remainder == 0) + padding = 0; + else + padding = bp - remainder; + } } if (padding > 0) { /* do not allow the record to exceed max plaintext length */ diff --git a/ssl/record/methods/tls_common.c b/ssl/record/methods/tls_common.c index 6cb8e88704..175086ee17 100644 --- a/ssl/record/methods/tls_common.c +++ b/ssl/record/methods/tls_common.c @@ -73,7 +73,7 @@ int ossl_set_tls_provider_parameters(OSSL_RECORD_LAYER *rl, if ((EVP_CIPHER_get_flags(ciph) & EVP_CIPH_FLAG_AEAD_CIPHER) == 0 && !rl->use_etm) imacsize = EVP_MD_get_size(md); - if (imacsize >= 0) + if (imacsize > 0) macsize = (size_t)imacsize; *pprm++ = OSSL_PARAM_construct_int(OSSL_CIPHER_PARAM_TLS_VERSION, @@ -744,14 +744,17 @@ int tls_get_more_records(OSSL_RECORD_LAYER *rl) * CCS messages must be exactly 1 byte long, containing the value 0x01 */ if (thisrr->length != 1 || thisrr->data[0] != 0x01) { - RLAYERfatal(rl, SSL_AD_ILLEGAL_PARAMETER, + RLAYERfatal(rl, SSL_AD_UNEXPECTED_MESSAGE, SSL_R_INVALID_CCS_MESSAGE); return OSSL_RECORD_RETURN_FATAL; } /* * CCS messages are ignored in TLSv1.3. We treat it like an empty - * handshake record + * handshake record - but we still call the msg_callback */ + if (rl->msg_callback != NULL) + rl->msg_callback(0, TLS1_3_VERSION, SSL3_RT_CHANGE_CIPHER_SPEC, + thisrr->data, 1, rl->cbarg); thisrr->type = SSL3_RT_HANDSHAKE; if (++(rl->empty_record_count) > MAX_EMPTY_RECORDS) { RLAYERfatal(rl, SSL_AD_UNEXPECTED_MESSAGE, @@ -770,7 +773,7 @@ int tls_get_more_records(OSSL_RECORD_LAYER *rl) if (tmpmd != NULL) { imac_size = EVP_MD_get_size(tmpmd); - if (!ossl_assert(imac_size >= 0 && imac_size <= EVP_MAX_MD_SIZE)) { + if (!ossl_assert(imac_size > 0 && imac_size <= EVP_MAX_MD_SIZE)) { RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); return OSSL_RECORD_RETURN_FATAL; } @@ -1218,6 +1221,12 @@ int tls_set_options(OSSL_RECORD_LAYER *rl, const OSSL_PARAM *options) ERR_raise(ERR_LIB_SSL, SSL_R_FAILED_TO_GET_PARAMETER); return 0; } + p = OSSL_PARAM_locate_const(options, + OSSL_LIBSSL_RECORD_LAYER_PARAM_HS_PADDING); + if (p != NULL && !OSSL_PARAM_get_size_t(p, &rl->hs_padding)) { + ERR_raise(ERR_LIB_SSL, SSL_R_FAILED_TO_GET_PARAMETER); + return 0; + } } if (rl->level == OSSL_RECORD_PROTECTION_LEVEL_APPLICATION) { @@ -1442,11 +1451,13 @@ static void tls_int_free(OSSL_RECORD_LAYER *rl) tls_release_write_buffer(rl); EVP_CIPHER_CTX_free(rl->enc_ctx); + EVP_MAC_CTX_free(rl->mac_ctx); EVP_MD_CTX_free(rl->md_ctx); #ifndef OPENSSL_NO_COMP COMP_CTX_free(rl->compctx); #endif - + OPENSSL_free(rl->iv); + OPENSSL_free(rl->nonce); if (rl->version == SSL3_VERSION) OPENSSL_cleanse(rl->mac_secret, sizeof(rl->mac_secret)); @@ -1922,10 +1933,13 @@ int tls_retry_write_records(OSSL_RECORD_LAYER *rl) else ret = OSSL_RECORD_RETURN_SUCCESS; } else { - if (BIO_should_retry(rl->bio)) + if (BIO_should_retry(rl->bio)) { ret = OSSL_RECORD_RETURN_RETRY; - else + } else { + ERR_raise_data(ERR_LIB_SYS, get_last_sys_error(), + "tls_retry_write_records failure"); ret = OSSL_RECORD_RETURN_FATAL; + } } } else { RLAYERfatal(rl, SSL_AD_INTERNAL_ERROR, SSL_R_BIO_NOT_SET); diff --git a/ssl/record/rec_layer_s3.c b/ssl/record/rec_layer_s3.c index 6a31efe1c0..14db7dab2c 100644 --- a/ssl/record/rec_layer_s3.c +++ b/ssl/record/rec_layer_s3.c @@ -19,6 +19,7 @@ #include #include "record_local.h" #include "internal/packet.h" +#include "internal/comp.h" void RECORD_LAYER_init(RECORD_LAYER *rl, SSL_CONNECTION *s) { @@ -1287,6 +1288,8 @@ int ssl_set_new_record_layer(SSL_CONNECTION *s, int version, } else { *opts++ = OSSL_PARAM_construct_size_t(OSSL_LIBSSL_RECORD_LAYER_PARAM_BLOCK_PADDING, &s->rlayer.block_padding); + *opts++ = OSSL_PARAM_construct_size_t(OSSL_LIBSSL_RECORD_LAYER_PARAM_HS_PADDING, + &s->rlayer.hs_padding); } *opts = OSSL_PARAM_construct_end(); diff --git a/ssl/record/record.h b/ssl/record/record.h index 9a076a1fb8..13f09fda8c 100644 --- a/ssl/record/record.h +++ b/ssl/record/record.h @@ -113,6 +113,7 @@ typedef struct record_layer_st { size_t (*record_padding_cb)(SSL *s, int type, size_t len, void *arg); void *record_padding_arg; size_t block_padding; + size_t hs_padding; /* How many records we have read from the record layer */ size_t num_recs; diff --git a/ssl/s3_enc.c b/ssl/s3_enc.c index 878556b069..cda1f7f83b 100644 --- a/ssl/s3_enc.c +++ b/ssl/s3_enc.c @@ -113,7 +113,7 @@ int ssl3_change_cipher_state(SSL_CONNECTION *s, int which) p = s->s3.tmp.key_block; mdi = EVP_MD_get_size(md); - if (mdi < 0) { + if (mdi <= 0) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); goto err; } @@ -188,7 +188,7 @@ int ssl3_setup_key_block(SSL_CONNECTION *s) #endif num = EVP_MD_get_size(hash); - if (num < 0) + if (num <= 0) return 0; num = EVP_CIPHER_get_key_length(c) + num + EVP_CIPHER_get_iv_length(c); diff --git a/ssl/s3_lib.c b/ssl/s3_lib.c index 2bc5e79fd1..86d81984a6 100644 --- a/ssl/s3_lib.c +++ b/ssl/s3_lib.c @@ -112,7 +112,40 @@ static SSL_CIPHER tls13_ciphers[] = { SSL_HANDSHAKE_MAC_SHA256, 64, /* CCM8 uses a short tag, so we have a low security strength */ 128, - } + }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS + { + 1, + TLS1_3_RFC_SHA256_SHA256, + TLS1_3_RFC_SHA256_SHA256, + TLS1_3_CK_SHA256_SHA256, + SSL_kANY, + SSL_aANY, + SSL_eNULL, + SSL_SHA256, + TLS1_3_VERSION, TLS1_3_VERSION, + 0, 0, + SSL_NOT_DEFAULT | SSL_STRONG_NONE, + SSL_HANDSHAKE_MAC_SHA256, + 0, + 256, + }, { + 1, + TLS1_3_RFC_SHA384_SHA384, + TLS1_3_RFC_SHA384_SHA384, + TLS1_3_CK_SHA384_SHA384, + SSL_kANY, + SSL_aANY, + SSL_eNULL, + SSL_SHA384, + TLS1_3_VERSION, TLS1_3_VERSION, + 0, 0, + SSL_NOT_DEFAULT | SSL_STRONG_NONE, + SSL_HANDSHAKE_MAC_SHA384, + 0, + 384, + }, +#endif }; /* @@ -126,6 +159,7 @@ static SSL_CIPHER tls13_ciphers[] = { * Weak ciphers */ static SSL_CIPHER ssl3_ciphers[] = { +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, SSL3_TXT_RSA_NULL_MD5, @@ -158,6 +192,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif #ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -170,7 +205,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -186,7 +221,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -202,7 +237,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -218,7 +253,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -352,6 +387,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_RSA_WITH_NULL_SHA256, @@ -368,6 +404,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif { 1, TLS1_TXT_RSA_WITH_AES_128_SHA256, @@ -944,6 +981,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 64, /* CCM8 uses a short tag, so we have a low security strength */ 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_ECDHE_ECDSA_WITH_NULL_SHA, @@ -960,6 +998,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -972,7 +1011,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, TLS1_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1010,6 +1049,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_ECDHE_RSA_WITH_NULL_SHA, @@ -1026,6 +1066,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -1038,7 +1079,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, TLS1_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1076,6 +1117,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_ECDH_anon_WITH_NULL_SHA, @@ -1092,6 +1134,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -1104,7 +1147,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, TLS1_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1270,6 +1313,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_PSK_WITH_NULL_SHA, @@ -1318,6 +1362,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -1330,7 +1375,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1380,7 +1425,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1430,7 +1475,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, SSL3_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1596,6 +1641,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_PSK_WITH_NULL_SHA256, @@ -1628,6 +1674,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif { 1, TLS1_TXT_DHE_PSK_WITH_AES_128_CBC_SHA256, @@ -1660,6 +1707,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_DHE_PSK_WITH_NULL_SHA256, @@ -1692,6 +1740,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif { 1, TLS1_TXT_RSA_PSK_WITH_AES_128_CBC_SHA256, @@ -1724,6 +1773,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_RSA_PSK_WITH_NULL_SHA256, @@ -1756,6 +1806,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -1768,7 +1819,7 @@ static SSL_CIPHER ssl3_ciphers[] = { SSL_SHA1, TLS1_VERSION, TLS1_2_VERSION, DTLS1_BAD_VER, DTLS1_2_VERSION, - SSL_NOT_DEFAULT | SSL_MEDIUM | SSL_FIPS, + SSL_NOT_DEFAULT | SSL_MEDIUM, SSL_HANDSHAKE_MAC_DEFAULT | TLS1_PRF, 112, 168, @@ -1838,6 +1889,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +#ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, TLS1_TXT_ECDHE_PSK_WITH_NULL_SHA, @@ -1886,7 +1938,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, - +#endif # ifndef OPENSSL_NO_WEAK_SSL_CIPHERS { 1, @@ -2613,6 +2665,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +# ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, "GOST2001-NULL-GOST94", @@ -2629,6 +2682,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +# endif { 1, "IANA-GOST2012-GOST8912-GOST8912", @@ -2661,6 +2715,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 256, 256, }, +# ifndef OPENSSL_NO_INTEGRITY_ONLY_CIPHERS { 1, "GOST2012-NULL-GOST12", @@ -2677,6 +2732,7 @@ static SSL_CIPHER ssl3_ciphers[] = { 0, 0, }, +# endif { 1, "GOST2012-KUZNYECHIK-KUZNYECHIKOMAC", diff --git a/ssl/ssl_cert.c b/ssl/ssl_cert.c index f11eb75827..04d08430e7 100644 --- a/ssl/ssl_cert.c +++ b/ssl/ssl_cert.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright (c) 2002, Oracle and/or its affiliates. All rights reserved * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -236,7 +236,7 @@ void ssl_cert_clear_certs(CERT *c) #ifndef OPENSSL_NO_COMP_ALG int j; #endif - + if (c == NULL) return; for (i = 0; i < c->ssl_pkey_num; i++) { @@ -813,16 +813,14 @@ STACK_OF(X509_NAME) *SSL_load_client_CA_file(const char *file) return SSL_load_client_CA_file_ex(file, NULL, NULL); } -int SSL_add_file_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, - const char *file) +static int add_file_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, + const char *file, + LHASH_OF(X509_NAME) *name_hash) { BIO *in; X509 *x = NULL; X509_NAME *xn = NULL; int ret = 1; - int (*oldcmp) (const X509_NAME *const *a, const X509_NAME *const *b); - - oldcmp = sk_X509_NAME_set_cmp_func(stack, xname_sk_cmp); in = BIO_new(BIO_s_file()); @@ -842,12 +840,15 @@ int SSL_add_file_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, xn = X509_NAME_dup(xn); if (xn == NULL) goto err; - if (sk_X509_NAME_find(stack, xn) >= 0) { + if (lh_X509_NAME_retrieve(name_hash, xn) != NULL) { /* Duplicate. */ X509_NAME_free(xn); } else if (!sk_X509_NAME_push(stack, xn)) { X509_NAME_free(xn); goto err; + } else { + /* Successful insert, add to hash table */ + lh_X509_NAME_insert(name_hash, xn); } } @@ -859,7 +860,42 @@ int SSL_add_file_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, done: BIO_free(in); X509_free(x); - (void)sk_X509_NAME_set_cmp_func(stack, oldcmp); + return ret; +} + +int SSL_add_file_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, + const char *file) +{ + X509_NAME *xn = NULL; + int ret = 1; + int idx = 0; + int num = 0; + LHASH_OF(X509_NAME) *name_hash = lh_X509_NAME_new(xname_hash, xname_cmp); + + if (name_hash == NULL) { + ERR_raise(ERR_LIB_SSL, ERR_R_CRYPTO_LIB); + goto err; + } + + /* + * Pre-populate the lhash with the existing entries of the stack, since + * using the LHASH_OF is much faster for duplicate checking. That's because + * xname_cmp converts the X509_NAMEs to DER involving a memory allocation + * for every single invocation of the comparison function. + */ + num = sk_X509_NAME_num(stack); + for (idx = 0; idx < num; idx++) { + xn = sk_X509_NAME_value(stack, idx); + lh_X509_NAME_insert(name_hash, xn); + } + + ret = add_file_cert_subjects_to_stack(stack, file, name_hash); + goto done; + + err: + ret = 0; + done: + lh_X509_NAME_free(name_hash); return ret; } @@ -869,8 +905,27 @@ int SSL_add_dir_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, OPENSSL_DIR_CTX *d = NULL; const char *filename; int ret = 0; + X509_NAME *xn = NULL; + int idx = 0; + int num = 0; + LHASH_OF(X509_NAME) *name_hash = lh_X509_NAME_new(xname_hash, xname_cmp); - /* Note that a side effect is that the CAs will be sorted by name */ + if (name_hash == NULL) { + ERR_raise(ERR_LIB_SSL, ERR_R_CRYPTO_LIB); + goto err; + } + + /* + * Pre-populate the lhash with the existing entries of the stack, since + * using the LHASH_OF is much faster for duplicate checking. That's because + * xname_cmp converts the X509_NAMEs to DER involving a memory allocation + * for every single invocation of the comparison function. + */ + num = sk_X509_NAME_num(stack); + for (idx = 0; idx < num; idx++) { + xn = sk_X509_NAME_value(stack, idx); + lh_X509_NAME_insert(name_hash, xn); + } while ((filename = OPENSSL_DIR_read(&d, dir))) { char buf[1024]; @@ -899,7 +954,7 @@ int SSL_add_dir_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, #endif if (r <= 0 || r >= (int)sizeof(buf)) goto err; - if (!SSL_add_file_cert_subjects_to_stack(stack, buf)) + if (!add_file_cert_subjects_to_stack(stack, buf, name_hash)) goto err; } @@ -915,6 +970,7 @@ int SSL_add_dir_cert_subjects_to_stack(STACK_OF(X509_NAME) *stack, err: if (d) OPENSSL_DIR_end(&d); + lh_X509_NAME_free(name_hash); return ret; } diff --git a/ssl/ssl_cert_comp.c b/ssl/ssl_cert_comp.c index 639610a5f7..ba9bfb480c 100644 --- a/ssl/ssl_cert_comp.c +++ b/ssl/ssl_cert_comp.c @@ -1,5 +1,5 @@ /* - * Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2022-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -21,7 +21,7 @@ size_t ossl_calculate_comp_expansion(int alg, size_t length) * Brotli: per RFC7932: N + 5 + 3 * (N >> 16) * ZSTD: N + 4 + 14 + 3 * (N >> 17) + 4 */ - + switch (alg) { case TLSEXT_comp_cert_zlib: ret = length + 11 + 5 * (length >> 14); diff --git a/ssl/ssl_ciph.c b/ssl/ssl_ciph.c index ddde21b968..e5d6237176 100644 --- a/ssl/ssl_ciph.c +++ b/ssl/ssl_ciph.c @@ -21,6 +21,7 @@ #include "ssl_local.h" #include "internal/thread_once.h" #include "internal/cryptlib.h" +#include "internal/comp.h" /* NB: make sure indices in these tables match values above */ @@ -57,16 +58,6 @@ static const ssl_cipher_table ssl_cipher_table_cipher[SSL_ENC_NUM_IDX] = { {SSL_KUZNYECHIK, NID_kuznyechik_ctr_acpkm}, /* SSL_ENC_KUZNYECHIK_IDX */ }; -#define SSL_COMP_NULL_IDX 0 -#define SSL_COMP_ZLIB_IDX 1 -#define SSL_COMP_NUM_IDX 2 - -static STACK_OF(SSL_COMP) *ssl_comp_methods = NULL; - -#ifndef OPENSSL_NO_COMP -static CRYPTO_ONCE ssl_load_builtin_comp_once = CRYPTO_ONCE_STATIC_INIT; -#endif - /* NB: make sure indices in this table matches values above */ static const ssl_cipher_table ssl_cipher_table_mac[SSL_MD_NUM_IDX] = { {SSL_MD5, NID_md5}, /* SSL_MD_MD5_IDX 0 */ @@ -347,7 +338,8 @@ int ssl_load_ciphers(SSL_CTX *ctx) ctx->disabled_mac_mask |= t->mask; } else { int tmpsize = EVP_MD_get_size(md); - if (!ossl_assert(tmpsize >= 0)) + + if (!ossl_assert(tmpsize > 0)) return 0; ctx->ssl_mac_secret_size[i] = tmpsize; } @@ -445,44 +437,11 @@ int ssl_load_ciphers(SSL_CTX *ctx) return 1; } -#ifndef OPENSSL_NO_COMP - -static int sk_comp_cmp(const SSL_COMP *const *a, const SSL_COMP *const *b) -{ - return ((*a)->id - (*b)->id); -} - -DEFINE_RUN_ONCE_STATIC(do_load_builtin_compressions) -{ - SSL_COMP *comp = NULL; - COMP_METHOD *method = COMP_zlib(); - - ssl_comp_methods = sk_SSL_COMP_new(sk_comp_cmp); - - if (COMP_get_type(method) != NID_undef && ssl_comp_methods != NULL) { - comp = OPENSSL_malloc(sizeof(*comp)); - if (comp != NULL) { - comp->method = method; - comp->id = SSL_COMP_ZLIB_IDX; - comp->name = COMP_get_name(method); - if (!sk_SSL_COMP_push(ssl_comp_methods, comp)) - OPENSSL_free(comp); - sk_SSL_COMP_sort(ssl_comp_methods); - } - } - return 1; -} - -static int load_builtin_compressions(void) -{ - return RUN_ONCE(&ssl_load_builtin_comp_once, do_load_builtin_compressions); -} -#endif - int ssl_cipher_get_evp_cipher(SSL_CTX *ctx, const SSL_CIPHER *sslc, const EVP_CIPHER **enc) { - int i = ssl_cipher_info_lookup(ssl_cipher_table_cipher, sslc->algorithm_enc); + int i = ssl_cipher_info_lookup(ssl_cipher_table_cipher, + sslc->algorithm_enc); if (i == -1) { *enc = NULL; @@ -508,6 +467,33 @@ int ssl_cipher_get_evp_cipher(SSL_CTX *ctx, const SSL_CIPHER *sslc, return 1; } +int ssl_cipher_get_evp_md_mac(SSL_CTX *ctx, const SSL_CIPHER *sslc, + const EVP_MD **md, + int *mac_pkey_type, size_t *mac_secret_size) +{ + int i = ssl_cipher_info_lookup(ssl_cipher_table_mac, sslc->algorithm_mac); + + if (i == -1) { + *md = NULL; + if (mac_pkey_type != NULL) + *mac_pkey_type = NID_undef; + if (mac_secret_size != NULL) + *mac_secret_size = 0; + } else { + const EVP_MD *digest = ctx->ssl_digest_methods[i]; + + if (digest == NULL || !ssl_evp_md_up_ref(digest)) + return 0; + + *md = digest; + if (mac_pkey_type != NULL) + *mac_pkey_type = ctx->ssl_mac_pkey_id[i]; + if (mac_secret_size != NULL) + *mac_secret_size = ctx->ssl_mac_secret_size[i]; + } + return 1; +} + int ssl_cipher_get_evp(SSL_CTX *ctx, const SSL_SESSION *s, const EVP_CIPHER **enc, const EVP_MD **md, int *mac_pkey_type, size_t *mac_secret_size, @@ -521,20 +507,15 @@ int ssl_cipher_get_evp(SSL_CTX *ctx, const SSL_SESSION *s, return 0; if (comp != NULL) { SSL_COMP ctmp; -#ifndef OPENSSL_NO_COMP - if (!load_builtin_compressions()) { - /* - * Currently don't care, since a failure only means that - * ssl_comp_methods is NULL, which is perfectly OK - */ - } -#endif + STACK_OF(SSL_COMP) *comp_methods; + *comp = NULL; ctmp.id = s->compress_meth; - if (ssl_comp_methods != NULL) { - i = sk_SSL_COMP_find(ssl_comp_methods, &ctmp); + comp_methods = SSL_COMP_get_compression_methods(); + if (comp_methods != NULL) { + i = sk_SSL_COMP_find(comp_methods, &ctmp); if (i >= 0) - *comp = sk_SSL_COMP_value(ssl_comp_methods, i); + *comp = sk_SSL_COMP_value(comp_methods, i); } /* If were only interested in comp then return success */ if ((enc == NULL) && (md == NULL)) @@ -547,34 +528,17 @@ int ssl_cipher_get_evp(SSL_CTX *ctx, const SSL_SESSION *s, if (!ssl_cipher_get_evp_cipher(ctx, c, enc)) return 0; - i = ssl_cipher_info_lookup(ssl_cipher_table_mac, c->algorithm_mac); - if (i == -1) { - *md = NULL; - if (mac_pkey_type != NULL) - *mac_pkey_type = NID_undef; - if (mac_secret_size != NULL) - *mac_secret_size = 0; - if (c->algorithm_mac == SSL_AEAD) - mac_pkey_type = NULL; - } else { - const EVP_MD *digest = ctx->ssl_digest_methods[i]; - - if (digest == NULL - || !ssl_evp_md_up_ref(digest)) { - ssl_evp_cipher_free(*enc); - return 0; - } - *md = digest; - if (mac_pkey_type != NULL) - *mac_pkey_type = ctx->ssl_mac_pkey_id[i]; - if (mac_secret_size != NULL) - *mac_secret_size = ctx->ssl_mac_secret_size[i]; + if (!ssl_cipher_get_evp_md_mac(ctx, c, md, mac_pkey_type, + mac_secret_size)) { + ssl_evp_cipher_free(*enc); + return 0; } if ((*enc != NULL) - && (*md != NULL + && (*md != NULL || (EVP_CIPHER_get_flags(*enc) & EVP_CIPH_FLAG_AEAD_CIPHER)) - && (!mac_pkey_type || *mac_pkey_type != NID_undef)) { + && (c->algorithm_mac == SSL_AEAD + || mac_pkey_type == NULL || *mac_pkey_type != NID_undef)) { const EVP_CIPHER *evp = NULL; if (use_etm @@ -638,6 +602,7 @@ const EVP_MD *ssl_prf_md(SSL_CONNECTION *s) ssl_get_algorithm2(s) >> TLS1_PRF_DGST_SHIFT); } + #define ITEM_SEP(a) \ (((a) == ':') || ((a) == ' ') || ((a) == ';') || ((a) == ',')) @@ -1977,17 +1942,19 @@ uint16_t SSL_CIPHER_get_protocol_id(const SSL_CIPHER *c) SSL_COMP *ssl3_comp_find(STACK_OF(SSL_COMP) *sk, int n) { SSL_COMP *ctmp; - int i, nn; + SSL_COMP srch_key; + int i; if ((n == 0) || (sk == NULL)) return NULL; - nn = sk_SSL_COMP_num(sk); - for (i = 0; i < nn; i++) { + srch_key.id = n; + i = sk_SSL_COMP_find(sk, &srch_key); + if (i >= 0) ctmp = sk_SSL_COMP_value(sk, i); - if (ctmp->id == n) - return ctmp; - } - return NULL; + else + ctmp = NULL; + + return ctmp; } #ifdef OPENSSL_NO_COMP @@ -2010,34 +1977,44 @@ int SSL_COMP_add_compression_method(int id, COMP_METHOD *cm) #else STACK_OF(SSL_COMP) *SSL_COMP_get_compression_methods(void) { - load_builtin_compressions(); - return ssl_comp_methods; + STACK_OF(SSL_COMP) **rv; + + rv = (STACK_OF(SSL_COMP) **)OSSL_LIB_CTX_get_data(NULL, + OSSL_LIB_CTX_COMP_METHODS); + if (rv != NULL) + return *rv; + else + return NULL; } STACK_OF(SSL_COMP) *SSL_COMP_set0_compression_methods(STACK_OF(SSL_COMP) *meths) { - STACK_OF(SSL_COMP) *old_meths = ssl_comp_methods; - ssl_comp_methods = meths; - return old_meths; -} + STACK_OF(SSL_COMP) **comp_methods; + STACK_OF(SSL_COMP) *old_meths; -static void cmeth_free(SSL_COMP *cm) -{ - OPENSSL_free(cm); -} + comp_methods = (STACK_OF(SSL_COMP) **)OSSL_LIB_CTX_get_data(NULL, + OSSL_LIB_CTX_COMP_METHODS); + if (comp_methods == NULL) { + old_meths = meths; + } else { + old_meths = *comp_methods; + *comp_methods = meths; + } -void ssl_comp_free_compression_methods_int(void) -{ - STACK_OF(SSL_COMP) *old_meths = ssl_comp_methods; - ssl_comp_methods = NULL; - sk_SSL_COMP_pop_free(old_meths, cmeth_free); + return old_meths; } int SSL_COMP_add_compression_method(int id, COMP_METHOD *cm) { + STACK_OF(SSL_COMP) *comp_methods; SSL_COMP *comp; + comp_methods = SSL_COMP_get_compression_methods(); + + if (comp_methods == NULL) + return 1; + if (cm == NULL || COMP_get_type(cm) == NID_undef) return 1; @@ -2059,18 +2036,17 @@ int SSL_COMP_add_compression_method(int id, COMP_METHOD *cm) return 1; comp->id = id; - comp->method = cm; - load_builtin_compressions(); - if (ssl_comp_methods && sk_SSL_COMP_find(ssl_comp_methods, comp) >= 0) { + if (sk_SSL_COMP_find(comp_methods, comp) >= 0) { OPENSSL_free(comp); ERR_raise(ERR_LIB_SSL, SSL_R_DUPLICATE_COMPRESSION_ID); return 1; } - if (ssl_comp_methods == NULL || !sk_SSL_COMP_push(ssl_comp_methods, comp)) { + if (!sk_SSL_COMP_push(comp_methods, comp)) { OPENSSL_free(comp); ERR_raise(ERR_LIB_SSL, ERR_R_CRYPTO_LIB); return 1; } + return 0; } #endif @@ -2184,7 +2160,7 @@ int ssl_cipher_get_overhead(const SSL_CIPHER *c, size_t *mac_overhead, size_t *int_overhead, size_t *blocksize, size_t *ext_overhead) { - size_t mac = 0, in = 0, blk = 0, out = 0; + int mac = 0, in = 0, blk = 0, out = 0; /* Some hard-coded numbers for the CCM/Poly1305 MAC overhead * because there are no handy #defines for those. */ @@ -2208,6 +2184,8 @@ int ssl_cipher_get_overhead(const SSL_CIPHER *c, size_t *mac_overhead, return 0; mac = EVP_MD_get_size(e_md); + if (mac <= 0) + return 0; if (c->algorithm_enc != SSL_eNULL) { int cipher_nid = SSL_CIPHER_get_cipher_nid(c); const EVP_CIPHER *e_ciph = EVP_get_cipherbynid(cipher_nid); @@ -2220,16 +2198,18 @@ int ssl_cipher_get_overhead(const SSL_CIPHER *c, size_t *mac_overhead, in = 1; /* padding length byte */ out = EVP_CIPHER_get_iv_length(e_ciph); + if (out < 0) + return 0; blk = EVP_CIPHER_get_block_size(e_ciph); - if (blk == 0) + if (blk <= 0) return 0; } } - *mac_overhead = mac; - *int_overhead = in; - *blocksize = blk; - *ext_overhead = out; + *mac_overhead = (size_t)mac; + *int_overhead = (size_t)in; + *blocksize = (size_t)blk; + *ext_overhead = (size_t)out; return 1; } diff --git a/ssl/ssl_conf.c b/ssl/ssl_conf.c index 77de00542b..5e2d7c1c98 100644 --- a/ssl/ssl_conf.c +++ b/ssl/ssl_conf.c @@ -649,21 +649,48 @@ static int cmd_DHParameters(SSL_CONF_CTX *cctx, const char *value) return rv > 0; } +/* + * |value| input is "" + * where the first number is the padding block size for + * application data, and the optional second is the + * padding block size for handshake messages + */ static int cmd_RecordPadding(SSL_CONF_CTX *cctx, const char *value) { int rv = 0; - int block_size = atoi(value); + unsigned long block_padding = 0, hs_padding = 0; + char *commap = NULL, *copy = NULL; + char *endptr = NULL; + + copy = OPENSSL_strdup(value); + if (copy == NULL) + return 0; + commap = strstr(copy, ","); + if (commap != NULL) { + *commap = '\0'; + if (*(commap + 1) == '\0') { + OPENSSL_free(copy); + return 0; + } + if (!OPENSSL_strtoul(commap + 1, &endptr, 0, &hs_padding)) + return 0; + } + if (!OPENSSL_strtoul(copy, &endptr, 0, &block_padding)) + return 0; + if (commap == NULL) + hs_padding = block_padding; + OPENSSL_free(copy); /* - * All we care about is a non-negative value, + * All we care about are non-negative values, * the setters check the range */ - if (block_size >= 0) { - if (cctx->ctx) - rv = SSL_CTX_set_block_padding(cctx->ctx, block_size); - if (cctx->ssl) - rv = SSL_set_block_padding(cctx->ssl, block_size); - } + if (cctx->ctx) + rv = SSL_CTX_set_block_padding_ex(cctx->ctx, (size_t)block_padding, + (size_t)hs_padding); + if (cctx->ssl) + rv = SSL_set_block_padding_ex(cctx->ssl, (size_t)block_padding, + (size_t)hs_padding); return rv; } diff --git a/ssl/ssl_err.c b/ssl/ssl_err.c index f5fb4107f6..3ef6afd03e 100644 --- a/ssl/ssl_err.c +++ b/ssl/ssl_err.c @@ -164,6 +164,8 @@ static const ERR_STRING_DATA SSL_str_reasons[] = { "encrypted length too long"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_ERROR_IN_RECEIVED_CIPHER_LIST), "error in received cipher list"}, + {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_ERROR_IN_SYSTEM_DEFAULT_CONFIG), + "error in system default config"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_ERROR_SETTING_TLSA_BASE_DOMAIN), "error setting tlsa base domain"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_EXCEEDS_MAX_FRAGMENT_SIZE), @@ -272,6 +274,8 @@ static const ERR_STRING_DATA SSL_str_reasons[] = { "can't find SRP server param"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_MISSING_SUPPORTED_GROUPS_EXTENSION), "missing supported groups extension"}, + {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_MISSING_SUPPORTED_VERSIONS_EXTENSION), + "missing supported versions extension"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_MISSING_TMP_DH_KEY), "missing tmp dh key"}, {ERR_PACK(ERR_LIB_SSL, 0, SSL_R_MISSING_TMP_ECDH_KEY), "missing tmp ecdh key"}, diff --git a/ssl/ssl_init.c b/ssl/ssl_init.c index 70e567b72c..ea6f60f72d 100644 --- a/ssl/ssl_init.c +++ b/ssl/ssl_init.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -19,8 +19,6 @@ static int stopped; -static void ssl_library_stop(void); - static CRYPTO_ONCE ssl_base = CRYPTO_ONCE_STATIC_INIT; static int ssl_base_inited = 0; DEFINE_RUN_ONCE_STATIC(ossl_init_ssl_base) @@ -36,11 +34,6 @@ DEFINE_RUN_ONCE_STATIC(ossl_init_ssl_base) #endif ssl_sort_cipher_list(); OSSL_TRACE(INIT, "ossl_init_ssl_base: SSL_add_ssl_module()\n"); - /* - * We ignore an error return here. Not much we can do - but not that bad - * either. We can still safely continue. - */ - OPENSSL_atexit(ssl_library_stop); ssl_base_inited = 1; return 1; } @@ -67,22 +60,6 @@ DEFINE_RUN_ONCE_STATIC_ALT(ossl_init_no_load_ssl_strings, return 1; } -static void ssl_library_stop(void) -{ - /* Might be explicitly called and also by atexit */ - if (stopped) - return; - stopped = 1; - - if (ssl_base_inited) { -#ifndef OPENSSL_NO_COMP - OSSL_TRACE(INIT, "ssl_library_stop: " - "ssl_comp_free_compression_methods_int()\n"); - ssl_comp_free_compression_methods_int(); -#endif - } -} - /* * If this function is called with a non NULL settings value then it must be * called prior to any threads making calls to any OpenSSL functions, diff --git a/ssl/ssl_lib.c b/ssl/ssl_lib.c index 4c20ac4bf1..ba9fcec55c 100644 --- a/ssl/ssl_lib.c +++ b/ssl/ssl_lib.c @@ -9,7 +9,6 @@ * https://www.openssl.org/source/license.html */ -#include #include "ssl_local.h" #include "internal/e_os.h" #include @@ -22,10 +21,12 @@ #include #include #include +#include #include "internal/cryptlib.h" #include "internal/nelem.h" #include "internal/refcount.h" #include "internal/ktls.h" +#include "internal/to_hex.h" #include "quic/quic_local.h" static int ssl_undefined_function_3(SSL_CONNECTION *sc, unsigned char *r, @@ -265,6 +266,7 @@ static int dane_tlsa_add(SSL_DANE *dane, int ilen = (int)dlen; int i; int num; + int mdsize; if (dane->trecs == NULL) { ERR_raise(ERR_LIB_SSL, SSL_R_DANE_NOT_ENABLED); @@ -294,9 +296,12 @@ static int dane_tlsa_add(SSL_DANE *dane, } } - if (md != NULL && dlen != (size_t)EVP_MD_get_size(md)) { - ERR_raise(ERR_LIB_SSL, SSL_R_DANE_TLSA_BAD_DIGEST_LENGTH); - return 0; + if (md != NULL) { + mdsize = EVP_MD_get_size(md); + if (mdsize <= 0 || dlen != (size_t)mdsize) { + ERR_raise(ERR_LIB_SSL, SSL_R_DANE_TLSA_BAD_DIGEST_LENGTH); + return 0; + } } if (!data) { ERR_raise(ERR_LIB_SSL, SSL_R_DANE_TLSA_NULL_DATA); @@ -781,6 +786,7 @@ SSL *ossl_ssl_connection_new_int(SSL_CTX *ctx, const SSL_METHOD *method) s->rlayer.record_padding_cb = ctx->record_padding_cb; s->rlayer.record_padding_arg = ctx->record_padding_arg; s->rlayer.block_padding = ctx->block_padding; + s->rlayer.hs_padding = ctx->hs_padding; s->sid_ctx_length = ctx->sid_ctx_length; if (!ossl_assert(s->sid_ctx_length <= sizeof(s->sid_ctx))) goto err; @@ -1111,8 +1117,7 @@ int SSL_add1_host(SSL *s, const char *hostname) /* If a hostname is provided and parses as an IP address, * treat it as such. */ - if (hostname) - { + if (hostname) { ASN1_OCTET_STRING *ip; char *old_ip; @@ -1122,8 +1127,7 @@ int SSL_add1_host(SSL *s, const char *hostname) ASN1_OCTET_STRING_free(ip); old_ip = X509_VERIFY_PARAM_get1_ip_asc(sc->param); - if (old_ip) - { + if (old_ip) { OPENSSL_free(old_ip); /* There can be only one IP address */ return 0; @@ -2599,7 +2603,8 @@ ossl_ssize_t SSL_sendfile(SSL *s, int fd, off_t offset, size_t size, int flags) BIO_set_retry_write(sc->wbio); else #endif - ERR_raise(ERR_LIB_SSL, SSL_R_UNINITIALIZED); + ERR_raise_data(ERR_LIB_SYS, get_last_sys_error(), + "ktls_sendfile failure"); return ret; } sc->rwstate = SSL_NOTHING; @@ -4108,7 +4113,10 @@ SSL_CTX *SSL_CTX_new_ex(OSSL_LIB_CTX *libctx, const char *propq, /* By default we send two session tickets automatically in TLSv1.3 */ ret->num_tickets = 2; - ssl_ctx_system_config(ret); + if (!ssl_ctx_system_config(ret)) { + ERR_raise(ERR_LIB_SSL, SSL_R_ERROR_IN_SYSTEM_DEFAULT_CONFIG); + goto err; + } return ret; err: @@ -4160,7 +4168,7 @@ void SSL_CTX_free(SSL_CTX *a) * (See ticket [openssl.org #212].) */ if (a->sessions != NULL) - SSL_CTX_flush_sessions(a, 0); + SSL_CTX_flush_sessions_ex(a, 0); CRYPTO_free_ex_data(CRYPTO_EX_INDEX_SSL_CTX, a, &a->ex_data); lh_SSL_SESSION_free(a->sessions); @@ -4553,7 +4561,7 @@ void ssl_update_cache(SSL_CONNECTION *s, int mode) else stat = &s->session_ctx->stats.sess_accept_good; if ((ssl_tsan_load(s->session_ctx, stat) & 0xff) == 0xff) - SSL_CTX_flush_sessions(s->session_ctx, (unsigned long)time(NULL)); + SSL_CTX_flush_sessions_ex(s->session_ctx, time(NULL)); } } @@ -4811,8 +4819,7 @@ int ssl_undefined_const_function(const SSL *s) const char *ssl_protocol_to_string(int version) { - switch (version) - { + switch (version) { case TLS1_3_VERSION: return "TLSv1.3"; @@ -5705,21 +5712,35 @@ void *SSL_CTX_get_record_padding_callback_arg(const SSL_CTX *ctx) return ctx->record_padding_arg; } -int SSL_CTX_set_block_padding(SSL_CTX *ctx, size_t block_size) +int SSL_CTX_set_block_padding_ex(SSL_CTX *ctx, size_t app_block_size, + size_t hs_block_size) { - if (IS_QUIC_CTX(ctx) && block_size > 1) + if (IS_QUIC_CTX(ctx) && (app_block_size > 1 || hs_block_size > 1)) return 0; /* block size of 0 or 1 is basically no padding */ - if (block_size == 1) + if (app_block_size == 1) { ctx->block_padding = 0; - else if (block_size <= SSL3_RT_MAX_PLAIN_LENGTH) - ctx->block_padding = block_size; - else + } else if (app_block_size <= SSL3_RT_MAX_PLAIN_LENGTH) { + ctx->block_padding = app_block_size; + } else { return 0; + } + if (hs_block_size == 1) { + ctx->hs_padding = 0; + } else if (hs_block_size <= SSL3_RT_MAX_PLAIN_LENGTH) { + ctx->hs_padding = hs_block_size; + } else { + return 0; + } return 1; } +int SSL_CTX_set_block_padding(SSL_CTX *ctx, size_t block_size) +{ + return SSL_CTX_set_block_padding_ex(ctx, block_size, block_size); +} + int SSL_set_record_padding_callback(SSL *ssl, size_t (*cb) (SSL *ssl, int type, size_t len, void *arg)) @@ -5758,23 +5779,39 @@ void *SSL_get_record_padding_callback_arg(const SSL *ssl) return sc->rlayer.record_padding_arg; } -int SSL_set_block_padding(SSL *ssl, size_t block_size) +int SSL_set_block_padding_ex(SSL *ssl, size_t app_block_size, + size_t hs_block_size) { SSL_CONNECTION *sc = SSL_CONNECTION_FROM_SSL(ssl); - if (sc == NULL || (IS_QUIC(ssl) && block_size > 1)) + if (sc == NULL + || (IS_QUIC(ssl) + && (app_block_size > 1 || hs_block_size > 1))) return 0; /* block size of 0 or 1 is basically no padding */ - if (block_size == 1) + if (app_block_size == 1) { sc->rlayer.block_padding = 0; - else if (block_size <= SSL3_RT_MAX_PLAIN_LENGTH) - sc->rlayer.block_padding = block_size; - else + } else if (app_block_size <= SSL3_RT_MAX_PLAIN_LENGTH) { + sc->rlayer.block_padding = app_block_size; + } else { return 0; + } + if (hs_block_size == 1) { + sc->rlayer.hs_padding = 0; + } else if (hs_block_size <= SSL3_RT_MAX_PLAIN_LENGTH) { + sc->rlayer.hs_padding = hs_block_size; + } else { + return 0; + } return 1; } +int SSL_set_block_padding(SSL *ssl, size_t block_size) +{ + return SSL_set_block_padding_ex(ssl, block_size, block_size); +} + int SSL_set_num_tickets(SSL *s, size_t num_tickets) { SSL_CONNECTION *sc = SSL_CONNECTION_FROM_SSL(s); @@ -6372,7 +6409,7 @@ int ssl_validate_ct(SSL_CONNECTION *s) CT_POLICY_EVAL_CTX_set_shared_CTLOG_STORE(ctx, SSL_CONNECTION_GET_CTX(s)->ctlog_store); CT_POLICY_EVAL_CTX_set_time( - ctx, (uint64_t)SSL_SESSION_get_time(s->session) * 1000); + ctx, (uint64_t)SSL_SESSION_get_time_ex(s->session) * 1000); scts = SSL_get0_peer_scts(SSL_CONNECTION_GET_SSL(s)); @@ -6404,7 +6441,7 @@ int ssl_validate_ct(SSL_CONNECTION *s) end: CT_POLICY_EVAL_CTX_free(ctx); /* - * With SSL_VERIFY_NONE the session may be cached and re-used despite a + * With SSL_VERIFY_NONE the session may be cached and reused despite a * failure return code here. Also the application may wish the complete * the handshake, and then disconnect cleanly at a higher layer, after * checking the verification status of the completed connection. @@ -6713,9 +6750,7 @@ static int nss_keylog_int(const char *prefix, { char *out = NULL; char *cursor = NULL; - size_t out_len = 0; - size_t i; - size_t prefix_len; + size_t out_len = 0, i, prefix_len; SSL_CTX *sctx = SSL_CONNECTION_GET_CTX(sc); if (sctx->keylog_callback == NULL) @@ -6734,26 +6769,21 @@ static int nss_keylog_int(const char *prefix, if ((out = cursor = OPENSSL_malloc(out_len)) == NULL) return 0; - strcpy(cursor, prefix); + memcpy(cursor, prefix, prefix_len); cursor += prefix_len; *cursor++ = ' '; - for (i = 0; i < parameter_1_len; i++) { - sprintf(cursor, "%02x", parameter_1[i]); - cursor += 2; - } + for (i = 0; i < parameter_1_len; ++i) + cursor += ossl_to_lowerhex(cursor, parameter_1[i]); *cursor++ = ' '; - for (i = 0; i < parameter_2_len; i++) { - sprintf(cursor, "%02x", parameter_2[i]); - cursor += 2; - } + for (i = 0; i < parameter_2_len; ++i) + cursor += ossl_to_lowerhex(cursor, parameter_2[i]); *cursor = '\0'; sctx->keylog_callback(SSL_CONNECTION_GET_SSL(sc), (const char *)out); OPENSSL_clear_free(out, out_len); return 1; - } int ssl_log_rsa_client_key_exchange(SSL_CONNECTION *sc, @@ -7199,6 +7229,20 @@ const EVP_CIPHER *ssl_evp_cipher_fetch(OSSL_LIB_CTX *libctx, */ ERR_set_mark(); ciph = EVP_CIPHER_fetch(libctx, OBJ_nid2sn(nid), properties); + if (ciph != NULL) { + OSSL_PARAM params[2]; + int decrypt_only = 0; + + params[0] = OSSL_PARAM_construct_int(OSSL_CIPHER_PARAM_DECRYPT_ONLY, + &decrypt_only); + params[1] = OSSL_PARAM_construct_end(); + if (EVP_CIPHER_get_params((EVP_CIPHER *)ciph, params) + && decrypt_only) { + /* If a cipher is decrypt-only, it is unusable */ + EVP_CIPHER_free((EVP_CIPHER *)ciph); + ciph = NULL; + } + } ERR_pop_to_mark(); return ciph; } diff --git a/ssl/ssl_local.h b/ssl/ssl_local.h index c5eb7bc395..d1c1afe94e 100644 --- a/ssl/ssl_local.h +++ b/ssl/ssl_local.h @@ -37,6 +37,7 @@ # include "internal/ktls.h" # include "internal/time.h" # include "internal/ssl.h" +# include "internal/cryptlib.h" # include "record/record.h" # ifdef OPENSSL_BUILD_SHLIBSSL @@ -274,9 +275,6 @@ # define SSL_IS_FIRST_HANDSHAKE(s) ((s)->s3.tmp.finish_md_len == 0 \ || (s)->s3.tmp.peer_finish_md_len == 0) -/* See if we need explicit IV */ -# define SSL_USE_EXPLICIT_IV(s) \ - (SSL_CONNECTION_GET_SSL(s)->method->ssl3_enc->enc_flags & SSL_ENC_FLAG_EXPLICIT_IV) /* * See if we use signature algorithms extension and signature algorithm * before signatures. @@ -421,7 +419,7 @@ struct ssl_cipher_st { struct ssl_method_st { int version; unsigned flags; - unsigned long mask; + uint64_t mask; SSL *(*ssl_new) (SSL_CTX *ctx); void (*ssl_free) (SSL *s); int (*ssl_reset) (SSL *s); @@ -641,11 +639,6 @@ typedef enum { #define MAX_COMPRESSIONS_SIZE 255 -struct ssl_comp_st { - int id; - const char *name; - COMP_METHOD *method; -}; typedef struct raw_extension_st { /* Raw packet data for the extension */ @@ -1133,6 +1126,7 @@ struct ssl_ctx_st { size_t (*record_padding_cb)(SSL *s, int type, size_t len, void *arg); void *record_padding_arg; size_t block_padding; + size_t hs_padding; /* Session ticket appdata */ SSL_CTX_generate_session_ticket_fn generate_ticket_cb; @@ -2157,8 +2151,6 @@ typedef struct ssl3_enc_method { /* Values for enc_flags */ -/* Uses explicit IV for CBC mode */ -# define SSL_ENC_FLAG_EXPLICIT_IV 0x1 /* Uses signature algorithms extension */ # define SSL_ENC_FLAG_SIGALGS 0x2 /* Uses SHA256 default PRF */ @@ -2217,6 +2209,40 @@ typedef enum downgrade_en { #define TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384 0x081b #define TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512 0x081c +/* Sigalgs names */ +#define TLSEXT_SIGALG_ecdsa_secp256r1_sha256_name "ecdsa_secp256r1_sha256" +#define TLSEXT_SIGALG_ecdsa_secp384r1_sha384_name "ecdsa_secp384r1_sha384" +#define TLSEXT_SIGALG_ecdsa_secp521r1_sha512_name "ecdsa_secp521r1_sha512" +#define TLSEXT_SIGALG_ecdsa_sha224_name "ecdsa_sha224" +#define TLSEXT_SIGALG_ecdsa_sha1_name "ecdsa_sha1" +#define TLSEXT_SIGALG_rsa_pss_rsae_sha256_name "rsa_pss_rsae_sha256" +#define TLSEXT_SIGALG_rsa_pss_rsae_sha384_name "rsa_pss_rsae_sha384" +#define TLSEXT_SIGALG_rsa_pss_rsae_sha512_name "rsa_pss_rsae_sha512" +#define TLSEXT_SIGALG_rsa_pss_pss_sha256_name "rsa_pss_pss_sha256" +#define TLSEXT_SIGALG_rsa_pss_pss_sha384_name "rsa_pss_pss_sha384" +#define TLSEXT_SIGALG_rsa_pss_pss_sha512_name "rsa_pss_pss_sha512" +#define TLSEXT_SIGALG_rsa_pkcs1_sha256_name "rsa_pkcs1_sha256" +#define TLSEXT_SIGALG_rsa_pkcs1_sha384_name "rsa_pkcs1_sha384" +#define TLSEXT_SIGALG_rsa_pkcs1_sha512_name "rsa_pkcs1_sha512" +#define TLSEXT_SIGALG_rsa_pkcs1_sha224_name "rsa_pkcs1_sha224" +#define TLSEXT_SIGALG_rsa_pkcs1_sha1_name "rsa_pkcs1_sha1" +#define TLSEXT_SIGALG_dsa_sha256_name "dsa_sha256" +#define TLSEXT_SIGALG_dsa_sha384_name "dsa_sha384" +#define TLSEXT_SIGALG_dsa_sha512_name "dsa_sha512" +#define TLSEXT_SIGALG_dsa_sha224_name "dsa_sha224" +#define TLSEXT_SIGALG_dsa_sha1_name "dsa_sha1" +#define TLSEXT_SIGALG_gostr34102012_256_intrinsic_name "gost2012_256" +#define TLSEXT_SIGALG_gostr34102012_512_intrinsic_name "gost2012_512" +#define TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256_name "gost2012_256" +#define TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512_name "gost2012_512" +#define TLSEXT_SIGALG_gostr34102001_gostr3411_name "gost2001_gost94" + +#define TLSEXT_SIGALG_ed25519_name "ed25519" +#define TLSEXT_SIGALG_ed448_name "ed448" +#define TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256_name "ecdsa_brainpoolP256r1_sha256" +#define TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384_name "ecdsa_brainpoolP384r1_sha384" +#define TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512_name "ecdsa_brainpoolP512r1_sha512" + /* Known PSK key exchange modes */ #define TLSEXT_KEX_MODE_KE 0x00 #define TLSEXT_KEX_MODE_KE_DHE 0x01 @@ -2501,6 +2527,9 @@ __owur int ossl_bytes_to_cipher_list(SSL_CONNECTION *s, PACKET *cipher_suites, void ssl_update_cache(SSL_CONNECTION *s, int mode); __owur int ssl_cipher_get_evp_cipher(SSL_CTX *ctx, const SSL_CIPHER *sslc, const EVP_CIPHER **enc); +__owur int ssl_cipher_get_evp_md_mac(SSL_CTX *ctx, const SSL_CIPHER *sslc, + const EVP_MD **md, + int *mac_pkey_type, size_t *mac_secret_size); __owur int ssl_cipher_get_evp(SSL_CTX *ctxc, const SSL_SESSION *s, const EVP_CIPHER **enc, const EVP_MD **md, int *mac_pkey_type, size_t *mac_secret_size, @@ -2920,7 +2949,7 @@ void custom_exts_free(custom_ext_methods *exts); void ssl_comp_free_compression_methods_int(void); /* ssl_mcnf.c */ -void ssl_ctx_system_config(SSL_CTX *ctx); +int ssl_ctx_system_config(SSL_CTX *ctx); const EVP_CIPHER *ssl_evp_cipher_fetch(OSSL_LIB_CTX *libctx, int nid, diff --git a/ssl/ssl_mcnf.c b/ssl/ssl_mcnf.c index 8bccce84d4..06a23344b2 100644 --- a/ssl/ssl_mcnf.c +++ b/ssl/ssl_mcnf.c @@ -1,5 +1,5 @@ /* - * Copyright 2015-2020 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2015-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -26,6 +26,7 @@ static int ssl_do_config(SSL *s, SSL_CTX *ctx, const char *name, int system) size_t i, idx, cmd_count; int err = 1; unsigned int flags; + unsigned int conf_diagnostics = 0; const SSL_METHOD *meth; const SSL_CONF_CMD *cmds; OSSL_LIB_CTX *prev_libctx = NULL; @@ -46,8 +47,11 @@ static int ssl_do_config(SSL *s, SSL_CTX *ctx, const char *name, int system) } cmds = conf_ssl_get(idx, &name, &cmd_count); cctx = SSL_CONF_CTX_new(); - if (cctx == NULL) + if (cctx == NULL) { + /* this is a fatal error, always report */ + system = 0; goto err; + } flags = SSL_CONF_FLAG_FILE; if (!system) flags |= SSL_CONF_FLAG_CERTIFICATE | SSL_CONF_FLAG_REQUIRE_PRIVATE; @@ -60,6 +64,9 @@ static int ssl_do_config(SSL *s, SSL_CTX *ctx, const char *name, int system) SSL_CONF_CTX_set_ssl_ctx(cctx, ctx); libctx = ctx->libctx; } + conf_diagnostics = OSSL_LIB_CTX_get_conf_diagnostics(libctx); + if (conf_diagnostics) + flags |= SSL_CONF_FLAG_SHOW_ERRORS; if (meth->ssl_accept != ssl_undefined_function) flags |= SSL_CONF_FLAG_SERVER; if (meth->ssl_connect != ssl_undefined_function) @@ -81,7 +88,7 @@ static int ssl_do_config(SSL *s, SSL_CTX *ctx, const char *name, int system) err: OSSL_LIB_CTX_set0_default(prev_libctx); SSL_CONF_CTX_free(cctx); - return err == 0; + return err == 0 || (system && !conf_diagnostics); } int SSL_config(SSL *s, const char *name) @@ -94,7 +101,7 @@ int SSL_CTX_config(SSL_CTX *ctx, const char *name) return ssl_do_config(NULL, ctx, name, 0); } -void ssl_ctx_system_config(SSL_CTX *ctx) +int ssl_ctx_system_config(SSL_CTX *ctx) { - ssl_do_config(NULL, ctx, NULL, 1); + return ssl_do_config(NULL, ctx, NULL, 1); } diff --git a/ssl/ssl_sess.c b/ssl/ssl_sess.c index 646cf1c52a..6b5d9bbb24 100644 --- a/ssl/ssl_sess.c +++ b/ssl/ssl_sess.c @@ -293,6 +293,7 @@ const unsigned char *SSL_SESSION_get_id(const SSL_SESSION *s, unsigned int *len) *len = (unsigned int)s->session_id_length; return s->session_id; } + const unsigned char *SSL_SESSION_get0_id_context(const SSL_SESSION *s, unsigned int *len) { @@ -946,10 +947,12 @@ long SSL_SESSION_get_timeout(const SSL_SESSION *s) return (long)ossl_time_to_time_t(s->timeout); } +#ifndef OPENSSL_NO_DEPRECATED_3_4 long SSL_SESSION_get_time(const SSL_SESSION *s) { return (long) SSL_SESSION_get_time_ex(s); } +#endif time_t SSL_SESSION_get_time_ex(const SSL_SESSION *s) { @@ -978,10 +981,12 @@ time_t SSL_SESSION_set_time_ex(SSL_SESSION *s, time_t t) return t; } +#ifndef OPENSSL_NO_DEPRECATED_3_4 long SSL_SESSION_set_time(SSL_SESSION *s, long t) { return (long) SSL_SESSION_set_time_ex(s, (time_t) t); } +#endif int SSL_SESSION_get_protocol_version(const SSL_SESSION *s) { @@ -1188,7 +1193,14 @@ int SSL_set_session_ticket_ext(SSL *s, void *ext_data, int ext_len) return 0; } +#ifndef OPENSSL_NO_DEPRECATED_3_4 void SSL_CTX_flush_sessions(SSL_CTX *s, long t) +{ + SSL_CTX_flush_sessions_ex(s, (time_t) t); +} +#endif + +void SSL_CTX_flush_sessions_ex(SSL_CTX *s, time_t t) { STACK_OF(SSL_SESSION) *sk; SSL_SESSION *current; diff --git a/ssl/ssl_stat.c b/ssl/ssl_stat.c index 8b93ccd4ac..686eba452d 100644 --- a/ssl/ssl_stat.c +++ b/ssl/ssl_stat.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2021 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2005 Nokia. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -343,7 +343,7 @@ const char *SSL_alert_desc_string_long(int value) case SSL3_AD_CLOSE_NOTIFY: return "close notify"; case SSL3_AD_UNEXPECTED_MESSAGE: - return "unexpected_message"; + return "unexpected message"; case SSL3_AD_BAD_RECORD_MAC: return "bad record mac"; case SSL3_AD_DECOMPRESSION_FAILURE: diff --git a/ssl/ssl_txt.c b/ssl/ssl_txt.c index 9e9c2e10ec..d928cb9bbd 100644 --- a/ssl/ssl_txt.c +++ b/ssl/ssl_txt.c @@ -1,5 +1,5 @@ /* - * Copyright 1995-2022 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 1995-2024 The OpenSSL Project Authors. All Rights Reserved. * Copyright 2005 Nokia. All rights reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use @@ -12,6 +12,8 @@ #include #include "ssl_local.h" +#include "internal/comp.h" + #ifndef OPENSSL_NO_STDIO int SSL_SESSION_print_fp(FILE *fp, const SSL_SESSION *x) { diff --git a/ssl/statem/extensions.c b/ssl/statem/extensions.c index 8765391f2c..a467948599 100644 --- a/ssl/statem/extensions.c +++ b/ssl/statem/extensions.c @@ -59,6 +59,8 @@ static int final_key_share(SSL_CONNECTION *s, unsigned int context, int sent); static int init_srtp(SSL_CONNECTION *s, unsigned int context); #endif static int final_sig_algs(SSL_CONNECTION *s, unsigned int context, int sent); +static int final_supported_versions(SSL_CONNECTION *s, unsigned int context, + int sent); static int final_early_data(SSL_CONNECTION *s, unsigned int context, int sent); static int final_maxfragmentlen(SSL_CONNECTION *s, unsigned int context, int sent); @@ -344,7 +346,7 @@ static const EXTENSION_DEFINITION ext_defs[] = { /* Processed inline as part of version selection */ NULL, tls_parse_stoc_supported_versions, tls_construct_stoc_supported_versions, - tls_construct_ctos_supported_versions, NULL + tls_construct_ctos_supported_versions, final_supported_versions }, { TLSEXT_TYPE_psk_kex_modes, @@ -1346,6 +1348,18 @@ static int final_sig_algs(SSL_CONNECTION *s, unsigned int context, int sent) return 1; } +static int final_supported_versions(SSL_CONNECTION *s, unsigned int context, + int sent) +{ + if (!sent && context == SSL_EXT_TLS1_3_HELLO_RETRY_REQUEST) { + SSLfatal(s, TLS13_AD_MISSING_EXTENSION, + SSL_R_MISSING_SUPPORTED_VERSIONS_EXTENSION); + return 0; + } + + return 1; +} + static int final_key_share(SSL_CONNECTION *s, unsigned int context, int sent) { #if !defined(OPENSSL_NO_TLS1_3) @@ -1368,12 +1382,15 @@ static int final_key_share(SSL_CONNECTION *s, unsigned int context, int sent) * fail; */ if (!s->server - && !sent - && (!s->hit - || (s->ext.psk_kex_mode & TLSEXT_KEX_MODE_FLAG_KE) == 0)) { - /* Nothing left we can do - just fail */ - SSLfatal(s, SSL_AD_MISSING_EXTENSION, SSL_R_NO_SUITABLE_KEY_SHARE); - return 0; + && !sent) { + if ((s->ext.psk_kex_mode & TLSEXT_KEX_MODE_FLAG_KE) == 0) { + SSLfatal(s, SSL_AD_ILLEGAL_PARAMETER, SSL_R_NO_SUITABLE_KEY_SHARE); + return 0; + } + if (!s->hit) { + SSLfatal(s, SSL_AD_MISSING_EXTENSION, SSL_R_NO_SUITABLE_KEY_SHARE); + return 0; + } } /* * IF @@ -1539,7 +1556,7 @@ int tls_psk_do_binder(SSL_CONNECTION *s, const EVP_MD *md, SSL_CTX *sctx = SSL_CONNECTION_GET_CTX(s); /* Ensure cast to size_t is safe */ - if (!ossl_assert(hashsizei >= 0)) { + if (!ossl_assert(hashsizei > 0)) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); goto err; } @@ -1683,7 +1700,7 @@ int tls_psk_do_binder(SSL_CONNECTION *s, const EVP_MD *md, /* HMAC keys can't do EVP_DigestVerify* - use CRYPTO_memcmp instead */ ret = (CRYPTO_memcmp(binderin, binderout, hashsize) == 0); if (!ret) - SSLfatal(s, SSL_AD_ILLEGAL_PARAMETER, SSL_R_BINDER_DOES_NOT_VERIFY); + SSLfatal(s, SSL_AD_DECRYPT_ERROR, SSL_R_BINDER_DOES_NOT_VERIFY); } err: diff --git a/ssl/statem/extensions_clnt.c b/ssl/statem/extensions_clnt.c index 5bce30b584..9fd84ecfd7 100644 --- a/ssl/statem/extensions_clnt.c +++ b/ssl/statem/extensions_clnt.c @@ -16,10 +16,37 @@ EXT_RETURN tls_construct_ctos_renegotiate(SSL_CONNECTION *s, WPACKET *pkt, unsigned int context, X509 *x, size_t chainidx) { - /* Add RI if renegotiating */ - if (!s->renegotiate) - return EXT_RETURN_NOT_SENT; + if (!s->renegotiate) { + /* If not renegotiating, send an empty RI extension to indicate support */ + +#if DTLS_MAX_VERSION_INTERNAL != DTLS1_2_VERSION +# error Internal DTLS version error +#endif + + if (!SSL_CONNECTION_IS_DTLS(s) + && (s->min_proto_version >= TLS1_3_VERSION + || (ssl_security(s, SSL_SECOP_VERSION, 0, TLS1_VERSION, NULL) + && s->min_proto_version <= TLS1_VERSION))) { + /* + * For TLS <= 1.0 SCSV is used instead, and for TLS 1.3 this + * extension isn't used at all. + */ + return EXT_RETURN_NOT_SENT; + } + + if (!WPACKET_put_bytes_u16(pkt, TLSEXT_TYPE_renegotiate) + || !WPACKET_start_sub_packet_u16(pkt) + || !WPACKET_put_bytes_u8(pkt, 0) + || !WPACKET_close(pkt)) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + return EXT_RETURN_FAIL; + } + + return EXT_RETURN_SENT; + } + + /* Add a complete RI extension if renegotiating */ if (!WPACKET_put_bytes_u16(pkt, TLSEXT_TYPE_renegotiate) || !WPACKET_start_sub_packet_u16(pkt) || !WPACKET_sub_memcpy_u8(pkt, s->s3.previous_client_finished, @@ -952,8 +979,12 @@ EXT_RETURN tls_construct_ctos_padding(SSL_CONNECTION *s, WPACKET *pkt, * Add the fixed PSK overhead, the identity length and the binder * length. */ + int md_size = EVP_MD_get_size(md); + + if (md_size <= 0) + return EXT_RETURN_FAIL; hlen += PSK_PRE_BINDER_OVERHEAD + s->session->ext.ticklen - + EVP_MD_get_size(md); + + md_size; } } @@ -992,7 +1023,8 @@ EXT_RETURN tls_construct_ctos_psk(SSL_CONNECTION *s, WPACKET *pkt, { #ifndef OPENSSL_NO_TLS1_3 uint32_t agesec, agems = 0; - size_t reshashsize = 0, pskhashsize = 0, binderoffset, msglen; + size_t binderoffset, msglen; + int reshashsize = 0, pskhashsize = 0; unsigned char *resbinder = NULL, *pskbinder = NULL, *msgstart = NULL; const EVP_MD *handmd = NULL, *mdres = NULL, *mdpsk = NULL; int dores = 0; @@ -1088,6 +1120,8 @@ EXT_RETURN tls_construct_ctos_psk(SSL_CONNECTION *s, WPACKET *pkt, agems += s->session->ext.tick_age_add; reshashsize = EVP_MD_get_size(mdres); + if (reshashsize <= 0) + goto dopsksess; s->ext.tick_identity++; dores = 1; } @@ -1117,6 +1151,10 @@ EXT_RETURN tls_construct_ctos_psk(SSL_CONNECTION *s, WPACKET *pkt, } pskhashsize = EVP_MD_get_size(mdpsk); + if (pskhashsize <= 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, SSL_R_BAD_PSK); + return EXT_RETURN_FAIL; + } } /* Create the extension, but skip over the binder for now */ diff --git a/ssl/statem/extensions_srvr.c b/ssl/statem/extensions_srvr.c index 3997493d87..5d91d3893f 100644 --- a/ssl/statem/extensions_srvr.c +++ b/ssl/statem/extensions_srvr.c @@ -1025,7 +1025,8 @@ int tls_parse_ctos_psk(SSL_CONNECTION *s, PACKET *pkt, unsigned int context, X509 *x, size_t chainidx) { PACKET identities, binders, binder; - size_t binderoffset, hashsize; + size_t binderoffset; + int hashsize; SSL_SESSION *sess = NULL; unsigned int id, i, ext = 0; const EVP_MD *md = NULL; @@ -1120,7 +1121,7 @@ int tls_parse_ctos_psk(SSL_CONNECTION *s, PACKET *pkt, unsigned int context, if (sesstmp == NULL) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); - return 0; + goto err; } SSL_SESSION_free(sess); sess = sesstmp; @@ -1226,6 +1227,8 @@ int tls_parse_ctos_psk(SSL_CONNECTION *s, PACKET *pkt, unsigned int context, binderoffset = PACKET_data(pkt) - (const unsigned char *)s->init_buf->data; hashsize = EVP_MD_get_size(md); + if (hashsize <= 0) + goto err; if (!PACKET_get_length_prefixed_2(pkt, &binders)) { SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_R_BAD_EXTENSION); @@ -1239,7 +1242,7 @@ int tls_parse_ctos_psk(SSL_CONNECTION *s, PACKET *pkt, unsigned int context, } } - if (PACKET_remaining(&binder) != hashsize) { + if (PACKET_remaining(&binder) != (size_t)hashsize) { SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_R_BAD_EXTENSION); goto err; } diff --git a/ssl/statem/statem_clnt.c b/ssl/statem/statem_clnt.c index 7d8b140373..80a997a73c 100644 --- a/ssl/statem/statem_clnt.c +++ b/ssl/statem/statem_clnt.c @@ -27,6 +27,7 @@ #include #include #include "internal/cryptlib.h" +#include "internal/comp.h" static MSG_PROCESS_RETURN tls_process_as_hello_retry_request(SSL_CONNECTION *s, PACKET *pkt); @@ -1885,7 +1886,7 @@ static MSG_PROCESS_RETURN tls_process_as_hello_retry_request(SSL_CONNECTION *s, MSG_PROCESS_RETURN tls_process_server_rpk(SSL_CONNECTION *sc, PACKET *pkt) { - EVP_PKEY *peer_rpk; + EVP_PKEY *peer_rpk = NULL; if (!tls_process_rpk(sc, pkt, &peer_rpk)) { /* SSLfatal() already called */ @@ -2698,7 +2699,7 @@ MSG_PROCESS_RETURN tls_process_new_session_ticket(SSL_CONNECTION *s, && (!PACKET_get_net_4(pkt, &age_add) || !PACKET_get_length_prefixed_1(pkt, &nonce))) || !PACKET_get_net_2(pkt, &ticklen) - || (SSL_CONNECTION_IS_TLS13(s) ? (ticklen == 0 + || (SSL_CONNECTION_IS_TLS13(s) ? (ticklen == 0 || PACKET_remaining(pkt) < ticklen) : PACKET_remaining(pkt) != ticklen)) { SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_R_LENGTH_MISMATCH); @@ -2828,7 +2829,7 @@ MSG_PROCESS_RETURN tls_process_new_session_ticket(SSL_CONNECTION *s, static const unsigned char nonce_label[] = "resumption"; /* Ensure cast to size_t is safe */ - if (!ossl_assert(hashleni >= 0)) { + if (!ossl_assert(hashleni > 0)) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); goto err; } @@ -4064,8 +4065,9 @@ int ssl_cipher_list_to_bytes(SSL_CONNECTION *s, STACK_OF(SSL_CIPHER) *sk, int i; size_t totlen = 0, len, maxlen, maxverok = 0; int empty_reneg_info_scsv = !s->renegotiate - && (SSL_CONNECTION_IS_DTLS(s) - || s->min_proto_version < TLS1_3_VERSION); + && !SSL_CONNECTION_IS_DTLS(s) + && ssl_security(s, SSL_SECOP_VERSION, 0, TLS1_VERSION, NULL) + && s->min_proto_version <= TLS1_VERSION; SSL *ssl = SSL_CONNECTION_GET_SSL(s); /* Set disabled masks for this session */ diff --git a/ssl/statem/statem_dtls.c b/ssl/statem/statem_dtls.c index b37ac80a60..d1800c193a 100644 --- a/ssl/statem/statem_dtls.c +++ b/ssl/statem/statem_dtls.c @@ -39,10 +39,12 @@ if (is_complete) for (ii = (((msg_len) - 1) >> 3) - 1; ii >= 0 ; ii--) \ if (bitmask[ii] != 0xff) { is_complete = 0; break; } } -static const unsigned char bitmask_start_values[] = - { 0xff, 0xfe, 0xfc, 0xf8, 0xf0, 0xe0, 0xc0, 0x80 }; -static const unsigned char bitmask_end_values[] = - { 0xff, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x7f }; +static const unsigned char bitmask_start_values[] = { + 0xff, 0xfe, 0xfc, 0xf8, 0xf0, 0xe0, 0xc0, 0x80 +}; +static const unsigned char bitmask_end_values[] = { + 0xff, 0x01, 0x03, 0x07, 0x0f, 0x1f, 0x3f, 0x7f +}; static void dtls1_fix_message_header(SSL_CONNECTION *s, size_t frag_off, size_t frag_len); @@ -1061,8 +1063,7 @@ int dtls1_read_failed(SSL_CONNECTION *s, int code) return code; } /* done, no need to send a retransmit */ - if (!SSL_in_init(ssl)) - { + if (!SSL_in_init(ssl)) { BIO_set_flags(SSL_get_rbio(ssl), BIO_FLAGS_READ); return code; } diff --git a/ssl/statem/statem_srvr.c b/ssl/statem/statem_srvr.c index 5ff479a2ec..db009f3b77 100644 --- a/ssl/statem/statem_srvr.c +++ b/ssl/statem/statem_srvr.c @@ -27,6 +27,7 @@ #include #include #include +#include "internal/comp.h" #define TICKET_NONCE_SIZE 8 @@ -1682,7 +1683,6 @@ static int tls_early_post_process_client_hello(SSL_CONNECTION *s) unsigned int j; int i, al = SSL_AD_INTERNAL_ERROR; int protverr; - size_t loop; unsigned long id; #ifndef OPENSSL_NO_COMP SSL_COMP *comp = NULL; @@ -1923,16 +1923,18 @@ static int tls_early_post_process_client_hello(SSL_CONNECTION *s) OSSL_TRACE_END(TLS_CIPHER); } - for (loop = 0; loop < clienthello->compressions_len; loop++) { - if (clienthello->compressions[loop] == 0) - break; - } - - if (loop >= clienthello->compressions_len) { - /* no compress */ + /* At least one compression method must be preset. */ + if (clienthello->compressions_len == 0) { SSLfatal(s, SSL_AD_DECODE_ERROR, SSL_R_NO_COMPRESSION_SPECIFIED); goto err; } + /* Make sure at least the null compression is supported. */ + if (memchr(clienthello->compressions, 0, + clienthello->compressions_len) == NULL) { + SSLfatal(s, SSL_AD_ILLEGAL_PARAMETER, + SSL_R_REQUIRED_COMPRESSION_ALGORITHM_MISSING); + goto err; + } if (s->options & SSL_OP_SAFARI_ECDHE_ECDSA_BUG) ssl_check_for_safari(s, clienthello); @@ -4174,7 +4176,7 @@ CON_FUNC_RETURN tls_construct_new_session_ticket(SSL_CONNECTION *s, WPACKET *pkt int hashleni = EVP_MD_get_size(md); /* Ensure cast to size_t is safe */ - if (!ossl_assert(hashleni >= 0)) { + if (!ossl_assert(hashleni > 0)) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); goto err; } diff --git a/ssl/t1_lib.c b/ssl/t1_lib.c index 4646311714..4e4671d013 100644 --- a/ssl/t1_lib.c +++ b/ssl/t1_lib.c @@ -54,7 +54,7 @@ SSL3_ENC_METHOD const TLSv1_1_enc_data = { TLS_MD_SERVER_FINISH_CONST, TLS_MD_SERVER_FINISH_CONST_SIZE, tls1_alert_code, tls1_export_keying_material, - SSL_ENC_FLAG_EXPLICIT_IV, + 0, ssl3_set_handshake_header, tls_close_construct_packet, ssl3_handshake_write @@ -69,7 +69,7 @@ SSL3_ENC_METHOD const TLSv1_2_enc_data = { TLS_MD_SERVER_FINISH_CONST, TLS_MD_SERVER_FINISH_CONST_SIZE, tls1_alert_code, tls1_export_keying_material, - SSL_ENC_FLAG_EXPLICIT_IV | SSL_ENC_FLAG_SIGALGS | SSL_ENC_FLAG_SHA256_PRF + SSL_ENC_FLAG_SIGALGS | SSL_ENC_FLAG_SHA256_PRF | SSL_ENC_FLAG_TLS1_2_CIPHERS, ssl3_set_handshake_header, tls_close_construct_packet, @@ -636,7 +636,7 @@ static int add_provider_sigalgs(const OSSL_PARAM params[], void *data) if (EVP_KEYMGMT_get0_provider(keymgmt) == provider) { /* * We have a match - so we could use this signature; - * Check proper object registration first, though. + * Check proper object registration first, though. * Don't care about return value as this may have been * done within providers or previous calls to * add_provider_sigalgs. @@ -724,7 +724,7 @@ int ssl_load_sigalgs(SSL_CTX *ctx) } } - /* + /* * For now, leave it at this: legacy sigalgs stay in their own * data structures until "legacy cleanup" occurs. */ @@ -1381,102 +1381,102 @@ static const uint16_t suiteb_sigalgs[] = { }; static const SIGALG_LOOKUP sigalg_lookup_tbl[] = { - {"ecdsa_secp256r1_sha256", TLSEXT_SIGALG_ecdsa_secp256r1_sha256, + {TLSEXT_SIGALG_ecdsa_secp256r1_sha256_name, TLSEXT_SIGALG_ecdsa_secp256r1_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA256, NID_X9_62_prime256v1, 1}, - {"ecdsa_secp384r1_sha384", TLSEXT_SIGALG_ecdsa_secp384r1_sha384, + {TLSEXT_SIGALG_ecdsa_secp384r1_sha384_name, TLSEXT_SIGALG_ecdsa_secp384r1_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA384, NID_secp384r1, 1}, - {"ecdsa_secp521r1_sha512", TLSEXT_SIGALG_ecdsa_secp521r1_sha512, + {TLSEXT_SIGALG_ecdsa_secp521r1_sha512_name, TLSEXT_SIGALG_ecdsa_secp521r1_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA512, NID_secp521r1, 1}, - {"ed25519", TLSEXT_SIGALG_ed25519, + {TLSEXT_SIGALG_ed25519_name, TLSEXT_SIGALG_ed25519, NID_undef, -1, EVP_PKEY_ED25519, SSL_PKEY_ED25519, NID_undef, NID_undef, 1}, - {"ed448", TLSEXT_SIGALG_ed448, + {TLSEXT_SIGALG_ed448_name, TLSEXT_SIGALG_ed448, NID_undef, -1, EVP_PKEY_ED448, SSL_PKEY_ED448, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_ecdsa_sha224, + {TLSEXT_SIGALG_ecdsa_sha224_name, TLSEXT_SIGALG_ecdsa_sha224, NID_sha224, SSL_MD_SHA224_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA224, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_ecdsa_sha1, + {TLSEXT_SIGALG_ecdsa_sha1_name, TLSEXT_SIGALG_ecdsa_sha1, NID_sha1, SSL_MD_SHA1_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA1, NID_undef, 1}, - {"ecdsa_brainpoolP256r1_sha256", TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256, + {TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256_name, TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA256, NID_brainpoolP256r1, 1}, - {"ecdsa_brainpoolP384r1_sha384", TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384, + {TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384_name, TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA384, NID_brainpoolP384r1, 1}, - {"ecdsa_brainpoolP512r1_sha512", TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512, + {TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512_name, TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_EC, SSL_PKEY_ECC, NID_ecdsa_with_SHA512, NID_brainpoolP512r1, 1}, - {"rsa_pss_rsae_sha256", TLSEXT_SIGALG_rsa_pss_rsae_sha256, + {TLSEXT_SIGALG_rsa_pss_rsae_sha256_name, TLSEXT_SIGALG_rsa_pss_rsae_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA, NID_undef, NID_undef, 1}, - {"rsa_pss_rsae_sha384", TLSEXT_SIGALG_rsa_pss_rsae_sha384, + {TLSEXT_SIGALG_rsa_pss_rsae_sha384_name, TLSEXT_SIGALG_rsa_pss_rsae_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA, NID_undef, NID_undef, 1}, - {"rsa_pss_rsae_sha512", TLSEXT_SIGALG_rsa_pss_rsae_sha512, + {TLSEXT_SIGALG_rsa_pss_rsae_sha512_name, TLSEXT_SIGALG_rsa_pss_rsae_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA, NID_undef, NID_undef, 1}, - {"rsa_pss_pss_sha256", TLSEXT_SIGALG_rsa_pss_pss_sha256, + {TLSEXT_SIGALG_rsa_pss_pss_sha256_name, TLSEXT_SIGALG_rsa_pss_pss_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA_PSS_SIGN, NID_undef, NID_undef, 1}, - {"rsa_pss_pss_sha384", TLSEXT_SIGALG_rsa_pss_pss_sha384, + {TLSEXT_SIGALG_rsa_pss_pss_sha384_name, TLSEXT_SIGALG_rsa_pss_pss_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA_PSS_SIGN, NID_undef, NID_undef, 1}, - {"rsa_pss_pss_sha512", TLSEXT_SIGALG_rsa_pss_pss_sha512, + {TLSEXT_SIGALG_rsa_pss_pss_sha512_name, TLSEXT_SIGALG_rsa_pss_pss_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_RSA_PSS, SSL_PKEY_RSA_PSS_SIGN, NID_undef, NID_undef, 1}, - {"rsa_pkcs1_sha256", TLSEXT_SIGALG_rsa_pkcs1_sha256, + {TLSEXT_SIGALG_rsa_pkcs1_sha256_name, TLSEXT_SIGALG_rsa_pkcs1_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_RSA, SSL_PKEY_RSA, NID_sha256WithRSAEncryption, NID_undef, 1}, - {"rsa_pkcs1_sha384", TLSEXT_SIGALG_rsa_pkcs1_sha384, + {TLSEXT_SIGALG_rsa_pkcs1_sha384_name, TLSEXT_SIGALG_rsa_pkcs1_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_RSA, SSL_PKEY_RSA, NID_sha384WithRSAEncryption, NID_undef, 1}, - {"rsa_pkcs1_sha512", TLSEXT_SIGALG_rsa_pkcs1_sha512, + {TLSEXT_SIGALG_rsa_pkcs1_sha512_name, TLSEXT_SIGALG_rsa_pkcs1_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_RSA, SSL_PKEY_RSA, NID_sha512WithRSAEncryption, NID_undef, 1}, - {"rsa_pkcs1_sha224", TLSEXT_SIGALG_rsa_pkcs1_sha224, + {TLSEXT_SIGALG_rsa_pkcs1_sha224_name, TLSEXT_SIGALG_rsa_pkcs1_sha224, NID_sha224, SSL_MD_SHA224_IDX, EVP_PKEY_RSA, SSL_PKEY_RSA, NID_sha224WithRSAEncryption, NID_undef, 1}, - {"rsa_pkcs1_sha1", TLSEXT_SIGALG_rsa_pkcs1_sha1, + {TLSEXT_SIGALG_rsa_pkcs1_sha1_name, TLSEXT_SIGALG_rsa_pkcs1_sha1, NID_sha1, SSL_MD_SHA1_IDX, EVP_PKEY_RSA, SSL_PKEY_RSA, NID_sha1WithRSAEncryption, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_dsa_sha256, + {TLSEXT_SIGALG_dsa_sha256_name, TLSEXT_SIGALG_dsa_sha256, NID_sha256, SSL_MD_SHA256_IDX, EVP_PKEY_DSA, SSL_PKEY_DSA_SIGN, NID_dsa_with_SHA256, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_dsa_sha384, + {TLSEXT_SIGALG_dsa_sha384_name, TLSEXT_SIGALG_dsa_sha384, NID_sha384, SSL_MD_SHA384_IDX, EVP_PKEY_DSA, SSL_PKEY_DSA_SIGN, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_dsa_sha512, + {TLSEXT_SIGALG_dsa_sha512_name, TLSEXT_SIGALG_dsa_sha512, NID_sha512, SSL_MD_SHA512_IDX, EVP_PKEY_DSA, SSL_PKEY_DSA_SIGN, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_dsa_sha224, + {TLSEXT_SIGALG_dsa_sha224_name, TLSEXT_SIGALG_dsa_sha224, NID_sha224, SSL_MD_SHA224_IDX, EVP_PKEY_DSA, SSL_PKEY_DSA_SIGN, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_dsa_sha1, + {TLSEXT_SIGALG_dsa_sha1_name, TLSEXT_SIGALG_dsa_sha1, NID_sha1, SSL_MD_SHA1_IDX, EVP_PKEY_DSA, SSL_PKEY_DSA_SIGN, NID_dsaWithSHA1, NID_undef, 1}, #ifndef OPENSSL_NO_GOST - {NULL, TLSEXT_SIGALG_gostr34102012_256_intrinsic, + {TLSEXT_SIGALG_gostr34102012_256_intrinsic_name, TLSEXT_SIGALG_gostr34102012_256_intrinsic, NID_id_GostR3411_2012_256, SSL_MD_GOST12_256_IDX, NID_id_GostR3410_2012_256, SSL_PKEY_GOST12_256, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_gostr34102012_512_intrinsic, + {TLSEXT_SIGALG_gostr34102012_512_intrinsic_name, TLSEXT_SIGALG_gostr34102012_512_intrinsic, NID_id_GostR3411_2012_512, SSL_MD_GOST12_512_IDX, NID_id_GostR3410_2012_512, SSL_PKEY_GOST12_512, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256, + {TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256_name, TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256, NID_id_GostR3411_2012_256, SSL_MD_GOST12_256_IDX, NID_id_GostR3410_2012_256, SSL_PKEY_GOST12_256, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512, + {TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512_name, TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512, NID_id_GostR3411_2012_512, SSL_MD_GOST12_512_IDX, NID_id_GostR3410_2012_512, SSL_PKEY_GOST12_512, NID_undef, NID_undef, 1}, - {NULL, TLSEXT_SIGALG_gostr34102001_gostr3411, + {TLSEXT_SIGALG_gostr34102001_gostr3411_name, TLSEXT_SIGALG_gostr34102001_gostr3411, NID_id_GostR3411_94, SSL_MD_GOST94_IDX, NID_id_GostR3410_2001, SSL_PKEY_GOST01, NID_undef, NID_undef, 1} @@ -1594,6 +1594,81 @@ int ssl_setup_sigalgs(SSL_CTX *ctx) return ret; } +#define SIGLEN_BUF_INCREMENT 100 + +char *SSL_get1_builtin_sigalgs(OSSL_LIB_CTX *libctx) +{ + size_t i, maxretlen = SIGLEN_BUF_INCREMENT; + const SIGALG_LOOKUP *lu; + EVP_PKEY *tmpkey = EVP_PKEY_new(); + char *retval = OPENSSL_malloc(maxretlen); + + if (retval == NULL) + return NULL; + + /* ensure retval string is NUL terminated */ + retval[0] = (char)0; + + for (i = 0, lu = sigalg_lookup_tbl; + i < OSSL_NELEM(sigalg_lookup_tbl); lu++, i++) { + EVP_PKEY_CTX *pctx; + int enabled = 1; + + ERR_set_mark(); + /* Check hash is available in some provider. */ + if (lu->hash != NID_undef) { + EVP_MD *hash = EVP_MD_fetch(libctx, OBJ_nid2ln(lu->hash), NULL); + + /* If unable to create we assume the hash algorithm is unavailable */ + if (hash == NULL) { + enabled = 0; + ERR_pop_to_mark(); + continue; + } + EVP_MD_free(hash); + } + + if (!EVP_PKEY_set_type(tmpkey, lu->sig)) { + enabled = 0; + ERR_pop_to_mark(); + continue; + } + pctx = EVP_PKEY_CTX_new_from_pkey(libctx, tmpkey, NULL); + /* If unable to create pctx we assume the sig algorithm is unavailable */ + if (pctx == NULL) + enabled = 0; + ERR_pop_to_mark(); + EVP_PKEY_CTX_free(pctx); + + if (enabled) { + const char *sa = lu->name; + + if (sa != NULL) { + if (strlen(sa) + strlen(retval) + 1 >= maxretlen) { + char *tmp; + + maxretlen += SIGLEN_BUF_INCREMENT; + tmp = OPENSSL_realloc(retval, maxretlen); + if (tmp == NULL) { + OPENSSL_free(retval); + return NULL; + } + retval = tmp; + } + if (strlen(retval) > 0) + OPENSSL_strlcat(retval, ":", maxretlen); + OPENSSL_strlcat(retval, sa, maxretlen); + } else { + /* lu->name must not be NULL */ + ERR_raise(ERR_LIB_SSL, ERR_R_INTERNAL_ERROR); + } + } + } + + EVP_PKEY_free(tmpkey); + return retval; +} + /* Lookup TLS signature algorithm */ static const SIGALG_LOOKUP *tls1_lookup_sigalg(const SSL_CONNECTION *s, uint16_t sigalg) @@ -1649,6 +1724,8 @@ static int rsa_pss_check_min_key_size(SSL_CTX *ctx, const EVP_PKEY *pkey, return 0; if (!tls1_lookup_md(ctx, lu, &md) || md == NULL) return 0; + if (EVP_MD_get_size(md) <= 0) + return 0; if (EVP_PKEY_get_size(pkey) < RSA_PSS_MINIMUM_KEY_SIZE(md)) return 0; return 1; @@ -1831,6 +1908,8 @@ static int sigalg_security_bits(SSL_CTX *ctx, const SIGALG_LOOKUP *lu) /* Security bits: half digest bits */ secbits = EVP_MD_get_size(md) * 4; + if (secbits <= 0) + return 0; /* * SHA1 and MD5 are known to be broken. Reduce security bits so that * they're no longer accepted at security level 1. The real values don't diff --git a/ssl/t1_trce.c b/ssl/t1_trce.c index 29dce65e4f..ac1199f174 100644 --- a/ssl/t1_trce.c +++ b/ssl/t1_trce.c @@ -1,5 +1,5 @@ /* - * Copyright 2012-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2012-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -446,6 +446,8 @@ static const ssl_trace_tbl ssl_ciphers_tbl[] = { {0xFEFF, "SSL_RSA_FIPS_WITH_3DES_EDE_CBC_SHA"}, {0xFF85, "LEGACY-GOST2012-GOST8912-GOST8912"}, {0xFF87, "GOST2012-NULL-GOST12"}, + {0xC0B4, "TLS_SHA256_SHA256"}, + {0xC0B5, "TLS_SHA384_SHA384"}, {0xC100, "GOST2012-KUZNYECHIK-KUZNYECHIKOMAC"}, {0xC101, "GOST2012-MAGMA-MAGMAOMAC"}, {0xC102, "GOST2012-GOST8912-IANA"}, @@ -566,37 +568,37 @@ static const ssl_trace_tbl ssl_mfl_tbl[] = { }; static const ssl_trace_tbl ssl_sigalg_tbl[] = { - {TLSEXT_SIGALG_ecdsa_secp256r1_sha256, "ecdsa_secp256r1_sha256"}, - {TLSEXT_SIGALG_ecdsa_secp384r1_sha384, "ecdsa_secp384r1_sha384"}, - {TLSEXT_SIGALG_ecdsa_secp521r1_sha512, "ecdsa_secp521r1_sha512"}, - {TLSEXT_SIGALG_ecdsa_sha224, "ecdsa_sha224"}, - {TLSEXT_SIGALG_ed25519, "ed25519"}, - {TLSEXT_SIGALG_ed448, "ed448"}, - {TLSEXT_SIGALG_ecdsa_sha1, "ecdsa_sha1"}, - {TLSEXT_SIGALG_rsa_pss_rsae_sha256, "rsa_pss_rsae_sha256"}, - {TLSEXT_SIGALG_rsa_pss_rsae_sha384, "rsa_pss_rsae_sha384"}, - {TLSEXT_SIGALG_rsa_pss_rsae_sha512, "rsa_pss_rsae_sha512"}, - {TLSEXT_SIGALG_rsa_pss_pss_sha256, "rsa_pss_pss_sha256"}, - {TLSEXT_SIGALG_rsa_pss_pss_sha384, "rsa_pss_pss_sha384"}, - {TLSEXT_SIGALG_rsa_pss_pss_sha512, "rsa_pss_pss_sha512"}, - {TLSEXT_SIGALG_rsa_pkcs1_sha256, "rsa_pkcs1_sha256"}, - {TLSEXT_SIGALG_rsa_pkcs1_sha384, "rsa_pkcs1_sha384"}, - {TLSEXT_SIGALG_rsa_pkcs1_sha512, "rsa_pkcs1_sha512"}, - {TLSEXT_SIGALG_rsa_pkcs1_sha224, "rsa_pkcs1_sha224"}, - {TLSEXT_SIGALG_rsa_pkcs1_sha1, "rsa_pkcs1_sha1"}, - {TLSEXT_SIGALG_dsa_sha256, "dsa_sha256"}, - {TLSEXT_SIGALG_dsa_sha384, "dsa_sha384"}, - {TLSEXT_SIGALG_dsa_sha512, "dsa_sha512"}, - {TLSEXT_SIGALG_dsa_sha224, "dsa_sha224"}, - {TLSEXT_SIGALG_dsa_sha1, "dsa_sha1"}, - {TLSEXT_SIGALG_gostr34102012_256_intrinsic, "gost2012_256"}, - {TLSEXT_SIGALG_gostr34102012_512_intrinsic, "gost2012_512"}, - {TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256, "gost2012_256"}, - {TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512, "gost2012_512"}, - {TLSEXT_SIGALG_gostr34102001_gostr3411, "gost2001_gost94"}, - {TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256, "ecdsa_brainpoolP256r1_sha256"}, - {TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384, "ecdsa_brainpoolP384r1_sha384"}, - {TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512, "ecdsa_brainpoolP512r1_sha512"}, + {TLSEXT_SIGALG_ecdsa_secp256r1_sha256, TLSEXT_SIGALG_ecdsa_secp256r1_sha256_name}, + {TLSEXT_SIGALG_ecdsa_secp384r1_sha384, TLSEXT_SIGALG_ecdsa_secp384r1_sha384_name}, + {TLSEXT_SIGALG_ecdsa_secp521r1_sha512,TLSEXT_SIGALG_ecdsa_secp521r1_sha512_name}, + {TLSEXT_SIGALG_ecdsa_sha224, TLSEXT_SIGALG_ecdsa_sha224_name}, + {TLSEXT_SIGALG_ed25519, TLSEXT_SIGALG_ed25519_name}, + {TLSEXT_SIGALG_ed448, TLSEXT_SIGALG_ed448_name}, + {TLSEXT_SIGALG_ecdsa_sha1, TLSEXT_SIGALG_ecdsa_sha1_name}, + {TLSEXT_SIGALG_rsa_pss_rsae_sha256, TLSEXT_SIGALG_rsa_pss_rsae_sha256_name}, + {TLSEXT_SIGALG_rsa_pss_rsae_sha384, TLSEXT_SIGALG_rsa_pss_rsae_sha384_name}, + {TLSEXT_SIGALG_rsa_pss_rsae_sha512, TLSEXT_SIGALG_rsa_pss_rsae_sha512_name}, + {TLSEXT_SIGALG_rsa_pss_pss_sha256, TLSEXT_SIGALG_rsa_pss_pss_sha256_name}, + {TLSEXT_SIGALG_rsa_pss_pss_sha384, TLSEXT_SIGALG_rsa_pss_pss_sha384_name}, + {TLSEXT_SIGALG_rsa_pss_pss_sha512, TLSEXT_SIGALG_rsa_pss_pss_sha512_name}, + {TLSEXT_SIGALG_rsa_pkcs1_sha256, TLSEXT_SIGALG_rsa_pkcs1_sha256_name}, + {TLSEXT_SIGALG_rsa_pkcs1_sha384, TLSEXT_SIGALG_rsa_pkcs1_sha384_name}, + {TLSEXT_SIGALG_rsa_pkcs1_sha512, TLSEXT_SIGALG_rsa_pkcs1_sha512_name}, + {TLSEXT_SIGALG_rsa_pkcs1_sha224, TLSEXT_SIGALG_rsa_pkcs1_sha224_name}, + {TLSEXT_SIGALG_rsa_pkcs1_sha1, TLSEXT_SIGALG_rsa_pkcs1_sha1_name}, + {TLSEXT_SIGALG_dsa_sha256, TLSEXT_SIGALG_dsa_sha256_name}, + {TLSEXT_SIGALG_dsa_sha384, TLSEXT_SIGALG_dsa_sha384_name}, + {TLSEXT_SIGALG_dsa_sha512, TLSEXT_SIGALG_dsa_sha512_name}, + {TLSEXT_SIGALG_dsa_sha224, TLSEXT_SIGALG_dsa_sha224_name}, + {TLSEXT_SIGALG_dsa_sha1, TLSEXT_SIGALG_dsa_sha1_name}, + {TLSEXT_SIGALG_gostr34102012_256_intrinsic, TLSEXT_SIGALG_gostr34102012_256_intrinsic_name}, + {TLSEXT_SIGALG_gostr34102012_512_intrinsic, TLSEXT_SIGALG_gostr34102012_512_intrinsic_name}, + {TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256, TLSEXT_SIGALG_gostr34102012_256_gostr34112012_256_name}, + {TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512, TLSEXT_SIGALG_gostr34102012_512_gostr34112012_512_name}, + {TLSEXT_SIGALG_gostr34102001_gostr3411, TLSEXT_SIGALG_gostr34102001_gostr3411_name}, + {TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256, TLSEXT_SIGALG_ecdsa_brainpoolP256r1_sha256_name}, + {TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384, TLSEXT_SIGALG_ecdsa_brainpoolP384r1_sha384_name}, + {TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512, TLSEXT_SIGALG_ecdsa_brainpoolP512r1_sha512_name} }; static const ssl_trace_tbl ssl_ctype_tbl[] = { @@ -1669,6 +1671,7 @@ static int ssl_print_handshake(BIO *bio, const SSL_CONNECTION *sc, int server, ssl_print_hex(bio, indent + 2, "verify_data", msg, msglen); break; + case SSL3_MT_END_OF_EARLY_DATA: case SSL3_MT_SERVER_DONE: if (msglen != 0) ssl_print_hex(bio, indent + 2, "unexpected value", msg, msglen); diff --git a/ssl/tls13_enc.c b/ssl/tls13_enc.c index 772a6fc173..7846c73a86 100644 --- a/ssl/tls13_enc.c +++ b/ssl/tls13_enc.c @@ -1,5 +1,5 @@ /* - * Copyright 2016-2023 The OpenSSL Project Authors. All Rights Reserved. + * Copyright 2016-2024 The OpenSSL Project Authors. All Rights Reserved. * * Licensed under the Apache License 2.0 (the "License"). You may not use * this file except in compliance with the License. You can obtain a copy @@ -188,7 +188,7 @@ int tls13_generate_secret(SSL_CONNECTION *s, const EVP_MD *md, mdleni = EVP_MD_get_size(md); /* Ensure cast to size_t is safe */ - if (!ossl_assert(mdleni >= 0)) { + if (!ossl_assert(mdleni > 0)) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); EVP_KDF_CTX_free(kctx); return 0; @@ -247,8 +247,14 @@ int tls13_generate_master_secret(SSL_CONNECTION *s, unsigned char *out, size_t *secret_size) { const EVP_MD *md = ssl_handshake_md(s); + int md_size; - *secret_size = EVP_MD_get_size(md); + md_size = EVP_MD_get_size(md); + if (md_size <= 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + return 0; + } + *secret_size = (size_t)md_size; /* Calls SSLfatal() if required */ return tls13_generate_secret(s, md, prev, NULL, 0, out); } @@ -317,10 +323,12 @@ int tls13_setup_key_block(SSL_CONNECTION *s) { const EVP_CIPHER *c; const EVP_MD *hash; + int mac_type = NID_undef; + size_t mac_secret_size = 0; s->session->cipher = s->s3.tmp.new_cipher; if (!ssl_cipher_get_evp(SSL_CONNECTION_GET_CTX(s), s->session, &c, &hash, - NULL, NULL, NULL, 0)) { + &mac_type, &mac_secret_size, NULL, 0)) { /* Error is already recorded */ SSLfatal_alert(s, SSL_AD_INTERNAL_ERROR); return 0; @@ -330,26 +338,30 @@ int tls13_setup_key_block(SSL_CONNECTION *s) s->s3.tmp.new_sym_enc = c; ssl_evp_md_free(s->s3.tmp.new_hash); s->s3.tmp.new_hash = hash; + s->s3.tmp.new_mac_pkey_type = mac_type; + s->s3.tmp.new_mac_secret_size = mac_secret_size; return 1; } static int derive_secret_key_and_iv(SSL_CONNECTION *s, const EVP_MD *md, const EVP_CIPHER *ciph, + int mac_type, + const EVP_MD *mac_md, const unsigned char *insecret, const unsigned char *hash, const unsigned char *label, size_t labellen, unsigned char *secret, unsigned char *key, size_t *keylen, - unsigned char *iv, size_t *ivlen, + unsigned char **iv, size_t *ivlen, size_t *taglen) { int hashleni = EVP_MD_get_size(md); size_t hashlen; - int mode; + int mode, mac_mdleni; /* Ensure cast to size_t is safe */ - if (!ossl_assert(hashleni >= 0)) { + if (!ossl_assert(hashleni > 0)) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); return 0; } @@ -361,48 +373,71 @@ static int derive_secret_key_and_iv(SSL_CONNECTION *s, const EVP_MD *md, return 0; } - *keylen = EVP_CIPHER_get_key_length(ciph); - - mode = EVP_CIPHER_get_mode(ciph); - if (mode == EVP_CIPH_CCM_MODE) { - uint32_t algenc; - - *ivlen = EVP_CCM_TLS_IV_LEN; - if (s->s3.tmp.new_cipher != NULL) { - algenc = s->s3.tmp.new_cipher->algorithm_enc; - } else if (s->session->cipher != NULL) { - /* We've not selected a cipher yet - we must be doing early data */ - algenc = s->session->cipher->algorithm_enc; - } else if (s->psksession != NULL && s->psksession->cipher != NULL) { - /* We must be doing early data with out-of-band PSK */ - algenc = s->psksession->cipher->algorithm_enc; - } else { - SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); + /* if ciph is NULL cipher, then use new_hash to calculate keylen */ + if (EVP_CIPHER_is_a(ciph, "NULL") + && mac_md != NULL + && mac_type == NID_hmac) { + mac_mdleni = EVP_MD_get_size(mac_md); + + if (mac_mdleni <= 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); return 0; } - if (algenc & (SSL_AES128CCM8 | SSL_AES256CCM8)) - *taglen = EVP_CCM8_TLS_TAG_LEN; - else - *taglen = EVP_CCM_TLS_TAG_LEN; + *ivlen = *taglen = (size_t)mac_mdleni; + *keylen = s->s3.tmp.new_mac_secret_size; } else { - int iivlen; - if (mode == EVP_CIPH_GCM_MODE) { - *taglen = EVP_GCM_TLS_TAG_LEN; + *keylen = EVP_CIPHER_get_key_length(ciph); + + mode = EVP_CIPHER_get_mode(ciph); + if (mode == EVP_CIPH_CCM_MODE) { + uint32_t algenc; + + *ivlen = EVP_CCM_TLS_IV_LEN; + if (s->s3.tmp.new_cipher != NULL) { + algenc = s->s3.tmp.new_cipher->algorithm_enc; + } else if (s->session->cipher != NULL) { + /* We've not selected a cipher yet - we must be doing early data */ + algenc = s->session->cipher->algorithm_enc; + } else if (s->psksession != NULL && s->psksession->cipher != NULL) { + /* We must be doing early data with out-of-band PSK */ + algenc = s->psksession->cipher->algorithm_enc; + } else { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); + return 0; + } + if (algenc & (SSL_AES128CCM8 | SSL_AES256CCM8)) + *taglen = EVP_CCM8_TLS_TAG_LEN; + else + *taglen = EVP_CCM_TLS_TAG_LEN; } else { - /* CHACHA20P-POLY1305 */ - *taglen = EVP_CHACHAPOLY_TLS_TAG_LEN; + int iivlen; + + if (mode == EVP_CIPH_GCM_MODE) { + *taglen = EVP_GCM_TLS_TAG_LEN; + } else { + /* CHACHA20P-POLY1305 */ + *taglen = EVP_CHACHAPOLY_TLS_TAG_LEN; + } + iivlen = EVP_CIPHER_get_iv_length(ciph); + if (iivlen < 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); + return 0; + } + *ivlen = iivlen; } - iivlen = EVP_CIPHER_get_iv_length(ciph); - if (iivlen < 0) { - SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_EVP_LIB); + } + + if (*ivlen > EVP_MAX_IV_LENGTH) { + *iv = OPENSSL_malloc(*ivlen); + if (*iv == NULL) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_MALLOC_FAILURE); return 0; } - *ivlen = iivlen; } if (!tls13_derive_key(s, md, secret, key, *keylen) - || !tls13_derive_iv(s, md, secret, iv, *ivlen)) { + || !tls13_derive_iv(s, md, secret, *iv, *ivlen)) { /* SSLfatal() already called */ return 0; } @@ -428,7 +463,8 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) static const unsigned char resumption_master_secret[] = "\x72\x65\x73\x20\x6D\x61\x73\x74\x65\x72"; /* ASCII: "e exp master", in hex for EBCDIC compatibility */ static const unsigned char early_exporter_master_secret[] = "\x65\x20\x65\x78\x70\x20\x6D\x61\x73\x74\x65\x72"; - unsigned char iv[EVP_MAX_IV_LENGTH]; + unsigned char iv_intern[EVP_MAX_IV_LENGTH]; + unsigned char *iv = iv_intern; unsigned char key[EVP_MAX_KEY_LENGTH]; unsigned char secret[EVP_MAX_MD_SIZE]; unsigned char hashval[EVP_MAX_MD_SIZE]; @@ -436,21 +472,22 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) unsigned char *insecret; unsigned char *finsecret = NULL; const char *log_label = NULL; - size_t finsecretlen = 0; + int finsecretlen = 0; const unsigned char *label; size_t labellen, hashlen = 0; int ret = 0; - const EVP_MD *md = NULL; + const EVP_MD *md = NULL, *mac_md = NULL; const EVP_CIPHER *cipher = NULL; + int mac_pkey_type = NID_undef; SSL_CTX *sctx = SSL_CONNECTION_GET_CTX(s); - size_t keylen, ivlen, taglen; + size_t keylen, ivlen = EVP_MAX_IV_LENGTH, taglen; int level; int direction = (which & SSL3_CC_READ) != 0 ? OSSL_RECORD_DIRECTION_READ : OSSL_RECORD_DIRECTION_WRITE; if (((which & SSL3_CC_CLIENT) && (which & SSL3_CC_WRITE)) || ((which & SSL3_CC_SERVER) && (which & SSL3_CC_READ))) { - if (which & SSL3_CC_EARLY) { + if ((which & SSL3_CC_EARLY) != 0) { EVP_MD_CTX *mdctx = NULL; long handlen; void *hdata; @@ -489,6 +526,23 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) goto err; } + /* + * This ups the ref count on cipher so we better make sure we free + * it again + */ + if (!ssl_cipher_get_evp_cipher(sctx, sslcipher, &cipher)) { + /* Error is already recorded */ + SSLfatal_alert(s, SSL_AD_INTERNAL_ERROR); + goto err; + } + + if (((EVP_CIPHER_flags(cipher) & EVP_CIPH_FLAG_AEAD_CIPHER) == 0) + && (!ssl_cipher_get_evp_md_mac(sctx, sslcipher, &mac_md, + &mac_pkey_type, NULL))) { + SSLfatal_alert(s, SSL_AD_INTERNAL_ERROR); + goto err; + } + /* * We need to calculate the handshake digest using the digest from * the session. We haven't yet selected our ciphersuite so we can't @@ -500,17 +554,6 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) goto err; } - /* - * This ups the ref count on cipher so we better make sure we free - * it again - */ - if (!ssl_cipher_get_evp_cipher(sctx, sslcipher, &cipher)) { - /* Error is already recorded */ - SSLfatal_alert(s, SSL_AD_INTERNAL_ERROR); - EVP_MD_CTX_free(mdctx); - goto err; - } - md = ssl_md(sctx, sslcipher->algorithm2); if (md == NULL || !EVP_DigestInit_ex(mdctx, md, NULL) || !EVP_DigestUpdate(mdctx, hdata, handlen) @@ -541,6 +584,10 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) insecret = s->handshake_secret; finsecret = s->client_finished_secret; finsecretlen = EVP_MD_get_size(ssl_handshake_md(s)); + if (finsecretlen <= 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + goto err; + } label = client_handshake_traffic; labellen = sizeof(client_handshake_traffic) - 1; log_label = CLIENT_HANDSHAKE_LABEL; @@ -573,6 +620,10 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) insecret = s->handshake_secret; finsecret = s->server_finished_secret; finsecretlen = EVP_MD_get_size(ssl_handshake_md(s)); + if (finsecretlen <= 0) { + SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); + goto err; + } label = server_handshake_traffic; labellen = sizeof(server_handshake_traffic) - 1; log_label = SERVER_HANDSHAKE_LABEL; @@ -584,9 +635,11 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) } } - if (!(which & SSL3_CC_EARLY)) { + if ((which & SSL3_CC_EARLY) == 0) { md = ssl_handshake_md(s); cipher = s->s3.tmp.new_sym_enc; + mac_md = s->s3.tmp.new_hash; + mac_pkey_type = s->s3.tmp.new_mac_pkey_type; if (!ssl3_digest_cached_records(s, 1) || !ssl_handshake_hash(s, hashval, sizeof(hashval), &hashlen)) { /* SSLfatal() already called */; @@ -623,9 +676,9 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) if (!ossl_assert(cipher != NULL)) goto err; - if (!derive_secret_key_and_iv(s, md, cipher, + if (!derive_secret_key_and_iv(s, md, cipher, mac_pkey_type, mac_md, insecret, hash, label, labellen, secret, key, - &keylen, iv, &ivlen, &taglen)) { + &keylen, &iv, &ivlen, &taglen)) { /* SSLfatal() already called */ goto err; } @@ -657,7 +710,7 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) if (finsecret != NULL && !tls13_derive_finishedkey(s, ssl_handshake_md(s), secret, - finsecret, finsecretlen)) { + finsecret, (size_t)finsecretlen)) { /* SSLfatal() already called */ goto err; } @@ -678,8 +731,8 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) if (!ssl_set_new_record_layer(s, s->version, direction, level, secret, hashlen, key, keylen, iv, - ivlen, NULL, 0, cipher, taglen, NID_undef, - NULL, NULL, md)) { + ivlen, NULL, 0, cipher, taglen, + mac_pkey_type, mac_md, NULL, md)) { /* SSLfatal already called */ goto err; } @@ -688,10 +741,14 @@ int tls13_change_cipher_state(SSL_CONNECTION *s, int which) err: if ((which & SSL3_CC_EARLY) != 0) { /* We up-refed this so now we need to down ref */ + if ((EVP_CIPHER_flags(cipher) & EVP_CIPH_FLAG_AEAD_CIPHER) == 0) + ssl_evp_md_free(mac_md); ssl_evp_cipher_free(cipher); } OPENSSL_cleanse(key, sizeof(key)); OPENSSL_cleanse(secret, sizeof(secret)); + if (iv != iv_intern) + OPENSSL_free(iv); return ret; } @@ -709,7 +766,8 @@ int tls13_update_key(SSL_CONNECTION *s, int sending) int ret = 0, l; int direction = sending ? OSSL_RECORD_DIRECTION_WRITE : OSSL_RECORD_DIRECTION_READ; - unsigned char iv[EVP_MAX_IV_LENGTH]; + unsigned char iv_intern[EVP_MAX_IV_LENGTH]; + unsigned char *iv = iv_intern; if ((l = EVP_MD_get_size(md)) <= 0) { SSLfatal(s, SSL_AD_INTERNAL_ERROR, ERR_R_INTERNAL_ERROR); @@ -723,10 +781,12 @@ int tls13_update_key(SSL_CONNECTION *s, int sending) insecret = s->client_app_traffic_secret; if (!derive_secret_key_and_iv(s, md, - s->s3.tmp.new_sym_enc, insecret, NULL, + s->s3.tmp.new_sym_enc, + s->s3.tmp.new_mac_pkey_type, s->s3.tmp.new_hash, + insecret, NULL, application_traffic, sizeof(application_traffic) - 1, secret, key, - &keylen, iv, &ivlen, &taglen)) { + &keylen, &iv, &ivlen, &taglen)) { /* SSLfatal() already called */ goto err; } @@ -753,6 +813,8 @@ int tls13_update_key(SSL_CONNECTION *s, int sending) err: OPENSSL_cleanse(key, sizeof(key)); OPENSSL_cleanse(secret, sizeof(secret)); + if (iv != iv_intern) + OPENSSL_free(iv); return ret; }