summaryrefslogtreecommitdiff
path: root/cipher/cipher.c
diff options
context:
space:
mode:
authorJussi Kivilinna <jussi.kivilinna@iki.fi>2013-09-04 10:00:45 +0300
committerJussi Kivilinna <jussi.kivilinna@iki.fi>2013-09-04 10:00:45 +0300
commita3aaa6ad03388ea3eaa24304b604cb864633332f (patch)
treef20ea17064c7c6826bd28f1d6ba71b9f6325545f /cipher/cipher.c
parentf3515240de9513ead975985c9f8ab714022cac8e (diff)
downloadlibgcrypt-a3aaa6ad03388ea3eaa24304b604cb864633332f.tar.gz
Move stack burning from block ciphers to cipher modes
* src/gcrypt-module.h (gcry_cipher_encrypt_t) (gcry_cipher_decrypt_t): Return 'unsigned int'. * cipher/cipher.c (dummy_encrypt_block, dummy_decrypt_block): Return zero. (do_ecb_encrypt, do_ecb_decrypt): Get largest stack burn depth from block cipher crypt function and burn stack at end. * cipher/cipher-aeswrap.c (_gcry_cipher_aeswrap_encrypt) (_gcry_cipher_aeswrap_decrypt): Ditto. * cipher/cipher-cbc.c (_gcry_cipher_cbc_encrypt) (_gcry_cipher_cbc_decrypt): Ditto. * cipher/cipher-cfb.c (_gcry_cipher_cfb_encrypt) (_gcry_cipher_cfb_decrypt): Ditto. * cipher/cipher-ctr.c (_gcry_cipher_cbc_encrypt): Ditto. * cipher/cipher-ofb.c (_gcry_cipher_ofb_encrypt) (_gcry_cipher_ofb_decrypt): Ditto. * cipher/blowfish.c (encrypt_block, decrypt_block): Return burn stack depth. * cipher/camellia-glue.c (camellia_encrypt, camellia_decrypt): Ditto. * cipher/cast5.c (encrypt_block, decrypt_block): Ditto. * cipher/des.c (do_tripledes_encrypt, do_tripledes_decrypt) (do_des_encrypt, do_des_decrypt): Ditto. * cipher/idea.c (idea_encrypt, idea_decrypt): Ditto. * cipher/rijndael.c (rijndael_encrypt, rijndael_decrypt): Ditto. * cipher/seed.c (seed_encrypt, seed_decrypt): Ditto. * cipher/serpent.c (serpent_encrypt, serpent_decrypt): Ditto. * cipher/twofish.c (twofish_encrypt, twofish_decrypt): Ditto. * cipher/rfc2268.c (encrypt_block, decrypt_block): New. (_gcry_cipher_spec_rfc2268_40): Use encrypt_block and decrypt_block. -- Patch moves stack burning from block ciphers and cipher mode loop to end of cipher mode functions. This greatly reduces the overall CPU usage of the problematic _gcry_burn_stack. Internal cipher module API is changed so that encrypt/decrypt functions now return the stack burn depth as unsigned int to cipher mode function. (Note, patch also adds missing burn_stack for RFC2268_40 cipher). _gcry_burn_stack CPU time (looping tests/benchmark cipher blowfish): arch CPU Old New i386 Intel-Haswell 4.1% 0.16% x86_64 Intel-Haswell 3.4% 0.07% armhf Cortex-A8 8.7% 0.14% New vs. old (armhf/Cortex-A8): ECB/Stream CBC CFB OFB CTR --------------- --------------- --------------- --------------- --------------- IDEA 1.05x 1.05x 1.04x 1.04x 1.04x 1.04x 1.07x 1.05x 1.04x 1.04x 3DES 1.04x 1.03x 1.04x 1.03x 1.04x 1.04x 1.04x 1.04x 1.04x 1.04x CAST5 1.19x 1.20x 1.15x 1.00x 1.17x 1.00x 1.15x 1.05x 1.00x 1.00x BLOWFISH 1.21x 1.22x 1.16x 1.00x 1.18x 1.00x 1.16x 1.16x 1.00x 1.00x AES 1.09x 1.09x 1.00x 1.00x 1.00x 1.00x 1.07x 1.07x 1.00x 1.00x AES192 1.11x 1.11x 1.00x 1.00x 1.00x 1.00x 1.08x 1.09x 1.01x 1.00x AES256 1.07x 1.08x 1.01x .99x 1.00x 1.00x 1.07x 1.06x 1.00x 1.00x TWOFISH 1.10x 1.09x 1.09x 1.00x 1.09x 1.00x 1.08x 1.09x 1.00x 1.00x ARCFOUR 1.00x 1.00x DES 1.07x 1.11x 1.06x 1.08x 1.07x 1.07x 1.06x 1.06x 1.06x 1.06x TWOFISH128 1.10x 1.10x 1.09x 1.00x 1.09x 1.00x 1.08x 1.08x 1.00x 1.00x SERPENT128 1.06x 1.07x 1.02x 1.00x 1.06x 1.00x 1.06x 1.05x 1.00x 1.00x SERPENT192 1.07x 1.06x 1.03x 1.00x 1.06x 1.00x 1.06x 1.05x 1.00x 1.00x SERPENT256 1.06x 1.07x 1.02x 1.00x 1.06x 1.00x 1.05x 1.06x 1.00x 1.00x RFC2268_40 0.97x 1.01x 0.99x 0.98x 1.00x 0.97x 0.96x 0.96x 0.97x 0.97x SEED 1.45x 1.54x 1.53x 1.56x 1.50x 1.51x 1.50x 1.50x 1.42x 1.42x CAMELLIA128 1.08x 1.07x 1.06x 1.00x 1.07x 1.00x 1.06x 1.06x 1.00x 1.00x CAMELLIA192 1.08x 1.08x 1.08x 1.00x 1.07x 1.00x 1.07x 1.07x 1.00x 1.00x CAMELLIA256 1.08x 1.09x 1.07x 1.01x 1.08x 1.00x 1.07x 1.07x 1.00x 1.00x SALSA20 .99x 1.00x Raw data: New (armhf/Cortex-A8): Running each test 100 times. ECB/Stream CBC CFB OFB CTR --------------- --------------- --------------- --------------- --------------- IDEA 8620ms 8680ms 9640ms 10010ms 9140ms 8960ms 9630ms 9660ms 9180ms 9180ms 3DES 13990ms 14000ms 14780ms 15300ms 14320ms 14370ms 14780ms 14780ms 14480ms 14480ms CAST5 2980ms 2980ms 3780ms 2300ms 3290ms 2320ms 3770ms 4100ms 2320ms 2320ms BLOWFISH 2740ms 2660ms 3530ms 2060ms 3050ms 2080ms 3530ms 3530ms 2070ms 2070ms AES 2200ms 2330ms 2330ms 2450ms 2270ms 2270ms 2700ms 2690ms 2330ms 2320ms AES192 2550ms 2670ms 2700ms 2910ms 2630ms 2640ms 3060ms 3060ms 2680ms 2690ms AES256 2920ms 3010ms 3040ms 3190ms 3010ms 3000ms 3380ms 3420ms 3050ms 3050ms TWOFISH 2790ms 2840ms 3300ms 2950ms 3010ms 2870ms 3310ms 3280ms 2940ms 2940ms ARCFOUR 2050ms 2050ms DES 5640ms 5630ms 6440ms 6970ms 5960ms 6000ms 6440ms 6440ms 6120ms 6120ms TWOFISH128 2790ms 2840ms 3300ms 2950ms 3010ms 2890ms 3310ms 3290ms 2930ms 2930ms SERPENT128 4530ms 4340ms 5210ms 4470ms 4740ms 4620ms 5020ms 5030ms 4680ms 4680ms SERPENT192 4510ms 4340ms 5190ms 4460ms 4750ms 4620ms 5020ms 5030ms 4680ms 4680ms SERPENT256 4540ms 4330ms 5220ms 4460ms 4730ms 4600ms 5030ms 5020ms 4680ms 4680ms RFC2268_40 10530ms 7790ms 11140ms 9490ms 10650ms 10710ms 11710ms 11690ms 11000ms 11000ms SEED 4530ms 4540ms 5050ms 5380ms 4760ms 4810ms 5060ms 5060ms 4850ms 4860ms CAMELLIA128 2660ms 2630ms 3170ms 2750ms 2880ms 2740ms 3170ms 3170ms 2780ms 2780ms CAMELLIA192 3430ms 3400ms 3930ms 3530ms 3650ms 3500ms 3940ms 3940ms 3570ms 3560ms CAMELLIA256 3430ms 3390ms 3940ms 3500ms 3650ms 3510ms 3930ms 3940ms 3550ms 3550ms SALSA20 1910ms 1900ms Old (armhf/Cortex-A8): Running each test 100 times. ECB/Stream CBC CFB OFB CTR --------------- --------------- --------------- --------------- --------------- IDEA 9030ms 9100ms 10050ms 10410ms 9540ms 9360ms 10350ms 10190ms 9560ms 9570ms 3DES 14580ms 14460ms 15300ms 15720ms 14880ms 14900ms 15350ms 15330ms 15030ms 15020ms CAST5 3560ms 3570ms 4350ms 2300ms 3860ms 2330ms 4340ms 4320ms 2330ms 2320ms BLOWFISH 3320ms 3250ms 4110ms 2060ms 3610ms 2080ms 4100ms 4090ms 2070ms 2070ms AES 2390ms 2530ms 2320ms 2460ms 2280ms 2270ms 2890ms 2880ms 2330ms 2330ms AES192 2830ms 2970ms 2690ms 2900ms 2630ms 2650ms 3320ms 3330ms 2700ms 2690ms AES256 3110ms 3250ms 3060ms 3170ms 3000ms 3000ms 3610ms 3610ms 3050ms 3060ms TWOFISH 3080ms 3100ms 3600ms 2940ms 3290ms 2880ms 3560ms 3570ms 2940ms 2930ms ARCFOUR 2060ms 2050ms DES 6060ms 6230ms 6850ms 7540ms 6380ms 6400ms 6830ms 6840ms 6500ms 6510ms TWOFISH128 3060ms 3110ms 3600ms 2940ms 3290ms 2890ms 3560ms 3560ms 2940ms 2930ms SERPENT128 4820ms 4630ms 5330ms 4460ms 5030ms 4620ms 5300ms 5300ms 4680ms 4680ms SERPENT192 4830ms 4620ms 5320ms 4460ms 5040ms 4620ms 5300ms 5300ms 4680ms 4680ms SERPENT256 4820ms 4640ms 5330ms 4460ms 5030ms 4620ms 5300ms 5300ms 4680ms 4660ms RFC2268_40 10260ms 7850ms 11080ms 9270ms 10620ms 10380ms 11250ms 11230ms 10690ms 10710ms SEED 6580ms 6990ms 7710ms 8370ms 7140ms 7240ms 7600ms 7610ms 6870ms 6900ms CAMELLIA128 2860ms 2820ms 3360ms 2750ms 3080ms 2740ms 3350ms 3360ms 2790ms 2790ms CAMELLIA192 3710ms 3680ms 4240ms 3520ms 3910ms 3510ms 4200ms 4210ms 3560ms 3560ms CAMELLIA256 3700ms 3680ms 4230ms 3520ms 3930ms 3510ms 4200ms 4210ms 3550ms 3560ms SALSA20 1900ms 1900ms Signed-off-by: Jussi Kivilinna <jussi.kivilinna@iki.fi>
Diffstat (limited to 'cipher/cipher.c')
-rw-r--r--cipher/cipher.c24
1 files changed, 20 insertions, 4 deletions
diff --git a/cipher/cipher.c b/cipher/cipher.c
index 08d61655..2337c09f 100644
--- a/cipher/cipher.c
+++ b/cipher/cipher.c
@@ -150,7 +150,7 @@ dummy_setkey (void *c, const unsigned char *key, unsigned int keylen)
return GPG_ERR_NO_ERROR;
}
-static void
+static unsigned int
dummy_encrypt_block (void *c,
unsigned char *outbuf, const unsigned char *inbuf)
{
@@ -158,9 +158,10 @@ dummy_encrypt_block (void *c,
(void)outbuf;
(void)inbuf;
BUG();
+ return 0;
}
-static void
+static unsigned int
dummy_decrypt_block (void *c,
unsigned char *outbuf, const unsigned char *inbuf)
{
@@ -168,6 +169,7 @@ dummy_decrypt_block (void *c,
(void)outbuf;
(void)inbuf;
BUG();
+ return 0;
}
static void
@@ -902,6 +904,7 @@ do_ecb_encrypt (gcry_cipher_hd_t c,
{
unsigned int blocksize = c->cipher->blocksize;
unsigned int n, nblocks;
+ unsigned int burn, nburn;
if (outbuflen < inbuflen)
return GPG_ERR_BUFFER_TOO_SHORT;
@@ -909,13 +912,19 @@ do_ecb_encrypt (gcry_cipher_hd_t c,
return GPG_ERR_INV_LENGTH;
nblocks = inbuflen / c->cipher->blocksize;
+ burn = 0;
for (n=0; n < nblocks; n++ )
{
- c->cipher->encrypt (&c->context.c, outbuf, (byte*)/*arggg*/inbuf);
+ nburn = c->cipher->encrypt (&c->context.c, outbuf, (byte*)/*arggg*/inbuf);
+ burn = nburn > burn ? nburn : burn;
inbuf += blocksize;
outbuf += blocksize;
}
+
+ if (burn > 0)
+ _gcry_burn_stack (burn + 4 * sizeof(void *));
+
return 0;
}
@@ -926,20 +935,27 @@ do_ecb_decrypt (gcry_cipher_hd_t c,
{
unsigned int blocksize = c->cipher->blocksize;
unsigned int n, nblocks;
+ unsigned int burn, nburn;
if (outbuflen < inbuflen)
return GPG_ERR_BUFFER_TOO_SHORT;
if ((inbuflen % blocksize))
return GPG_ERR_INV_LENGTH;
+
nblocks = inbuflen / c->cipher->blocksize;
+ burn = 0;
for (n=0; n < nblocks; n++ )
{
- c->cipher->decrypt (&c->context.c, outbuf, (byte*)/*arggg*/inbuf );
+ nburn = c->cipher->decrypt (&c->context.c, outbuf, (byte*)/*arggg*/inbuf);
+ burn = nburn > burn ? nburn : burn;
inbuf += blocksize;
outbuf += blocksize;
}
+ if (burn > 0)
+ _gcry_burn_stack (burn + 4 * sizeof(void *));
+
return 0;
}