g10/decrypt-data: use iobuf_read for higher performance
authorJussi Kivilinna <jussi.kivilinna@iki.fi>
Thu, 8 Nov 2018 19:31:12 +0000 (21:31 +0200)
committerJussi Kivilinna <jussi.kivilinna@iki.fi>
Thu, 8 Nov 2018 19:31:12 +0000 (21:31 +0200)
* g10/decrypt-data.c (fill_buffer): Use iobuf_read instead of iobuf_get
for reading data.
--

This patch reduces iobuf_read per byte processing overhead and speeds
up decryption.

Benchmark results below, tested on Intel Core i7-4790K (turbo off).
Encrypted 2 GiB through pipe to ramfs file using AES128. Decrypt
ramfs file out through pipe to /dev/null.

before patch-set
----------------
       gpg process
no-armor:      user time    pipe transfer rate
 encrypt-aead:  1.02         1.0 GB/s
 decrypt-aead:  10.8         185 MB/s
 encrypt-cfb:   4.8          342 MB/s
 decrypt-cfb:   12.7         157 MB/s

               gpg process
armor:         user time    pipe transfer rate
 encrypt-aead:  13.8         140 MB/s
 decrypt-aead:  30.6         68 MB/s
 encrypt-cfb:   17.4         114 MB/s
 decrypt-cfb:   32.6         64 MB/s

after (decrypt opt)
-------------------
               gpg process
no-armor:      user time    pipe transfer rate
 decrypt-aead:  7.3          263 MB/s
 decrypt-cfb:   9.3          211 MB/s

               gpg process
armor:         user time    pipe transfer rate
 decrypt-aead:  27.0         77 MB/s
 decrypt-cfb:   29.0         72 MB/s

Note: decryption results are much slower than encryption because of
extra SHA1 & RIPEMD160 hashing.

GnuPG-bug-id: 3786
Signed-off-by: Jussi Kivilinna <jussi.kivilinna@iki.fi>
g10/decrypt-data.c

index a3c9b80..4d9dc86 100644 (file)
@@ -551,31 +551,42 @@ fill_buffer (decode_filter_ctx_t dfx, iobuf_t stream,
              byte *buffer, size_t nbytes, size_t offset)
 {
   size_t nread = offset;
-  int c;
+  size_t curr;
+  int ret;
 
   if (dfx->partial)
     {
-      for (; nread < nbytes; nread++ )
+      while (nread < nbytes)
         {
-          if ((c = iobuf_get (stream)) == -1)
+          curr = nbytes - nread;
+
+          ret = iobuf_read (stream, &buffer[nread], curr);
+          if (ret == -1)
             {
               dfx->eof_seen = 1; /* Normal EOF. */
               break;
             }
-          buffer[nread] = c;
+
+          nread += ret;
         }
     }
   else
     {
-      for (; nread < nbytes && dfx->length; nread++, dfx->length--)
+      while (nread < nbytes && dfx->length)
         {
-          c = iobuf_get (stream);
-          if (c == -1)
+          curr = nbytes - nread;
+          if (curr > dfx->length)
+            curr = dfx->length;
+
+          ret = iobuf_read (stream, &buffer[nread], curr);
+          if (ret == -1)
             {
               dfx->eof_seen = 3; /* Premature EOF. */
               break;
             }
-          buffer[nread] = c;
+
+          nread += ret;
+          dfx->length -= ret;
         }
       if (!dfx->length)
         dfx->eof_seen = 1; /* Normal EOF.  */