- test for external iterator
[oweals/gnunet.git] / src / util / crypto_ecc.c
index 1569c6a232595919bd388c0e1ccca3ea6c182d8b..a397724f454fe0d66e6120bb154e1425484ce29e 100644 (file)
@@ -251,6 +251,7 @@ point_to_public_key (gcry_mpi_point_t q,
     LOG_GCRY (GNUNET_ERROR_TYPE_ERROR, "get_affine failed", 0);
     return;
   }
+
   mpi_print (pub->q_x, sizeof (pub->q_x), q_x);
   mpi_print (pub->q_y, sizeof (pub->q_y), q_y);
   gcry_mpi_release (q_x);
@@ -831,7 +832,7 @@ GNUNET_CRYPTO_ecc_verify (uint32_t purpose,
   gcry_sexp_release (sig_sexpr);
   if (0 != rc)
   {
-    LOG (GNUNET_ERROR_TYPE_WARNING,
+    LOG (GNUNET_ERROR_TYPE_INFO,
          _("ECC signature verification failed at %s:%d: %s\n"), __FILE__,
          __LINE__, gcry_strerror (rc));
     return GNUNET_SYSERR;
@@ -925,11 +926,14 @@ GNUNET_CRYPTO_ecc_ecdh (const struct GNUNET_CRYPTO_EccPrivateKey *priv,
  *
  * @param pub public key for deriviation
  * @param label label for deriviation
+ * @param context additional context to use for HKDF of 'h';
+ *        typically the name of the subsystem/application
  * @return h value
  */ 
 static gcry_mpi_t 
 derive_h (const struct GNUNET_CRYPTO_EccPublicKey *pub,
-         const char *label)
+         const char *label,
+         const char *context)
 {
   gcry_mpi_t h;
   struct GNUNET_HashCode hc;
@@ -937,7 +941,8 @@ derive_h (const struct GNUNET_CRYPTO_EccPublicKey *pub,
   GNUNET_CRYPTO_kdf (&hc, sizeof (hc),
                     "key-derivation", strlen ("key-derivation"),
                     pub, sizeof (*pub),
-                    label, sizeof (label),
+                    label, strlen (label),
+                    context, strlen (context),
                     NULL, 0);
   mpi_scan (&h, (unsigned char *) &hc, sizeof (hc));
   return h;
@@ -952,11 +957,14 @@ derive_h (const struct GNUNET_CRYPTO_EccPublicKey *pub,
  *
  * @param priv original private key
  * @param label label to use for key deriviation
+ * @param context additional context to use for HKDF of 'h';
+ *        typically the name of the subsystem/application
  * @return derived private key
  */
 struct GNUNET_CRYPTO_EccPrivateKey *
 GNUNET_CRYPTO_ecc_key_derive (const struct GNUNET_CRYPTO_EccPrivateKey *priv,
-                             const char *label)
+                             const char *label,
+                             const char *context)
 {
   struct GNUNET_CRYPTO_EccPublicKey pub;
   struct GNUNET_CRYPTO_EccPrivateKey *ret;
@@ -967,14 +975,16 @@ GNUNET_CRYPTO_ecc_key_derive (const struct GNUNET_CRYPTO_EccPrivateKey *priv,
   gcry_ctx_t ctx;
 
   GNUNET_assert (0 == gcry_mpi_ec_new (&ctx, NULL, CURVE));
-  n = gcry_mpi_ec_get_mpi ("n", ctx, 0 /* no copy */);
+  n = gcry_mpi_ec_get_mpi ("n", ctx, 1);
   GNUNET_CRYPTO_ecc_key_get_public (priv, &pub);
-  h = derive_h (&pub, label);
+  h = derive_h (&pub, label, context);
   mpi_scan (&x, priv->d, sizeof (priv->d));
   d = gcry_mpi_new (256);
   gcry_mpi_mulm (d, h, x, n);
   gcry_mpi_release (h);
   gcry_mpi_release (x);
+  gcry_mpi_release (n);
+  gcry_ctx_release (ctx);
   ret = GNUNET_new (struct GNUNET_CRYPTO_EccPrivateKey);
   mpi_print (ret->d, sizeof (ret->d), d);
   gcry_mpi_release (d);
@@ -988,11 +998,14 @@ GNUNET_CRYPTO_ecc_key_derive (const struct GNUNET_CRYPTO_EccPrivateKey *priv,
  *
  * @param pub original public key
  * @param label label to use for key deriviation
+ * @param context additional context to use for HKDF of 'h';
+ *        typically the name of the subsystem/application
  * @param result where to write the derived public key
  */
 void
 GNUNET_CRYPTO_ecc_public_key_derive (const struct GNUNET_CRYPTO_EccPublicKey *pub,
                                     const char *label,
+                                    const char *context,
                                     struct GNUNET_CRYPTO_EccPublicKey *result)
 {
   gcry_ctx_t ctx;
@@ -1016,8 +1029,8 @@ GNUNET_CRYPTO_ecc_public_key_derive (const struct GNUNET_CRYPTO_EccPublicKey *pu
   gcry_mpi_release (q_y);
 
   /* calulcate h_mod_n = h % n */
-  h = derive_h (pub, label);
-  n = gcry_mpi_ec_get_mpi ("n", ctx, 0 /* no copy */);
+  h = derive_h (pub, label, context);
+  n = gcry_mpi_ec_get_mpi ("n", ctx, 1);
   h_mod_n = gcry_mpi_new (256);
   gcry_mpi_mod (h_mod_n, h, n);
   /* calculate v = h_mod_n * q */
@@ -1025,6 +1038,7 @@ GNUNET_CRYPTO_ecc_public_key_derive (const struct GNUNET_CRYPTO_EccPublicKey *pu
   gcry_mpi_ec_mul (v, h_mod_n, q, ctx);
   gcry_mpi_release (h_mod_n);
   gcry_mpi_release (h);
+  gcry_mpi_release (n);
   gcry_mpi_point_release (q);
   /* convert point 'v' to public key that we return */
   point_to_public_key (v, ctx, result);