SET service: accurate results for symmetric mode
[oweals/gnunet.git] / src / include / gnunet_crypto_lib.h
index ae899c1dbb7ffeaa671631afae9911888d5c7eb1..33ad1af2be27230423a3f4a3871a8de53d84bd48 100644 (file)
@@ -1,6 +1,6 @@
 /*
      This file is part of GNUnet.
-     (C) 2001-2013 Christian Grothoff (and other contributing authors)
+     Copyright (C) 2001-2013 Christian Grothoff (and other contributing authors)
 
      GNUnet is free software; you can redistribute it and/or modify
      it under the terms of the GNU General Public License as published
@@ -14,8 +14,8 @@
 
      You should have received a copy of the GNU General Public License
      along with GNUnet; see the file COPYING.  If not, write to the
-     Free Software Foundation, Inc., 59 Temple Place - Suite 330,
-     Boston, MA 02111-1307, USA.
+     Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+     Boston, MA 02110-1301, USA.
 */
 
 /**
@@ -54,7 +54,6 @@ struct GNUNET_HashCode;
 struct GNUNET_PeerIdentity;
 
 #include "gnunet_common.h"
-#include "gnunet_scheduler_lib.h"
 #include <gcrypt.h>
 
 
@@ -405,7 +404,9 @@ GNUNET_CRYPTO_seed_weak_random (int32_t seed);
  * @return updated crc sum (must be subjected to #GNUNET_CRYPTO_crc16_finish to get actual crc16)
  */
 uint32_t
-GNUNET_CRYPTO_crc16_step (uint32_t sum, const void *buf, size_t len);
+GNUNET_CRYPTO_crc16_step (uint32_t sum,
+                          const void *buf,
+                          size_t len);
 
 
 /**
@@ -427,7 +428,8 @@ GNUNET_CRYPTO_crc16_finish (uint32_t sum);
  * @return crc16 value
  */
 uint16_t
-GNUNET_CRYPTO_crc16_n (const void *buf, size_t len);
+GNUNET_CRYPTO_crc16_n (const void *buf,
+                       size_t len);
 
 
 /**
@@ -440,7 +442,8 @@ GNUNET_CRYPTO_crc16_n (const void *buf, size_t len);
  * @return the resulting CRC32 checksum
  */
 int32_t
-GNUNET_CRYPTO_crc32_n (const void *buf, size_t len);
+GNUNET_CRYPTO_crc32_n (const void *buf,
+                       size_t len);
 
 
 /**
@@ -452,7 +455,9 @@ GNUNET_CRYPTO_crc32_n (const void *buf, size_t len);
  * @param length buffer length
  */
 void
-GNUNET_CRYPTO_random_block (enum GNUNET_CRYPTO_Quality mode, void *buffer, size_t length);
+GNUNET_CRYPTO_random_block (enum GNUNET_CRYPTO_Quality mode,
+                            void *buffer,
+                            size_t length);
 
 /**
  * @ingroup crypto
@@ -463,7 +468,8 @@ GNUNET_CRYPTO_random_block (enum GNUNET_CRYPTO_Quality mode, void *buffer, size_
  * @return a random value in the interval [0,@a i) (exclusive).
  */
 uint32_t
-GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, uint32_t i);
+GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode,
+                          uint32_t i);
 
 
 /**
@@ -475,7 +481,8 @@ GNUNET_CRYPTO_random_u32 (enum GNUNET_CRYPTO_Quality mode, uint32_t i);
  * @return random 64-bit number
  */
 uint64_t
-GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max);
+GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode,
+                          uint64_t max);
 
 
 /**
@@ -488,7 +495,8 @@ GNUNET_CRYPTO_random_u64 (enum GNUNET_CRYPTO_Quality mode, uint64_t max);
  * @return the permutation array (allocated from heap)
  */
 unsigned int *
-GNUNET_CRYPTO_random_permute (enum GNUNET_CRYPTO_Quality mode, unsigned int n);
+GNUNET_CRYPTO_random_permute (enum GNUNET_CRYPTO_Quality mode,
+                              unsigned int n);
 
 
 /**
@@ -513,7 +521,8 @@ GNUNET_CRYPTO_symmetric_create_session_key (struct GNUNET_CRYPTO_SymmetricSessio
  * @return the size of the encrypted block, -1 for errors
  */
 ssize_t
