/*
This file is part of GNUnet.
(C) 2001, 2002, 2003, 2004, 2005, 2006, 2009 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
by the Free Software Foundation; either version 2, or (at your
option) any later version.
GNUnet is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
General Public License for more details.
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.
*/
/**
* @file util/crypto_rsa.c
* @brief public key cryptography (RSA) with libgcrypt
* @author Christian Grothoff
*/
#include "platform.h"
#include <gcrypt.h>
#include "gnunet_common.h"
#include "gnunet_util_lib.h"
#define LOG(kind,...) GNUNET_log_from (kind, "util", __VA_ARGS__)
#define LOG_STRERROR(kind,syscall) GNUNET_log_from_strerror (kind, "util", syscall)
#define LOG_STRERROR_FILE(kind,syscall,filename) GNUNET_log_from_strerror_file (kind, "util", syscall, filename)
#define HOSTKEY_LEN 2048
#define EXTRA_CHECKS ALLOW_EXTRA_CHECKS
/**
* The private information of an RSA key pair.
* NOTE: this must match the definition in crypto_ksk.c and gnunet-rsa.c!
*/
struct GNUNET_CRYPTO_RsaPrivateKey
{
/**
* Libgcrypt S-expression for the ECC key.
*/
gcry_sexp_t sexp;
};
/**
* Log an error message at log-level 'level' that indicates
* a failure of the command 'cmd' with the message given
* by gcry_strerror(rc).
*/
#define LOG_GCRY(level, cmd, rc) do { LOG(level, _("`%s' failed at %s:%d with error: %s\n"), cmd, __FILE__, __LINE__, gcry_strerror(rc)); } while(0);
/**
* If target != size, move target bytes to the
* end of the size-sized buffer and zero out the
* first target-size bytes.
*
* @param buf original buffer
* @param size number of bytes in the buffer
* @param target target size of the buffer
*/
static void
adjust (unsigned char *buf, size_t size, size_t target)
{
if (size < target)
{
memmove (&buf[target - size], buf, size);
memset (buf, 0, target - size);
}
}
/**
* Free memory occupied by RSA private key.
*
* @param key pointer to the memory to free
*/
void
GNUNET_CRYPTO_rsa_key_free (struct GNUNET_CRYPTO_RsaPrivateKey *key)
{
gcry_sexp_release (key->sexp);
GNUNET_free (key);
}
/**
* 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 i;
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