From 8d717c4b3d126104929aeb5e3a2176dd534e25ea Mon Sep 17 00:00:00 2001 From: Markus Teich Date: Tue, 21 Jun 2016 23:06:15 +0200 Subject: [PATCH] use proof structs. fix bug in mpi_serialize --- crypto.c | 342 ++++++++++++++++++++++++++++++++------------------ crypto.h | 62 ++++----- test_crypto.c | 102 ++++----------- 3 files changed, 269 insertions(+), 237 deletions(-) diff --git a/crypto.c b/crypto.c index d3da75d..d7d2e0f 100644 --- a/crypto.c +++ b/crypto.c @@ -157,19 +157,26 @@ ec_skey_create (gcry_mpi_t skey) /** - * ec_keypair_create + * ec_keypair_create creates a new keypair by creating a random secret key first + * and multipyling the base point with it to get the public key. * * @param[out] pkey where to store the generated public key - * @param[out] skey where to store the generated secret key + * @param[out] skey where to store the generated secret key. May be NULL if + * you're not interested in the secret key and just need a random point. */ void ec_keypair_create (gcry_mpi_point_t pkey, gcry_mpi_t skey) { - brandt_assert (NULL != pkey); - brandt_assert (NULL != skey); + gcry_mpi_t sk; - ec_skey_create (skey); - gcry_mpi_ec_mul (pkey, skey, ec_gen, ec_ctx); + brandt_assert (NULL != pkey); + sk = (NULL == skey) ? gcry_mpi_new (0) : skey; + + ec_skey_create (sk); + gcry_mpi_ec_mul (pkey, sk, ec_gen, ec_ctx); + + if (NULL == skey) + gcry_mpi_release (sk); } @@ -244,19 +251,21 @@ mpi_serialize (struct ec_mpi *dst, gcry_mpi_t src) { size_t rsize = 0; unsigned int nbits; - const void *p; + const void *vp; + char *cp = (char *)dst; gcry_error_t rc; + if (gcry_mpi_get_flag (src, GCRYMPI_FLAG_OPAQUE)) { /* Store opaque MPIs left aligned into the buffer. Used by Ed25519 point * compression */ - p = gcry_mpi_get_opaque (src, &nbits); - brandt_assert (p); + vp = gcry_mpi_get_opaque (src, &nbits); + brandt_assert (vp); rsize = (nbits + 7) / 8; if (rsize > sizeof (struct ec_mpi)) rsize = sizeof (struct ec_mpi); - memcpy (dst, p, rsize); + memcpy (dst, vp, rsize); if (rsize < sizeof (struct ec_mpi)) memset (((char *)dst) + rsize, 0, sizeof (struct ec_mpi) - rsize); } @@ -270,7 +279,7 @@ mpi_serialize (struct ec_mpi *dst, gcry_mpi_t src) /* Shift the output to the right, if shorter than available space */ if (rsize && rsize < sizeof (struct ec_mpi)) { - memmove (&dst[sizeof (struct ec_mpi) - rsize], dst, rsize); + memmove (&cp[sizeof (struct ec_mpi) - rsize], dst, rsize); memset (dst, 0, sizeof (struct ec_mpi) - rsize); } } @@ -577,8 +586,8 @@ smc_encrypt_bid (struct AuctionData *ad, gcry_mpi_t r1, gcry_mpi_t r2) { - smc_zkp_0og (ad->alpha[ad->i][j], (j == ad->b ? ec_gen : ec_zero), ad->Y, - ad->beta[ad->i][j], a1, a2, b1, b2, d1, d2, r1, r2); +// smc_zkp_0og (ad->alpha[ad->i][j], j == ad->b, ad->Y, +// ad->beta[ad->i][j], a1, a2, b1, b2, d1, d2, r1, r2); } @@ -604,27 +613,28 @@ smc_compute_outcome (struct AuctionData *ad) /** - * smc_zkp_dl + * smc_zkp_dl creates a proof of knowledge of @a x with \f$v = xg\f$ where + * \f$g\f$ is the base point on Ed25519. * - * @param v \todo - * @param g \todo - * @param x \todo - * @param a \todo - * @param r \todo + * @param[in] v input point. Must be known to the verifier. + * @param[in] x private key. Knowledge of this number is certified in the proof + * @param[out] proof pointer where to save the output proof structure. Must be + * shared with the verifier. */ void smc_zkp_dl (const gcry_mpi_point_t v, - const gcry_mpi_point_t g, const gcry_mpi_t x, - const gcry_mpi_point_t a, - gcry_mpi_t r) + struct proof_dl *proof) { struct zkp_challenge_dl challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t a = gcry_mpi_point_new (0); + gcry_mpi_t r = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); gcry_mpi_t z = gcry_mpi_new (0); - ec_keypair_create_base (a, z, g); + /* a = zg */ + ec_keypair_create (a, z); /* compute challenge c */ ec_point_serialize (&challenge.g, ec_gen); @@ -634,36 +644,44 @@ smc_zkp_dl (const gcry_mpi_point_t v, mpi_parse (c, (struct ec_mpi *)&challhash); gcry_mpi_mod (c, c, ec_n); + /* r = z + cx */ gcry_mpi_mulm (r, c, x, ec_n); gcry_mpi_addm (r, r, z, ec_n); + ec_point_serialize (&proof->a, a); + mpi_serialize (&proof->r, r); + + gcry_mpi_point_release (a); + gcry_mpi_release (r); gcry_mpi_release (c); gcry_mpi_release (z); } /** - * smc_zkp_dl_check + * smc_zkp_dl_check verifies a proof of knowledge of \f$x = ECDL_g(v)\f$ where + * \f$g\f$ is the base point on Ed25519. * - * @param v \todo - * @param g \todo - * @param a \todo - * @param r \todo + * @param[in] v input point. Received from the prover. + * @param[in] proof pointer to the proof structure. Received from the prover. * @return 0 if the proof is correct, something else otherwise */ int smc_zkp_dl_check (const gcry_mpi_point_t v, - const gcry_mpi_point_t g, - const gcry_mpi_point_t a, - const gcry_mpi_t r) + const struct proof_dl *proof) { int ret; struct zkp_challenge_dl challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t a = gcry_mpi_point_new (0); + gcry_mpi_t r = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); gcry_mpi_point_t left = gcry_mpi_point_new (0); gcry_mpi_point_t right = gcry_mpi_point_new (0); + ec_point_parse (a, &proof->a); + mpi_parse (r, &proof->r); + /* compute challenge c */ ec_point_serialize (&challenge.g, ec_gen); ec_point_serialize (&challenge.v, v); @@ -672,11 +690,14 @@ smc_zkp_dl_check (const gcry_mpi_point_t v, mpi_parse (c, (struct ec_mpi *)&challhash); gcry_mpi_mod (c, c, ec_n); - gcry_mpi_ec_mul (left, r, g, ec_ctx); + /* rg =? a + cv */ + gcry_mpi_ec_mul (left, r, ec_gen, ec_ctx); gcry_mpi_ec_mul (right, c, v, ec_ctx); gcry_mpi_ec_add (right, a, right, ec_ctx); - ret = ec_point_cmp (left, right); + + gcry_mpi_point_release (a); + gcry_mpi_release (r); gcry_mpi_release (c); gcry_mpi_point_release (left); gcry_mpi_point_release (right); @@ -686,82 +707,116 @@ smc_zkp_dl_check (const gcry_mpi_point_t v, /** - * smc_zkp_2dle \todo + * smc_zkp_2dle creates a proof that two ECDLs are equal without revealing the + * ECDL. \f$v=xg_1, w=xg_2\f$ are calculated as well and can be returned to the + * caller if needed. * - * @param v TODO - * @param w TODO - * @param g1 TODO - * @param g2 TODO - * @param x TODO - * @param a TODO - * @param b TODO - * @param r TODO + * @param[out] v first output point. May be NULL if not needed by the caller. + * Must be known to the verifier. + * @param[out] w second output point. May be NULL if not needed by the caller. + * Must be known to the verifier. + * @param[in] g1 first base point. Must be known to the verifier. + * @param[in] g2 second base point. Must be known to the verifier. + * @param[in] x private number to prove knowledge of. + * @param[out] proof pointer where to save the output proof structure. Must be + * shared with the verifier. */ void -smc_zkp_2dle (const gcry_mpi_point_t v, - const gcry_mpi_point_t w, +smc_zkp_2dle (gcry_mpi_point_t v, + gcry_mpi_point_t w, const gcry_mpi_point_t g1, const gcry_mpi_point_t g2, const gcry_mpi_t x, - gcry_mpi_point_t a, - gcry_mpi_point_t b, - gcry_mpi_t r) + struct proof_2dle *proof) { struct zkp_challenge_2dle challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t rv; + gcry_mpi_point_t rw; + gcry_mpi_point_t a = gcry_mpi_point_new (0); + gcry_mpi_point_t b = gcry_mpi_point_new (0); + gcry_mpi_t r = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); gcry_mpi_t z = gcry_mpi_new (0); + rv = (NULL == v) ? rv = gcry_mpi_point_new (0) : v; + rw = (NULL == w) ? rw = gcry_mpi_point_new (0) : w; + + /* v = x*g1 */ + gcry_mpi_ec_mul (rv, x, g1, ec_ctx); + + /* w = x*g2 */ + gcry_mpi_ec_mul (rw, x, g2, ec_ctx); + + /* a = z*g1 */ ec_keypair_create_base (a, z, g1); + + /* b = z*g2 */ gcry_mpi_ec_mul (b, z, g2, ec_ctx); /* compute challenge c */ ec_point_serialize (&challenge.g1, g1); ec_point_serialize (&challenge.g2, g2); - ec_point_serialize (&challenge.v, v); - ec_point_serialize (&challenge.w, w); + ec_point_serialize (&challenge.v, rv); + ec_point_serialize (&challenge.w, rw); ec_point_serialize (&challenge.a, a); ec_point_serialize (&challenge.b, b); brandt_hash (&challenge, sizeof (struct zkp_challenge_dl), &challhash); mpi_parse (c, (struct ec_mpi *)&challhash); gcry_mpi_mod (c, c, ec_n); + /* r = z + cx */ gcry_mpi_mulm (r, c, x, ec_n); gcry_mpi_addm (r, r, z, ec_n); + mpi_serialize (&proof->r, r); + ec_point_serialize (&proof->a, a); + ec_point_serialize (&proof->b, b); + + if (NULL == v) + gcry_mpi_point_release (rv); + if (NULL == w) + gcry_mpi_point_release (rw); + gcry_mpi_point_release (a); + gcry_mpi_point_release (b); + gcry_mpi_release (r); gcry_mpi_release (c); gcry_mpi_release (z); } /** - * smc_zkp_2dle_check \todo + * smc_zkp_2dle_check verifies a proof of knowledge of \f$x\f$ with \f$v=xg_1\f$ + * and \f$w=xg_2\f$. * - * @param v TODO - * @param w TODO - * @param g1 TODO - * @param g2 TODO - * @param a TODO - * @param b TODO - * @param r TODO - * @return TODO + * @param[in] v first input point. + * @param[in] w second input point. + * @param[in] g1 first base point. + * @param[in] g2 second base point. + * @param[in] proof pointer to the proof structure. Received from the prover. + * @return 0 if the proof is correct, something else otherwise */ int -smc_zkp_2dle_check (const gcry_mpi_point_t v, - const gcry_mpi_point_t w, - const gcry_mpi_point_t g1, - const gcry_mpi_point_t g2, - const gcry_mpi_point_t a, - const gcry_mpi_point_t b, - const gcry_mpi_t r) +smc_zkp_2dle_check (const gcry_mpi_point_t v, + const gcry_mpi_point_t w, + const gcry_mpi_point_t g1, + const gcry_mpi_point_t g2, + const struct proof_2dle *proof) { int ret; struct zkp_challenge_2dle challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t a = gcry_mpi_point_new (0); + gcry_mpi_point_t b = gcry_mpi_point_new (0); + gcry_mpi_t r = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); gcry_mpi_point_t left = gcry_mpi_point_new (0); gcry_mpi_point_t right = gcry_mpi_point_new (0); + mpi_parse (r, &proof->r); + ec_point_parse (a, &proof->a); + ec_point_parse (b, &proof->b); + /* compute challenge c */ ec_point_serialize (&challenge.g1, g1); ec_point_serialize (&challenge.g2, g2); @@ -773,16 +828,21 @@ smc_zkp_2dle_check (const gcry_mpi_point_t v, mpi_parse (c, (struct ec_mpi *)&challhash); gcry_mpi_mod (c, c, ec_n); + /* r*g1 =? a + cv */ gcry_mpi_ec_mul (left, r, g1, ec_ctx); gcry_mpi_ec_mul (right, c, v, ec_ctx); gcry_mpi_ec_add (right, a, right, ec_ctx); ret = ec_point_cmp (left, right); + /* r*g2 =? b + cw */ gcry_mpi_ec_mul (left, r, g2, ec_ctx); gcry_mpi_ec_mul (right, c, w, ec_ctx); gcry_mpi_ec_add (right, b, right, ec_ctx); ret |= ec_point_cmp (left, right); + gcry_mpi_point_release (a); + gcry_mpi_point_release (b); + gcry_mpi_release (r); gcry_mpi_release (c); gcry_mpi_point_release (left); gcry_mpi_point_release (right); @@ -792,55 +852,57 @@ smc_zkp_2dle_check (const gcry_mpi_point_t v, /** - * smc_zkp_0og \todo + * smc_zkp_0og encrypts one of two values and creates a proof that the + * ciphertext decrypts to either one of those two values without revealing which + * one was encrypted. The two values are the zero point or the base point of the + * Ed25519 curve. Encryption is done via ElGamal: \f$(\alpha,\beta)=(m+ry,rg)\f$ + * where \f$m\f$ is the value to encrypt, \f$y\f$ is the public key and \f$g\f$ + * is the base point. The nonce \f$r\f$ is generated as well and can be returned + * to the caller if he needs it (e.g. for another proof). * - * @param alpha TODO - * @param m TODO - * @param y TODO - * @param beta TODO - * @param a1 TODO - * @param a2 TODO - * @param b1 TODO - * @param b2 TODO - * @param d1 TODO - * @param d2 TODO - * @param r1 TODO - * @param r2 TODO + * @param[in] m_is_gen if true, the base point is encrypted, else the zero point + * is encrypted. + * @param[in] y public key to use for encryption. + * @param[out] r random number used for encryption. May be NULL if caller + * doesn't need it. + * @param[out] alpha first part of the ciphertext output + * @param[out] beta second part of the ciphertext output + * @param[out] proof pointer where to save the output proof structure. Must be + * shared with the verifier. */ void -smc_zkp_0og (gcry_mpi_point_t alpha, - const gcry_mpi_point_t m, +smc_zkp_0og (int m_is_gen, const gcry_mpi_point_t y, + gcry_mpi_t r, + gcry_mpi_point_t alpha, gcry_mpi_point_t beta, - gcry_mpi_point_t a1, - gcry_mpi_point_t a2, - gcry_mpi_point_t b1, - gcry_mpi_point_t b2, - gcry_mpi_t d1, - gcry_mpi_t d2, - gcry_mpi_t r1, - gcry_mpi_t r2) + struct proof_0og *proof) { struct zkp_challenge_0og challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t a1 = gcry_mpi_point_new (0); + gcry_mpi_point_t a2 = gcry_mpi_point_new (0); + gcry_mpi_point_t b1 = gcry_mpi_point_new (0); + gcry_mpi_point_t b2 = gcry_mpi_point_new (0); + gcry_mpi_t d1 = gcry_mpi_new (0); + gcry_mpi_t d2 = gcry_mpi_new (0); + gcry_mpi_t r1 = gcry_mpi_new (0); + gcry_mpi_t r2 = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); - gcry_mpi_t r = gcry_mpi_new (0); + gcry_mpi_t rr; gcry_mpi_t w = gcry_mpi_new (0); - int eq0 = !ec_point_cmp (m, ec_zero); - int eqg = !ec_point_cmp (m, ec_gen); - if (!(eq0 ^ eqg)) - eprintf ("zero knowledge proof: m is neither 0 nor g"); + rr = (NULL == r) ? gcry_mpi_new (0) : r; /* beta = r*g */ - ec_keypair_create (beta, r); - gcry_mpi_mod (r, r, ec_n); + ec_keypair_create (beta, rr); + gcry_mpi_mod (rr, rr, ec_n); /* alpha = m + r*y */ - gcry_mpi_ec_mul (alpha, r, y, ec_ctx); - gcry_mpi_ec_add (alpha, m, alpha, ec_ctx); + gcry_mpi_ec_mul (alpha, rr, y, ec_ctx); + gcry_mpi_ec_add (alpha, m_is_gen ? ec_gen : ec_zero, alpha, ec_ctx); - if (eq0) + if (!m_is_gen) { /* m == 0 */ ec_keypair_create_base (a1, d1, beta); gcry_mpi_mod (d1, d1, ec_n); @@ -900,13 +962,13 @@ smc_zkp_0og (gcry_mpi_point_t alpha, mpi_parse (c, (struct ec_mpi *)&challhash); gcry_mpi_mod (c, c, ec_n); - if (eq0) + if (!m_is_gen) { /* m == 0 */ /* d2 = c - d1 */ gcry_mpi_subm (d2, c, d1, ec_n); /* r2 = w - r*d2 */ - gcry_mpi_mulm (r2, r, d2, ec_n); + gcry_mpi_mulm (r2, rr, d2, ec_n); gcry_mpi_subm (r2, w, r2, ec_n); } else @@ -915,53 +977,75 @@ smc_zkp_0og (gcry_mpi_point_t alpha, gcry_mpi_subm (d1, c, d2, ec_n); /* r1 = w - r*d1 */ - gcry_mpi_mulm (r1, r, d1, ec_n); + gcry_mpi_mulm (r1, rr, d1, ec_n); gcry_mpi_subm (r1, w, r1, ec_n); } + ec_point_serialize (&proof->a1, a1); + ec_point_serialize (&proof->a2, a2); + ec_point_serialize (&proof->b1, b1); + ec_point_serialize (&proof->b2, b2); + mpi_serialize (&proof->d1, d1); + mpi_serialize (&proof->d2, d2); + mpi_serialize (&proof->r1, r1); + mpi_serialize (&proof->r2, r2); + + gcry_mpi_point_release (a1); + gcry_mpi_point_release (a2); + gcry_mpi_point_release (b1); + gcry_mpi_point_release (b2); + gcry_mpi_release (d1); + gcry_mpi_release (d2); + gcry_mpi_release (r1); + gcry_mpi_release (r2); gcry_mpi_release (c); - gcry_mpi_release (r); + if (NULL == r) + gcry_mpi_release (rr); gcry_mpi_release (w); } /** - * smc_zkp_0og_check \todo + * smc_zkp_0og_check verifies a proof that \f$(\alpha,\beta\f$ decrypts either + * to the base point \f$g\f$ or the zero point. * - * @param alpha TODO - * @param y TODO - * @param beta TODO - * @param a1 TODO - * @param a2 TODO - * @param b1 TODO - * @param b2 TODO - * @param d1 TODO - * @param d2 TODO - * @param r1 TODO - * @param r2 TODO - * @return TODO + * @param[in] y the public key used for encryption + * @param[in] alpha first part of the ciphertext + * @param[in] beta second part of the ciphertext + * @param[in] proof pointer to the proof structure. Received from the prover. + * @return 0 if the proof is correct, something else otherwise */ int -smc_zkp_0og_check (const gcry_mpi_point_t alpha, - const gcry_mpi_point_t y, +smc_zkp_0og_check (const gcry_mpi_point_t y, + const gcry_mpi_point_t alpha, const gcry_mpi_point_t beta, - const gcry_mpi_point_t a1, - const gcry_mpi_point_t a2, - const gcry_mpi_point_t b1, - const gcry_mpi_point_t b2, - const gcry_mpi_t d1, - const gcry_mpi_t d2, - const gcry_mpi_t r1, - const gcry_mpi_t r2) + const struct proof_0og *proof) { int ret; struct zkp_challenge_0og challenge; struct brandt_hash_code challhash; + gcry_mpi_point_t a1 = gcry_mpi_point_new (0); + gcry_mpi_point_t a2 = gcry_mpi_point_new (0); + gcry_mpi_point_t b1 = gcry_mpi_point_new (0); + gcry_mpi_point_t b2 = gcry_mpi_point_new (0); + gcry_mpi_t d1 = gcry_mpi_new (0); + gcry_mpi_t d2 = gcry_mpi_new (0); + gcry_mpi_t r1 = gcry_mpi_new (0); + gcry_mpi_t r2 = gcry_mpi_new (0); gcry_mpi_t c = gcry_mpi_new (0); gcry_mpi_t sum = gcry_mpi_new (0); gcry_mpi_point_t right = gcry_mpi_point_new (0); gcry_mpi_point_t tmp = gcry_mpi_point_new (0); + ec_point_parse (a1, &proof->a1); + ec_point_parse (a2, &proof->a2); + ec_point_parse (b1, &proof->b1); + ec_point_parse (b2, &proof->b2); + mpi_parse (d1, &proof->d1); + mpi_parse (d2, &proof->d2); + mpi_parse (r1, &proof->r1); + mpi_parse (r2, &proof->r2); + /* compute challenge c */ ec_point_serialize (&challenge.g, ec_gen); ec_point_serialize (&challenge.alpha, alpha); @@ -1003,6 +1087,14 @@ smc_zkp_0og_check (const gcry_mpi_point_t alpha, gcry_mpi_ec_add (right, right, tmp, ec_ctx); ret |= ec_point_cmp (b2, right) << 4; + gcry_mpi_point_release (a1); + gcry_mpi_point_release (a2); + gcry_mpi_point_release (b1); + gcry_mpi_point_release (b2); + gcry_mpi_release (d1); + gcry_mpi_release (d2); + gcry_mpi_release (r1); + gcry_mpi_release (r2); gcry_mpi_release (c); gcry_mpi_release (sum); gcry_mpi_point_release (right); diff --git a/crypto.h b/crypto.h index 87e4c65..a7b06d8 100644 --- a/crypto.h +++ b/crypto.h @@ -73,55 +73,45 @@ struct proof_2dle { struct ec_mpi b; }; +struct proof_0og { + struct ec_mpi a1; + struct ec_mpi a2; + struct ec_mpi b1; + struct ec_mpi b2; + struct ec_mpi d1; + struct ec_mpi d2; + struct ec_mpi r1; + struct ec_mpi r2; +}; + void smc_zkp_dl (const gcry_mpi_point_t v, - const gcry_mpi_point_t g, const gcry_mpi_t x, - const gcry_mpi_point_t a, - gcry_mpi_t r); + struct proof_dl *proof); int smc_zkp_dl_check (const gcry_mpi_point_t v, - const gcry_mpi_point_t g, - const gcry_mpi_point_t a, - const gcry_mpi_t r); + const struct proof_dl *proof); void smc_zkp_2dle (const gcry_mpi_point_t v, const gcry_mpi_point_t w, const gcry_mpi_point_t g1, const gcry_mpi_point_t g2, const gcry_mpi_t x, - gcry_mpi_point_t a, - gcry_mpi_point_t b, - gcry_mpi_t r); -int smc_zkp_2dle_check (const gcry_mpi_point_t v, - const gcry_mpi_point_t w, - const gcry_mpi_point_t g1, - const gcry_mpi_point_t g2, - const gcry_mpi_point_t a, - const gcry_mpi_point_t b, - const gcry_mpi_t r); + struct proof_2dle *proof); +int smc_zkp_2dle_check (const gcry_mpi_point_t v, + const gcry_mpi_point_t w, + const gcry_mpi_point_t g1, + const gcry_mpi_point_t g2, + const struct proof_2dle *proof); -void smc_zkp_0og (gcry_mpi_point_t alpha, - const gcry_mpi_point_t m, +void smc_zkp_0og (int m_is_gen, const gcry_mpi_point_t y, + gcry_mpi_t r, + gcry_mpi_point_t alpha, gcry_mpi_point_t beta, - gcry_mpi_point_t a1, - gcry_mpi_point_t a2, - gcry_mpi_point_t b1, - gcry_mpi_point_t b2, - gcry_mpi_t d1, - gcry_mpi_t d2, - gcry_mpi_t r1, - gcry_mpi_t r2); -int smc_zkp_0og_check (const gcry_mpi_point_t alpha, - const gcry_mpi_point_t y, + struct proof_0og *proof); +int smc_zkp_0og_check (const gcry_mpi_point_t y, + const gcry_mpi_point_t alpha, const gcry_mpi_point_t beta, - const gcry_mpi_point_t a1, - const gcry_mpi_point_t a2, - const gcry_mpi_point_t b1, - const gcry_mpi_point_t b2, - const gcry_mpi_t d1, - const gcry_mpi_t d2, - const gcry_mpi_t r1, - const gcry_mpi_t r2); + const struct proof_0og *proof); /* --- Protocol implementation --- */ diff --git a/test_crypto.c b/test_crypto.c index 93f1cb4..f8abe68 100644 --- a/test_crypto.c +++ b/test_crypto.c @@ -88,6 +88,10 @@ test_serialization () check (!ec_point_cmp (oldp, newp), "serialization changed point"); check (!gcry_mpi_cmp (oldi, newi), "serialization changed mpi"); + mpi_serialize (&seri, GCRYMPI_CONST_ONE); + mpi_parse (newi, &seri); + check (!gcry_mpi_cmp (GCRYMPI_CONST_ONE, newi), "serializing mpi 1 fail"); + gcry_mpi_point_release (oldp); gcry_mpi_point_release (newp); gcry_mpi_release (oldi); @@ -98,33 +102,18 @@ test_serialization () int test_smc_zkp_dl () { - gcry_mpi_t r = gcry_mpi_new (0); + struct proof_dl proof; gcry_mpi_t x = gcry_mpi_new (0); - gcry_mpi_point_t a = gcry_mpi_point_new (0); - gcry_mpi_point_t g = gcry_mpi_point_new (0); gcry_mpi_point_t v = gcry_mpi_point_new (0); - ec_keypair_create (g, r); + /* v = xg */ + ec_keypair_create (v, x); - if (0 == tests_run) - { - /* \todo: there has to be a better way to copy a point */ - gcry_mpi_ec_mul (g, GCRYMPI_CONST_ONE, ec_gen, ec_ctx); - } - - ec_keypair_create_base (v, x, g); - - smc_zkp_dl (v, g, x, a, r); - check (!smc_zkp_dl_check (v, g, a, r), "zkp dl wrong"); - - check (gcry_mpi_ec_curve_point (a, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (g, ec_ctx), "not on curve"); + smc_zkp_dl (v, x, &proof); check (gcry_mpi_ec_curve_point (v, ec_ctx), "not on curve"); + check (!smc_zkp_dl_check (v, &proof), "zkp dl wrong"); - gcry_mpi_release (r); gcry_mpi_release (x); - gcry_mpi_point_release (a); - gcry_mpi_point_release (g); gcry_mpi_point_release (v); } @@ -132,42 +121,24 @@ test_smc_zkp_dl () int test_smc_zkp_2dle () { - gcry_mpi_t r = gcry_mpi_new (0); - gcry_mpi_t x = gcry_mpi_new (0); - gcry_mpi_point_t a = gcry_mpi_point_new (0); - gcry_mpi_point_t b = gcry_mpi_point_new (0); - gcry_mpi_point_t g1 = gcry_mpi_point_new (0); - gcry_mpi_point_t g2 = gcry_mpi_point_new (0); - gcry_mpi_point_t v = gcry_mpi_point_new (0); - gcry_mpi_point_t w = gcry_mpi_point_new (0); + struct proof_2dle proof; + gcry_mpi_t x = gcry_mpi_new (0); + gcry_mpi_point_t g1 = gcry_mpi_point_new (0); + gcry_mpi_point_t g2 = gcry_mpi_point_new (0); + gcry_mpi_point_t v = gcry_mpi_point_new (0); + gcry_mpi_point_t w = gcry_mpi_point_new (0); - ec_keypair_create (g1, r); - ec_keypair_create (g2, r); + ec_keypair_create (g1, x); + ec_keypair_create (g2, x); - if (0 == tests_run) - { - /* \todo: there has to be a better way to copy a point */ - gcry_mpi_ec_mul (g1, GCRYMPI_CONST_ONE, ec_gen, ec_ctx); - gcry_mpi_ec_mul (g2, GCRYMPI_CONST_ONE, ec_gen, ec_ctx); - } - - ec_keypair_create_base (v, x, g1); - gcry_mpi_ec_mul (w, x, g2, ec_ctx); - - smc_zkp_2dle (v, w, g1, g2, x, a, b, r); - check (!smc_zkp_2dle_check (v, w, g1, g2, a, b, r), "zkp 2dle wrong"); - - check (gcry_mpi_ec_curve_point (a, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (b, ec_ctx), "not on curve"); + smc_zkp_2dle (v, w, g1, g2, x, &proof); check (gcry_mpi_ec_curve_point (g1, ec_ctx), "not on curve"); check (gcry_mpi_ec_curve_point (g2, ec_ctx), "not on curve"); check (gcry_mpi_ec_curve_point (v, ec_ctx), "not on curve"); check (gcry_mpi_ec_curve_point (w, ec_ctx), "not on curve"); + check (!smc_zkp_2dle_check (v, w, g1, g2, &proof), "zkp 2dle wrong"); - gcry_mpi_release (r); gcry_mpi_release (x); - gcry_mpi_point_release (a); - gcry_mpi_point_release (b); gcry_mpi_point_release (g1); gcry_mpi_point_release (g2); gcry_mpi_point_release (v); @@ -178,51 +149,30 @@ test_smc_zkp_2dle () int test_smc_zkp_0og () { - gcry_mpi_t d1 = gcry_mpi_new (0); - gcry_mpi_t d2 = gcry_mpi_new (0); - gcry_mpi_t r1 = gcry_mpi_new (0); - gcry_mpi_t r2 = gcry_mpi_new (0); + struct proof_0og proof; gcry_mpi_point_t y = gcry_mpi_point_new (0); gcry_mpi_point_t alpha = gcry_mpi_point_new (0); gcry_mpi_point_t beta = gcry_mpi_point_new (0); - gcry_mpi_point_t a1 = gcry_mpi_point_new (0); - gcry_mpi_point_t a2 = gcry_mpi_point_new (0); - gcry_mpi_point_t b1 = gcry_mpi_point_new (0); - gcry_mpi_point_t b2 = gcry_mpi_point_new (0); - ec_keypair_create (y, r1); + /* get random public key point. We don't need the secret key to check the + * proof here */ + ec_keypair_create (y, NULL); - smc_zkp_0og (alpha, (tests_run % 2 ? ec_zero : ec_gen), y, beta, a1, a2, b1, - b2, d1, d2, r1, r2); - check (!smc_zkp_0og_check (alpha, y, beta, a1, a2, b1, b2, d1, d2, r1, - r2), "zkp 0og is wrong"); - - check (gcry_mpi_ec_curve_point (y, ec_ctx), "not on curve"); + smc_zkp_0og (tests_run % 2, y, NULL, alpha, beta, &proof); check (gcry_mpi_ec_curve_point (alpha, ec_ctx), "not on curve"); check (gcry_mpi_ec_curve_point (beta, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (a1, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (a2, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (b1, ec_ctx), "not on curve"); - check (gcry_mpi_ec_curve_point (b2, ec_ctx), "not on curve"); + check (!smc_zkp_0og_check (y, alpha, beta, &proof), "zkp 0og is wrong"); - gcry_mpi_release (d1); - gcry_mpi_release (d2); - gcry_mpi_release (r1); - gcry_mpi_release (r2); gcry_mpi_point_release (y); gcry_mpi_point_release (alpha); gcry_mpi_point_release (beta); - gcry_mpi_point_release (a1); - gcry_mpi_point_release (a2); - gcry_mpi_point_release (b1); - gcry_mpi_point_release (b2); } int main (int argc, char *argv[]) { - int repeat = 8; + int repeat = 16; BRANDT_init ();