X-Git-Url: http://git.silcnet.org/gitweb/?a=blobdiff_plain;f=lib%2Fsilccrypt%2Fsilcpkcs1.c;h=347addecbfd59d06647d2b1d67848f7591857a80;hb=bd548b5771a325d3dc051887d3fd0225550d4418;hp=b4ea51ca0e65790c02eab907b513e910132a4bfe;hpb=abfab56ac76372f17c2e509b2e2fdd4675ec7764;p=crypto.git diff --git a/lib/silccrypt/silcpkcs1.c b/lib/silccrypt/silcpkcs1.c index b4ea51ca..347addec 100644 --- a/lib/silccrypt/silcpkcs1.c +++ b/lib/silccrypt/silcpkcs1.c @@ -4,7 +4,7 @@ Author: Pekka Riikonen - Copyright (C) 2003 - 2007 Pekka Riikonen + Copyright (C) 2003 - 2008 Pekka Riikonen This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by @@ -16,9 +16,8 @@ GNU General Public License for more details. */ -/* $Id$ */ -#include "silc.h" +#include "silccrypto.h" #include "rsa.h" #include "silcpkcs1_i.h" @@ -169,11 +168,7 @@ SilcBool silc_pkcs1_decode(SilcPkcs1BlockType bt, /* Generates RSA key pair. */ -SilcBool silc_pkcs1_generate_key(const struct SilcPKCSAlgorithmStruct *pkcs, - SilcUInt32 keylen, - SilcRng rng, - void **ret_public_key, - void **ret_private_key) +SILC_PKCS_ALG_GENERATE_KEY(silc_pkcs1_generate_key) { SilcUInt32 prime_bits = keylen / 2; SilcMPInt p, q; @@ -217,10 +212,7 @@ SilcBool silc_pkcs1_generate_key(const struct SilcPKCSAlgorithmStruct *pkcs, /* Import PKCS #1 compliant public key */ -int silc_pkcs1_import_public_key(const struct SilcPKCSAlgorithmStruct *pkcs, - void *key, - SilcUInt32 key_len, - void **ret_public_key) +SILC_PKCS_ALG_IMPORT_PUBLIC_KEY(silc_pkcs1_import_public_key) { SilcAsn1 asn1 = NULL; SilcBufferStruct alg_key; @@ -263,11 +255,7 @@ int silc_pkcs1_import_public_key(const struct SilcPKCSAlgorithmStruct *pkcs, /* Export PKCS #1 compliant public key */ -unsigned char * -silc_pkcs1_export_public_key(const struct SilcPKCSAlgorithmStruct *pkcs, - SilcStack stack, - void *public_key, - SilcUInt32 *ret_len) +SILC_PKCS_ALG_EXPORT_PUBLIC_KEY(silc_pkcs1_export_public_key) { RsaPublicKey *key = public_key; SilcAsn1 asn1 = NULL; @@ -301,9 +289,7 @@ silc_pkcs1_export_public_key(const struct SilcPKCSAlgorithmStruct *pkcs, /* Returns key length */ -SilcUInt32 -silc_pkcs1_public_key_bitlen(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key) +SILC_PKCS_ALG_PUBLIC_KEY_BITLEN(silc_pkcs1_public_key_bitlen) { RsaPublicKey *key = public_key; return key->bits; @@ -311,8 +297,7 @@ silc_pkcs1_public_key_bitlen(const struct SilcPKCSAlgorithmStruct *pkcs, /* Copy public key */ -void *silc_pkcs1_public_key_copy(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key) +SILC_PKCS_ALG_PUBLIC_KEY_COPY(silc_pkcs1_public_key_copy) { RsaPublicKey *key = public_key, *new_key; @@ -331,9 +316,7 @@ void *silc_pkcs1_public_key_copy(const struct SilcPKCSAlgorithmStruct *pkcs, /* Compare public keys */ -SilcBool -silc_pkcs1_public_key_compare(const struct SilcPKCSAlgorithmStruct *pkcs, - void *key1, void *key2) +SILC_PKCS_ALG_PUBLIC_KEY_COMPARE(silc_pkcs1_public_key_compare) { RsaPublicKey *k1 = key1, *k2 = key2; @@ -349,22 +332,19 @@ silc_pkcs1_public_key_compare(const struct SilcPKCSAlgorithmStruct *pkcs, /* Frees public key */ -void silc_pkcs1_public_key_free(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key) +SILC_PKCS_ALG_PUBLIC_KEY_FREE(silc_pkcs1_public_key_free) { RsaPublicKey *key = public_key; silc_mp_uninit(&key->n); silc_mp_uninit(&key->e); + silc_hash_free(key->hash); silc_free(key); } /* Import PKCS #1 compliant private key */ -int silc_pkcs1_import_private_key(const struct SilcPKCSAlgorithmStruct *pkcs, - void *key, - SilcUInt32 key_len, - void **ret_private_key) +SILC_PKCS_ALG_IMPORT_PRIVATE_KEY(silc_pkcs1_import_private_key) { SilcAsn1 asn1; SilcBufferStruct alg_key; @@ -418,11 +398,7 @@ int silc_pkcs1_import_private_key(const struct SilcPKCSAlgorithmStruct *pkcs, /* Export PKCS #1 compliant private key */ -unsigned char * -silc_pkcs1_export_private_key(const struct SilcPKCSAlgorithmStruct *pkcs, - SilcStack stack, - void *private_key, - SilcUInt32 *ret_len) +SILC_PKCS_ALG_EXPORT_PRIVATE_KEY(silc_pkcs1_export_private_key) { RsaPrivateKey *key = private_key; SilcAsn1 asn1; @@ -462,9 +438,7 @@ silc_pkcs1_export_private_key(const struct SilcPKCSAlgorithmStruct *pkcs, /* Returns key length */ -SilcUInt32 -silc_pkcs1_private_key_bitlen(const struct SilcPKCSAlgorithmStruct *pkcs, - void *private_key) +SILC_PKCS_ALG_PRIVATE_KEY_BITLEN(silc_pkcs1_private_key_bitlen) { RsaPrivateKey *key = private_key; return key->bits; @@ -472,8 +446,7 @@ silc_pkcs1_private_key_bitlen(const struct SilcPKCSAlgorithmStruct *pkcs, /* Frees private key */ -void silc_pkcs1_private_key_free(const struct SilcPKCSAlgorithmStruct *pkcs, - void *private_key) +SILC_PKCS_ALG_PRIVATE_KEY_FREE(silc_pkcs1_private_key_free) { RsaPrivateKey *key = private_key; @@ -485,19 +458,13 @@ void silc_pkcs1_private_key_free(const struct SilcPKCSAlgorithmStruct *pkcs, silc_mp_uninit(&key->qP); silc_mp_uninit(&key->p); silc_mp_uninit(&key->q); + silc_hash_free(key->hash); silc_free(key); } /* PKCS #1 RSA routines */ -SilcAsyncOperation -silc_pkcs1_encrypt(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key, - unsigned char *src, - SilcUInt32 src_len, - SilcRng rng, - SilcPKCSEncryptCb encrypt_cb, - void *context) +SILC_PKCS_ALG_ENCRYPT(silc_pkcs1_encrypt) { RsaPublicKey *key = public_key; SilcMPInt mp_tmp; @@ -536,20 +503,14 @@ silc_pkcs1_encrypt(const struct SilcPKCSAlgorithmStruct *pkcs, encrypt_cb(TRUE, padded, len, context); memset(padded, 0, sizeof(padded)); - silc_mp_suninit(stack, &mp_tmp); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp); + silc_mp_uninit(&mp_dst); silc_stack_free(stack); return NULL; } -SilcAsyncOperation -silc_pkcs1_decrypt(const struct SilcPKCSAlgorithmStruct *pkcs, - void *private_key, - unsigned char *src, - SilcUInt32 src_len, - SilcPKCSDecryptCb decrypt_cb, - void *context) +SILC_PKCS_ALG_DECRYPT(silc_pkcs1_decrypt) { RsaPrivateKey *key = private_key; SilcMPInt mp_tmp; @@ -582,8 +543,8 @@ silc_pkcs1_decrypt(const struct SilcPKCSAlgorithmStruct *pkcs, unpadded, sizeof(unpadded), &dst_len)) { memset(padded, 0, padded_len); silc_free(padded); - silc_mp_suninit(stack, &mp_tmp); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp); + silc_mp_uninit(&mp_dst); decrypt_cb(FALSE, NULL, 0, context); return NULL; } @@ -594,8 +555,8 @@ silc_pkcs1_decrypt(const struct SilcPKCSAlgorithmStruct *pkcs, memset(padded, 0, padded_len); memset(unpadded, 0, sizeof(unpadded)); silc_free(padded); - silc_mp_suninit(stack, &mp_tmp); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp); + silc_mp_uninit(&mp_dst); silc_stack_free(stack); return NULL; @@ -603,15 +564,7 @@ silc_pkcs1_decrypt(const struct SilcPKCSAlgorithmStruct *pkcs, /* PKCS #1 sign with appendix, hash OID included in the signature */ -SilcAsyncOperation -silc_pkcs1_sign(const struct SilcPKCSAlgorithmStruct *pkcs, - void *private_key, - unsigned char *src, - SilcUInt32 src_len, - SilcBool compute_hash, - SilcHash hash, - SilcPKCSSignCb sign_cb, - void *context) +SILC_PKCS_ALG_SIGN(silc_pkcs1_sign) { RsaPrivateKey *key = private_key; unsigned char padded[2048 + 1], hashr[SILC_HASH_MAXLEN]; @@ -647,6 +600,8 @@ silc_pkcs1_sign(const struct SilcPKCSAlgorithmStruct *pkcs, /* Compute hash */ if (compute_hash) { + if (!hash) + hash = key->hash; silc_hash_make(hash, src, src_len, hashr); src = hashr; src_len = silc_hash_len(hash); @@ -697,8 +652,8 @@ silc_pkcs1_sign(const struct SilcPKCSAlgorithmStruct *pkcs, memset(padded, 0, sizeof(padded)); if (compute_hash) memset(hashr, 0, sizeof(hashr)); - silc_mp_suninit(stack, &mp_tmp); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp); + silc_mp_uninit(&mp_dst); silc_asn1_free(asn1); silc_stack_free(stack); @@ -707,16 +662,7 @@ silc_pkcs1_sign(const struct SilcPKCSAlgorithmStruct *pkcs, /* PKCS #1 verification with appendix. */ -SilcAsyncOperation -silc_pkcs1_verify(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key, - unsigned char *signature, - SilcUInt32 signature_len, - unsigned char *data, - SilcUInt32 data_len, - SilcHash hash, - SilcPKCSVerifyCb verify_cb, - void *context) +SILC_PKCS_ALG_VERIFY(silc_pkcs1_verify) { RsaPublicKey *key = public_key; SilcBool ret = FALSE; @@ -760,33 +706,35 @@ silc_pkcs1_verify(const struct SilcPKCSAlgorithmStruct *pkcs, silc_buffer_set(&di, unpadded, len); /* If hash isn't given, allocate the one given in digest info */ - if (!hash) { - has_null = FALSE; + if (compute_hash) { + if (!hash) { + has_null = FALSE; - /* Decode digest info */ - if (!silc_asn1_decode(asn1, &di, - SILC_ASN1_OPTS(SILC_ASN1_ACCUMUL), - SILC_ASN1_SEQUENCE, + /* Decode digest info */ + if (!silc_asn1_decode(asn1, &di, + SILC_ASN1_OPTS(SILC_ASN1_ACCUMUL), SILC_ASN1_SEQUENCE, - SILC_ASN1_OID(&oid), - SILC_ASN1_NULL_T(SILC_ASN1_OPTIONAL, - SILC_ASN1_TAG_NULL, &has_null), - SILC_ASN1_END, - SILC_ASN1_END, SILC_ASN1_END)) - goto err; - - if (!silc_hash_alloc_by_oid(oid, &ihash)) { - SILC_LOG_DEBUG(("Unknown OID %s", oid)); - goto err; + SILC_ASN1_SEQUENCE, + SILC_ASN1_OID(&oid), + SILC_ASN1_NULL_T(SILC_ASN1_OPTIONAL, + SILC_ASN1_TAG_NULL, &has_null), + SILC_ASN1_END, + SILC_ASN1_END, SILC_ASN1_END)) + goto err; + + if (!silc_hash_alloc_by_oid(oid, &ihash)) { + SILC_LOG_DEBUG(("Unknown OID %s", oid)); + goto err; + } + hash = ihash; } - hash = ihash; - } - /* Hash the data */ - silc_hash_make(hash, data, data_len, hashr); - data = hashr; - data_len = silc_hash_len(hash); - oid = (char *)silc_hash_get_oid(hash); + /* Hash the data */ + silc_hash_make(hash, data, data_len, hashr); + data = hashr; + data_len = silc_hash_len(hash); + oid = (char *)silc_hash_get_oid(hash); + } /* Encode digest info for comparison */ memset(&ldi, 0, sizeof(ldi)); @@ -818,9 +766,9 @@ silc_pkcs1_verify(const struct SilcPKCSAlgorithmStruct *pkcs, memset(verify, 0, verify_len); memset(unpadded, 0, sizeof(unpadded)); silc_free(verify); - silc_mp_suninit(stack, &mp_tmp2); - silc_mp_suninit(stack, &mp_dst); - if (hash) + silc_mp_uninit(&mp_tmp2); + silc_mp_uninit(&mp_dst); + if (compute_hash) memset(hashr, 0, sizeof(hashr)); if (ihash) silc_hash_free(ihash); @@ -832,8 +780,8 @@ silc_pkcs1_verify(const struct SilcPKCSAlgorithmStruct *pkcs, err: memset(verify, 0, verify_len); silc_free(verify); - silc_mp_suninit(stack, &mp_tmp2); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp2); + silc_mp_uninit(&mp_dst); if (ihash) silc_hash_free(ihash); silc_asn1_free(asn1); @@ -845,15 +793,7 @@ silc_pkcs1_verify(const struct SilcPKCSAlgorithmStruct *pkcs, /* PKCS #1 sign without hash oid */ -SilcAsyncOperation -silc_pkcs1_sign_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, - void *private_key, - unsigned char *src, - SilcUInt32 src_len, - SilcBool compute_hash, - SilcHash hash, - SilcPKCSSignCb sign_cb, - void *context) +SILC_PKCS_ALG_SIGN(silc_pkcs1_sign_no_oid) { RsaPrivateKey *key = private_key; SilcMPInt mp_tmp; @@ -871,6 +811,8 @@ silc_pkcs1_sign_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, /* Compute hash if requested */ if (compute_hash) { + if (!hash) + hash = key->hash; silc_hash_make(hash, src, src_len, hashr); src = hashr; src_len = silc_hash_len(hash); @@ -903,8 +845,8 @@ silc_pkcs1_sign_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, memset(padded, 0, sizeof(padded)); if (compute_hash) memset(hashr, 0, sizeof(hashr)); - silc_mp_suninit(stack, &mp_tmp); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp); + silc_mp_uninit(&mp_dst); silc_stack_free(stack); return NULL; @@ -912,16 +854,7 @@ silc_pkcs1_sign_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, /* PKCS #1 verify without hash oid */ -SilcAsyncOperation -silc_pkcs1_verify_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, - void *public_key, - unsigned char *signature, - SilcUInt32 signature_len, - unsigned char *data, - SilcUInt32 data_len, - SilcHash hash, - SilcPKCSVerifyCb verify_cb, - void *context) +SILC_PKCS_ALG_VERIFY(silc_pkcs1_verify_no_oid) { RsaPublicKey *key = public_key; SilcBool ret = FALSE; @@ -952,15 +885,17 @@ silc_pkcs1_verify_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, unpadded, sizeof(unpadded), &len)) { memset(verify, 0, verify_len); silc_free(verify); - silc_mp_suninit(stack, &mp_tmp2); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp2); + silc_mp_uninit(&mp_dst); silc_stack_free(stack); verify_cb(FALSE, context); return NULL; } /* Hash data if requested */ - if (hash) { + if (compute_hash) { + if (!hash) + hash = key->hash; silc_hash_make(hash, data, data_len, hashr); data = hashr; data_len = silc_hash_len(hash); @@ -975,11 +910,11 @@ silc_pkcs1_verify_no_oid(const struct SilcPKCSAlgorithmStruct *pkcs, memset(verify, 0, verify_len); memset(unpadded, 0, sizeof(unpadded)); - if (hash) + if (compute_hash) memset(hashr, 0, sizeof(hashr)); silc_free(verify); - silc_mp_suninit(stack, &mp_tmp2); - silc_mp_suninit(stack, &mp_dst); + silc_mp_uninit(&mp_tmp2); + silc_mp_uninit(&mp_dst); silc_stack_free(stack); return NULL;