commit b18bb3e3c91c8630bee6817f0e264cc138d982b3
Author: Regev Shemy <regev.shemy@intel.com>
Date:   Thu May 14 10:41:54 2015 +0300

    Improved performance Multi Block CBC-SHA1 and CBC-SHA256

diff --git a/crypto/evp/e_aes_cbc_hmac_sha1.c b/crypto/evp/e_aes_cbc_hmac_sha1.c
old mode 100644
new mode 100755
index 7f2848e..30e5c60
--- a/crypto/evp/e_aes_cbc_hmac_sha1.c
+++ b/crypto/evp/e_aes_cbc_hmac_sha1.c
@@ -47,6 +47,54 @@
  * ====================================================================
  */
 
+ /*
+##############################################################################
+#                                                                            # 
+# Copyright 2015 Intel Corporation                                           #
+#                                                                            #
+# Licensed under the Apache License, Version 2.0 (the "License");            #
+# you may not use this file except in compliance with the License.           #
+# You may obtain a copy of the License at                                    #
+#                                                                            #
+#    http://www.apache.org/licenses/LICENSE-2.0                              #
+#                                                                            #
+# Unless required by applicable law or agreed to in writing, software        #
+# distributed under the License is distributed on an "AS IS" BASIS,          #
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   #
+# See the License for the specific language governing permissions and        #
+# limitations under the License.                                             #
+#                                                                            # 
+# This Source Code Form is subject to the terms of the Mozilla Public        #
+# License, v. 2.0. If a copy of the MPL was not distributed with this file,  #
+# You can obtain one at http://mozilla.org/MPL/2.0/.                         #
+############################################################################## 
+*/
+/******************************************************************************/
+/* Using, modifying, extracting from this code and/or algorithm(s)            */
+/* requires appropriate referencing.                                          */
+/******************************************************************************/
+/* DISCLAIMER:                                                                */
+/* THIS SOFTWARE IS PROVIDED BY THE CONTRIBUTORS AND THE COPYRIGHT OWNERS     */
+/* ``AS IS''. ANY EXPRESSED 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 THE CONTRIBUTORS OR THE COPYRIGHT*/
+/* OWNERS 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.                                                */
+/******************************************************************************/
+/*
+Developers and authors:
+***************************************************************************
+Shay Gueron (1, 2), Regev Shemy (2), Tal Uliel (2)
+(1) University of Haifa, Israel
+(2) Intel Corporation, Israel Development Center, Haifa, Israel
+***************************************************************************
+*/
+ 
 #include <openssl/opensslconf.h>
 
 #include <stdio.h>
