diff options
| author | NIIBE Yutaka <[email protected]> | 2024-04-10 02:09:29 +0000 |
|---|---|---|
| committer | NIIBE Yutaka <[email protected]> | 2024-04-10 02:09:29 +0000 |
| commit | 04b81ec236cf66987a77e0aaafd9f2363daac60c (patch) | |
| tree | 2c9450ae19a95cb66ea4fa12fd3fdf1460205e21 /common/kmac.c | |
| parent | gpg: Some support to allow Kyber decryption. (diff) | |
| download | gnupg-04b81ec236cf66987a77e0aaafd9f2363daac60c.tar.gz gnupg-04b81ec236cf66987a77e0aaafd9f2363daac60c.zip | |
common,agent: Factor out KEM functions into common/kem.c.
* common/util.h (compute_kmac256): Remove.
(gnupg_ecc_kem_kdf, gnupg_kem_combiner): New.
* common/kmac.c (compute_kmac256): Don't expose.
(gnupg_ecc_kem_kdf, gnupg_kem_combiner): New.
* agent/pkdecrypt.c (agent_hybrid_pgp_kem_decrypt): Use
gnupg_ecc_kem_kdf and gnupg_kem_combiner.
--
Signed-off-by: NIIBE Yutaka <[email protected]>
Diffstat (limited to 'common/kmac.c')
| -rw-r--r-- | common/kmac.c | 77 |
1 files changed, 75 insertions, 2 deletions
diff --git a/common/kmac.c b/common/kmac.c index 69e18a2c3..c5de8b102 100644 --- a/common/kmac.c +++ b/common/kmac.c @@ -1,4 +1,4 @@ -/* kmac.c - Keccak based MAC +/* kem.c - KEM helper functions * Copyright (C) 2024 g10 Code GmbH. * * This file is part of GnuPG. @@ -36,7 +36,7 @@ #include "mischelp.h" #define KECCAK512_BLOCKSIZE 136 -gpg_error_t +static gpg_error_t compute_kmac256 (void *digest, size_t digestlen, const void *key, size_t keylen, const void *custom, size_t customlen, @@ -134,3 +134,76 @@ compute_kmac256 (void *digest, size_t digestlen, return gpg_error (GPG_ERR_NOT_IMPLEMENTED); #endif } + +/* Compute KEK (shared secret) for ECC with HASHALGO, ECDH result, + ciphertext in ECC_CT, public key in ECC_PK. */ +gpg_error_t +gnupg_ecc_kem_kdf (void *kek, size_t kek_len, + int hashalgo, const void *ecdh, size_t ecdh_len, + const void *ecc_ct, size_t ecc_ct_len, + const void *ecc_pk, size_t ecc_pk_len) +{ + gcry_buffer_t iov[3]; + unsigned int dlen; + + dlen = gcry_md_get_algo_dlen (hashalgo); + if (kek_len != dlen) + return gpg_error (GPG_ERR_INV_LENGTH); + + memset (iov, 0, sizeof (iov)); + + iov[0].data = (unsigned char *)ecdh; + iov[0].len = ecdh_len; + iov[1].data = (unsigned char *)ecc_ct; + iov[1].len = ecc_ct_len; + iov[2].data = (unsigned char *)ecc_pk; + iov[2].len = ecc_pk_len; + gcry_md_hash_buffers (hashalgo, 0, kek, iov, 3); + + return 0; +} + + +/* domSeperation */ +#define KMAC_KEY "OpenPGPCompositeKeyDerivationFunction" + +/* customizationString */ +#define KMAC_CUSTOM "KDF" + +/* Compute KEK by combining two KEMs. */ +gpg_error_t +gnupg_kem_combiner (void *kek, size_t kek_len, + const void *ecc_ss, size_t ecc_ss_len, + const void *ecc_ct, size_t ecc_ct_len, + const void *mlkem_ss, size_t mlkem_ss_len, + const void *mlkem_ct, size_t mlkem_ct_len, + const void *fixedinfo, size_t fixedinfo_len) +{ + gpg_error_t err; + gcry_buffer_t iov[6]; + + memset (iov, 0, sizeof (iov)); + + iov[0].data = "\x00\x00\x00\x01"; /* Counter */ + iov[0].len = 4; + + iov[1].data = (unsigned char *)ecc_ss; + iov[1].len = ecc_ss_len; + + iov[2].data = (unsigned char *)ecc_ct; + iov[2].len = ecc_ct_len; + + iov[3].data = (unsigned char *)mlkem_ss; + iov[3].len = mlkem_ss_len; + + iov[4].data = (unsigned char *)mlkem_ct; + iov[4].len = mlkem_ct_len; + + iov[5].data = (unsigned char *)fixedinfo; + iov[5].len = fixedinfo_len; + + err = compute_kmac256 (kek, kek_len, + KMAC_KEY, strlen (KMAC_KEY), + KMAC_CUSTOM, strlen (KMAC_CUSTOM), iov, 6); + return err; +} |
