summaryrefslogtreecommitdiff
path: root/tests/bench-slope.c
diff options
context:
space:
mode:
authorDmitry Eremin-Solenikov <dbaryshkov@gmail.com>2013-11-19 23:26:26 +0200
committerJussi Kivilinna <jussi.kivilinna@iki.fi>2013-11-19 23:26:26 +0200
commit90cce18b9eced4f412ceeec5bcae18c4493322df (patch)
tree8018c676ab8f35e2e9b50938f90761e1454a6597 /tests/bench-slope.c
parent9816ae9d9931b75e4fdc9a5be10e6af447132313 (diff)
downloadlibgcrypt-90cce18b9eced4f412ceeec5bcae18c4493322df.tar.gz
Initial implementation of GCM
* cipher/Makefile.am: Add 'cipher-gcm.c'. * cipher/cipher-ccm.c (_gcry_ciphert_ccm_set_lengths) (_gcry_cipher_ccm_authenticate, _gcry_cipher_ccm_tag) (_gcry_cipher_ccm_encrypt, _gcry_cipher_ccm_decrypt): Change 'c->u_mode.ccm.tag' to 'c->marks.tag'. * cipher/cipher-gcm.c: New. * cipher/cipher-internal.h (GCM_USE_TABLES): New. (gcry_cipher_handle): Add 'marks.tag', 'u_tag', 'length' and 'gcm_table'; Remove 'u_mode.ccm.tag'. (_gcry_cipher_gcm_encrypt, _gcry_cipher_gcm_decrypt) (_gcry_cipher_gcm_setiv, _gcry_cipher_gcm_authenticate) (_gcry_cipher_gcm_get_tag, _gcry_cipher_gcm_check_tag): New. * cipher/cipher.c (_gcry_cipher_open_internal, cipher_setkey) (cipher_encrypt, cipher_decrypt, _gcry_cipher_authenticate) (_gcry_cipher_gettag, _gcry_cipher_checktag): Add GCM mode handling. * src/gcrypt.h.in (gcry_cipher_modes): Add GCRY_CIPHER_MODE_GCM. (GCRY_GCM_BLOCK_LEN): New. * tests/basic.c (check_gcm_cipher): New. (check_ciphers): Add GCM check. (check_cipher_modes): Call 'check_gcm_cipher'. * tests/bench-slope.c (bench_gcm_encrypt_do_bench) (bench_gcm_decrypt_do_bench, bench_gcm_authenticate_do_bench) (gcm_encrypt_ops, gcm_decrypt_ops, gcm_authenticate_ops): New. (cipher_modes): Add GCM enc/dec/auth. (cipher_bench_one): Limit GCM to block ciphers with 16 byte block-size. * tests/benchmark.c (cipher_bench): Add GCM. -- Currently it is still quite slow. Still no support for generate_iv(). Is it really necessary? TODO: Merge/reuse cipher-internal state used by CCM. Changelog entry will be present in final patch submission. Changes since v1: - 6x-7x speedup. - added bench-slope support Signed-off-by: Dmitry Eremin-Solenikov <dbaryshkov@gmail.com> [jk: mangle new file throught 'indent -nut'] [jk: few fixes] [jk: changelog]
Diffstat (limited to 'tests/bench-slope.c')
-rw-r--r--tests/bench-slope.c128
1 files changed, 128 insertions, 0 deletions
diff --git a/tests/bench-slope.c b/tests/bench-slope.c
index f9d3c46e..d29a4ade 100644
--- a/tests/bench-slope.c
+++ b/tests/bench-slope.c
@@ -787,6 +787,127 @@ static struct bench_ops ccm_authenticate_ops = {
&bench_ccm_authenticate_do_bench
};
+static void
+bench_gcm_encrypt_do_bench (struct bench_obj *obj, void *buf, size_t buflen)
+{
+ gcry_cipher_hd_t hd = obj->priv;
+ int err;
+ char tag[16];
+ char nonce[12] = { 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce,
+ 0xdb, 0xad, 0xde, 0xca, 0xf8, 0x88, };
+
+ gcry_cipher_setiv (hd, nonce, sizeof (nonce));
+
+ err = gcry_cipher_encrypt (hd, buf, buflen, buf, buflen);
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_encrypt failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+
+ err = gcry_cipher_gettag (hd, tag, sizeof (tag));
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_gettag failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+}
+
+static void
+bench_gcm_decrypt_do_bench (struct bench_obj *obj, void *buf, size_t buflen)
+{
+ gcry_cipher_hd_t hd = obj->priv;
+ int err;
+ char tag[16] = { 0, };
+ char nonce[12] = { 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce,
+ 0xdb, 0xad, 0xde, 0xca, 0xf8, 0x88, };
+
+ gcry_cipher_setiv (hd, nonce, sizeof (nonce));
+
+ err = gcry_cipher_decrypt (hd, buf, buflen, buf, buflen);
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_encrypt failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+
+ err = gcry_cipher_checktag (hd, tag, sizeof (tag));
+ if (gpg_err_code (err) == GPG_ERR_CHECKSUM)
+ err = gpg_error (GPG_ERR_NO_ERROR);
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_gettag failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+}
+
+static void
+bench_gcm_authenticate_do_bench (struct bench_obj *obj, void *buf,
+ size_t buflen)
+{
+ gcry_cipher_hd_t hd = obj->priv;
+ int err;
+ char tag[16] = { 0, };
+ char nonce[12] = { 0xca, 0xfe, 0xba, 0xbe, 0xfa, 0xce,
+ 0xdb, 0xad, 0xde, 0xca, 0xf8, 0x88, };
+ char data = 0xff;
+
+ gcry_cipher_setiv (hd, nonce, sizeof (nonce));
+
+ err = gcry_cipher_authenticate (hd, buf, buflen);
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_authenticate failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+
+ err = gcry_cipher_encrypt (hd, &data, sizeof (data), &data, sizeof (data));
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_encrypt failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+
+ err = gcry_cipher_gettag (hd, tag, sizeof (tag));
+ if (err)
+ {
+ fprintf (stderr, PGM ": gcry_cipher_gettag failed: %s\n",
+ gpg_strerror (err));
+ gcry_cipher_close (hd);
+ exit (1);
+ }
+}
+
+static struct bench_ops gcm_encrypt_ops = {
+ &bench_encrypt_init,
+ &bench_encrypt_free,
+ &bench_gcm_encrypt_do_bench
+};
+
+static struct bench_ops gcm_decrypt_ops = {
+ &bench_encrypt_init,
+ &bench_encrypt_free,
+ &bench_gcm_decrypt_do_bench
+};
+
+static struct bench_ops gcm_authenticate_ops = {
+ &bench_encrypt_init,
+ &bench_encrypt_free,
+ &bench_gcm_authenticate_do_bench
+};
+
static struct bench_cipher_mode cipher_modes[] = {
{GCRY_CIPHER_MODE_ECB, "ECB enc", &encrypt_ops},
@@ -802,6 +923,9 @@ static struct bench_cipher_mode cipher_modes[] = {
{GCRY_CIPHER_MODE_CCM, "CCM enc", &ccm_encrypt_ops},
{GCRY_CIPHER_MODE_CCM, "CCM dec", &ccm_decrypt_ops},
{GCRY_CIPHER_MODE_CCM, "CCM auth", &ccm_authenticate_ops},
+ {GCRY_CIPHER_MODE_GCM, "GCM enc", &gcm_encrypt_ops},
+ {GCRY_CIPHER_MODE_GCM, "GCM dec", &gcm_decrypt_ops},
+ {GCRY_CIPHER_MODE_GCM, "GCM auth", &gcm_authenticate_ops},
{0},
};
@@ -834,6 +958,10 @@ cipher_bench_one (int algo, struct bench_cipher_mode *pmode)
if (mode.mode == GCRY_CIPHER_MODE_CCM && blklen != GCRY_CCM_BLOCK_LEN)
return;
+ /* CCM has restrictions for block-size */
+ if (mode.mode == GCRY_CIPHER_MODE_GCM && blklen != GCRY_GCM_BLOCK_LEN)
+ return;
+
printf (" %14s | ", mode.name);
fflush (stdout);