-GNUNET_CRYPTO_symmetric_encrypt (const void *block, size_t size,
+GNUNET_CRYPTO_symmetric_encrypt (const void *block,
+                                 size_t size,
                                  const struct GNUNET_CRYPTO_SymmetricSessionKey *sessionkey,
                                  const struct GNUNET_CRYPTO_SymmetricInitializationVector *iv,
                                  void *result);
@@ -531,7 +540,8 @@ GNUNET_CRYPTO_symmetric_encrypt (const void *block, size_t size,
  * @return -1 on failure, size of decrypted block on success
  */
 ssize_t
-GNUNET_CRYPTO_symmetric_decrypt (const void *block, size_t size,
+GNUNET_CRYPTO_symmetric_decrypt (const void *block,
+                                 size_t size,
                                  const struct GNUNET_CRYPTO_SymmetricSessionKey *sessionkey,
                                  const struct GNUNET_CRYPTO_SymmetricInitializationVector *iv,
                                  void *result);
@@ -577,7 +587,7 @@ GNUNET_CRYPTO_symmetric_derive_iv_v (struct GNUNET_CRYPTO_SymmetricInitializatio
  *  safely cast to char*, a '\\0' termination is set).
  */
 void
-GNUNET_CRYPTO_hash_to_enc (const struct GNUNET_HashCode * block,
+GNUNET_CRYPTO_hash_to_enc (const struct GNUNET_HashCode *block,
                            struct GNUNET_CRYPTO_HashAsciiEncoded *result);
 
 
@@ -591,7 +601,8 @@ GNUNET_CRYPTO_hash_to_enc (const struct GNUNET_HashCode * block,
  * @return #GNUNET_OK on success, #GNUNET_SYSERR if result has the wrong encoding
  */
 int
-GNUNET_CRYPTO_hash_from_string2 (const char *enc, size_t enclen,
+GNUNET_CRYPTO_hash_from_string2 (const char *enc,
+                                 size_t enclen,
                                  struct GNUNET_HashCode *result);
 
 
@@ -662,8 +673,8 @@ GNUNET_CRYPTO_hash_context_start (void);
  */
 void
 GNUNET_CRYPTO_hash_context_read (struct GNUNET_HashContext *hc,
-                         const void *buf,
-                         size_t size);
+                                 const void *buf,
+                                 size_t size);
 
 
 /**
@@ -674,7 +685,7 @@ GNUNET_CRYPTO_hash_context_read (struct GNUNET_HashContext *hc,
  */
 void
 GNUNET_CRYPTO_hash_context_finish (struct GNUNET_HashContext *hc,
-                           struct GNUNET_HashCode *r_hash);
+                                   struct GNUNET_HashCode *r_hash);
 
 
 /**
@@ -697,8 +708,9 @@ GNUNET_CRYPTO_hash_context_abort (struct GNUNET_HashContext *hc);
  */
 void
 GNUNET_CRYPTO_hmac (const struct GNUNET_CRYPTO_AuthKey *key,
-                    const void *plaintext, size_t plaintext_len,
-                    struct GNUNET_HashCode * hmac);
+                    const void *plaintext,
+                    size_t plaintext_len,
+                    struct GNUNET_HashCode *hmac);
 
 
 /**
@@ -708,8 +720,9 @@ GNUNET_CRYPTO_hmac (const struct GNUNET_CRYPTO_AuthKey *key,
  * @param cls closure
  * @param res resulting hash, NULL on error
  */
-typedef void (*GNUNET_CRYPTO_HashCompletedCallback) (void *cls,
-                                                     const struct GNUNET_HashCode *res);
+typedef void
+(*GNUNET_CRYPTO_HashCompletedCallback) (void *cls,
+                                        const struct GNUNET_HashCode *res);
 
 
 /**
@@ -731,7 +744,8 @@ struct GNUNET_CRYPTO_FileHashContext;
  */
 struct GNUNET_CRYPTO_FileHashContext *
 GNUNET_CRYPTO_hash_file (enum GNUNET_SCHEDULER_Priority priority,
-                         const char *filename, size_t blocksize,
+                         const char *filename,
+                         size_t blocksize,
                          GNUNET_CRYPTO_HashCompletedCallback callback,
                          void *callback_cls);
 
@@ -901,7 +915,8 @@ GNUNET_CRYPTO_hmac_derive_key_v (struct GNUNET_CRYPTO_AuthKey *key,
 void
 GNUNET_CRYPTO_hmac_derive_key (struct GNUNET_CRYPTO_AuthKey *key,
                                const struct GNUNET_CRYPTO_SymmetricSessionKey *rkey,
-                               const void *salt, size_t salt_len, ...);
+                               const void *salt, size_t salt_len,
+                               ...);
 
 
 /**
@@ -919,9 +934,15 @@ GNUNET_CRYPTO_hmac_derive_key (struct GNUNET_CRYPTO_AuthKey *key,
  * @return #GNUNET_YES on success
  */
 int
-GNUNET_CRYPTO_hkdf (void *result, size_t out_len, int xtr_algo, int prf_algo,
-                    const void *xts, size_t xts_len, const void *skm,
-                    size_t skm_len, ...);
+GNUNET_CRYPTO_hkdf (void *result,
+                    size_t out_len,
+                    int xtr_algo,
+                    int prf_algo,
+                    const void *xts,
+                    size_t xts_len,
+                    const void *skm,
+                    size_t skm_len,
+                    ...);
 
 
 /**
@@ -939,9 +960,15 @@ GNUNET_CRYPTO_hkdf (void *result, size_t out_len, int xtr_algo, int prf_algo,
  * @return #GNUNET_YES on success
  */
 int
-GNUNET_CRYPTO_hkdf_v (void *result, size_t out_len, int xtr_algo, int prf_algo,
-                      const void *xts, size_t xts_len, const void *skm,
-                      size_t skm_len, va_list argp);
+GNUNET_CRYPTO_hkdf_v (void *result,
+                      size_t out_len,
+                      int xtr_algo,
+                      int prf_algo,
+                      const void *xts,
+                      size_t xts_len,
+                      const void *skm,
+                      size_t skm_len,
+                      va_list argp);
 
 
 /**
@@ -956,8 +983,12 @@ GNUNET_CRYPTO_hkdf_v (void *result, size_t out_len, int xtr_algo, int prf_algo,
  * @return #GNUNET_YES on success
  */
 int
-GNUNET_CRYPTO_kdf_v (void *result, size_t out_len, const void *xts,
-                     size_t xts_len, const void *skm, size_t skm_len,
+GNUNET_CRYPTO_kdf_v (void *result,
+                     size_t out_len,
+                     const void *xts,
+                     size_t xts_len,
+                     const void *skm,
+                     size_t skm_len,
                      va_list argp);
 
 
@@ -974,8 +1005,13 @@ GNUNET_CRYPTO_kdf_v (void *result, size_t out_len, const void *xts,
  * @return #GNUNET_YES on success
  */
 int
-GNUNET_CRYPTO_kdf (void *result, size_t out_len, const void *xts,
-                   size_t xts_len, const void *skm, size_t skm_len, ...);
+GNUNET_CRYPTO_kdf (void *result,
+                   size_t out_len,
+                   const void *xts,
+                   size_t xts_len,
+                   const void *skm,
+                   size_t skm_len,
+                   ...);
 
 
 /**
@@ -1001,6 +1037,7 @@ GNUNET_CRYPTO_eddsa_key_get_public (const struct GNUNET_CRYPTO_EddsaPrivateKey *
                                     struct GNUNET_CRYPTO_EddsaPublicKey *pub);
 
 
+
 /**
  * @ingroup crypto
  * Extract the public key for the given private key.
@@ -1047,6 +1084,20 @@ GNUNET_CRYPTO_ecdsa_public_key_from_string (const char *enc,
                                             struct GNUNET_CRYPTO_EcdsaPublicKey *pub);
 
 
+/**
+ * Convert a string representing a private key to a private key.
+ *
+ * @param enc encoded public key
+ * @param enclen number of bytes in @a enc (without 0-terminator)
+ * @param priv where to store the private key
+ * @return #GNUNET_OK on success
+ */
+int
+GNUNET_CRYPTO_eddsa_private_key_from_string (const char *enc,
+                                             size_t enclen,
+                                             struct GNUNET_CRYPTO_EddsaPrivateKey *pub);
+
+
 /**
  * Convert a string representing a public key to a public key.
  *
@@ -1098,6 +1149,10 @@ GNUNET_CRYPTO_ecdsa_key_create_from_file (const char *filename);
 struct GNUNET_CRYPTO_EddsaPrivateKey *
 GNUNET_CRYPTO_eddsa_key_create_from_file (const char *filename);
 
+
+/**
+ * Forward declaration to simplify #include-structure.
+ */
 struct GNUNET_CONFIGURATION_Handle;
 
 
@@ -1163,6 +1218,7 @@ GNUNET_CRYPTO_eddsa_key_clear (struct GNUNET_CRYPTO_EddsaPrivateKey *pk);
 void
 GNUNET_CRYPTO_ecdsa_key_clear (struct GNUNET_CRYPTO_EcdsaPrivateKey *pk);
 
+
 /**
  * @ingroup crypto
  * Clear memory that was used to store a private key.
@@ -1224,6 +1280,194 @@ GNUNET_CRYPTO_cmp_peer_identity (const struct GNUNET_PeerIdentity *first,
                                  const struct GNUNET_PeerIdentity *second);
 
 
+/**
+ * Internal structure used to cache pre-calculated values for DLOG calculation.
+ */
+struct GNUNET_CRYPTO_EccDlogContext;
+
+
+/**
+ * Point on a curve (always for Curve25519) encoded in a format suitable
+ * for network transmission (ECDH), see http://cr.yp.to/ecdh.html.
+ */
+struct GNUNET_CRYPTO_EccPoint
+{
+  /**
+   * Q consists of an x- and a y-value, each mod p (256 bits), given
+   * here in affine coordinates and Ed25519 standard compact format.
+   */
+  unsigned char q_y[256 / 8];
+};
+
+
+/**
+ * Do pre-calculation for ECC discrete logarithm for small factors.
+ *
+ * @param max maximum value the factor can be
+ * @param mem memory to use (should be smaller than @a max), must not be zero.
+ * @return @a max if dlog failed, otherwise the factor
+ */
+struct GNUNET_CRYPTO_EccDlogContext *
+GNUNET_CRYPTO_ecc_dlog_prepare (unsigned int max,
+                               unsigned int mem);
+
+
+/**
+ * Calculate ECC discrete logarithm for small factors.
+ * Opposite of #GNUNET_CRYPTO_ecc_dexp().
+ *
+ * @param dlc precalculated values, determine range of factors
+ * @param input point on the curve to factor
+ * @return `dlc->max` if dlog failed, otherwise the factor
+ */
+int
+GNUNET_CRYPTO_ecc_dlog (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                       gcry_mpi_point_t input);
+
+
+/**
+ * Multiply the generator g of the elliptic curve by @a val
+ * to obtain the point on the curve representing @a val.
+ * Afterwards, point addition will correspond to integer
+ * addition.  #GNUNET_CRYPTO_ecc_dlog() can be used to
+ * convert a point back to an integer (as long as the
+ * integer is smaller than the MAX of the @a edc context).
+ *
+ * @param edc calculation context for ECC operations
+ * @param val value to encode into a point
+ * @return representation of the value as an ECC point,
+ *         must be freed using #GNUNET_CRYPTO_ecc_free()
+ */
+gcry_mpi_point_t
+GNUNET_CRYPTO_ecc_dexp (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                       int val);
+
+
+/**
+ * Multiply the generator g of the elliptic curve by @a val
+ * to obtain the point on the curve representing @a val.
+ *
+ * @param edc calculation context for ECC operations
+ * @param val (positive) value to encode into a point
+ * @return representation of the value as an ECC point,
+ *         must be freed using #GNUNET_CRYPTO_ecc_free()
+ */
+gcry_mpi_point_t
+GNUNET_CRYPTO_ecc_dexp_mpi (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                           gcry_mpi_t val);
+
+
+/**
+ * Multiply the point @a p on the elliptic curve by @a val.
+ *
+ * @param edc calculation context for ECC operations
+ * @param p point to multiply
+ * @param val (positive) value to encode into a point
+ * @return representation of the value as an ECC point,
+ *         must be freed using #GNUNET_CRYPTO_ecc_free()
+ */
+gcry_mpi_point_t
+GNUNET_CRYPTO_ecc_pmul_mpi (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                            gcry_mpi_point_t p,
+                           gcry_mpi_t val);
+
+
+/**
+ * Convert point value to binary representation.
+ *
+ * @param edc calculation context for ECC operations
+ * @param point computational point representation
+ * @param[out] bin binary point representation
+ */
+void
+GNUNET_CRYPTO_ecc_point_to_bin (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                                gcry_mpi_point_t point,
+                                struct GNUNET_CRYPTO_EccPoint *bin);
+
+
+/**
+ * Convert binary representation of a point to computational representation.
+ *
+ * @param edc calculation context for ECC operations
+ * @param bin binary point representation
+ * @return computational representation
+ */
+gcry_mpi_point_t
+GNUNET_CRYPTO_ecc_bin_to_point (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                                const struct GNUNET_CRYPTO_EccPoint *bin);
+
+
+/**
+ * Add two points on the elliptic curve.
+ *
+ * @param edc calculation context for ECC operations
+ * @param a some value
+ * @param b some value
+ * @return @a a + @a b, must be freed using #GNUNET_CRYPTO_ecc_free()
+ */
+gcry_mpi_point_t
+GNUNET_CRYPTO_ecc_add (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                      gcry_mpi_point_t a,
+                      gcry_mpi_point_t b);
+
+
+/**
+ * Obtain a random point on the curve and its
+ * additive inverse. Both returned values
+ * must be freed using #GNUNET_CRYPTO_ecc_free().
+ *
+ * @param edc calculation context for ECC operations
+ * @param[out] r set to a random point on the curve
+ * @param[out] r_inv set to the additive inverse of @a r
+ */
+void
+GNUNET_CRYPTO_ecc_rnd (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                      gcry_mpi_point_t *r,
+                      gcry_mpi_point_t *r_inv);
+
+
+/**
+ * Obtain a random scalar for point multiplication on the curve and
+ * its multiplicative inverse.
+ *
+ * @param edc calculation context for ECC operations
+ * @param[out] r set to a random scalar on the curve
+ * @param[out] r_inv set to the multiplicative inverse of @a r
+ */
+void
+GNUNET_CRYPTO_ecc_rnd_mpi (struct GNUNET_CRYPTO_EccDlogContext *edc,
+                           gcry_mpi_t *r,
+                           gcry_mpi_t *r_inv);
+
+
+/**
+ * Generate a random value mod n.
+ *
+ * @param edc ECC context
+ * @return random value mod n.
+ */
+gcry_mpi_t
+GNUNET_CRYPTO_ecc_random_mod_n (struct GNUNET_CRYPTO_EccDlogContext *edc);
+
+
+/**
+ * Free a point value returned by the API.
+ *
+ * @param p point to free
+ */
+void
+GNUNET_CRYPTO_ecc_free (gcry_mpi_point_t p);
+
+
+/**
+ * Release precalculated values.
+ *
+ * @param dlc dlog context
+ */
+void
+GNUNET_CRYPTO_ecc_dlog_release (struct GNUNET_CRYPTO_EccDlogContext *dlc);
+
+
 /**
  * @ingroup crypto
  * Derive key material from a public and a private ECC key.
@@ -1239,6 +1483,38 @@ GNUNET_CRYPTO_ecc_ecdh (const struct GNUNET_CRYPTO_EcdhePrivateKey *priv,
                         struct GNUNET_HashCode *key_material);
 
 
+/**
+ * @ingroup crypto
+ * Derive key material from a ECDH public key and a private EdDSA key.
+ * Dual to #GNUNET_CRRYPTO_ecdh_eddsa.
+ *
+ * @param priv private key from EdDSA to use for the ECDH (x)
+ * @param pub public key to use for the ECDH (yG)
+ * @param key_material where to write the key material H(h(x)yG)
+ * @return #GNUNET_SYSERR on error, #GNUNET_OK on success
+ */
+int
+GNUNET_CRYPTO_eddsa_ecdh (const struct GNUNET_CRYPTO_EddsaPrivateKey *priv,
+                          const struct GNUNET_CRYPTO_EcdhePublicKey *pub,
+                          struct GNUNET_HashCode *key_material);
+
+
+/**
+ * @ingroup crypto
+ * Derive key material from a EdDSA public key and a private ECDH key.
+ * Dual to #GNUNET_CRRYPTO_eddsa_ecdh.
+ *
+ * @param priv private key to use for the ECDH (y)
+ * @param pub public key from EdDSA to use for the ECDH (X=h(x)G)
+ * @param key_material where to write the key material H(yX)=H(h(x)yG)
+ * @return #GNUNET_SYSERR on error, #GNUNET_OK on success
+ */
+int
+GNUNET_CRYPTO_ecdh_eddsa (const struct GNUNET_CRYPTO_EcdhePrivateKey *priv,
+                          const struct GNUNET_CRYPTO_EddsaPublicKey *pub,
+                          struct GNUNET_HashCode *key_material);
+
+
 /**
  * @ingroup crypto
  * EdDSA sign a given block.
@@ -1498,7 +1774,7 @@ GNUNET_CRYPTO_rsa_private_key_free (struct GNUNET_CRYPTO_rsa_PrivateKey *key);
  */
 size_t
 GNUNET_CRYPTO_rsa_private_key_encode (const struct GNUNET_CRYPTO_rsa_PrivateKey *key,
-                              char **buffer);
+                                     char **buffer);
 
 
 /**
@@ -1511,7 +1787,17 @@ GNUNET_CRYPTO_rsa_private_key_encode (const struct GNUNET_CRYPTO_rsa_PrivateKey
  */
 struct GNUNET_CRYPTO_rsa_PrivateKey *
 GNUNET_CRYPTO_rsa_private_key_decode (const char *buf,
-                              size_t len);
+                                     size_t len);
+
+
+/**
+ * Duplicate the given private key
+ *
+ * @param key the private key to duplicate
+ * @return the duplicate key; NULL upon error
+ */
+struct GNUNET_CRYPTO_rsa_PrivateKey *
+GNUNET_CRYPTO_rsa_private_key_dup (const struct GNUNET_CRYPTO_rsa_PrivateKey *key);
 
 
 /**
@@ -1524,6 +1810,27 @@ struct GNUNET_CRYPTO_rsa_PublicKey *
 GNUNET_CRYPTO_rsa_private_key_get_public (const struct GNUNET_CRYPTO_rsa_PrivateKey *priv);
 
 
+/**
+ * Compute hash over the public key.
+ *
+ * @param key public key to hash
+ * @param hc where to store the hash code
+ */
+void
+GNUNET_CRYPTO_rsa_public_key_hash (const struct GNUNET_CRYPTO_rsa_PublicKey *key,
+                                   struct GNUNET_HashCode *hc);
+
+
+/**
+ * Obtain the length of the RSA key in bits.
+ *
+ * @param key the public key to introspect
+ * @return length of the key in bits
+ */
+unsigned int
+GNUNET_CRYPTO_rsa_public_key_len (const struct GNUNET_CRYPTO_rsa_PublicKey *key);
+
+
 /**
  * Free memory occupied by the public key.
  *
@@ -1543,7 +1850,7 @@ GNUNET_CRYPTO_rsa_public_key_free (struct GNUNET_CRYPTO_rsa_PublicKey *key);
  */
 size_t
 GNUNET_CRYPTO_rsa_public_key_encode (const struct GNUNET_CRYPTO_rsa_PublicKey *key,
-                             char **buffer);
+                                    char **buffer);
 
 
 /**
@@ -1556,7 +1863,17 @@ GNUNET_CRYPTO_rsa_public_key_encode (const struct GNUNET_CRYPTO_rsa_PublicKey *k
  */
 struct GNUNET_CRYPTO_rsa_PublicKey *
 GNUNET_CRYPTO_rsa_public_key_decode (const char *buf,
-                             size_t len);
+                                    size_t len);
+
+
+/**
+ * Duplicate the given public key
+ *
+ * @param key the public key to duplicate
+ * @return the duplicate key; NULL upon error
+ */
+struct GNUNET_CRYPTO_rsa_PublicKey *
+GNUNET_CRYPTO_rsa_public_key_dup (const struct GNUNET_CRYPTO_rsa_PublicKey *key);
 
 
 /**
@@ -1569,6 +1886,53 @@ struct GNUNET_CRYPTO_rsa_BlindingKey *
 GNUNET_CRYPTO_rsa_blinding_key_create (unsigned int len);
 
 
+/**
+ * Compare the values of two blinding keys.
+ *
+ * @param b1 one key
+ * @param b2 the other key
+ * @return 0 if the two are equal
+ */
+int
+GNUNET_CRYPTO_rsa_blinding_key_cmp (struct GNUNET_CRYPTO_rsa_BlindingKey *b1,
+                                   struct GNUNET_CRYPTO_rsa_BlindingKey *b2);
+
+
+/**
+ * Compare the values of two signatures.
+ *
+ * @param s1 one signature
+ * @param s2 the other signature
+ * @return 0 if the two are equal
+ */
+int
+GNUNET_CRYPTO_rsa_signature_cmp (struct GNUNET_CRYPTO_rsa_Signature *s1,
+                                struct GNUNET_CRYPTO_rsa_Signature *s2);
+
+/**
+ * Compare the values of two private keys.
+ *
+ * @param p1 one private key
+ * @param p2 the other private key
+ * @return 0 if the two are equal
+ */
+int
+GNUNET_CRYPTO_rsa_private_key_cmp (struct GNUNET_CRYPTO_rsa_PrivateKey *p1,
+                                 struct GNUNET_CRYPTO_rsa_PrivateKey *p2);
+
+
+/**
+ * Compare the values of two public keys.
+ *
+ * @param p1 one public key
+ * @param p2 the other public key
+ * @return 0 if the two are equal
+ */
+int
+GNUNET_CRYPTO_rsa_public_key_cmp (struct GNUNET_CRYPTO_rsa_PublicKey *p1,
+                                 struct GNUNET_CRYPTO_rsa_PublicKey *p2);
+
+
 /**
  * Destroy a blinding key
  *
@@ -1588,7 +1952,7 @@ GNUNET_CRYPTO_rsa_blinding_key_free (struct GNUNET_CRYPTO_rsa_BlindingKey *bkey)
  */
 size_t
 GNUNET_CRYPTO_rsa_blinding_key_encode (const struct GNUNET_CRYPTO_rsa_BlindingKey *bkey,
-                               char **buffer);
+                                       char **buffer);
 
 
 /**
@@ -1601,7 +1965,7 @@ GNUNET_CRYPTO_rsa_blinding_key_encode (const struct GNUNET_CRYPTO_rsa_BlindingKe
  */
 struct GNUNET_CRYPTO_rsa_BlindingKey *
 GNUNET_CRYPTO_rsa_blinding_key_decode (const char *buf,
-                               size_t len);
+                                       size_t len);
 
 
 /**
@@ -1615,9 +1979,9 @@ GNUNET_CRYPTO_rsa_blinding_key_decode (const char *buf,
  */
 size_t
 GNUNET_CRYPTO_rsa_blind (const struct GNUNET_HashCode *hash,
-                 struct GNUNET_CRYPTO_rsa_BlindingKey *bkey,
-                 struct GNUNET_CRYPTO_rsa_PublicKey *pkey,
-                 char **buffer);
+                         struct GNUNET_CRYPTO_rsa_BlindingKey *bkey,
+                         struct GNUNET_CRYPTO_rsa_PublicKey *pkey,
+                         char **buffer);
 
 
 /**
@@ -1630,22 +1994,21 @@ GNUNET_CRYPTO_rsa_blind (const struct GNUNET_HashCode *hash,
  */
 struct GNUNET_CRYPTO_rsa_Signature *
 GNUNET_CRYPTO_rsa_sign (const struct GNUNET_CRYPTO_rsa_PrivateKey *key,
-                const void *msg,
-                size_t msg_len);
+                        const void *msg,
+                        size_t msg_len);
 
 
 /**
  * Free memory occupied by signature.
  *
- * @param sig memory to freee
+ * @param sig memory to free
  */
 void
 GNUNET_CRYPTO_rsa_signature_free (struct GNUNET_CRYPTO_rsa_Signature *sig);
 
 
 /**
- * Encode the signature key in a format suitable for
- * storing it into a file.
+ * Encode the given signature in a format suitable for storing it into a file.
  *
  * @param sig the signature
  * @param[out] buffer set to a buffer with the encoded key
@@ -1653,12 +2016,12 @@ GNUNET_CRYPTO_rsa_signature_free (struct GNUNET_CRYPTO_rsa_Signature *sig);
  */
 size_t
 GNUNET_CRYPTO_rsa_signature_encode (const struct GNUNET_CRYPTO_rsa_Signature *sig,
-                            char **buffer);
+                                   char **buffer);
 
 
 /**
- * Decode the public key from the data-format back
- * to the "normal", internal format.
+ * Decode the signature from the data-format back to the "normal", internal
+ * format.
  *
  * @param buf the buffer where the public key data is stored
  * @param len the length of the data in @a buf
@@ -1666,13 +2029,23 @@ GNUNET_CRYPTO_rsa_signature_encode (const struct GNUNET_CRYPTO_rsa_Signature *si
  */
 struct GNUNET_CRYPTO_rsa_Signature *
 GNUNET_CRYPTO_rsa_signature_decode (const char *buf,
-                            size_t len);
+                                   size_t len);
+
+
+/**
+ * Duplicate the given rsa signature
+ *
+ * @param sig the signature to duplicate
+ * @return the duplicate key; NULL upon error
+ */
+struct GNUNET_CRYPTO_rsa_Signature *
+GNUNET_CRYPTO_rsa_signature_dup (const struct GNUNET_CRYPTO_rsa_Signature *sig);
 
 
 /**
- * Unblind a signature made on blinding signature purpose.  The signature
- * purpose should have been generated with #GNUNET_CRYPTO_rsa_sign() using
- * a message that was generated with #GNUNET_CRYPTO_rsa_blind().
+ * Unblind a blind-signed signature.  The signature should have been generated
+ * with #GNUNET_CRYPTO_rsa_sign() using a hash that was blinded with
+ * #GNUNET_CRYPTO_rsa_blind().
  *
  * @param sig the signature made on the blinded signature purpose
  * @param bkey the blinding key used to blind the signature purpose
@@ -1681,12 +2054,13 @@ GNUNET_CRYPTO_rsa_signature_decode (const char *buf,
  */
 struct GNUNET_CRYPTO_rsa_Signature *
 GNUNET_CRYPTO_rsa_unblind (struct GNUNET_CRYPTO_rsa_Signature *sig,
-                   struct GNUNET_CRYPTO_rsa_BlindingKey *bkey,
-                   struct GNUNET_CRYPTO_rsa_PublicKey *pkey);
+                          struct GNUNET_CRYPTO_rsa_BlindingKey *bkey,
+                          struct GNUNET_CRYPTO_rsa_PublicKey *pkey);
 
 
 /**
- * Verify signature with the given hash.
+ * Verify whether the given hash corresponds to the given signature and the
+ * signature is valid with respect to the given public key.
  *
  * @param hash the message to verify to match the @a sig
  * @param sig signature that is being validated
@@ -1695,8 +2069,8 @@ GNUNET_CRYPTO_rsa_unblind (struct GNUNET_CRYPTO_rsa_Signature *sig,
  */
 int
 GNUNET_CRYPTO_rsa_verify (const struct GNUNET_HashCode *hash,
-                  const struct GNUNET_CRYPTO_rsa_Signature *sig,
-                  const struct GNUNET_CRYPTO_rsa_PublicKey *public_key);
+                         const struct GNUNET_CRYPTO_rsa_Signature *sig,
+                         const struct GNUNET_CRYPTO_rsa_PublicKey *public_key);
 
 
 #if 0                           /* keep Emacsens' auto-indent happy */