diff --git a/include/libssh/libgcrypt.h b/include/libssh/libgcrypt.h index 7556acae..ec353910 100644 --- a/include/libssh/libgcrypt.h +++ b/include/libssh/libgcrypt.h @@ -32,7 +32,7 @@ typedef gcry_md_hd_t SHA384CTX; typedef gcry_md_hd_t SHA512CTX; typedef gcry_md_hd_t MD5CTX; typedef gcry_md_hd_t HMACCTX; -typedef void *EVPCTX; +typedef gcry_md_hd_t EVPCTX; #define SHA_DIGEST_LENGTH 20 #define SHA_DIGEST_LEN SHA_DIGEST_LENGTH #define MD5_DIGEST_LEN 16 @@ -51,6 +51,11 @@ typedef void *EVPCTX; typedef gcry_mpi_t bignum; +/* Constants for curves. */ +#define NID_gcrypt_nistp256 0 +#define NID_gcrypt_nistp384 1 +#define NID_gcrypt_nistp521 2 + /* missing gcrypt functions */ int ssh_gcry_dec2bn(bignum *bn, const char *data); char *ssh_gcry_bn2dec(bignum bn); diff --git a/src/libgcrypt.c b/src/libgcrypt.c index 60f6536c..0e85d5d3 100644 --- a/src/libgcrypt.c +++ b/src/libgcrypt.c @@ -71,6 +71,59 @@ void sha1(unsigned char *digest, int len, unsigned char *hash) { gcry_md_hash_buffer(GCRY_MD_SHA1, hash, digest, len); } +#ifdef HAVE_GCRYPT_ECC +static int nid_to_md_algo(int nid) +{ + switch (nid) { + case NID_gcrypt_nistp256: + return GCRY_MD_SHA256; + case NID_gcrypt_nistp384: + return GCRY_MD_SHA384; + case NID_gcrypt_nistp521: + return GCRY_MD_SHA512; + } + return GCRY_MD_NONE; +} + +void evp(int nid, unsigned char *digest, int len, + unsigned char *hash, unsigned int *hlen) +{ + int algo = nid_to_md_algo(nid); + + /* Note: What gcrypt calls 'hash' is called 'digest' here and + vice-versa. */ + gcry_md_hash_buffer(algo, hash, digest, len); + *hlen = gcry_md_get_algo_dlen(algo); +} + +EVPCTX evp_init(int nid) +{ + gcry_error_t err; + int algo = nid_to_md_algo(nid); + EVPCTX ctx; + + err = gcry_md_open(&ctx, algo, 0); + if (err) { + return NULL; + } + + return ctx; +} + +void evp_update(EVPCTX ctx, const void *data, unsigned long len) +{ + gcry_md_write(ctx, data, len); +} + +void evp_final(EVPCTX ctx, unsigned char *md, unsigned int *mdlen) +{ + int algo = gcry_md_get_algo(ctx); + *mdlen = gcry_md_get_algo_dlen(algo); + memcpy(md, gcry_md_read(ctx, algo), *mdlen); + gcry_md_close(ctx); +} +#endif + SHA256CTX sha256_init(void) { SHA256CTX ctx = NULL; gcry_md_open(&ctx, GCRY_MD_SHA256, 0);