@@ -145,6 +193,7 @@ static int aesni_cbc_hmac_sha1_init_key(EVP_CIPHER_CTX *ctx,
 #   define aes_off 0
 #  endif
 
+
 void sha1_block_data_order(void *c, const void *p, size_t len);
 
 static void sha1_update(SHA_CTX *c, const void *data, size_t len)
@@ -204,6 +253,20 @@ typedef struct {
 
 void aesni_multi_cbc_encrypt(CIPH_DESC *, void *, int);
 
+/* CHANGE-START */
+/*
+   This buffer is set to take values “1” – “16” (encoded in 128 bits) to be used as” input ciphertext” whose decryption (with a random creates pseudorandom strings. These are used as the IV’s. AVX MB needs 4 IV’s; AVX2 MB needs 8 IV’s. Futher AVX512 would require 16 IV’s.
+*/
+static const u64 TEMP_CT[32] =
+{0x0000000000000001, 0x0000000000000000, 0x0000000000000002, 0x0000000000000000, 0x0000000000000003, 0x0000000000000000,
+ 0x0000000000000004, 0x0000000000000000, 0x0000000000000005, 0x0000000000000000, 0x0000000000000006, 0x0000000000000000,
+ 0x0000000000000007, 0x0000000000000000, 0x0000000000000008, 0x0000000000000000, 0x0000000000000009, 0x0000000000000000,
+ 0x000000000000000a, 0x0000000000000000, 0x000000000000000b, 0x0000000000000000, 0x000000000000000c, 0x0000000000000000,
+ 0x000000000000000d, 0x0000000000000000, 0x000000000000000e, 0x0000000000000000, 0x000000000000000f, 0x0000000000000000,
+ 0x0000000000000010, 0x0000000000000000};
+
+/* CHANGE-END */
+
 static size_t tls1_1_multi_block_encrypt(EVP_AES_HMAC_SHA1 *key,
                                          unsigned char *out,
                                          const unsigned char *inp,
@@ -218,6 +281,7 @@ static size_t tls1_1_multi_block_encrypt(EVP_AES_HMAC_SHA1 *key,
         u8 c[128];
     } blocks[8];
     SHA1_MB_CTX *ctx;
+
     unsigned int frag, last, packlen, i, x4 = 4 * n4x, minblocks, processed =
         0;
     size_t ret = 0;
@@ -225,11 +289,33 @@ static size_t tls1_1_multi_block_encrypt(EVP_AES_HMAC_SHA1 *key,
 #   if defined(BSWAP8)
     u64 seqnum;
 #   endif
-
-    /* ask for IVs in bulk */
-    if (RAND_bytes((IVs = blocks[0].c), 16 * x4) <= 0)
+    /* CHANGE-START */
+    /* Adding 3 variables that are used below */
+    size_t num_rand;
+    AES_KEY TEMP_RAND_KS;
+    u64 ZERO[2] = {0,0};
+
+//    if (RAND_bytes((IVs = blocks[0].c), 16 * x4) <= 0)
+  //      return 0;
+
+/*Extract only NUM_RAND_BYTES bytes from RAND_bytes. Use AES (with this value as the key) as a PRF.
+  Obtain the appropriate amount of pseudo random (unpredictable) IV's */
+#define NUM_RAND_BYTES 16
+
+    num_rand = NUM_RAND_BYTES;
+    IVs = blocks[0].c;
+    memcpy(IVs, ZERO, 16);
+    if (RAND_bytes(IVs, num_rand) <= 0)
         return 0;
 
+    aesni_set_decrypt_key(IVs, 128, &TEMP_RAND_KS);
+    aesni_cbc_encrypt((const u8*)TEMP_CT, IVs, 16*x4,
+                        &TEMP_RAND_KS, (unsigned char*)ZERO, 0);
+    /* CHANGE-END */
+
+
+
+
     ctx = (SHA1_MB_CTX *) (storage + 32 - ((size_t)storage % 32)); /* align */
 
     frag = (unsigned int)inp_len >> (1 + n4x);
@@ -846,10 +932,8 @@ static int aesni_cbc_hmac_sha1_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
         {
             unsigned char *p = ptr;
             unsigned int len;
-
             if (arg != EVP_AEAD_TLS1_AAD_LEN)
                 return -1;
- 
             len = p[arg - 2] << 8 | p[arg - 1];
 
             if (ctx->encrypt) {
diff --git a/crypto/evp/e_aes_cbc_hmac_sha256.c b/crypto/evp/e_aes_cbc_hmac_sha256.c
old mode 100644
new mode 100755
index 3b6827a..7c0bdea
--- a/crypto/evp/e_aes_cbc_hmac_sha256.c
+++ b/crypto/evp/e_aes_cbc_hmac_sha256.c
@@ -47,6 +47,54 @@
  * ====================================================================
  */
 
+ /*
+##############################################################################
+#                                                                            # 
+# Copyright 2015 Intel Corporation                                           #
+#                                                                            #
+# Licensed under the Apache License, Version 2.0 (the "License");            #
+# you may not use this file except in compliance with the License.           #
+# You may obtain a copy of the License at                                    #
+#                                                                            #
+#    http://www.apache.org/licenses/LICENSE-2.0                              #
+#                                                                            #
+# Unless required by applicable law or agreed to in writing, software        #
+# distributed under the License is distributed on an "AS IS" BASIS,          #
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.   #
+# See the License for the specific language governing permissions and        #
+# limitations under the License.                                             #
+#                                                                            # 
+# This Source Code Form is subject to the terms of the Mozilla Public        #
+# License, v. 2.0. If a copy of the MPL was not distributed with this file,  #
+# You can obtain one at http://mozilla.org/MPL/2.0/.                         #
+############################################################################## 
+*/
+/******************************************************************************/
+/* Using, modifying, extracting from this code and/or algorithm(s)            */
+/* requires appropriate referencing.                                          */
+/******************************************************************************/
+/* DISCLAIMER:                                                                */
+/* THIS SOFTWARE IS PROVIDED BY THE CONTRIBUTORS AND THE COPYRIGHT OWNERS     */
+/* ``AS IS''. ANY EXPRESSED 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 THE CONTRIBUTORS OR THE COPYRIGHT*/
+/* OWNERS 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.                                                */
+/******************************************************************************/
+/*
+Developers and authors:
+***************************************************************************
+Shay Gueron (1, 2), Regev Shemy (2), Tal Uliel (2)
+(1) University of Haifa, Israel
+(2) Intel Corporation, Israel Development Center, Haifa, Israel
+***************************************************************************
+*/
+ 
 #include <openssl/opensslconf.h>
 
 #include <stdio.h>
@@ -200,6 +248,21 @@ typedef struct {
 
 void aesni_multi_cbc_encrypt(CIPH_DESC *, void *, int);
 
+/* CHANGE-START */
+/*
+   This buffer is set to take values “1” – “16” (encoded in 128 bits) to be used as” input ciphertext” whose decryption (with a random creates pseudorandom strings. These are used as the IV’s. AVX MB needs 4 IV’s; AVX2 MB needs 8 IV’s. Futher AVX512 would require 16 IV’s.
+*/
+static const u64 TEMP_CT[32] =
+{0x0000000000000001, 0x0000000000000000, 0x0000000000000002, 0x0000000000000000, 0x0000000000000003, 0x0000000000000000,
+ 0x0000000000000004, 0x0000000000000000, 0x0000000000000005, 0x0000000000000000, 0x0000000000000006, 0x0000000000000000,
+ 0x0000000000000007, 0x0000000000000000, 0x0000000000000008, 0x0000000000000000, 0x0000000000000009, 0x0000000000000000,
+ 0x000000000000000a, 0x0000000000000000, 0x000000000000000b, 0x0000000000000000, 0x000000000000000c, 0x0000000000000000,
+ 0x000000000000000d, 0x0000000000000000, 0x000000000000000e, 0x0000000000000000, 0x000000000000000f, 0x0000000000000000,
+ 0x0000000000000010, 0x0000000000000000};
+
+/* CHANGE-END */
+
+
 static size_t tls1_1_multi_block_encrypt(EVP_AES_HMAC_SHA256 *key,
                                          unsigned char *out,
                                          const unsigned char *inp,
@@ -217,16 +280,34 @@ static size_t tls1_1_multi_block_encrypt(EVP_AES_HMAC_SHA256 *key,
     unsigned int frag, last, packlen, i, x4 = 4 * n4x, minblocks, processed =
         0;
     size_t ret = 0;
-    u8 *IVs;
+    u8 *IVs;	
 #   if defined(BSWAP8)
     u64 seqnum;
 #   endif
-
-    /* ask for IVs in bulk */
-    if (RAND_bytes((IVs = blocks[0].c), 16 * x4) <= 0)
+    /* CHANGE-START */
+    /* Adding 3 variables that are used below */
+    size_t num_rand;
+    AES_KEY TEMP_RAND_KS;
+    u64 ZERO[2] = {0,0};
+
+//    if (RAND_bytes((IVs = blocks[0].c), 16 * x4) <= 0)
+  //      return 0;
+
+/*Extract only NUM_RAND_BYTES bytes from RAND_bytes. Use AES (with this value as the key) as a PRF.
+  Obtain the appropriate amount of pseudo random (unpredictable) IV's */
+#define NUM_RAND_BYTES 16
+
+    num_rand = NUM_RAND_BYTES;
+    IVs = blocks[0].c;
+    memcpy(IVs, ZERO, 16);
+    if (RAND_bytes(IVs, num_rand) <= 0)
         return 0;
 
-    /* align */
+    aesni_set_decrypt_key(IVs, 128, &TEMP_RAND_KS);
+    aesni_cbc_encrypt((const u8*)TEMP_CT, IVs, 16*x4,
+                        &TEMP_RAND_KS, (unsigned char*)ZERO, 0);
+    /* CHANGE-END */
+
     ctx = (SHA256_MB_CTX *) (storage + 32 - ((size_t)storage % 32));
 
     frag = (unsigned int)inp_len >> (1 + n4x);
@@ -789,7 +870,6 @@ static int aesni_cbc_hmac_sha256_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
 
             if (arg < 0)
                 return -1;
-
             if (u_arg > sizeof(hmac_key)) {
                 SHA256_Init(&key->head);
                 SHA256_Update(&key->head, ptr, arg);
@@ -819,9 +899,7 @@ static int aesni_cbc_hmac_sha256_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
 
             if (arg != EVP_AEAD_TLS1_AAD_LEN)
                 return -1;
-
             len = p[arg - 2] << 8 | p[arg - 1];
-
             if (ctx->encrypt) {
                 key->payload_length = len;
                 if ((key->aux.tls_ver =
@@ -855,7 +933,6 @@ static int aesni_cbc_hmac_sha256_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
 
             if (arg < 0)
                 return -1;
-
             if (u_arg < sizeof(EVP_CTRL_TLS1_1_MULTIBLOCK_PARAM))
                 return -1;
 
