summaryrefslogtreecommitdiff
path: root/src/test/test_crypto.c
diff options
context:
space:
mode:
authorYawning Angel <yawning@schwanenlied.me>2015-07-06 10:11:10 +0000
committerYawning Angel <yawning@schwanenlied.me>2015-07-06 10:11:10 +0000
commit840e68d9171d62a1fdaf0395e248daad2cbe014f (patch)
tree3a8fba7c3e90ddb885ad817e68e8bb0afe003245 /src/test/test_crypto.c
parentf079c27761a676f7c4200f7275112edd0b5e1270 (diff)
downloadtor-840e68d9171d62a1fdaf0395e248daad2cbe014f.tar.gz
tor-840e68d9171d62a1fdaf0395e248daad2cbe014f.zip
Integrate and enable ed25519-donna.
The runtime sanity checking is slightly different from the optimized basepoint stuff in that it uses a given implementation's self tests if available, and checks if signing/verification works with a test vector from the IETF EdDSA draft. The unit tests include a new testcase that will fuzz donna against ref0, including the blinding and curve25519 key conversion routines. If this is something that should be done at runtime (No?), the code can be stolen from there. Note: Integrating batch verification is not done yet.
Diffstat (limited to 'src/test/test_crypto.c')
-rw-r--r--src/test/test_crypto.c72
1 files changed, 72 insertions, 0 deletions
diff --git a/src/test/test_crypto.c b/src/test/test_crypto.c
index bc88248db0..2bc477083c 100644
--- a/src/test/test_crypto.c
+++ b/src/test/test_crypto.c
@@ -1637,6 +1637,77 @@ test_crypto_ed25519_testvectors(void *arg)
}
static void
+test_crypto_ed25519_fuzz_donna(void *arg)
+{
+ const unsigned iters = 1024;
+ uint8_t msg[1024];
+ unsigned i;
+ (void)arg;
+
+ tt_assert(sizeof(msg) == iters);
+ crypto_rand((char*) msg, sizeof(msg));
+
+ /* Fuzz Ed25519-donna vs ref10, alternating the implementation used to
+ * generate keys/sign per iteration.
+ */
+ for (i = 0; i < iters; ++i) {
+ const int use_donna = i & 1;
+ uint8_t blinding[32];
+ curve25519_keypair_t ckp;
+ ed25519_keypair_t kp, kp_blind, kp_curve25519;
+ ed25519_public_key_t pk, pk_blind, pk_curve25519;
+ ed25519_signature_t sig, sig_blind;
+ int bit = 0;
+
+ crypto_rand((char*) blinding, sizeof(blinding));
+
+ /* Impl. A:
+ * 1. Generate a keypair.
+ * 2. Blinded the keypair.
+ * 3. Sign a message (unblinded).
+ * 4. Sign a message (blinded).
+ * 5. Generate a curve25519 keypair, and convert it to Ed25519.
+ */
+ ed25519_set_impl_params(use_donna);
+ tt_int_op(0, OP_EQ, ed25519_keypair_generate(&kp, i&1));
+ tt_int_op(0, OP_EQ, ed25519_keypair_blind(&kp_blind, &kp, blinding));
+ tt_int_op(0, OP_EQ, ed25519_sign(&sig, msg, i, &kp));
+ tt_int_op(0, OP_EQ, ed25519_sign(&sig_blind, msg, i, &kp_blind));
+
+ tt_int_op(0, OP_EQ, curve25519_keypair_generate(&ckp, i&1));
+ tt_int_op(0, OP_EQ, ed25519_keypair_from_curve25519_keypair(
+ &kp_curve25519, &bit, &ckp));
+
+ /* Impl. B:
+ * 1. Validate the public key by rederiving it.
+ * 2. Validate the blinded public key by rederiving it.
+ * 3. Validate the unblinded signature (and test a invalid signature).
+ * 4. Validate the blinded signature.
+ * 5. Validate the public key (from Curve25519) by rederiving it.
+ */
+ ed25519_set_impl_params(!use_donna);
+ tt_int_op(0, OP_EQ, ed25519_public_key_generate(&pk, &kp.seckey));
+ tt_mem_op(pk.pubkey, OP_EQ, kp.pubkey.pubkey, 32);
+
+ tt_int_op(0, OP_EQ, ed25519_public_blind(&pk_blind, &kp.pubkey, blinding));
+ tt_mem_op(pk_blind.pubkey, OP_EQ, kp_blind.pubkey.pubkey, 32);
+
+ tt_int_op(0, OP_EQ, ed25519_checksig(&sig, msg, i, &pk));
+ sig.sig[0] ^= 15;
+ tt_int_op(-1, OP_EQ, ed25519_checksig(&sig, msg, sizeof(msg), &pk));
+
+ tt_int_op(0, OP_EQ, ed25519_checksig(&sig_blind, msg, i, &pk_blind));
+
+ tt_int_op(0, OP_EQ, ed25519_public_key_from_curve25519_public_key(
+ &pk_curve25519, &ckp.pubkey, bit));
+ tt_mem_op(pk_curve25519.pubkey, OP_EQ, kp_curve25519.pubkey.pubkey, 32);
+ }
+
+ done:
+ ;
+}
+
+static void
test_crypto_siphash(void *arg)
{
/* From the reference implementation, taking
@@ -1767,6 +1838,7 @@ struct testcase_t crypto_tests[] = {
{ "ed25519_convert", test_crypto_ed25519_convert, 0, NULL, NULL },
{ "ed25519_blinding", test_crypto_ed25519_blinding, 0, NULL, NULL },
{ "ed25519_testvectors", test_crypto_ed25519_testvectors, 0, NULL, NULL },
+ { "ed25519_fuzz_donna", test_crypto_ed25519_fuzz_donna, TT_FORK, NULL, NULL },
{ "siphash", test_crypto_siphash, 0, NULL, NULL },
END_OF_TESTCASES
};