diff options
| author | Miloslav Trmač <mitr@redhat.com> | 2010-10-27 00:06:56 +0200 |
|---|---|---|
| committer | Miloslav Trmač <mitr@redhat.com> | 2010-10-27 00:06:56 +0200 |
| commit | e056fd22f61b2881945bf6bc9389c243fbfcde4a (patch) | |
| tree | ced31e7e2679d62afbb1a6cc1736b42c836d8edc | |
| parent | 665a66c7f5f4128bac6bcec7f358a5919da3942e (diff) | |
| parent | 06a02e2391625a09e194acf1c6d31aecf2266b8f (diff) | |
| download | ncrypto-e056fd22f61b2881945bf6bc9389c243fbfcde4a.tar.gz ncrypto-e056fd22f61b2881945bf6bc9389c243fbfcde4a.tar.xz ncrypto-e056fd22f61b2881945bf6bc9389c243fbfcde4a.zip | |
Merge branch 'local'
Conflicts:
lib/ncrypto_local.c
| -rw-r--r-- | Makefile.am | 5 | ||||
| -rw-r--r-- | include/ncrypto/ncrypto.h | 34 | ||||
| -rw-r--r-- | lib/ncrypto_local.c | 273 | ||||
| -rw-r--r-- | tests/rsa.c | 4 | ||||
| -rw-r--r-- | tests/symm_signatures.c | 266 |
5 files changed, 574 insertions, 8 deletions
diff --git a/Makefile.am b/Makefile.am index 5c74dae..022099b 100644 --- a/Makefile.am +++ b/Makefile.am @@ -35,7 +35,7 @@ AM_CPPFLAGS = -I $(top_srcdir)/include $(GLIB_CFLAGS) $(NSS_CFLAGS) \ ## Targets lib_LTLIBRARIES = lib/libncrypto.la pkginclude_HEADERS = include/ncrypto/ncrypto.h -TESTS = tests/digests tests/rsa tests/symm_ciphers +TESTS = tests/digests tests/rsa tests/symm_ciphers tests/symm_signatures ## Rules noinst_PROGRAMS = $(TESTS) @@ -52,3 +52,6 @@ tests_rsa_LDFLAGS = -no-install tests_symm_ciphers_LDADD = lib/libncrypto.la $(GLIB_LIBS) tests_symm_ciphers_LDFLAGS = -no-install + +tests_symm_signatures_LDADD = lib/libncrypto.la $(GLIB_LIBS) +tests_symm_signatures_LDFLAGS = -no-install diff --git a/include/ncrypto/ncrypto.h b/include/ncrypto/ncrypto.h index aef6bb4..24d8e8e 100644 --- a/include/ncrypto/ncrypto.h +++ b/include/ncrypto/ncrypto.h @@ -183,4 +183,38 @@ CK_RV ncr_symm_cipher_decrypt (struct ncr_symm_cipher_session *sess, void *dest, size_t *dest_size_ptr, const void *src, size_t src_size); + /* Symmetric signatures */ + +struct ncr_symm_signature_session; + +/* Session lifetime management. */ +CK_RV ncr_symm_signature_alloc (struct ncr_symm_signature_session **sess, + CK_MECHANISM_TYPE mech); +CK_RV ncr_symm_signature_free (struct ncr_symm_signature_session *sess); +/* Use either ncr_symm_signature_sign_{init,update,final} (), or + ncr_symm_signature_{sign_init,sign} (). After finishing such a call + sequence, a new sequence can be started within the same session. Same for + verification sequences. + + Symmetric signature mechanisms tend to use keys of type + CKK_GENERIC_SECRET. */ +CK_RV ncr_symm_signature_sign_init (struct ncr_symm_signature_session *sess, + struct ncr_symm_key *key); +CK_RV ncr_symm_signature_sign_update (struct ncr_symm_signature_session *sess, + const void *data, size_t size); +CK_RV ncr_symm_signature_sign_final (struct ncr_symm_signature_session *sess, + void *dest, size_t *size_ptr); +CK_RV ncr_symm_signature_sign (struct ncr_symm_signature_session *sess, + void *dest, size_t *dest_size_ptr, + const void *data, size_t data_size); +CK_RV ncr_symm_signature_verify_init (struct ncr_symm_signature_session *sess, + struct ncr_symm_key *key); +CK_RV ncr_symm_signature_verify_update (struct ncr_symm_signature_session *sess, + const void *data, size_t size); +CK_RV ncr_symm_signature_verify_final (struct ncr_symm_signature_session *sess, + const void *signature, size_t size); +CK_RV ncr_symm_signature_verify (struct ncr_symm_signature_session *sess, + const void *signature, size_t signature_size, + const void *data, size_t data_size); + #endif diff --git a/lib/ncrypto_local.c b/lib/ncrypto_local.c index 72bc6fd..7062479 100644 --- a/lib/ncrypto_local.c +++ b/lib/ncrypto_local.c @@ -32,6 +32,7 @@ Red Hat author: Miloslav Trmač <mitr@redhat.com> */ #include <glib.h> #include <openssl/evp.h> +#include <openssl/hmac.h> #include <openssl/rand.h> #include <ncrypto/ncrypto.h> @@ -165,6 +166,12 @@ ncr_symm_key_generate (struct ncr_symm_key **key, CK_MECHANISM_TYPE mech, value_size = 24; break; + case CKM_GENERIC_SECRET_KEY_GEN: + type = CKK_GENERIC_SECRET; + g_return_val_if_fail (value_size <= SIZE_MAX - sizeof (*k), + CKR_HOST_MEMORY); + break; + default: g_return_val_if_reached (CKR_MECHANISM_INVALID); } @@ -209,7 +216,7 @@ struct ncr_symm_cipher_session EVP_CIPHER_CTX ctx; CK_MECHANISM_TYPE mech; size_t padding_size; /* Additional space to reserve for padding */ - _Bool encrypting; + bool encrypting; /* Debugging only */ enum { NSCS_NEW, NSCS_INITIALIZED, NSCS_UPDATED, NSCS_FINISHED } state; }; @@ -245,12 +252,12 @@ ncr_symm_cipher_free (struct ncr_symm_cipher_session *sess) } static CK_RV -symm_cipher_init (struct ncr_symm_cipher_session *sess, _Bool encrypt, +symm_cipher_init (struct ncr_symm_cipher_session *sess, bool encrypt, struct ncr_symm_key *key, const void *param, size_t param_size) { const EVP_CIPHER *type; - _Bool padding; + bool padding; g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); g_return_val_if_fail (sess->state == NSCS_NEW || sess->state == NSCS_FINISHED, @@ -324,7 +331,7 @@ symm_cipher_init (struct ncr_symm_cipher_session *sess, _Bool encrypt, } static CK_RV -symm_cipher_update (struct ncr_symm_cipher_session *sess, _Bool encrypt, +symm_cipher_update (struct ncr_symm_cipher_session *sess, bool encrypt, void *dest, size_t *dest_size_ptr, const void *src, size_t src_size) { @@ -363,7 +370,7 @@ symm_cipher_update (struct ncr_symm_cipher_session *sess, _Bool encrypt, /* EVP_CipherUpdate + EVP_CipherFinal_ex */ static CK_RV do_symm_cipher_update_final (struct ncr_symm_cipher_session *sess, - _Bool encrypt, void *dest, size_t *dest_size_ptr, + bool encrypt, void *dest, size_t *dest_size_ptr, const void *src, size_t src_size) { int outl; @@ -410,7 +417,7 @@ do_symm_cipher_update_final (struct ncr_symm_cipher_session *sess, } static CK_RV -symm_cipher_final (struct ncr_symm_cipher_session *sess, _Bool encrypt, +symm_cipher_final (struct ncr_symm_cipher_session *sess, bool encrypt, void *dest, size_t *dest_size_ptr, const void *src, size_t src_size) { @@ -424,7 +431,7 @@ symm_cipher_final (struct ncr_symm_cipher_session *sess, _Bool encrypt, } static CK_RV -symm_cipher (struct ncr_symm_cipher_session *sess, _Bool encrypt, void *dest, +symm_cipher (struct ncr_symm_cipher_session *sess, bool encrypt, void *dest, size_t *dest_size_ptr, const void *src, size_t src_size) { g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); @@ -498,3 +505,255 @@ ncr_symm_cipher_decrypt (struct ncr_symm_cipher_session *sess, void *dest, { return symm_cipher (sess, false, dest, dest_size_ptr, src, src_size); } + + /* Symmetric signature handling */ + +static const EVP_MD * +symm_signature_evp_from_hmac_mech (CK_MECHANISM_TYPE mech) +{ + switch (mech) + { +#define E(M, E) \ + case CKM_##M##_HMAC: \ + return EVP_##E (); + E (MD5, md5); + E (SHA_1, sha1); + E (SHA224, sha224); + E (SHA256, sha256); + E (SHA384, sha384); + E (SHA512, sha512); +#undef E + default: + g_return_val_if_reached (NULL); + } +} + +struct ncr_symm_signature_session +{ + HMAC_CTX ctx; + const EVP_MD *md; + size_t md_size; + bool signing; + /* Debugging only */ + enum { NSSS_NEW, NSSS_INITIALIZED, NSSS_UPDATED, NSSS_FINISHED } state; +}; + +CK_RV +ncr_symm_signature_alloc (struct ncr_symm_signature_session **sess, + CK_MECHANISM_TYPE mech) +{ + struct ncr_symm_signature_session *s; + const EVP_MD *md; + + g_return_val_if_fail (sess != NULL, CKR_ARGUMENTS_BAD); + + md = symm_signature_evp_from_hmac_mech (mech); + if (md == NULL) + return CKR_MECHANISM_INVALID; + + s = malloc (sizeof (*s)); + if (s == NULL) + return CKR_HOST_MEMORY; + + HMAC_CTX_init (&s->ctx); + s->state = NSSS_NEW; + s->md = md; + s->md_size = EVP_MD_size (md); + g_assert (s->md_size <= EVP_MAX_MD_SIZE); + *sess = s; + return CKR_OK; +} + +CK_RV +ncr_symm_signature_free (struct ncr_symm_signature_session *sess) +{ + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + + HMAC_CTX_cleanup (&sess->ctx); + free (sess); + return CKR_OK; +} + +static CK_RV +symm_signature_init (struct ncr_symm_signature_session *sess, bool sign, + struct ncr_symm_key *key) +{ + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (sess->state == NSSS_NEW || sess->state == NSSS_FINISHED, + CKR_OPERATION_ACTIVE); + g_return_val_if_fail (key != NULL, CKR_KEY_HANDLE_INVALID); + + /* This is not assured, but holds for supported mechanisms. */ + g_return_val_if_fail (key->type == CKK_GENERIC_SECRET, + CKR_KEY_TYPE_INCONSISTENT); + + if (HMAC_Init_ex (&sess->ctx, key->value, key->size, sess->md, NULL) == 0) + return ckr_openssl (); + + sess->signing = sign; + sess->state = NSSS_INITIALIZED; + return CKR_OK; +} + +static CK_RV +symm_signature_update (struct ncr_symm_signature_session *sess, bool sign, + const void *data, size_t size) +{ + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (data != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (sess->state == NSSS_INITIALIZED + || sess->state == NSSS_UPDATED, + CKR_OPERATION_NOT_INITIALIZED); + g_return_val_if_fail (sess->signing == sign, CKR_OPERATION_NOT_INITIALIZED); + + if (HMAC_Update (&sess->ctx, data, size) == 0) + return ckr_openssl (); + + sess->state = NSSS_UPDATED; + return CKR_OK; +} + +CK_RV +ncr_symm_signature_sign_init (struct ncr_symm_signature_session *sess, + struct ncr_symm_key *key) +{ + return symm_signature_init (sess, true, key); +} + +CK_RV +ncr_symm_signature_sign_update (struct ncr_symm_signature_session *sess, + const void *data, size_t size) +{ + return symm_signature_update (sess, true, data, size); +} + +CK_RV +ncr_symm_signature_sign_final (struct ncr_symm_signature_session *sess, + void *dest, size_t *size_ptr) +{ + int res; + + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (sess->state == NSSS_INITIALIZED + || sess->state == NSSS_UPDATED, + CKR_OPERATION_NOT_INITIALIZED); + g_return_val_if_fail (size_ptr != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (sess->signing == true, CKR_OPERATION_NOT_INITIALIZED); + + if (dest == NULL) + { + *size_ptr = sess->md_size; + return CKR_OK; + } + if (*size_ptr < sess->md_size) + { + *size_ptr = sess->md_size; + return CKR_BUFFER_TOO_SMALL; + } + *size_ptr = sess->md_size; + + g_return_val_if_fail (dest != NULL, CKR_ARGUMENTS_BAD); + + res = HMAC_Final (&sess->ctx, dest, NULL); + sess->state = NSSS_FINISHED; + return res ? CKR_OK : ckr_openssl (); +} + +CK_RV +ncr_symm_signature_sign (struct ncr_symm_signature_session *sess, void *dest, + size_t *dest_size_ptr, const void *data, + size_t data_size) +{ + int res; + + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (sess->state == NSSS_INITIALIZED, + CKR_OPERATION_NOT_INITIALIZED); + g_return_val_if_fail (dest_size_ptr != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (sess->signing == true, CKR_OPERATION_NOT_INITIALIZED); + + if (dest == NULL) + { + *dest_size_ptr = sess->md_size; + return CKR_OK; + } + if (*dest_size_ptr < sess->md_size) + { + *dest_size_ptr = sess->md_size; + return CKR_BUFFER_TOO_SMALL; + } + *dest_size_ptr = sess->md_size; + + g_return_val_if_fail (data != NULL, CKR_ARGUMENTS_BAD); + + res = (HMAC_Update (&sess->ctx, data, data_size) != 0 + && HMAC_Final (&sess->ctx, dest, NULL) != 0); + sess->state = NSSS_FINISHED; + return res ? CKR_OK : ckr_openssl (); +} + +CK_RV +ncr_symm_signature_verify_init (struct ncr_symm_signature_session *sess, + struct ncr_symm_key *key) +{ + return symm_signature_init (sess, false, key); +} + +CK_RV +ncr_symm_signature_verify_update (struct ncr_symm_signature_session *sess, + const void *data, size_t size) +{ + return symm_signature_update (sess, false, data, size); +} + +CK_RV +ncr_symm_signature_verify_final (struct ncr_symm_signature_session *sess, + const void *signature, size_t size) +{ + uint8_t buf[EVP_MAX_MD_SIZE]; + int res; + + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (sess->state == NSSS_INITIALIZED + || sess->state == NSSS_UPDATED, + CKR_OPERATION_NOT_INITIALIZED); + g_return_val_if_fail (signature != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (sess->signing == false, CKR_OPERATION_NOT_INITIALIZED); + + res = HMAC_Final (&sess->ctx, buf, NULL); + sess->state = NSSS_FINISHED; + if (res == 0) + return ckr_openssl (); + if (size != sess->md_size) + return CKR_SIGNATURE_LEN_RANGE; + if (memcmp (signature, buf, size) != 0) + return CKR_SIGNATURE_INVALID; + return CKR_OK; +} + +CK_RV +ncr_symm_signature_verify (struct ncr_symm_signature_session *sess, + const void *signature, size_t signature_size, + const void *data, size_t data_size) +{ + uint8_t buf[EVP_MAX_MD_SIZE]; + int res; + + g_return_val_if_fail (sess != NULL, CKR_SESSION_HANDLE_INVALID); + g_return_val_if_fail (sess->state == NSSS_INITIALIZED, + CKR_OPERATION_NOT_INITIALIZED); + g_return_val_if_fail (data != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (signature != NULL, CKR_ARGUMENTS_BAD); + g_return_val_if_fail (sess->signing == false, CKR_OPERATION_NOT_INITIALIZED); + + res = (HMAC_Update (&sess->ctx, data, data_size) != 0 + && HMAC_Final (&sess->ctx, buf, NULL) != 0); + sess->state = NSSS_FINISHED; + if (res == 0) + return ckr_openssl (); + if (signature_size != sess->md_size) + return CKR_SIGNATURE_LEN_RANGE; + if (memcmp (signature, buf, signature_size) != 0) + return CKR_SIGNATURE_INVALID; + return CKR_OK; +} diff --git a/tests/rsa.c b/tests/rsa.c index 9addcf4..224f5c1 100644 --- a/tests/rsa.c +++ b/tests/rsa.c @@ -88,6 +88,10 @@ main (void) res = ncr_public_key_verify (CKM_RSA_PKCS, public, dest, dest_size, input, sizeof (input)); assert (res == CKR_OK); + dest[0]++; + res = ncr_public_key_verify (CKM_RSA_PKCS, public, dest, dest_size, input, + sizeof (input)); + assert (res != CKR_OK); res = ncr_private_key_destroy (private); assert (res == CKR_OK); diff --git a/tests/symm_signatures.c b/tests/symm_signatures.c new file mode 100644 index 0000000..17ca560 --- /dev/null +++ b/tests/symm_signatures.c @@ -0,0 +1,266 @@ +/* ncr_symm_signature_* tests. + +Copyright 2010 Red Hat, Inc. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +1. Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +2. Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +THIS SOFTWARE IS PROVIDED BY CONTRIBUTORS ``AS IS'' AND ANY EXPRESS OR IMPLIED +WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO +EVENT SHALL CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, +SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, +PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR +BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER +IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) +ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE +POSSIBILITY OF SUCH DAMAGE. + +Red Hat author: Miloslav Trmač <mitr@redhat.com> */ + +#include <assert.h> +#include <stdint.h> +#include <stdlib.h> +#include <string.h> + +#include <glib.h> +#include <ncrypto/ncrypto.h> + +struct tv +{ + CK_MECHANISM_TYPE mech; + const uint8_t *input; + size_t input_size; + const uint8_t *key; + size_t key_size; + const uint8_t *output; + size_t output_size; +}; + +static const struct tv tvs[] = + { +#define TV(M, IN, KEY, OUT) \ + { \ + (M), (const uint8_t *)(IN), sizeof (IN) - 1, \ + (const uint8_t *)(KEY), sizeof (KEY) - 1, (const uint8_t *)(OUT), \ + sizeof (OUT) - 1 \ + } + TV (CKM_SHA_1_HMAC, "Sample #1", + "\x00\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0A\x0B\x0C\x0D\x0E\x0F\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1A\x1B\x1C\x1D\x1E\x1F\x20\x21\x22\x23\x24\x25\x26\x27\x28\x29\x2A\x2B\x2C\x2D\x2E\x2F\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3A\x3B\x3C\x3D\x3E\x3F", + "\x4F\x4C\xA3\xD5\xD6\x8B\xA7\xCC\x0A\x12\x08\xC9\xC6\x1E\x9C\x5D\xA0\x40\x3C\x0A"), + TV (CKM_SHA_1_HMAC, "Sample #2", + "\x30\x31\x32\x33\x34\x35\x36\x37\x38\x39\x3A\x3B\x3C\x3D\x3E\x3F\x40\x41\x42\x43", + "\x09\x22\xD3\x40\x5F\xAA\x3D\x19\x4F\x82\xA4\x58\x30\x73\x7D\x5C\xC6\xC7\x5D\x24"), + TV (CKM_SHA_1_HMAC, "Sample #3", + "\x50\x51\x52\x53\x54\x55\x56\x57\x58\x59\x5A\x5B\x5C\x5D\x5E\x5F\x60\x61\x62\x63\x64\x65\x66\x67\x68\x69\x6A\x6B\x6C\x6D\x6E\x6F\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7A\x7B\x7C\x7D\x7E\x7F\x80\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8A\x8B\x8C\x8D\x8E\x8F\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9A\x9B\x9C\x9D\x9E\x9F\xA0\xA1\xA2\xA3\xA4\xA5\xA6\xA7\xA8\xA9\xAA\xAB\xAC\xAD\xAE\xAF\xB0\xB1\xB2\xB3", + "\xBC\xF4\x1E\xAB\x8B\xB2\xD8\x02\xF3\xD0\x5C\xAF\x7C\xB0\x92\xEC\xF8\xD1\xA3\xAA"), + TV (CKM_SHA_1_HMAC, "Sample #4", + "\x70\x71\x72\x73\x74\x75\x76\x77\x78\x79\x7A\x7B\x7C\x7D\x7E\x7F\x80\x81\x82\x83\x84\x85\x86\x87\x88\x89\x8A\x8B\x8C\x8D\x8E\x8F\x90\x91\x92\x93\x94\x95\x96\x97\x98\x99\x9A\x9B\x9C\x9D\x9E\x9F\xA0", + "\x9E\xA8\x86\xEF\xE2\x68\xDB\xEC\xCE\x42\x0C\x75\x24\xDF\x32\xE0\x75\x1A\x2A\x26") +#undef TV + }; + +int +main (void) +{ + struct ncr_symm_signature_session *sess; + struct ncr_symm_key *key; + uint8_t dest[256]; + size_t i, j, k, dest_size; + CK_RV res; + + for (i = 0; i < G_N_ELEMENTS (tvs); i++) + { + res = ncr_symm_signature_alloc (&sess, tvs[i].mech); + assert (res == CKR_OK); + + res = ncr_symm_key_create (&key, CKK_GENERIC_SECRET, tvs[i].key, + tvs[i].key_size); + assert (res == CKR_OK); + + for (j = 0; j < 2; j++) + { + res = ncr_symm_signature_sign_init (sess, key); + assert (res == CKR_OK); + + res = ncr_symm_signature_sign_update (sess, tvs[i].input, + tvs[i].input_size); + assert (res == CKR_OK); + + dest_size = sizeof (dest); + res = ncr_symm_signature_sign_final (sess, dest, &dest_size); + assert (res == CKR_OK); + assert (dest_size == tvs[i].output_size); + assert (memcmp (dest, tvs[i].output, dest_size) == 0); + + for (k = 0; k < 2; k++) + { + res = ncr_symm_signature_verify_init (sess, key); + assert (res == CKR_OK); + + res = ncr_symm_signature_verify_update (sess, tvs[i].input, + tvs[i].input_size); + assert (res == CKR_OK); + + memcpy (dest, tvs[i].output, tvs[i].output_size); + dest[0] += k; + res = ncr_symm_signature_verify_final (sess, dest, + tvs[i].output_size); + if (k == 0) + assert (res == CKR_OK); + else + assert (res == CKR_SIGNATURE_INVALID); + } + } + + res = ncr_symm_key_destroy (key); + assert (res == CKR_OK); + + res = ncr_symm_signature_free (sess); + assert (res == CKR_OK); + } + + for (i = 0; i < G_N_ELEMENTS (tvs); i++) + { + res = ncr_symm_signature_alloc (&sess, tvs[i].mech); + assert (res == CKR_OK); + + res = ncr_symm_key_create (&key, CKK_GENERIC_SECRET, tvs[i].key, + tvs[i].key_size); + assert (res == CKR_OK); + + for (j = 0; j < 2; j++) + { + res = ncr_symm_signature_sign_init (sess, key); + assert (res == CKR_OK); + + dest_size = sizeof (dest); + res = ncr_symm_signature_sign (sess, dest, &dest_size, + tvs[i].input, tvs[i].input_size); + assert (res == CKR_OK); + assert (dest_size == tvs[i].output_size); + assert (memcmp (dest, tvs[i].output, dest_size) == 0); + + for (k = 0; k < 2; k++) + { + res = ncr_symm_signature_verify_init (sess, key); + assert (res == CKR_OK); + + memcpy (dest, tvs[i].output, tvs[i].output_size); + dest[0] += k; + res = ncr_symm_signature_verify (sess, dest, tvs[i].output_size, + tvs[i].input, tvs[i].input_size); + if (k == 0) + assert (res == CKR_OK); + else + assert (res == CKR_SIGNATURE_INVALID); + } + } + + res = ncr_symm_key_destroy (key); + assert (res == CKR_OK); + + res = ncr_symm_signature_free (sess); + assert (res == CKR_OK); + } + + for (i = 0; i < G_N_ELEMENTS (tvs); i++) + { + res = ncr_symm_signature_alloc (&sess, tvs[i].mech); + assert (res == CKR_OK); + + res = ncr_symm_key_generate (&key, CKM_GENERIC_SECRET_KEY_GEN, + tvs[i].key_size); + assert (res == CKR_OK); + + for (j = 0; j < 2; j++) + { + res = ncr_symm_signature_sign_init (sess, key); + assert (res == CKR_OK); + + res = ncr_symm_signature_sign_update (sess, tvs[i].input, + tvs[i].input_size); + assert (res == CKR_OK); + + dest_size = sizeof (dest); + res = ncr_symm_signature_sign_final (sess, dest, &dest_size); + assert (res == CKR_OK); + assert (dest_size == tvs[i].output_size); + + for (k = 0; k < 2; k++) + { + res = ncr_symm_signature_verify_init (sess, key); + assert (res == CKR_OK); + + res = ncr_symm_signature_verify_update (sess, tvs[i].input, + tvs[i].input_size); + assert (res == CKR_OK); + + dest[0] += k; + res = ncr_symm_signature_verify_final (sess, dest, + tvs[i].output_size); + if (k == 0) + assert (res == CKR_OK); + else + assert (res == CKR_SIGNATURE_INVALID); + } + } + + res = ncr_symm_key_destroy (key); + assert (res == CKR_OK); + + res = ncr_symm_signature_free (sess); + assert (res == CKR_OK); + } + + for (i = 0; i < G_N_ELEMENTS (tvs); i++) + { + res = ncr_symm_signature_alloc (&sess, tvs[i].mech); + assert (res == CKR_OK); + + res = ncr_symm_key_generate (&key, CKM_GENERIC_SECRET_KEY_GEN, + tvs[i].key_size); + assert (res == CKR_OK); + + for (j = 0; j < 2; j++) + { + res = ncr_symm_signature_sign_init (sess, key); + assert (res == CKR_OK); + + dest_size = sizeof (dest); + res = ncr_symm_signature_sign (sess, dest, &dest_size, + tvs[i].input, tvs[i].input_size); + assert (res == CKR_OK); + assert (dest_size == tvs[i].output_size); + + for (k = 0; k < 2; k++) + { + res = ncr_symm_signature_verify_init (sess, key); + assert (res == CKR_OK); + + dest[0] += k; + res = ncr_symm_signature_verify (sess, dest, tvs[i].output_size, + tvs[i].input, tvs[i].input_size); + if (k == 0) + assert (res == CKR_OK); + else + assert (res == CKR_SIGNATURE_INVALID); + } + } + + res = ncr_symm_key_destroy (key); + assert (res == CKR_OK); + + res = ncr_symm_signature_free (sess); + assert (res == CKR_OK); + } + + return EXIT_SUCCESS; +} |
