summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorChristian Grothoff <christian@grothoff.org>2020-12-25 08:44:57 +0100
committerChristian Grothoff <christian@grothoff.org>2020-12-25 08:44:57 +0100
commite1e9250ff770625d8a81326e6e5f5011f909cfca (patch)
tree02b06e9a0b6ac4b8d89588cc1260e5ece47c75eb /src
parent247d1ca3e56461069c02481c7071b56e950fe78a (diff)
downloadexchange-e1e9250ff770625d8a81326e6e5f5011f909cfca.tar.gz
exchange-e1e9250ff770625d8a81326e6e5f5011f909cfca.tar.bz2
exchange-e1e9250ff770625d8a81326e6e5f5011f909cfca.zip
add check for sufficiently recent version of libgnunetutil, remove now unnecessary crypto blinding logic
Diffstat (limited to 'src')
-rw-r--r--src/util/crypto.c423
1 files changed, 0 insertions, 423 deletions
diff --git a/src/util/crypto.c b/src/util/crypto.c
index 4f084b19..a7ea4f4c 100644
--- a/src/util/crypto.c
+++ b/src/util/crypto.c
@@ -25,18 +25,6 @@
#include "taler_util.h"
#include <gcrypt.h>
-/**
- * Should we use the RSA blind signing implementation from libgnunetutil? The
- * blinding only works correctly with a current version of libgnunetutil.
- *
- * Only applies to blinding and unblinding, but
- * not to blind signing.
- *
- * FIXME: Can we define some macro for this in configure.ac
- * to detect the version?
- */
-#define USE_GNUNET_RSA_BLINDING 0
-
/**
* Function called by libgcrypt on serious errors.
@@ -312,280 +300,6 @@ TALER_refresh_get_commitment (struct TALER_RefreshCommitmentP *rc,
}
-#if ! USE_GNUNET_RSA_BLINDING
-
-
-/**
- * The private information of an RSA key pair.
- *
- * FIXME: This declaration is evil, as it defines
- * an opaque struct that is "owned" by GNUnet.
- */
-struct GNUNET_CRYPTO_RsaPrivateKey
-{
- /**
- * Libgcrypt S-expression for the RSA private key.
- */
- gcry_sexp_t sexp;
-};
-
-
-/**
- * The public information of an RSA key pair.
- *
- * FIXME: This declaration is evil, as it defines
- * an opaque struct that is "owned" by GNUnet.
- */
-struct GNUNET_CRYPTO_RsaPublicKey
-{
- /**
- * Libgcrypt S-expression for the RSA public key.
- */
- gcry_sexp_t sexp;
-};
-
-/**
- * @brief an RSA signature
- *
- * FIXME: This declaration is evil, as it defines
- * an opaque struct that is "owned" by GNUnet.
- */
-struct GNUNET_CRYPTO_RsaSignature
-{
- /**
- * Libgcrypt S-expression for the RSA signature.
- */
- gcry_sexp_t sexp;
-};
-
-/**
- * @brief RSA blinding key
- */
-struct RsaBlindingKey
-{
- /**
- * Random value used for blinding.
- */
- gcry_mpi_t r;
-};
-
-
-/**
- * Destroy a blinding key
- *
- * @param bkey the blinding key to destroy
- */
-static void
-rsa_blinding_key_free (struct RsaBlindingKey *bkey)
-{
- gcry_mpi_release (bkey->r);
- GNUNET_free (bkey);
-}
-
-
-/**
- * Extract values from an S-expression.
- *
- * @param array where to store the result(s)
- * @param sexp S-expression to parse
- * @param topname top-level name in the S-expression that is of interest
- * @param elems names of the elements to extract
- * @return 0 on success
- */
-static int
-key_from_sexp (gcry_mpi_t *array,
- gcry_sexp_t sexp,
- const char *topname,
- const char *elems)
-{
- gcry_sexp_t list;
- gcry_sexp_t l2;
- const char *s;
- unsigned int idx;
-
- if (! (list = gcry_sexp_find_token (sexp, topname, 0)))
- return 1;
- l2 = gcry_sexp_cadr (list);
- gcry_sexp_release (list);
- list = l2;
- if (! list)
- return 2;
- idx = 0;
- for (s = elems; *s; s++, idx++)
- {
- if (! (l2 = gcry_sexp_find_token (list, s, 1)))
- {
- for (unsigned int i = 0; i < idx; i++)
- {
- gcry_free (array[i]);
- array[i] = NULL;
- }
- gcry_sexp_release (list);
- return 3; /* required parameter not found */
- }
- array[idx] = gcry_sexp_nth_mpi (l2, 1, GCRYMPI_FMT_USG);
- gcry_sexp_release (l2);
- if (! array[idx])
- {
- for (unsigned int i = 0; i < idx; i++)
- {
- gcry_free (array[i]);
- array[i] = NULL;
- }
- gcry_sexp_release (list);
- return 4; /* required parameter is invalid */
- }
- }
- gcry_sexp_release (list);
- return 0;
-}
-
-
-/**
- * Test for malicious RSA key.
- *
- * Assuming n is an RSA modulous and r is generated using a call to
- * GNUNET_CRYPTO_kdf_mod_mpi, if gcd(r,n) != 1 then n must be a
- * malicious RSA key designed to deanomize the user.
- *
- * @param r KDF result
- * @param n RSA modulus
- * @return True if gcd(r,n) = 1, False means RSA key is malicious
- */
-static int
-rsa_gcd_validate (gcry_mpi_t r, gcry_mpi_t n)
-{
- gcry_mpi_t g;
- int t;
-
- g = gcry_mpi_new (0);
- t = gcry_mpi_gcd (g, r, n);
- gcry_mpi_release (g);
- return t;
-}
-
-
-/**
- * Computes a full domain hash seeded by the given public key.
- * This gives a measure of provable security to the Taler exchange
- * against one-more forgery attacks. See:
- * https://eprint.iacr.org/2001/002.pdf
- * http://www.di.ens.fr/~pointche/Documents/Papers/2001_fcA.pdf
- *
- * @param hash initial hash of the message to sign
- * @param pkey the public key of the signer
- * @return MPI value set to the FDH, NULL if RSA key is malicious
- */
-static gcry_mpi_t
-rsa_full_domain_hash (const struct GNUNET_CRYPTO_RsaPublicKey *pkey,
- const struct GNUNET_HashCode *hash)
-{
- gcry_mpi_t r, n;
- void *xts;
- size_t xts_len;
- int ok;
-
- /* Extract the composite n from the RSA public key */
- GNUNET_assert (0 == key_from_sexp (&n, pkey->sexp, "rsa", "n"));
- /* Assert that it at least looks like an RSA key */
- GNUNET_assert (0 == gcry_mpi_get_flag (n, GCRYMPI_FLAG_OPAQUE));
-
- /* We key with the public denomination key as a homage to RSA-PSS by *
- * Mihir Bellare and Phillip Rogaway. Doing this lowers the degree *
- * of the hypothetical polyomial-time attack on RSA-KTI created by a *
- * polynomial-time one-more forgary attack. Yey seeding! */
- xts_len = GNUNET_CRYPTO_rsa_public_key_encode (pkey, &xts);
-
- GNUNET_CRYPTO_kdf_mod_mpi (&r,
- n,
- xts, xts_len,
- hash, sizeof(*hash),
- "RSA-FDA FTpsW!");
- GNUNET_free (xts);
-
- ok = rsa_gcd_validate (r, n);
- gcry_mpi_release (n);
- if (ok)
- return r;
- gcry_mpi_release (r);
- return NULL;
-}
-
-
-/**
- * Create a blinding key
- *
- * @param pkey the public key to blind for
- * @param bks pre-secret to use to derive the blinding key
- * @return the newly created blinding key, NULL if RSA key is malicious
- */
-static struct RsaBlindingKey *
-rsa_blinding_key_derive (const struct GNUNET_CRYPTO_RsaPublicKey *pkey,
- const struct GNUNET_CRYPTO_RsaBlindingKeySecret *bks)
-{
- char *xts = "Blinding KDF extractor HMAC key"; /* Trusts bks' randomness more */
- struct RsaBlindingKey *blind;
- gcry_mpi_t n;
-
- blind = GNUNET_new (struct RsaBlindingKey);
- GNUNET_assert (NULL != blind);
-
- /* Extract the composite n from the RSA public key */
- GNUNET_assert (0 == key_from_sexp (&n, pkey->sexp, "rsa", "n"));
- /* Assert that it at least looks like an RSA key */
- GNUNET_assert (0 == gcry_mpi_get_flag (n, GCRYMPI_FLAG_OPAQUE));
-
- GNUNET_CRYPTO_kdf_mod_mpi (&blind->r,
- n,
- xts, strlen (xts),
- bks, sizeof(*bks),
- "Blinding KDF");
- if (0 == rsa_gcd_validate (blind->r, n))
- {
- GNUNET_free (blind);
- blind = NULL;
- }
-
- gcry_mpi_release (n);
- return blind;
-}
-
-
-/**
- * Print an MPI to a newly created buffer
- *
- * @param v MPI to print.
- * @param[out] buffer newly allocated buffer containing the result
- * @return number of bytes stored in @a buffer
- */
-static size_t
-numeric_mpi_alloc_n_print (gcry_mpi_t v,
- char **buffer)
-{
- size_t n;
- char *b;
- size_t rsize;
-
- gcry_mpi_print (GCRYMPI_FMT_USG,
- NULL,
- 0,
- &n,
- v);
- b = GNUNET_malloc (n);
- GNUNET_assert (0 ==
- gcry_mpi_print (GCRYMPI_FMT_USG,
- (unsigned char *) b,
- n,
- &rsize,
- v));
- *buffer = b;
- return n;
-}
-
-
-#endif /* ! USE_GNUNET_RSA_BLINDING */
-
-
enum GNUNET_GenericReturnValue
TALER_rsa_blind (const struct GNUNET_HashCode *hash,
const struct GNUNET_CRYPTO_RsaBlindingKeySecret *bks,
@@ -593,75 +307,11 @@ TALER_rsa_blind (const struct GNUNET_HashCode *hash,
void **buf,
size_t *buf_size)
{
-#if USE_GNUNET_RSA_BLINDING
return GNUNET_CRYPTO_rsa_blind (hash,
bks,
pkey,
buf,
buf_size);
-#else
- struct RsaBlindingKey *bkey;
- gcry_mpi_t data;
- gcry_mpi_t ne[2];
- gcry_mpi_t r_e;
- gcry_mpi_t data_r_e;
- int ret;
-
- GNUNET_assert (buf != NULL);
- GNUNET_assert (buf_size != NULL);
- ret = key_from_sexp (ne, pkey->sexp, "public-key", "ne");
- if (0 != ret)
- ret = key_from_sexp (ne, pkey->sexp, "rsa", "ne");
- if (0 != ret)
- {
- GNUNET_break (0);
- *buf = NULL;
- *buf_size = 0;
- return GNUNET_NO;
- }
-
- data = rsa_full_domain_hash (pkey, hash);
- if (NULL == data)
- goto rsa_gcd_validate_failure;
-
- bkey = rsa_blinding_key_derive (pkey, bks);
- if (NULL == bkey)
- {
- gcry_mpi_release (data);
- goto rsa_gcd_validate_failure;
- }
-
- r_e = gcry_mpi_new (0);
- gcry_mpi_powm (r_e,
- bkey->r,
- ne[1],
- ne[0]);
- data_r_e = gcry_mpi_new (0);
- gcry_mpi_mulm (data_r_e,
- data,
- r_e,
- ne[0]);
- gcry_mpi_release (data);
- gcry_mpi_release (ne[0]);
- gcry_mpi_release (ne[1]);
- gcry_mpi_release (r_e);
- rsa_blinding_key_free (bkey);
-
- *buf_size = numeric_mpi_alloc_n_print (data_r_e,
- (char **) buf);
- gcry_mpi_release (data_r_e);
-
- return GNUNET_YES;
-
-rsa_gcd_validate_failure:
- /* We know the RSA key is malicious here, so warn the wallet. */
- /* GNUNET_break_op (0); */
- gcry_mpi_release (ne[0]);
- gcry_mpi_release (ne[1]);
- *buf = NULL;
- *buf_size = 0;
- return GNUNET_NO;
-#endif
}
@@ -670,82 +320,9 @@ TALER_rsa_unblind (const struct GNUNET_CRYPTO_RsaSignature *sig,
const struct GNUNET_CRYPTO_RsaBlindingKeySecret *bks,
struct GNUNET_CRYPTO_RsaPublicKey *pkey)
{
-#if USE_GNUNET_RSA_BLINDING
return GNUNET_CRYPTO_rsa_unblind (sig,
bks,
pkey);
-#else
- struct RsaBlindingKey *bkey;
- gcry_mpi_t n;
- gcry_mpi_t s;
- gcry_mpi_t r_inv;
- gcry_mpi_t ubsig;
- int ret;
- struct GNUNET_CRYPTO_RsaSignature *sret;
-
- ret = key_from_sexp (&n, pkey->sexp, "public-key", "n");
- if (0 != ret)
- ret = key_from_sexp (&n, pkey->sexp, "rsa", "n");
- if (0 != ret)
- {
- GNUNET_break_op (0);
- return NULL;
- }
- ret = key_from_sexp (&s, sig->sexp, "sig-val", "s");
- if (0 != ret)
- ret = key_from_sexp (&s, sig->sexp, "rsa", "s");
- if (0 != ret)
- {
- gcry_mpi_release (n);
- GNUNET_break_op (0);
- return NULL;
- }
-
- bkey = rsa_blinding_key_derive (pkey, bks);
- if (NULL == bkey)
- {
- /* RSA key is malicious since rsa_gcd_validate failed here.
- * It should have failed during GNUNET_CRYPTO_rsa_blind too though,
- * so the exchange is being malicious in an unfamilair way, maybe
- * just trying to crash us. */
- GNUNET_break_op (0);
- gcry_mpi_release (n);
- gcry_mpi_release (s);
- return NULL;
- }
-
- r_inv = gcry_mpi_new (0);
- if (1 !=
- gcry_mpi_invm (r_inv,
- bkey->r,
- n))
- {
- /* We cannot find r mod n, so gcd(r,n) != 1, which should get *
- * caught above, but we handle it the same here. */
- GNUNET_break_op (0);
- gcry_mpi_release (r_inv);
- rsa_blinding_key_free (bkey);
- gcry_mpi_release (n);
- gcry_mpi_release (s);
- return NULL;
- }
-
- ubsig = gcry_mpi_new (0);
- gcry_mpi_mulm (ubsig, s, r_inv, n);
- gcry_mpi_release (n);
- gcry_mpi_release (r_inv);
- gcry_mpi_release (s);
- rsa_blinding_key_free (bkey);
-
- sret = GNUNET_new (struct GNUNET_CRYPTO_RsaSignature);
- GNUNET_assert (0 ==
- gcry_sexp_build (&sret->sexp,
- NULL,
- "(sig-val (rsa (s %M)))",
- ubsig));
- gcry_mpi_release (ubsig);
- return sret;
-#endif
}