[meta-freescale] [meta-fsl-ppc][PATCH v2 3/5] openssl: use fsl maintained source

ting.liu at freescale.com ting.liu at freescale.com
Thu Jul 10 03:28:33 PDT 2014


From: Ting Liu <b28495 at freescale.com>

add bbappend to use fsl own openssl source code which was tested

Signed-off-by: Ting Liu <b28495 at freescale.com>
---
 ...double-initialization-of-cryptodev-engine.patch |   83 +
 ...2-ECC-Support-header-for-Cryptodev-Engine.patch |  318 +++
 ...03-add-support-for-TLS-algorithms-offload.patch |  296 +++
 .../0004-Fixed-private-key-support-for-DH.patch    |   33 +
 .../0005-Fixed-private-key-support-for-DH.patch    |   35 +
 ...itial-support-for-PKC-in-cryptodev-engine.patch | 1563 +++++++++++++++
 ...007-Added-hwrng-dev-file-as-source-of-RNG.patch |   28 +
 ...s-interface-added-for-PKC-cryptodev-inter.patch | 2039 ++++++++++++++++++++
 ...ev-extend-TLS-offload-with-new-algorithms.patch |  106 +
 ...gen-operation-and-support-gendsa-command-.patch |  153 ++
 .../openssl/openssl-fsl/0011-RSA-Keygen-Fix.patch  |   64 +
 .../0012-Removed-local-copy-of-curve_t-type.patch  |  164 ++
 ...us-parameter-is-not-populated-by-dhparams.patch |   43 +
 .../0014-SW-Backoff-mechanism-for-dsa-keygen.patch |   53 +
 .../0015-Fixed-DH-keygen-pair-generator.patch      |  100 +
 .../openssl/openssl_1.0.1g.bbappend                |   59 +
 16 files changed, 5137 insertions(+)
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0001-remove-double-initialization-of-cryptodev-engine.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0002-ECC-Support-header-for-Cryptodev-Engine.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0003-add-support-for-TLS-algorithms-offload.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0004-Fixed-private-key-support-for-DH.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0005-Fixed-private-key-support-for-DH.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0006-Initial-support-for-PKC-in-cryptodev-engine.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0007-Added-hwrng-dev-file-as-source-of-RNG.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0008-Asynchronous-interface-added-for-PKC-cryptodev-inter.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0009-eng_cryptodev-extend-TLS-offload-with-new-algorithms.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0010-Add-RSA-keygen-operation-and-support-gendsa-command-.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0011-RSA-Keygen-Fix.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0012-Removed-local-copy-of-curve_t-type.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0013-Modulus-parameter-is-not-populated-by-dhparams.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0014-SW-Backoff-mechanism-for-dsa-keygen.patch
 create mode 100644 recipes-connectivity/openssl/openssl-fsl/0015-Fixed-DH-keygen-pair-generator.patch
 create mode 100644 recipes-connectivity/openssl/openssl_1.0.1g.bbappend

diff --git a/recipes-connectivity/openssl/openssl-fsl/0001-remove-double-initialization-of-cryptodev-engine.patch b/recipes-connectivity/openssl/openssl-fsl/0001-remove-double-initialization-of-cryptodev-engine.patch
new file mode 100644
index 0000000..eae6878
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0001-remove-double-initialization-of-cryptodev-engine.patch
@@ -0,0 +1,83 @@
+From f174dd904fb4995a89eed53be3e2ebf7bee25a9b Mon Sep 17 00:00:00 2001
+From: Cristian Stoica <cristian.stoica at freescale.com>
+Date: Tue, 10 Sep 2013 12:46:46 +0300
+Subject: [PATCH][fsl 01/15] remove double initialization of cryptodev engine
+
+Upstream-status: Pending
+
+cryptodev engine is initialized together with the other engines in
+ENGINE_load_builtin_engines. The initialization done through
+OpenSSL_add_all_algorithms is redundant.
+
+Signed-off-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_all.c |   11 -----------
+ crypto/engine/engine.h  |    4 ----
+ crypto/evp/c_all.c      |    5 -----
+ util/libeay.num         |    2 +-
+ 4 files changed, 1 insertion(+), 21 deletions(-)
+
+diff --git a/crypto/engine/eng_all.c b/crypto/engine/eng_all.c
+index 6093376..f16c043 100644
+--- a/crypto/engine/eng_all.c
++++ b/crypto/engine/eng_all.c
+@@ -122,14 +122,3 @@ void ENGINE_load_builtin_engines(void)
+ #endif
+ 	ENGINE_register_all_complete();
+ 	}
+-
+-#if defined(__OpenBSD__) || defined(__FreeBSD__) || defined(HAVE_CRYPTODEV)
+-void ENGINE_setup_bsd_cryptodev(void) {
+-	static int bsd_cryptodev_default_loaded = 0;
+-	if (!bsd_cryptodev_default_loaded) {
+-		ENGINE_load_cryptodev();
+-		ENGINE_register_all_complete();
+-	}
+-	bsd_cryptodev_default_loaded=1;
+-}
+-#endif
+diff --git a/crypto/engine/engine.h b/crypto/engine/engine.h
+index f8be497..237a6c9 100644
+--- a/crypto/engine/engine.h
++++ b/crypto/engine/engine.h
+@@ -740,10 +740,6 @@ typedef int (*dynamic_bind_engine)(ENGINE *e, const char *id,
+  * values. */
+ void *ENGINE_get_static_state(void);
+ 
+-#if defined(__OpenBSD__) || defined(__FreeBSD__) || defined(HAVE_CRYPTODEV)
+-void ENGINE_setup_bsd_cryptodev(void);
+-#endif
+-
+ /* BEGIN ERROR CODES */
+ /* The following lines are auto generated by the script mkerr.pl. Any changes
+  * made after this point may be overwritten when the script is next run.
+diff --git a/crypto/evp/c_all.c b/crypto/evp/c_all.c
+index 766c4ce..5d6c21b 100644
+--- a/crypto/evp/c_all.c
++++ b/crypto/evp/c_all.c
+@@ -82,9 +82,4 @@ void OPENSSL_add_all_algorithms_noconf(void)
+ 	OPENSSL_cpuid_setup();
+ 	OpenSSL_add_all_ciphers();
+ 	OpenSSL_add_all_digests();
+-#ifndef OPENSSL_NO_ENGINE
+-# if defined(__OpenBSD__) || defined(__FreeBSD__) || defined(HAVE_CRYPTODEV)
+-	ENGINE_setup_bsd_cryptodev();
+-# endif
+-#endif
+ 	}
+diff --git a/util/libeay.num b/util/libeay.num
+index aa86b2b..ae50040 100755
+--- a/util/libeay.num
++++ b/util/libeay.num
+@@ -2801,7 +2801,7 @@ BIO_indent                              3242	EXIST::FUNCTION:
+ BUF_strlcpy                             3243	EXIST::FUNCTION:
+ OpenSSLDie                              3244	EXIST::FUNCTION:
+ OPENSSL_cleanse                         3245	EXIST::FUNCTION:
+-ENGINE_setup_bsd_cryptodev              3246	EXIST:__FreeBSD__:FUNCTION:ENGINE
++ENGINE_setup_bsd_cryptodev              3246	NOEXIST::FUNCTION:
+ ERR_release_err_state_table             3247	EXIST::FUNCTION:LHASH
+ EVP_aes_128_cfb8                        3248	EXIST::FUNCTION:AES
+ FIPS_corrupt_rsa                        3249	NOEXIST::FUNCTION:
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0002-ECC-Support-header-for-Cryptodev-Engine.patch b/recipes-connectivity/openssl/openssl-fsl/0002-ECC-Support-header-for-Cryptodev-Engine.patch
new file mode 100644
index 0000000..717a345
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0002-ECC-Support-header-for-Cryptodev-Engine.patch
@@ -0,0 +1,318 @@
+From 154601fba4907a7eb3f98e670d62cfa15a767500 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 11 Mar 2014 05:56:54 +0545
+Subject: [PATCH][fsl 02/15] ECC Support header for Cryptodev Engine
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ crypto/engine/eng_cryptodev_ec.h |  296 ++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 296 insertions(+)
+ create mode 100644 crypto/engine/eng_cryptodev_ec.h
+
+diff --git a/crypto/engine/eng_cryptodev_ec.h b/crypto/engine/eng_cryptodev_ec.h
+new file mode 100644
+index 0000000..77aee71
+--- /dev/null
++++ b/crypto/engine/eng_cryptodev_ec.h
+@@ -0,0 +1,296 @@
++/*
++ * Copyright (C) 2012 Freescale Semiconductor, 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 THE AUTHOR ``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 THE AUTHOR 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.
++ */
++#ifndef __ENG_EC_H
++#define __ENG_EC_H
++
++#define SPCF_CPARAM_INIT(X,...) \
++static unsigned char X##_c[] = {__VA_ARGS__} \
++
++#define SPCF_FREE_BN(X) do { if(X) { BN_clear_free(X); X = NULL; } } while (0)
++
++#define SPCF_COPY_CPARAMS(NIDBUF) \
++  do { \
++      memcpy (buf, NIDBUF, buf_len); \
++    } while (0)
++
++#define SPCF_CPARAM_CASE(X) \
++  case NID_##X: \
++      SPCF_COPY_CPARAMS(X##_c); \
++      break
++
++SPCF_CPARAM_INIT(sect113r1, 0x01, 0x73, 0xE8, 0x34, 0xAF, 0x28, 0xEC, 0x76,
++		 0xCB, 0x83, 0xBD, 0x8D, 0xFE, 0xB2, 0xD5);
++SPCF_CPARAM_INIT(sect113r2, 0x00, 0x54, 0xD9, 0xF0, 0x39, 0x57, 0x17, 0x4A,
++		 0x32, 0x32, 0x91, 0x67, 0xD7, 0xFE, 0x71);
++SPCF_CPARAM_INIT(sect131r1, 0x03, 0xDB, 0x89, 0xB4, 0x05, 0xE4, 0x91, 0x16,
++		 0x0E, 0x3B, 0x2F, 0x07, 0xB0, 0xCE, 0x20, 0xB3, 0x7E);
++SPCF_CPARAM_INIT(sect131r2, 0x07, 0xCB, 0xB9, 0x92, 0x0D, 0x71, 0xA4, 0x8E,
++		 0x09, 0x9C, 0x38, 0xD7, 0x1D, 0xA6, 0x49, 0x0E, 0xB1);
++SPCF_CPARAM_INIT(sect163k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(sect163r1, 0x05, 0xED, 0x40, 0x3E, 0xD5, 0x8E, 0xB4, 0x5B,
++		 0x1C, 0xCE, 0xCA, 0x0F, 0x4F, 0x61, 0x65, 0x55, 0x49, 0x86,
++		 0x1B, 0xE0, 0x52);
++SPCF_CPARAM_INIT(sect163r2, 0x07, 0x2C, 0x4E, 0x1E, 0xF7, 0xCB, 0x2F, 0x3A,
++		 0x03, 0x5D, 0x33, 0x10, 0x42, 0x94, 0x15, 0x96, 0x09, 0x13,
++		 0x8B, 0xB4, 0x04);
++SPCF_CPARAM_INIT(sect193r1, 0x01, 0x67, 0xB3, 0x5E, 0xB4, 0x31, 0x3F, 0x26,
++		 0x3D, 0x0F, 0x7A, 0x3D, 0x50, 0x36, 0xF0, 0xA0, 0xA3, 0xC9,
++		 0x80, 0xD4, 0x0E, 0x5A, 0x05, 0x3E, 0xD2);
++SPCF_CPARAM_INIT(sect193r2, 0x00, 0x69, 0x89, 0xFE, 0x6B, 0xFE, 0x30, 0xED,
++		 0xDC, 0x32, 0x44, 0x26, 0x9F, 0x3A, 0xAD, 0x18, 0xD6, 0x6C,
++		 0xF3, 0xDB, 0x3E, 0x33, 0x02, 0xFA, 0xA8);
++SPCF_CPARAM_INIT(sect233k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x01);
++SPCF_CPARAM_INIT(sect233r1, 0x00, 0x07, 0xD5, 0xEF, 0x43, 0x89, 0xDF, 0xF1,
++		 0x1E, 0xCD, 0xBA, 0x39, 0xC3, 0x09, 0x70, 0xD3, 0xCE, 0x35,
++		 0xCE, 0xBB, 0xA5, 0x84, 0x73, 0xF6, 0x4B, 0x4D, 0xC0, 0xF2,
++		 0x68, 0x6C);
++SPCF_CPARAM_INIT(sect239k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x01);
++SPCF_CPARAM_INIT(sect283k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(sect283r1, 0x03, 0xD8, 0xC9, 0x3D, 0x3B, 0x0E, 0xA8, 0x1D,
++		 0x92, 0x94, 0x03, 0x4D, 0x7E, 0xE3, 0x13, 0x5D, 0x0A, 0xC5,
++		 0xFC, 0x8D, 0x9C, 0xB0, 0x27, 0x6F, 0x72, 0x11, 0xF8, 0x80,
++		 0xF0, 0xD8, 0x1C, 0xA4, 0xC6, 0xE8, 0x7B, 0x38);
++SPCF_CPARAM_INIT(sect409k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(sect409r1, 0x01, 0x49, 0xB8, 0xB7, 0xBE, 0xBD, 0x9B, 0x63,
++		 0x65, 0x3E, 0xF1, 0xCD, 0x8C, 0x6A, 0x5D, 0xD1, 0x05, 0xA2,
++		 0xAA, 0xAC, 0x36, 0xFE, 0x2E, 0xAE, 0x43, 0xCF, 0x28, 0xCE,
++		 0x1C, 0xB7, 0xC8, 0x30, 0xC1, 0xEC, 0xDB, 0xFA, 0x41, 0x3A,
++		 0xB0, 0x7F, 0xE3, 0x5A, 0x57, 0x81, 0x1A, 0xE4, 0xF8, 0x8D,
++		 0x30, 0xAC, 0x63, 0xFB);
++SPCF_CPARAM_INIT(sect571k1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(sect571r1, 0x06, 0x39, 0x5D, 0xB2, 0x2A, 0xB5, 0x94, 0xB1,
++		 0x86, 0x8C, 0xED, 0x95, 0x25, 0x78, 0xB6, 0x53, 0x9F, 0xAB,
++		 0xA6, 0x94, 0x06, 0xD9, 0xB2, 0x98, 0x61, 0x23, 0xA1, 0x85,
++		 0xC8, 0x58, 0x32, 0xE2, 0x5F, 0xD5, 0xB6, 0x38, 0x33, 0xD5,
++		 0x14, 0x42, 0xAB, 0xF1, 0xA9, 0xC0, 0x5F, 0xF0, 0xEC, 0xBD,
++		 0x88, 0xD7, 0xF7, 0x79, 0x97, 0xF4, 0xDC, 0x91, 0x56, 0xAA,
++		 0xF1, 0xCE, 0x08, 0x16, 0x46, 0x86, 0xDD, 0xFF, 0x75, 0x11,
++		 0x6F, 0xBC, 0x9A, 0x7A);
++SPCF_CPARAM_INIT(X9_62_c2pnb163v1, 0x04, 0x53, 0xE1, 0xE4, 0xB7, 0x29, 0x1F,
++		 0x5C, 0x2D, 0x53, 0xCE, 0x18, 0x48, 0x3F, 0x00, 0x70, 0x81,
++		 0xE7, 0xEA, 0x26, 0xEC);
++SPCF_CPARAM_INIT(X9_62_c2pnb163v2, 0x04, 0x35, 0xC0, 0x19, 0x66, 0x0E, 0x01,
++		 0x01, 0xBA, 0x87, 0x0C, 0xA3, 0x9F, 0xD9, 0xA7, 0x76, 0x86,
++		 0x50, 0x9D, 0x28, 0x13);
++SPCF_CPARAM_INIT(X9_62_c2pnb163v3, 0x06, 0x55, 0xC4, 0x54, 0xE4, 0x1E, 0x38,
++		 0x0C, 0x7A, 0x60, 0xB6, 0x67, 0x9A, 0x5B, 0x7A, 0x3F, 0x3A,
++		 0xF6, 0x8E, 0x22, 0xC5);
++SPCF_CPARAM_INIT(X9_62_c2pnb176v1, 0x00, 0x69, 0xF7, 0xDA, 0x36, 0x19, 0xA7,
++		 0x42, 0xA3, 0x82, 0xFF, 0x05, 0x08, 0x8F, 0xD3, 0x99, 0x42,
++		 0xCA, 0x0F, 0x1D, 0x90, 0xB6, 0x5B);
++SPCF_CPARAM_INIT(X9_62_c2tnb191v1, 0x4C, 0x45, 0x25, 0xAB, 0x0B, 0x68, 0x4A,
++		 0x64, 0x44, 0x62, 0x0A, 0x86, 0x45, 0xEF, 0x54, 0x6D, 0x54,
++		 0x69, 0x39, 0x68, 0xC2, 0xAE, 0x84, 0xAC);
++SPCF_CPARAM_INIT(X9_62_c2tnb191v2, 0x03, 0x7C, 0x8F, 0x57, 0xA2, 0x25, 0xC7,
++		 0xB3, 0xD4, 0xED, 0xD5, 0x88, 0x0F, 0x38, 0x0A, 0xCC, 0x55,
++		 0x74, 0xEC, 0xB3, 0x6C, 0x9F, 0x51, 0x21);
++SPCF_CPARAM_INIT(X9_62_c2tnb191v3, 0x37, 0x39, 0xFF, 0x98, 0xB4, 0xD1, 0x69,
++		 0x3E, 0xCF, 0x52, 0x7A, 0x98, 0x51, 0xED, 0xCF, 0x99, 0x9D,
++		 0x9E, 0x75, 0x05, 0x43, 0x33, 0x43, 0x24);
++SPCF_CPARAM_INIT(X9_62_c2pnb208w1, 0x00, 0xDB, 0x05, 0x3C, 0x41, 0x76, 0xCC,
++		 0x1D, 0xA1, 0x27, 0x85, 0x2C, 0xA6, 0xD9, 0x88, 0xBE, 0x1A,
++		 0xCC, 0xD1, 0x5B, 0x2A, 0xC1, 0xC1, 0x07, 0x42, 0x57, 0x34);
++SPCF_CPARAM_INIT(X9_62_c2tnb239v1, 0x24, 0x59, 0xFC, 0xF4, 0x51, 0x7B, 0xC5,
++		 0xA6, 0xB9, 0x9B, 0xE5, 0xC6, 0xC5, 0x62, 0x85, 0xC0, 0x21,
++		 0xFE, 0x32, 0xEE, 0x2B, 0x6F, 0x1C, 0x22, 0xEA, 0x5B, 0xE1,
++		 0xB8, 0x4B, 0x93);
++SPCF_CPARAM_INIT(X9_62_c2tnb239v2, 0x64, 0x98, 0x84, 0x19, 0x3B, 0x56, 0x2D,
++		 0x4A, 0x50, 0xB4, 0xFA, 0x56, 0x34, 0xE0, 0x34, 0x41, 0x3F,
++		 0x94, 0xC4, 0x59, 0xDA, 0x7C, 0xDB, 0x16, 0x64, 0x9D, 0xDD,
++		 0xF7, 0xE6, 0x0A);
++SPCF_CPARAM_INIT(X9_62_c2tnb239v3, 0x32, 0x63, 0x2E, 0x65, 0x2B, 0xEE, 0x91,
++		 0xC2, 0xE4, 0xA2, 0xF5, 0x42, 0xA3, 0x2D, 0x67, 0xA8, 0xB5,
++		 0xB4, 0x5F, 0x21, 0xA0, 0x81, 0x02, 0xFB, 0x1F, 0x2A, 0xFB,
++		 0xB6, 0xAC, 0xDA);
++SPCF_CPARAM_INIT(X9_62_c2pnb272w1, 0x00, 0xDA, 0x7B, 0x60, 0x28, 0xF4, 0xC8,
++		 0x09, 0xA0, 0xB9, 0x78, 0x81, 0xC3, 0xA5, 0x7E, 0x4D, 0x71,
++		 0x81, 0x34, 0xD1, 0x3F, 0xEC, 0xE0, 0x90, 0x85, 0x8A, 0xC3,
++		 0x1A, 0xE2, 0xDC, 0x2E, 0xDF, 0x8E, 0x3C, 0x8B);
++SPCF_CPARAM_INIT(X9_62_c2pnb304w1, 0x00, 0x3C, 0x67, 0xB4, 0x07, 0xC6, 0xF3,
++		 0x3F, 0x81, 0x0B, 0x17, 0xDC, 0x16, 0xE2, 0x14, 0x8A, 0x2C,
++		 0x9C, 0xE2, 0x9D, 0x56, 0x05, 0x23, 0x69, 0x6A, 0x55, 0x93,
++		 0x8A, 0x15, 0x40, 0x81, 0xE3, 0xE3, 0xAE, 0xFB, 0xCE, 0x45,
++		 0x70, 0xC9);
++SPCF_CPARAM_INIT(X9_62_c2tnb359v1, 0x22, 0x39, 0xAA, 0x58, 0x4A, 0xC5, 0x9A,
++		 0xF9, 0x61, 0xD0, 0xFA, 0x2D, 0x52, 0x85, 0xB6, 0xFD, 0xF7,
++		 0x34, 0x9B, 0xC6, 0x0E, 0x91, 0xE3, 0x20, 0xF4, 0x71, 0x64,
++		 0xCE, 0x11, 0xF5, 0x18, 0xEF, 0xB4, 0xC0, 0x8B, 0x9B, 0xDA,
++		 0x99, 0x9A, 0x8A, 0x37, 0xF8, 0x2A, 0x22, 0x61);
++SPCF_CPARAM_INIT(X9_62_c2pnb368w1, 0x00, 0xC0, 0x6C, 0xCF, 0x42, 0x89, 0x3A,
++		 0x8A, 0xAA, 0x00, 0x1E, 0x0B, 0xC0, 0xD2, 0xA2, 0x27, 0x66,
++		 0xEF, 0x3E, 0x41, 0x88, 0x7C, 0xC6, 0x77, 0x6F, 0x4A, 0x04,
++		 0x1E, 0xE4, 0x45, 0x14, 0xB2, 0x0A, 0xFC, 0x4E, 0x5C, 0x30,
++		 0x40, 0x60, 0x06, 0x5B, 0xC8, 0xD6, 0xCF, 0x04, 0xD3, 0x25);
++SPCF_CPARAM_INIT(X9_62_c2tnb431r1, 0x64, 0xF5, 0xBB, 0xE9, 0xBB, 0x31, 0x66,
++		 0xA3, 0xA0, 0x2F, 0x2F, 0x22, 0xBF, 0x05, 0xD9, 0xF7, 0xDA,
++		 0x43, 0xEE, 0x70, 0xC1, 0x79, 0x03, 0x15, 0x2B, 0x70, 0xA0,
++		 0xB4, 0x25, 0x9B, 0xD2, 0xFC, 0xB2, 0x20, 0x3B, 0x7F, 0xB8,
++		 0xD3, 0x39, 0x4E, 0x20, 0xEB, 0x0E, 0xA9, 0x84, 0xDD, 0xB1,
++		 0xE1, 0xF1, 0x4C, 0x67, 0xB1, 0x36, 0x2B);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls1, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls3, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls4, 0x01, 0x73, 0xE8, 0x34, 0xAF, 0x28,
++		 0xEC, 0x76, 0xCB, 0x83, 0xBD, 0x8D, 0xFE, 0xB2, 0xD5);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls5, 0x04, 0x53, 0xE1, 0xE4, 0xB7, 0x29,
++		 0x1F, 0x5C, 0x2D, 0x53, 0xCE, 0x18, 0x48, 0x3F, 0x00, 0x70,
++		 0x81, 0xE7, 0xEA, 0x26, 0xEC);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
++		 0x00, 0x00, 0x00, 0x01);
++SPCF_CPARAM_INIT(wap_wsg_idm_ecid_wtls11, 0x00, 0x07, 0xD5, 0xEF, 0x43, 0x89,
++		 0xDF, 0xF1, 0x1E, 0xCD, 0xBA, 0x39, 0xC3, 0x09, 0x70, 0xD3,
++		 0xCE, 0x35, 0xCE, 0xBB, 0xA5, 0x84, 0x73, 0xF6, 0x4B, 0x4D,
++		 0xC0, 0xF2, 0x68, 0x6C);
++/* Oakley curve #3 over 155 bit binary filed */
++SPCF_CPARAM_INIT(ipsec3, 0x00, 0x31, 0x10, 0x00, 0x00, 0x02, 0x23, 0xA0, 0x00,
++		 0xC4, 0x47, 0x40, 0x00, 0x08, 0x8E, 0x80, 0x00, 0x11, 0x1D,
++		 0x1D);
++/* Oakley curve #4 over 185 bit binary filed */
++SPCF_CPARAM_INIT(ipsec4, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00,
++		 0x01, 0x80, 0x00, 0xC0, 0x0C, 0x00, 0x00, 0x00, 0x63, 0x80,
++		 0x30, 0x00, 0x1C, 0x00, 0x09);
++
++static inline int
++eng_ec_get_cparam(int nid, unsigned char *buf, unsigned int buf_len)
++{
++	int ret = 0;
++	switch (nid) {
++		SPCF_CPARAM_CASE(sect113r1);
++		SPCF_CPARAM_CASE(sect113r2);
++		SPCF_CPARAM_CASE(sect131r1);
++		SPCF_CPARAM_CASE(sect131r2);
++		SPCF_CPARAM_CASE(sect163k1);
++		SPCF_CPARAM_CASE(sect163r1);
++		SPCF_CPARAM_CASE(sect163r2);
++		SPCF_CPARAM_CASE(sect193r1);
++		SPCF_CPARAM_CASE(sect193r2);
++		SPCF_CPARAM_CASE(sect233k1);
++		SPCF_CPARAM_CASE(sect233r1);
++		SPCF_CPARAM_CASE(sect239k1);
++		SPCF_CPARAM_CASE(sect283k1);
++		SPCF_CPARAM_CASE(sect283r1);
++		SPCF_CPARAM_CASE(sect409k1);
++		SPCF_CPARAM_CASE(sect409r1);
++		SPCF_CPARAM_CASE(sect571k1);
++		SPCF_CPARAM_CASE(sect571r1);
++		SPCF_CPARAM_CASE(X9_62_c2pnb163v1);
++		SPCF_CPARAM_CASE(X9_62_c2pnb163v2);
++		SPCF_CPARAM_CASE(X9_62_c2pnb163v3);
++		SPCF_CPARAM_CASE(X9_62_c2pnb176v1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb191v1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb191v2);
++		SPCF_CPARAM_CASE(X9_62_c2tnb191v3);
++		SPCF_CPARAM_CASE(X9_62_c2pnb208w1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb239v1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb239v2);
++		SPCF_CPARAM_CASE(X9_62_c2tnb239v3);
++		SPCF_CPARAM_CASE(X9_62_c2pnb272w1);
++		SPCF_CPARAM_CASE(X9_62_c2pnb304w1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb359v1);
++		SPCF_CPARAM_CASE(X9_62_c2pnb368w1);
++		SPCF_CPARAM_CASE(X9_62_c2tnb431r1);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls1);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls3);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls4);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls5);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls10);
++		SPCF_CPARAM_CASE(wap_wsg_idm_ecid_wtls11);
++		/* Oakley curve #3 over 155 bit binary filed */
++		SPCF_CPARAM_CASE(ipsec3);
++		/* Oakley curve #4 over 185 bit binary filed */
++		SPCF_CPARAM_CASE(ipsec4);
++	default:
++		ret = -EINVAL;
++		break;
++	}
++	return ret;
++}
++
++/* Copies the curve points to a flat buffer with appropriate padding */
++static inline unsigned char *eng_copy_curve_points(BIGNUM * x, BIGNUM * y,
++						   int xy_len, int crv_len)
++{
++	unsigned char *xy = NULL;
++	int len1 = 0, len2 = 0;
++
++	len1 = BN_num_bytes(x);
++	len2 = BN_num_bytes(y);
++
++	if (!(xy = malloc(xy_len))) {
++		return NULL;
++	}
++
++	memset(xy, 0, xy_len);
++
++	if (len1 < crv_len) {
++		if (!BN_is_zero(x))
++			BN_bn2bin(x, xy + (crv_len - len1));
++	}  else {
++		BN_bn2bin(x, xy);
++	}
++
++	if (len2 < crv_len) {
++		if (!BN_is_zero(y))
++			BN_bn2bin(y, xy+crv_len+(crv_len-len2));
++	} else {
++		BN_bn2bin(y, xy+crv_len);
++	}
++
++	return xy;
++}
++
++enum curve_t {
++	DISCRETE_LOG,
++	ECC_PRIME,
++	ECC_BINARY,
++	MAX_ECC_TYPE
++};
++#endif
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0003-add-support-for-TLS-algorithms-offload.patch b/recipes-connectivity/openssl/openssl-fsl/0003-add-support-for-TLS-algorithms-offload.patch
new file mode 100644
index 0000000..dd99ca9
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0003-add-support-for-TLS-algorithms-offload.patch
@@ -0,0 +1,296 @@
+From 1a8886909afc7e4c9e8539644c815baee8ee4816 Mon Sep 17 00:00:00 2001
+From: Cristian Stoica <cristian.stoica at freescale.com>
+Date: Thu, 29 Aug 2013 16:51:18 +0300
+Subject: [PATCH][fsl 03/15] add support for TLS algorithms offload
+
+Upstream-status: Pending
+
+Requires TLS patches on cryptodev and TLS algorithm support in Linux
+kernel driver.
+
+Signed-off-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |  204 ++++++++++++++++++++++++++++++++++++++---
+ 1 file changed, 193 insertions(+), 11 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 5a715ac..123613d 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -72,6 +72,9 @@ ENGINE_load_cryptodev(void)
+ struct dev_crypto_state {
+ 	struct session_op d_sess;
+ 	int d_fd;
++	unsigned char *aad;
++	unsigned int aad_len;
++	unsigned int len;
+ 
+ #ifdef USE_CRYPTODEV_DIGESTS
+ 	char dummy_mac_key[HASH_MAX_LEN];
+@@ -140,17 +143,19 @@ static struct {
+ 	int	nid;
+ 	int	ivmax;
+ 	int	keylen;
++	int	mackeylen;
+ } ciphers[] = {
+-	{ CRYPTO_ARC4,			NID_rc4,		0,	16, },
+-	{ CRYPTO_DES_CBC,		NID_des_cbc,		8,	 8, },
+-	{ CRYPTO_3DES_CBC,		NID_des_ede3_cbc,	8,	24, },
+-	{ CRYPTO_AES_CBC,		NID_aes_128_cbc,	16,	16, },
+-	{ CRYPTO_AES_CBC,		NID_aes_192_cbc,	16,	24, },
+-	{ CRYPTO_AES_CBC,		NID_aes_256_cbc,	16,	32, },
+-	{ CRYPTO_BLF_CBC,		NID_bf_cbc,		8,	16, },
+-	{ CRYPTO_CAST_CBC,		NID_cast5_cbc,		8,	16, },
+-	{ CRYPTO_SKIPJACK_CBC,		NID_undef,		0,	 0, },
+-	{ 0,				NID_undef,		0,	 0, },
++	{ CRYPTO_ARC4,          NID_rc4,          0,  16, 0},
++	{ CRYPTO_DES_CBC,       NID_des_cbc,	  8,  8,  0},
++	{ CRYPTO_3DES_CBC,      NID_des_ede3_cbc, 8,  24, 0},
++	{ CRYPTO_AES_CBC,       NID_aes_128_cbc,  16, 16, 0},
++	{ CRYPTO_AES_CBC,       NID_aes_192_cbc,  16, 24, 0},
++	{ CRYPTO_AES_CBC,       NID_aes_256_cbc,  16, 32, 0},
++	{ CRYPTO_BLF_CBC,       NID_bf_cbc,       8,  16, 0},
++	{ CRYPTO_CAST_CBC,      NID_cast5_cbc,    8,  16, 0},
++	{ CRYPTO_SKIPJACK_CBC,  NID_undef,        0,  0,  0},
++	{ CRYPTO_TLS10_AES_CBC_HMAC_SHA1, NID_aes_128_cbc_hmac_sha1, 16, 16, 20},
++	{ 0, NID_undef,	0, 0, 0},
+ };
+ 
+ #ifdef USE_CRYPTODEV_DIGESTS
+@@ -250,13 +255,15 @@ get_cryptodev_ciphers(const int **cnids)
+ 	}
+ 	memset(&sess, 0, sizeof(sess));
+ 	sess.key = (caddr_t)"123456789abcdefghijklmno";
++	sess.mackey = (caddr_t)"123456789ABCDEFGHIJKLMNO";
+ 
+ 	for (i = 0; ciphers[i].id && count < CRYPTO_ALGORITHM_MAX; i++) {
+ 		if (ciphers[i].nid == NID_undef)
+ 			continue;
+ 		sess.cipher = ciphers[i].id;
+ 		sess.keylen = ciphers[i].keylen;
+-		sess.mac = 0;
++		sess.mackeylen = ciphers[i].mackeylen;
++
+ 		if (ioctl(fd, CIOCGSESSION, &sess) != -1 &&
+ 		    ioctl(fd, CIOCFSESSION, &sess.ses) != -1)
+ 			nids[count++] = ciphers[i].nid;
+@@ -414,6 +421,67 @@ cryptodev_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ 	return (1);
+ }
+ 
++
++static int cryptodev_aead_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
++		const unsigned char *in, size_t len)
++{
++	struct crypt_auth_op cryp;
++	struct dev_crypto_state *state = ctx->cipher_data;
++	struct session_op *sess = &state->d_sess;
++	const void *iiv;
++	unsigned char save_iv[EVP_MAX_IV_LENGTH];
++
++	if (state->d_fd < 0)
++		return (0);
++	if (!len)
++		return (1);
++	if ((len % ctx->cipher->block_size) != 0)
++		return (0);
++
++	memset(&cryp, 0, sizeof(cryp));
++
++	/* TODO: make a seamless integration with cryptodev flags */
++	switch (ctx->cipher->nid) {
++	case NID_aes_128_cbc_hmac_sha1:
++		cryp.flags = COP_FLAG_AEAD_TLS_TYPE;
++	}
++	cryp.ses = sess->ses;
++	cryp.len = state->len;
++	cryp.dst_len = len;
++	cryp.src = (caddr_t) in;
++	cryp.dst = (caddr_t) out;
++	cryp.auth_src = state->aad;
++	cryp.auth_len = state->aad_len;
++
++	cryp.op = ctx->encrypt ? COP_ENCRYPT : COP_DECRYPT;
++
++	if (ctx->cipher->iv_len) {
++		cryp.iv = (caddr_t) ctx->iv;
++		if (!ctx->encrypt) {
++			iiv = in + len - ctx->cipher->iv_len;
++			memcpy(save_iv, iiv, ctx->cipher->iv_len);
++		}
++	} else
++		cryp.iv = NULL;
++
++	if (ioctl(state->d_fd, CIOCAUTHCRYPT, &cryp) == -1) {
++		/* XXX need better errror handling
++		 * this can fail for a number of different reasons.
++		 */
++		return (0);
++	}
++
++	if (ctx->cipher->iv_len) {
++		if (ctx->encrypt)
++			iiv = out + len - ctx->cipher->iv_len;
++		else
++			iiv = save_iv;
++		memcpy(ctx->iv, iiv, ctx->cipher->iv_len);
++	}
++	return (1);
++}
++
++
+ static int
+ cryptodev_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
+     const unsigned char *iv, int enc)
+@@ -452,6 +520,45 @@ cryptodev_init_key(EVP_CIPHER_CTX *ctx, const unsigned char *key,
+ 	return (1);
+ }
+ 
++/* Save the encryption key provided by upper layers.
++ *
++ * This function is called by EVP_CipherInit_ex to initialize the algorithm's
++ * extra data. We can't do much here because the mac key is not available.
++ * The next call should/will be to cryptodev_cbc_hmac_sha1_ctrl with parameter
++ * EVP_CTRL_AEAD_SET_MAC_KEY, to set the hmac key. There we call CIOCGSESSION
++ * with both the crypto and hmac keys.
++ */
++static int cryptodev_init_aead_key(EVP_CIPHER_CTX *ctx,
++		const unsigned char *key, const unsigned char *iv, int enc)
++{
++	struct dev_crypto_state *state = ctx->cipher_data;
++	struct session_op *sess = &state->d_sess;
++	int cipher = -1, i;
++
++	for (i = 0; ciphers[i].id; i++)
++		if (ctx->cipher->nid == ciphers[i].nid &&
++		    ctx->cipher->iv_len <= ciphers[i].ivmax &&
++		    ctx->key_len == ciphers[i].keylen) {
++			cipher = ciphers[i].id;
++			break;
++		}
++
++	if (!ciphers[i].id) {
++		state->d_fd = -1;
++		return (0);
++	}
++
++	memset(sess, 0, sizeof(struct session_op));
++
++	sess->key = (caddr_t)key;
++	sess->keylen = ctx->key_len;
++	sess->cipher = cipher;
++
++	/* for whatever reason, (1) means success */
++	return (1);
++}
++
++
+ /*
+  * free anything we allocated earlier when initting a
+  * session, and close the session.
+@@ -488,6 +595,63 @@ cryptodev_cleanup(EVP_CIPHER_CTX *ctx)
+ 	return (ret);
+ }
+ 
++static int cryptodev_cbc_hmac_sha1_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
++		void *ptr)
++{
++	switch (type) {
++	case EVP_CTRL_AEAD_SET_MAC_KEY:
++	{
++		/* TODO: what happens with hmac keys larger than 64 bytes? */
++		struct dev_crypto_state *state = ctx->cipher_data;
++		struct session_op *sess = &state->d_sess;
++
++		if ((state->d_fd = get_dev_crypto()) < 0)
++			return (0);
++
++		/* the rest should have been set in cryptodev_init_aead_key */
++		sess->mackey = ptr;
++		sess->mackeylen = arg;
++
++		if (ioctl(state->d_fd, CIOCGSESSION, sess) == -1) {
++			put_dev_crypto(state->d_fd);
++			state->d_fd = -1;
++			return (0);
++		}
++		return (1);
++	}
++	case EVP_CTRL_AEAD_TLS1_AAD:
++	{
++		/* ptr points to the associated data buffer of 13 bytes */
++		struct dev_crypto_state *state = ctx->cipher_data;
++		unsigned char *p = ptr;
++		unsigned int cryptlen = p[arg - 2] << 8 | p[arg - 1];
++		unsigned int maclen, padlen;
++		unsigned int bs = ctx->cipher->block_size;
++		int j;
++
++		state->aad = ptr;
++		state->aad_len = arg;
++		state->len = cryptlen;
++
++		/* TODO: this should be an extension of EVP_CIPHER struct */
++		switch (ctx->cipher->nid) {
++		case NID_aes_128_cbc_hmac_sha1:
++			maclen = SHA_DIGEST_LENGTH;
++		}
++
++		/* space required for encryption (not only TLS padding) */
++		padlen = maclen;
++		if (ctx->encrypt) {
++			cryptlen += maclen;
++			padlen += bs - (cryptlen % bs);
++		}
++		return padlen;
++	}
++	default:
++		return -1;
++	}
++}
++
+ /*
+  * libcrypto EVP stuff - this is how we get wired to EVP so the engine
+  * gets called when libcrypto requests a cipher NID.
+@@ -600,6 +764,20 @@ const EVP_CIPHER cryptodev_aes_256_cbc = {
+ 	NULL
+ };
+ 
++const EVP_CIPHER cryptodev_aes_128_cbc_hmac_sha1 = {
++	NID_aes_128_cbc_hmac_sha1,
++	16, 16, 16,
++	EVP_CIPH_CBC_MODE | EVP_CIPH_FLAG_AEAD_CIPHER,
++	cryptodev_init_aead_key,
++	cryptodev_aead_cipher,
++	cryptodev_cleanup,
++	sizeof(struct dev_crypto_state),
++	EVP_CIPHER_set_asn1_iv,
++	EVP_CIPHER_get_asn1_iv,
++	cryptodev_cbc_hmac_sha1_ctrl,
++	NULL
++};
++
+ /*
+  * Registered by the ENGINE when used to find out how to deal with
+  * a particular NID in the ENGINE. this says what we'll do at the
+@@ -637,6 +815,9 @@ cryptodev_engine_ciphers(ENGINE *e, const EVP_CIPHER **cipher,
+ 	case NID_aes_256_cbc:
+ 		*cipher = &cryptodev_aes_256_cbc;
+ 		break;
++	case NID_aes_128_cbc_hmac_sha1:
++		*cipher = &cryptodev_aes_128_cbc_hmac_sha1;
++		break;
+ 	default:
+ 		*cipher = NULL;
+ 		break;
+@@ -1384,6 +1565,7 @@ ENGINE_load_cryptodev(void)
+ 	}
+ 	put_dev_crypto(fd);
+ 
++	EVP_add_cipher(&cryptodev_aes_128_cbc_hmac_sha1);
+ 	if (!ENGINE_set_id(engine, "cryptodev") ||
+ 	    !ENGINE_set_name(engine, "BSD cryptodev engine") ||
+ 	    !ENGINE_set_ciphers(engine, cryptodev_engine_ciphers) ||
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0004-Fixed-private-key-support-for-DH.patch b/recipes-connectivity/openssl/openssl-fsl/0004-Fixed-private-key-support-for-DH.patch
new file mode 100644
index 0000000..607f603
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0004-Fixed-private-key-support-for-DH.patch
@@ -0,0 +1,33 @@
+From c994fa6c5eb9b684dd6aff45dd5e8eb98237c31e Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 11 Mar 2014 05:57:47 +0545
+Subject: [PATCH][fsl 04/15] Fixed private key support for DH
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ crypto/dh/dh_ameth.c |    7 +++++++
+ 1 file changed, 7 insertions(+)
+
+diff --git a/crypto/dh/dh_ameth.c b/crypto/dh/dh_ameth.c
+index 02ec2d4..ed32004 100644
+--- a/crypto/dh/dh_ameth.c
++++ b/crypto/dh/dh_ameth.c
+@@ -422,6 +422,13 @@ static int dh_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from)
+ 	if (to->pkey.dh->g != NULL)
+ 		BN_free(to->pkey.dh->g);
+ 	to->pkey.dh->g=a;
++	if ((a=BN_dup(from->pkey.dh->q)) != NULL) {
++		if (to->pkey.dh->q != NULL)
++			BN_free(to->pkey.dh->q);
++		to->pkey.dh->q=a;
++	}
++
++	to->pkey.dh->length = from->pkey.dh->length;
+ 
+ 	return 1;
+ 	}
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0005-Fixed-private-key-support-for-DH.patch b/recipes-connectivity/openssl/openssl-fsl/0005-Fixed-private-key-support-for-DH.patch
new file mode 100644
index 0000000..06dff88
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0005-Fixed-private-key-support-for-DH.patch
@@ -0,0 +1,35 @@
+From 408bdb2a3971edd6a949f5a93bd44d0a6f3eb823 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Thu, 20 Mar 2014 19:55:51 -0500
+Subject: [PATCH][fsl 05/15] Fixed private key support for DH
+
+Upstream-status: Pending
+
+Required Length of the DH result is not returned in dh method in openssl
+
+Tested-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ crypto/dh/dh_ameth.c |    7 -------
+ 1 file changed, 7 deletions(-)
+
+diff --git a/crypto/dh/dh_ameth.c b/crypto/dh/dh_ameth.c
+index ed32004..02ec2d4 100644
+--- a/crypto/dh/dh_ameth.c
++++ b/crypto/dh/dh_ameth.c
+@@ -422,13 +422,6 @@ static int dh_copy_parameters(EVP_PKEY *to, const EVP_PKEY *from)
+ 	if (to->pkey.dh->g != NULL)
+ 		BN_free(to->pkey.dh->g);
+ 	to->pkey.dh->g=a;
+-	if ((a=BN_dup(from->pkey.dh->q)) != NULL) {
+-		if (to->pkey.dh->q != NULL)
+-			BN_free(to->pkey.dh->q);
+-		to->pkey.dh->q=a;
+-	}
+-
+-	to->pkey.dh->length = from->pkey.dh->length;
+ 
+ 	return 1;
+ 	}
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0006-Initial-support-for-PKC-in-cryptodev-engine.patch b/recipes-connectivity/openssl/openssl-fsl/0006-Initial-support-for-PKC-in-cryptodev-engine.patch
new file mode 100644
index 0000000..b5ac55d
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0006-Initial-support-for-PKC-in-cryptodev-engine.patch
@@ -0,0 +1,1563 @@
+From 8e9a39aab2fce48c117460eb1d14bcc02be6de6c Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 11 Mar 2014 06:29:52 +0545
+Subject: [PATCH][fsl 06/15] Initial support for PKC in cryptodev engine
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c | 1343 ++++++++++++++++++++++++++++++++++++-----
+ 1 file changed, 1183 insertions(+), 160 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 123613d..88caec1 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -54,11 +54,14 @@ ENGINE_load_cryptodev(void)
+ #else 
+  
+ #include <sys/types.h>
+-#include <crypto/cryptodev.h>
+ #include <crypto/dh/dh.h>
+ #include <crypto/dsa/dsa.h>
+ #include <crypto/err/err.h>
+ #include <crypto/rsa/rsa.h>
++#include <crypto/ecdsa/ecs_locl.h>
++#include <crypto/ecdh/ech_locl.h>
++#include <crypto/ec/ec_lcl.h>
++#include <crypto/ec/ec.h>
+ #include <sys/ioctl.h>
+ #include <errno.h>
+ #include <stdio.h>
+@@ -68,6 +71,8 @@ ENGINE_load_cryptodev(void)
+ #include <syslog.h>
+ #include <errno.h>
+ #include <string.h>
++#include "eng_cryptodev_ec.h"
++#include <crypto/cryptodev.h>
+ 
+ struct dev_crypto_state {
+ 	struct session_op d_sess;
+@@ -116,24 +121,112 @@ static int cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a,
+ static int cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I,
+     RSA *rsa, BN_CTX *ctx);
+ static int cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx);
+-static int cryptodev_dsa_bn_mod_exp(DSA *dsa, BIGNUM *r, BIGNUM *a,
+-    const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx);
+-static int cryptodev_dsa_dsa_mod_exp(DSA *dsa, BIGNUM *t1, BIGNUM *g,
+-    BIGNUM *u1, BIGNUM *pub_key, BIGNUM *u2, BIGNUM *p,
+-    BN_CTX *ctx, BN_MONT_CTX *mont);
+ static DSA_SIG *cryptodev_dsa_do_sign(const unsigned char *dgst,
+     int dlen, DSA *dsa);
+ static int cryptodev_dsa_verify(const unsigned char *dgst, int dgst_len,
+     DSA_SIG *sig, DSA *dsa);
+-static int cryptodev_mod_exp_dh(const DH *dh, BIGNUM *r, const BIGNUM *a,
+-    const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx,
+-    BN_MONT_CTX *m_ctx);
+ static int cryptodev_dh_compute_key(unsigned char *key,
+     const BIGNUM *pub_key, DH *dh);
+ static int cryptodev_ctrl(ENGINE *e, int cmd, long i, void *p,
+     void (*f)(void));
+ void ENGINE_load_cryptodev(void);
+ 
++inline int spcf_bn2bin(BIGNUM *bn, unsigned char **bin,  int *bin_len)
++{
++	int len;
++	unsigned char *p;
++
++	len = BN_num_bytes(bn);
++
++	if (!len)
++		return -1;
++
++	p = malloc(len);
++	if (!p)
++		return -1;
++
++	BN_bn2bin(bn,p);
++
++	*bin = p;
++	*bin_len = len;
++
++	return 0;
++}
++
++inline int spcf_bn2bin_ex(BIGNUM *bn, unsigned char **bin,  int *bin_len)
++{
++	int len;
++	unsigned char *p;
++
++	len = BN_num_bytes(bn);
++
++	if (!len)
++		return -1;
++
++	if (len < *bin_len)
++		p = malloc(*bin_len);
++	else
++		p = malloc(len);
++
++	if (!p)
++		return -ENOMEM;
++
++	if (len < *bin_len) {
++		/* place padding */
++		memset(p, 0, (*bin_len - len));
++		BN_bn2bin(bn,p+(*bin_len-len));
++	} else {
++		BN_bn2bin(bn,p);
++	}
++
++	*bin = p;
++	if (len >= *bin_len)
++		*bin_len = len;
++
++	return 0;
++}
++
++/**
++ * Convert an ECC F2m 'b' parameter into the 'c' parameter.
++ *Inputs:
++ * q, the curve's modulus
++ * b, the curve's b parameter
++ * (a bignum for b, a buffer for c)
++ * Output:
++ * c, written into bin, right-adjusted to fill q_len bytes.
++ */
++static int
++eng_ec_compute_cparam(const BIGNUM* b, const BIGNUM* q,
++			unsigned char **bin, int *bin_len)
++{
++	BIGNUM* c = BN_new();
++	BIGNUM* exp = BN_new();
++	BN_CTX *ctx = BN_CTX_new();
++	int m = BN_num_bits(q) - 1;
++	int ok = 0;
++
++	if (!c || !exp || !ctx || *bin)
++		goto err;
++
++	/*
++	 * We have to compute c, where b = c^4, i.e., the fourth root of b.
++	 * The equation for c is c = b^(2^(m-2))
++	 * Compute exp = 2^(m-2)
++	 * (1 << x) == 2^x
++	 * and then compute c = b^exp
++	 */
++	BN_lshift(exp, BN_value_one(), m-2);
++	BN_GF2m_mod_exp(c, b, exp, q, ctx);
++	/* Store c */
++	spcf_bn2bin_ex(c, bin, bin_len);
++	ok = 1;
++err:
++	if (ctx) BN_CTX_free(ctx);
++	if (c) BN_free(c);
++	if (exp) BN_free(exp);
++	return ok;
++}
++
+ static const ENGINE_CMD_DEFN cryptodev_defns[] = {
+ 	{ 0, NULL, NULL, 0 }
+ };
+@@ -1106,7 +1199,6 @@ cryptodev_engine_digests(ENGINE *e, const EVP_MD **digest,
+ static int
+ bn2crparam(const BIGNUM *a, struct crparam *crp)
+ {
+-	int i, j, k;
+ 	ssize_t bytes, bits;
+ 	u_char *b;
+ 
+@@ -1123,15 +1215,7 @@ bn2crparam(const BIGNUM *a, struct crparam *crp)
+ 
+ 	crp->crp_p = (caddr_t) b;
+ 	crp->crp_nbits = bits;
+-
+-	for (i = 0, j = 0; i < a->top; i++) {
+-		for (k = 0; k < BN_BITS2 / 8; k++) {
+-			if ((j + k) >= bytes)
+-				return (0);
+-			b[j + k] = a->d[i] >> (k * 8);
+-		}
+-		j += BN_BITS2 / 8;
+-	}
++	BN_bn2bin(a, crp->crp_p);
+ 	return (0);
+ }
+ 
+@@ -1139,22 +1223,14 @@ bn2crparam(const BIGNUM *a, struct crparam *crp)
+ static int
+ crparam2bn(struct crparam *crp, BIGNUM *a)
+ {
+-	u_int8_t *pd;
+-	int i, bytes;
++	int bytes;
+ 
+ 	bytes = (crp->crp_nbits + 7) / 8;
+ 
+ 	if (bytes == 0)
+ 		return (-1);
+ 
+-	if ((pd = (u_int8_t *) malloc(bytes)) == NULL)
+-		return (-1);
+-
+-	for (i = 0; i < bytes; i++)
+-		pd[i] = crp->crp_p[bytes - i - 1];
+-
+-	BN_bin2bn(pd, bytes, a);
+-	free(pd);
++	BN_bin2bn(crp->crp_p, bytes, a);
+ 
+ 	return (0);
+ }
+@@ -1202,6 +1278,32 @@ cryptodev_asym(struct crypt_kop *kop, int rlen, BIGNUM *r, int slen, BIGNUM *s)
+ 	return (ret);
+ }
+ 
++/* Close an opened instance of cryptodev engine */
++void cryptodev_close_instance(void *handle)
++{
++	int fd;
++
++	if (handle) {
++		fd = *(int *)handle;
++		close(fd);
++		free(handle);
++	}
++}
++
++/* Create an instance of cryptodev for asynchronous interface */
++void *cryptodev_init_instance(void)
++{
++	int *fd = malloc(sizeof(int));
++
++	if (fd) {
++		if ((*fd = open("/dev/crypto", O_RDWR, 0)) == -1) {
++			free(fd);
++			return NULL;
++		}
++	}
++	return fd;
++}
++
+ static int
+ cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+     const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *in_mont)
+@@ -1217,9 +1319,9 @@ cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+ 		return (ret);
+ 	}
+ 
+-	memset(&kop, 0, sizeof kop);
+ 	kop.crk_op = CRK_MOD_EXP;
+-
++	kop.crk_oparams = 0;
++	kop.crk_status = 0;
+ 	/* inputs: a^p % m */
+ 	if (bn2crparam(a, &kop.crk_param[0]))
+ 		goto err;
+@@ -1260,28 +1362,38 @@ static int
+ cryptodev_rsa_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
+ {
+ 	struct crypt_kop kop;
+-	int ret = 1;
++	int ret = 1, f_len, p_len, q_len;
++	unsigned char *f = NULL, *p = NULL, *q = NULL, *dp = NULL, *dq = NULL, *c = NULL;
+ 
+ 	if (!rsa->p || !rsa->q || !rsa->dmp1 || !rsa->dmq1 || !rsa->iqmp) {
+ 		/* XXX 0 means failure?? */
+ 		return (0);
+ 	}
+ 
+-	memset(&kop, 0, sizeof kop);
++	kop.crk_oparams = 0;
++	kop.crk_status = 0;
+ 	kop.crk_op = CRK_MOD_EXP_CRT;
++	f_len = BN_num_bytes(rsa->n);
++	spcf_bn2bin_ex(I, &f, &f_len);
++	spcf_bn2bin(rsa->p, &p, &p_len);
++	spcf_bn2bin(rsa->q, &q, &q_len);
++	spcf_bn2bin_ex(rsa->dmp1, &dp, &p_len);
++	spcf_bn2bin_ex(rsa->iqmp, &c, &p_len);
++	spcf_bn2bin_ex(rsa->dmq1, &dq, &q_len);
+ 	/* inputs: rsa->p rsa->q I rsa->dmp1 rsa->dmq1 rsa->iqmp */
+-	if (bn2crparam(rsa->p, &kop.crk_param[0]))
+-		goto err;
+-	if (bn2crparam(rsa->q, &kop.crk_param[1]))
+-		goto err;
+-	if (bn2crparam(I, &kop.crk_param[2]))
+-		goto err;
+-	if (bn2crparam(rsa->dmp1, &kop.crk_param[3]))
+-		goto err;
+-	if (bn2crparam(rsa->dmq1, &kop.crk_param[4]))
+-		goto err;
+-	if (bn2crparam(rsa->iqmp, &kop.crk_param[5]))
+-		goto err;
++	kop.crk_param[0].crp_p = p;
++	kop.crk_param[0].crp_nbits = p_len * 8;
++	kop.crk_param[1].crp_p = q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = f;
++	kop.crk_param[2].crp_nbits = f_len * 8;
++	kop.crk_param[3].crp_p = dp;
++	kop.crk_param[3].crp_nbits = p_len * 8;
++	/* dq must of length q, rest all of length p*/
++	kop.crk_param[4].crp_p = dq;
++	kop.crk_param[4].crp_nbits = q_len * 8;
++	kop.crk_param[5].crp_p = c;
++	kop.crk_param[5].crp_nbits = p_len * 8;
+ 	kop.crk_iparams = 6;
+ 
+ 	if (cryptodev_asym(&kop, BN_num_bytes(rsa->n), r0, 0, NULL)) {
+@@ -1317,90 +1429,117 @@ static RSA_METHOD cryptodev_rsa = {
+ 	NULL				/* rsa_verify */
+ };
+ 
+-static int
+-cryptodev_dsa_bn_mod_exp(DSA *dsa, BIGNUM *r, BIGNUM *a, const BIGNUM *p,
+-    const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *m_ctx)
+-{
+-	return (cryptodev_bn_mod_exp(r, a, p, m, ctx, m_ctx));
+-}
+-
+-static int
+-cryptodev_dsa_dsa_mod_exp(DSA *dsa, BIGNUM *t1, BIGNUM *g,
+-    BIGNUM *u1, BIGNUM *pub_key, BIGNUM *u2, BIGNUM *p,
+-    BN_CTX *ctx, BN_MONT_CTX *mont)
++static DSA_SIG *
++cryptodev_dsa_do_sign(const unsigned char *dgst, int dlen, DSA *dsa)
+ {
+-	BIGNUM t2;
+-	int ret = 0;
+-
+-	BN_init(&t2);
+-
+-	/* v = ( g^u1 * y^u2 mod p ) mod q */
+-	/* let t1 = g ^ u1 mod p */
+-	ret = 0;
++	struct crypt_kop kop;
++	BIGNUM *c = NULL, *d = NULL;
++	DSA_SIG *dsaret = NULL;
++	int q_len = 0, r_len = 0, g_len = 0;
++	int priv_key_len = 0, ret;
++	unsigned char *q = NULL, *r = NULL, *g = NULL, *priv_key = NULL, *f = NULL;
+ 
+-	if (!dsa->meth->bn_mod_exp(dsa,t1,dsa->g,u1,dsa->p,ctx,mont))
++	memset(&kop, 0, sizeof kop);
++	if ((c = BN_new()) == NULL) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
++	}
+ 
+-	/* let t2 = y ^ u2 mod p */
+-	if (!dsa->meth->bn_mod_exp(dsa,&t2,dsa->pub_key,u2,dsa->p,ctx,mont))
++	if ((d = BN_new()) == NULL) {
++		BN_free(c);
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	/* let u1 = t1 * t2 mod p */
+-	if (!BN_mod_mul(u1,t1,&t2,dsa->p,ctx))
++	}
++
++	if (spcf_bn2bin(dsa->p, &q, &q_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE);
+ 		goto err;
++	}
+ 
+-	BN_copy(t1,u1);
++	/* Get order of the field of private keys into plain buffer */
++	if (spcf_bn2bin (dsa->q, &r, &r_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
+ 
+-	ret = 1;
+-err:
+-	BN_free(&t2);
+-	return(ret);
+-}
++	/* sanity test */
++	if (dlen > r_len) {
++		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE);
++		goto err;
++	}
+ 
+-static DSA_SIG *
+-cryptodev_dsa_do_sign(const unsigned char *dgst, int dlen, DSA *dsa)
+-{
+-	struct crypt_kop kop;
+-	BIGNUM *r = NULL, *s = NULL;
+-	DSA_SIG *dsaret = NULL;
++	g_len = q_len;
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
+ 
+-	if ((r = BN_new()) == NULL)
++	priv_key_len = r_len;
++	/**
++	 * Get private key into a plain buffer. If length is less than
++	 * r_len then add leading padding bytes.
++	 */
++	 if (spcf_bn2bin_ex(dsa->priv_key, &priv_key, &priv_key_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if ((s = BN_new()) == NULL) {
+-		BN_free(r);
++	}
++
++	/* Allocate memory to store hash. */
++	f = OPENSSL_malloc (r_len);
++	if (!f) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+ 	}
+ 
+-	memset(&kop, 0, sizeof kop);
++	/* Add padding, since SEC expects hash to of size r_len */
++	if (dlen < r_len)
++		memset(f, 0, r_len - dlen);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len - dlen, dgst, dlen);
++
+ 	kop.crk_op = CRK_DSA_SIGN;
+ 
+ 	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
+-	kop.crk_param[0].crp_p = (caddr_t)dgst;
+-	kop.crk_param[0].crp_nbits = dlen * 8;
+-	if (bn2crparam(dsa->p, &kop.crk_param[1]))
+-		goto err;
+-	if (bn2crparam(dsa->q, &kop.crk_param[2]))
+-		goto err;
+-	if (bn2crparam(dsa->g, &kop.crk_param[3]))
+-		goto err;
+-	if (bn2crparam(dsa->priv_key, &kop.crk_param[4]))
+-		goto err;
++	kop.crk_param[0].crp_p = (void*)f;
++	kop.crk_param[0].crp_nbits = r_len * 8;
++	kop.crk_param[1].crp_p = (void*)q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = (void*)r;
++	kop.crk_param[2].crp_nbits = r_len * 8;
++	kop.crk_param[3].crp_p = (void*)g;
++	kop.crk_param[3].crp_nbits = g_len * 8;
++	kop.crk_param[4].crp_p = (void*)priv_key;
++	kop.crk_param[4].crp_nbits = priv_key_len * 8;
+ 	kop.crk_iparams = 5;
+ 
+-	if (cryptodev_asym(&kop, BN_num_bytes(dsa->q), r,
+-	    BN_num_bytes(dsa->q), s) == 0) {
+-		dsaret = DSA_SIG_new();
+-		dsaret->r = r;
+-		dsaret->s = s;
+-	} else {
+-		const DSA_METHOD *meth = DSA_OpenSSL();
+-		BN_free(r);
+-		BN_free(s);
+-		dsaret = (meth->dsa_do_sign)(dgst, dlen, dsa);
++	ret = cryptodev_asym(&kop, r_len, c, r_len, d);
++
++	if (ret) {
++		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_DECODE_ERROR);
++		goto err;
+ 	}
+-err:
+-	kop.crk_param[0].crp_p = NULL;
++
++	dsaret = DSA_SIG_new();
++	dsaret->r = c;
++	dsaret->s = d;
++
+ 	zapparams(&kop);
+ 	return (dsaret);
++err:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++		if (c)
++			BN_free(c);
++		if (d)
++			BN_free(d);
++		dsaret = (meth->dsa_do_sign)(dgst, dlen, dsa);
++		return (dsaret);
++	}
+ }
+ 
+ static int
+@@ -1408,42 +1547,179 @@ cryptodev_dsa_verify(const unsigned char *dgst, int dlen,
+     DSA_SIG *sig, DSA *dsa)
+ {
+ 	struct crypt_kop kop;
+-	int dsaret = 1;
++	int dsaret = 1, q_len = 0, r_len = 0, g_len = 0;
++	int w_len = 0 ,c_len = 0, d_len = 0, ret = -1;
++	unsigned char   * q = NULL, * r = NULL, * w = NULL, * g = NULL;
++	unsigned char   * c = NULL, * d = NULL, *f = NULL;
+ 
+ 	memset(&kop, 0, sizeof kop);
+ 	kop.crk_op = CRK_DSA_VERIFY;
+ 
+-	/* inputs: dgst dsa->p dsa->q dsa->g dsa->pub_key sig->r sig->s */
+-	kop.crk_param[0].crp_p = (caddr_t)dgst;
+-	kop.crk_param[0].crp_nbits = dlen * 8;
+-	if (bn2crparam(dsa->p, &kop.crk_param[1]))
++	if (spcf_bn2bin(dsa->p, &q, &q_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		return ret;
++	}
++
++	/* Get Order of field of private keys */
++	if (spcf_bn2bin(dsa->q, &r, &r_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(dsa->q, &kop.crk_param[2]))
++	}
++
++	g_len = q_len;
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(dsa->g, &kop.crk_param[3]))
++	}
++	w_len = q_len;
++	/**
++	 * Get public key into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->pub_key, &w, &w_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++	/**
++	 * Get the 1st part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	c_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->r, &c, &c_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(dsa->pub_key, &kop.crk_param[4]))
++	}
++
++	/**
++	 * Get the 2nd part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	d_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(sig->r, &kop.crk_param[5]))
++	}
++
++
++	/* Sanity test */
++	if (dlen > r_len) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(sig->s, &kop.crk_param[6]))
++	}
++
++	/* Allocate memory to store hash. */
++	f = OPENSSL_malloc (r_len);
++	if (!f) {
++		DSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+ 		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	if (dlen < r_len)
++		memset(f, 0, r_len - dlen);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len - dlen, dgst, dlen);
++
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->pub_key sig->r sig->s */
++	kop.crk_param[0].crp_p = (void*)f;
++	kop.crk_param[0].crp_nbits = r_len * 8;
++	kop.crk_param[1].crp_p = q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = r;
++	kop.crk_param[2].crp_nbits = r_len * 8;
++	kop.crk_param[3].crp_p = g;
++	kop.crk_param[3].crp_nbits = g_len * 8;
++	kop.crk_param[4].crp_p = w;
++	kop.crk_param[4].crp_nbits = w_len * 8;
++	kop.crk_param[5].crp_p = c;
++	kop.crk_param[5].crp_nbits = c_len * 8;
++	kop.crk_param[6].crp_p = d;
++	kop.crk_param[6].crp_nbits = d_len * 8;
+ 	kop.crk_iparams = 7;
+ 
+-	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
+-/*OCF success value is 0, if not zero, change dsaret to fail*/
+-		if(0 != kop.crk_status) dsaret  = 0;
+-	} else {
+-		const DSA_METHOD *meth = DSA_OpenSSL();
++	if ((cryptodev_asym(&kop, 0, NULL, 0, NULL))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, DSA_R_DECODE_ERROR);
++		goto err;
++	}
+ 
+-		dsaret = (meth->dsa_do_verify)(dgst, dlen, sig, dsa);
++	/*OCF success value is 0, if not zero, change dsaret to fail*/
++	if(0 != kop.crk_status) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, DSA_R_DECODE_ERROR);
++		goto err;
+ 	}
+-err:
+-	kop.crk_param[0].crp_p = NULL;
++
+ 	zapparams(&kop);
+ 	return (dsaret);
++err:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++
++		dsaret = (meth->dsa_do_verify)(dgst, dlen, sig, dsa);
++	}
++	return dsaret;
+ }
+ 
++/* Cryptodev DSA Key Gen routine */
++static int cryptodev_dsa_keygen(DSA *dsa)
++{
++	struct crypt_kop kop;
++	int ret = 1, g_len;
++	unsigned char *g = NULL;
++
++	if (dsa->priv_key == NULL)	{
++		if ((dsa->priv_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	if (dsa->pub_key == NULL) {
++		if ((dsa->pub_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	g_len = BN_num_bytes(dsa->p);
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * p_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
++
++	memset(&kop, 0, sizeof kop);
++
++	kop.crk_op = CRK_DSA_GENERATE_KEY;
++	if (bn2crparam(dsa->p, &kop.crk_param[0]))
++		goto sw_try;
++	if (bn2crparam(dsa->q, &kop.crk_param[1]))
++		goto sw_try;
++	kop.crk_param[2].crp_p = g;
++	kop.crk_param[2].crp_nbits = g_len * 8;
++	kop.crk_iparams = 3;
++
++	/* pub_key is or prime length while priv key is of length of order */
++	if (cryptodev_asym(&kop, BN_num_bytes(dsa->p), dsa->pub_key,
++	    BN_num_bytes(dsa->q), dsa->priv_key))
++	    goto sw_try;
++
++	return ret;
++sw_try:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++		ret = (meth->dsa_keygen)(dsa);
++	}
++	return ret;
++}
++
++
++
+ static DSA_METHOD cryptodev_dsa = {
+ 	"cryptodev DSA method",
+ 	NULL,
+@@ -1457,12 +1733,543 @@ static DSA_METHOD cryptodev_dsa = {
+ 	NULL	/* app_data */
+ };
+ 
+-static int
+-cryptodev_mod_exp_dh(const DH *dh, BIGNUM *r, const BIGNUM *a,
+-    const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx,
+-    BN_MONT_CTX *m_ctx)
++static ECDSA_METHOD cryptodev_ecdsa = {
++	"cryptodev ECDSA method",
++	NULL,
++	NULL,				/* ecdsa_sign_setup */
++	NULL,
++	NULL,
++	0,	/* flags */
++	NULL	/* app_data */
++};
++
++typedef enum ec_curve_s
++{
++	EC_PRIME,
++	EC_BINARY
++} ec_curve_t;
++
++/* ENGINE handler for ECDSA Sign */
++static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
++	int dgst_len, const BIGNUM *in_kinv, const BIGNUM *in_r, EC_KEY *eckey)
+ {
+-	return (cryptodev_bn_mod_exp(r, a, p, m, ctx, m_ctx));
++	BIGNUM	*m = NULL, *p = NULL, *a = NULL;
++	BIGNUM  *b = NULL, *x = NULL, *y = NULL;
++	BN_CTX  *ctx = NULL;
++	ECDSA_SIG *ret = NULL;
++	ECDSA_DATA *ecdsa = NULL;
++	unsigned char  * q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL;
++	unsigned char  * s = NULL, *c = NULL, *d = NULL, *f = NULL, *tmp_dgst = NULL;
++	int	i = 0, q_len = 0, priv_key_len = 0, r_len = 0;
++	int	g_len = 0, d_len = 0, ab_len = 0;
++	const BIGNUM   *order = NULL, *priv_key=NULL;
++	const EC_GROUP *group = NULL;
++	struct crypt_kop kop;
++	ec_curve_t ec_crv = EC_PRIME;
++
++	memset(&kop, 0, sizeof(kop));
++	ecdsa = ecdsa_check(eckey);
++	if (!ecdsa) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		return NULL;
++	}
++
++	group = EC_KEY_get0_group(eckey);
++	priv_key = EC_KEY_get0_private_key(eckey);
++
++	if (!group || !priv_key) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		return NULL;
++	}
++
++	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
++		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
++		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
++		(y = BN_new()) == NULL) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	order = &group->order;
++	if (!order || BN_is_zero(order)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ECDSA_R_MISSING_PARAMETERS);
++		goto err;
++	}
++
++	i = BN_num_bits(order);
++	/* Need to truncate digest if it is too long: first truncate whole
++	 bytes */
++	if (8 * dgst_len > i)
++		dgst_len = (i + 7)/8;
++
++	if (!BN_bin2bn(dgst, dgst_len, m)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* If still too long truncate remaining bits with a shift */
++	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* copy the truncated bits into plain buffer */
++	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len))  {
++		fprintf(stderr, "%s:%d: OPENSSL_malloc failec\n", __FUNCTION__, __LINE__);
++		goto err;
++	}
++
++	ret = ECDSA_SIG_new();
++	if  (!ret) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* check if this is prime or binary EC request */
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GFp (group, EC_GROUP_get0_generator(group),
++			x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_characteristic_two_field) {
++		ec_crv = EC_BINARY;
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group), x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++		goto err;
++	}
++
++	if (spcf_bn2bin(order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	priv_key_len = r_len;
++
++	/**
++	 * If BN_num_bytes of priv_key returns less then r_len then
++	 * add padding bytes before the key
++	 */
++	if (spcf_bn2bin_ex(priv_key, &s, &priv_key_len))  {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++	ab = eng_copy_curve_points(a, b, ab_len, q_len);
++	if (!ab) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		if (eng_ec_get_cparam(EC_GROUP_get_curve_name(group), ab+q_len, q_len))
++		{
++			unsigned char *c_temp = NULL;
++			int c_temp_len = q_len;
++			if (eng_ec_compute_cparam(b, p, &c_temp, &c_temp_len))
++				memcpy(ab+q_len, c_temp, q_len);
++			else
++				goto err;
++		}
++		kop.curve_type = ECC_BINARY;
++	}
++
++	/* Calculation of Generator point */
++	g_len = 2*q_len;
++	g_xy = eng_copy_curve_points(x, y, g_len, q_len);
++	if (!g_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Memory allocation for first part of digital signature */
++	c = malloc(r_len);
++	if (!c) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	d_len = r_len;
++
++	/* Memory allocation for second part of digital signature */
++	d = malloc(d_len);
++	if (!d) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* memory for message representative */
++	f = malloc(r_len);
++	if (!f) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	memset(f, 0, r_len - dgst_len);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f +  r_len - dgst_len, tmp_dgst, dgst_len);
++
++	dgst_len +=  r_len - dgst_len;
++	kop.crk_op = CRK_DSA_SIGN;
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop.crk_param[0].crp_p = f;
++	kop.crk_param[0].crp_nbits = dgst_len * 8;
++	kop.crk_param[1].crp_p = q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = r;
++	kop.crk_param[2].crp_nbits = r_len * 8;
++	kop.crk_param[3].crp_p = g_xy;
++	kop.crk_param[3].crp_nbits = g_len * 8;
++	kop.crk_param[4].crp_p = s;
++	kop.crk_param[4].crp_nbits = priv_key_len * 8;
++	kop.crk_param[5].crp_p = ab;
++	kop.crk_param[5].crp_nbits = ab_len * 8;
++	kop.crk_iparams = 6;
++	kop.crk_param[6].crp_p = c;
++	kop.crk_param[6].crp_nbits = d_len * 8;
++	kop.crk_param[7].crp_p = d;
++	kop.crk_param[7].crp_nbits = d_len * 8;
++	kop.crk_oparams = 2;
++
++	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
++		/* Check if ret->r and s needs to allocated */
++		crparam2bn(&kop.crk_param[6], ret->r);
++		crparam2bn(&kop.crk_param[7], ret->s);
++	} else {
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++		ret = (meth->ecdsa_do_sign)(dgst, dgst_len, in_kinv, in_r, eckey);
++	}
++	kop.crk_param[0].crp_p = NULL;
++	zapparams(&kop);
++err:
++	if (!ret) {
++		ECDSA_SIG_free(ret);
++		ret = NULL;
++	}
++	return ret;
++}
++
++static int cryptodev_ecdsa_verify(const unsigned char *dgst, int dgst_len,
++		ECDSA_SIG *sig, EC_KEY *eckey)
++{
++	BIGNUM	*m = NULL, *p = NULL, *a = NULL, *b = NULL;
++	BIGNUM	*x = NULL, *y = NULL, *w_x = NULL, *w_y = NULL;
++	BN_CTX	*ctx = NULL;
++	ECDSA_DATA	*ecdsa = NULL;
++	unsigned char *q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL, *w_xy = NULL;
++	unsigned char *c = NULL, *d = NULL, *f = NULL, *tmp_dgst = NULL;
++	int	i = 0, q_len = 0, pub_key_len = 0, r_len = 0, c_len = 0, g_len = 0;
++	int	d_len = 0, ab_len = 0, ret = -1;
++	const EC_POINT *pub_key = NULL;
++	const BIGNUM   *order = NULL;
++	const EC_GROUP *group=NULL;
++	ec_curve_t       ec_crv = EC_PRIME;
++	struct crypt_kop kop;
++
++	memset(&kop, 0, sizeof kop);
++	ecdsa = ecdsa_check(eckey);
++	if (!ecdsa) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_PASSED_NULL_PARAMETER);
++		return ret;
++	}
++
++	group    = EC_KEY_get0_group(eckey);
++	pub_key  = EC_KEY_get0_public_key(eckey);
++
++	if (!group || !pub_key) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_PASSED_NULL_PARAMETER);
++		return ret;
++	}
++
++	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
++		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
++		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
++		(y = BN_new()) == NULL || (w_x = BN_new()) == NULL ||
++		(w_y = BN_new()) == NULL) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	order = &group->order;
++	if (!order || BN_is_zero(order)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ECDSA_R_MISSING_PARAMETERS);
++		goto err;
++	}
++
++	i = BN_num_bits(order);
++	/* Need to truncate digest if it is too long: first truncate whole
++	* bytes */
++	if (8 * dgst_len > i)
++		dgst_len = (i + 7)/8;
++
++	if (!BN_bin2bn(dgst, dgst_len, m)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* If still too long truncate remaining bits with a shift */
++	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
++		goto err;
++	}
++	/* copy the truncated bits into plain buffer */
++	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* check if this is prime or binary EC request */
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GFp (group,
++			EC_GROUP_get0_generator(group), x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for prime curve */
++		if (!EC_POINT_get_affine_coordinates_GFp (group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b, ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_characteristic_two_field){
++		ec_crv = EC_BINARY;
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group),x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for binary curve */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++	}else {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++		goto err;
++	}
++
++	/* Get the order of the subgroup of private keys */
++	if (spcf_bn2bin((BIGNUM*)order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the irreducible polynomial that creates the field */
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the public key into a flat buffer with appropriate padding */
++	pub_key_len = 2 * q_len;
++
++	w_xy = eng_copy_curve_points (w_x, w_y, pub_key_len, q_len);
++	if (!w_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++
++	ab = eng_copy_curve_points (a, b, ab_len, q_len);
++	if (!ab) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		/* copy b' i.e c(b), instead of only b */
++		if (eng_ec_get_cparam(EC_GROUP_get_curve_name(group), ab+q_len, q_len))
++		{
++			unsigned char *c_temp = NULL;
++			int c_temp_len = q_len;
++			if (eng_ec_compute_cparam(b, p, &c_temp, &c_temp_len))
++				memcpy(ab+q_len, c_temp, q_len);
++			else
++				goto err;
++		}
++		kop.curve_type = ECC_BINARY;
++	}
++
++	/* Calculation of Generator point */
++	g_len = 2 * q_len;
++
++	g_xy = eng_copy_curve_points (x, y, g_len, q_len);
++	if (!g_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/**
++	 * Get the 1st part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	if (BN_num_bytes(sig->r) < r_len)
++		c_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->r, &c, &c_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/**
++	 * Get the 2nd part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	if (BN_num_bytes(sig->s) < r_len)
++		d_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* memory for message representative */
++	f = malloc(r_len);
++	if (!f) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	memset(f, 0, r_len-dgst_len);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len-dgst_len, tmp_dgst, dgst_len);
++	dgst_len += r_len-dgst_len;
++	kop.crk_op = CRK_DSA_VERIFY;
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop.crk_param[0].crp_p = f;
++	kop.crk_param[0].crp_nbits = dgst_len * 8;
++	kop.crk_param[1].crp_p = q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = r;
++	kop.crk_param[2].crp_nbits = r_len * 8;
++	kop.crk_param[3].crp_p = g_xy;
++	kop.crk_param[3].crp_nbits = g_len * 8;
++	kop.crk_param[4].crp_p = w_xy;
++	kop.crk_param[4].crp_nbits = pub_key_len * 8;
++	kop.crk_param[5].crp_p = ab;
++	kop.crk_param[5].crp_nbits = ab_len * 8;
++	kop.crk_param[6].crp_p = c;
++	kop.crk_param[6].crp_nbits = d_len * 8;
++	kop.crk_param[7].crp_p = d;
++	kop.crk_param[7].crp_nbits = d_len * 8;
++	kop.crk_iparams = 8;
++
++	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
++		/*OCF success value is 0, if not zero, change ret to fail*/
++		if(0 == kop.crk_status)
++			ret  = 1;
++	} else {
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++
++		ret = (meth->ecdsa_do_verify)(dgst, dgst_len, sig, eckey);
++	}
++	kop.crk_param[0].crp_p = NULL;
++	zapparams(&kop);
++
++err:
++	return ret;
++}
++
++static int cryptodev_dh_keygen(DH *dh)
++{
++	struct crypt_kop kop;
++	int ret = 1, g_len;
++	unsigned char *g = NULL;
++
++	if (dh->priv_key == NULL)	{
++		if ((dh->priv_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	if (dh->pub_key == NULL) {
++		if ((dh->pub_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	g_len = BN_num_bytes(dh->p);
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dh->g, &g, &g_len)) {
++		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
++
++	memset(&kop, 0, sizeof kop);
++	kop.crk_op = CRK_DH_GENERATE_KEY;
++	if (bn2crparam(dh->p, &kop.crk_param[0]))
++		goto sw_try;
++	if (bn2crparam(dh->q, &kop.crk_param[1]))
++		goto sw_try;
++	kop.crk_param[2].crp_p = g;
++	kop.crk_param[2].crp_nbits = g_len * 8;
++	kop.crk_iparams = 3;
++
++	/* pub_key is or prime length while priv key is of length of order */
++	if (cryptodev_asym(&kop, BN_num_bytes(dh->p), dh->pub_key,
++	    BN_num_bytes(dh->q), dh->priv_key))
++	    goto sw_try;
++
++	return ret;
++sw_try:
++	{
++		const DH_METHOD *meth = DH_OpenSSL();
++		ret = (meth->generate_key)(dh);
++	}
++	return ret;
+ }
+ 
+ static int
+@@ -1470,43 +2277,234 @@ cryptodev_dh_compute_key(unsigned char *key, const BIGNUM *pub_key, DH *dh)
+ {
+ 	struct crypt_kop kop;
+ 	int dhret = 1;
+-	int fd, keylen;
++	int fd, p_len;
++	BIGNUM *temp = NULL;
++	unsigned char *padded_pub_key = NULL, *p = NULL;
++
++	if ((fd = get_asym_dev_crypto()) < 0)
++		goto sw_try;
++
++	memset(&kop, 0, sizeof kop);
++	kop.crk_op = CRK_DH_COMPUTE_KEY;
++	/* inputs: dh->priv_key pub_key dh->p key */
++	spcf_bn2bin(dh->p, &p, &p_len);
++	spcf_bn2bin_ex(pub_key, &padded_pub_key, &p_len);
++	if (bn2crparam(dh->priv_key, &kop.crk_param[0]))
++		goto sw_try;
++
++	kop.crk_param[1].crp_p = padded_pub_key;
++	kop.crk_param[1].crp_nbits = p_len * 8;
++	kop.crk_param[2].crp_p = p;
++	kop.crk_param[2].crp_nbits = p_len * 8;
++	kop.crk_iparams = 3;
++	kop.crk_param[3].crp_p = (void*) key;
++	kop.crk_param[3].crp_nbits = p_len * 8;
++	kop.crk_oparams = 1;
++	dhret = p_len;
++
++	if (ioctl(fd, CIOCKEY, &kop))
++		goto sw_try;
+ 
+-	if ((fd = get_asym_dev_crypto()) < 0) {
++	if ((temp = BN_new())) {
++		if (!BN_bin2bn(key, p_len, temp)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++			goto sw_try;
++		}
++		if (dhret > BN_num_bytes(temp))
++			dhret=BN_bn2bin(temp,key);
++		BN_free(temp);
++	}
++
++	kop.crk_param[3].crp_p = NULL;
++	zapparams(&kop);
++	return (dhret);
++sw_try:
++	{
+ 		const DH_METHOD *meth = DH_OpenSSL();
+ 
+-		return ((meth->compute_key)(key, pub_key, dh));
++		dhret = (meth->compute_key)(key, pub_key, dh);
+ 	}
++	return (dhret);
++}
+ 
+-	keylen = BN_num_bits(dh->p);
++int cryptodev_ecdh_compute_key(void *out, size_t outlen,
++	const EC_POINT *pub_key, EC_KEY *ecdh, void *(*KDF)(const void *in, size_t inlen,
++	void *out, size_t *outlen))
++{
++	ec_curve_t       ec_crv = EC_PRIME;
++	unsigned char * q = NULL, *w_xy = NULL, *ab = NULL, *s = NULL, *r = NULL;
++	BIGNUM         * w_x = NULL, *w_y = NULL;
++	int q_len = 0, ab_len = 0, pub_key_len = 0, r_len = 0, priv_key_len = 0;
++	BIGNUM * p = NULL, *a = NULL, *b = NULL;
++	BN_CTX *ctx;
++	EC_POINT *tmp=NULL;
++	BIGNUM *x=NULL, *y=NULL;
++	const BIGNUM *priv_key;
++	const EC_GROUP* group = NULL;
++	int ret = -1;
++	size_t buflen, len;
++	struct crypt_kop kop;
+ 
+ 	memset(&kop, 0, sizeof kop);
+-	kop.crk_op = CRK_DH_COMPUTE_KEY;
+ 
+-	/* inputs: dh->priv_key pub_key dh->p key */
+-	if (bn2crparam(dh->priv_key, &kop.crk_param[0]))
++	if ((ctx = BN_CTX_new()) == NULL) goto err;
++	BN_CTX_start(ctx);
++	x = BN_CTX_get(ctx);
++	y = BN_CTX_get(ctx);
++	p = BN_CTX_get(ctx);
++	a = BN_CTX_get(ctx);
++	b = BN_CTX_get(ctx);
++	w_x = BN_CTX_get(ctx);
++	w_y = BN_CTX_get(ctx);
++
++	if (!x || !y || !p || !a || !b || !w_x || !w_y) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	if (bn2crparam(pub_key, &kop.crk_param[1]))
++	}
++
++	priv_key = EC_KEY_get0_private_key(ecdh);
++	if (priv_key == NULL) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_NO_PRIVATE_VALUE);
+ 		goto err;
+-	if (bn2crparam(dh->p, &kop.crk_param[2]))
++	}
++
++	group = EC_KEY_get0_group(ecdh);
++	if ((tmp=EC_POINT_new(group)) == NULL) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_MALLOC_FAILURE);
+ 		goto err;
+-	kop.crk_iparams = 3;
++	}
+ 
+-	kop.crk_param[3].crp_p = (caddr_t) key;
+-	kop.crk_param[3].crp_nbits = keylen * 8;
+-	kop.crk_oparams = 1;
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) ==
++		NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
+ 
+-	if (ioctl(fd, CIOCKEY, &kop) == -1) {
+-		const DH_METHOD *meth = DH_OpenSSL();
++		if (!EC_POINT_get_affine_coordinates_GFp(group,
++			EC_GROUP_get0_generator(group), x, y, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_POINT_ARITHMETIC_FAILURE);
++			goto err;
++		}
+ 
+-		dhret = (meth->compute_key)(key, pub_key, dh);
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for prime curve */
++		if (!EC_POINT_get_affine_coordinates_GFp (group, pub_key, w_x, w_y,ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++	} else {
++		ec_crv = EC_BINARY;
++
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group), x, y, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_POINT_ARITHMETIC_FAILURE);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for binary curve */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	}
++
++	/* irreducible polynomial that creates the field */
++	if (spcf_bn2bin((BIGNUM*)&group->order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the irreducible polynomial that creates the field */
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++		goto err;
+ 	}
++
++	/* Get the public key into a flat buffer with appropriate padding */
++	pub_key_len = 2 * q_len;
++	w_xy = eng_copy_curve_points (w_x, w_y, pub_key_len, q_len);
++	if (!w_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++	ab = eng_copy_curve_points (a, b, ab_len, q_len);
++	if (!ab) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		/* copy b' i.e c(b), instead of only b */
++		if (eng_ec_get_cparam(EC_GROUP_get_curve_name(group), ab+q_len, q_len))
++		{
++			unsigned char *c_temp = NULL;
++			int c_temp_len = q_len;
++			if (eng_ec_compute_cparam(b, p, &c_temp, &c_temp_len))
++				memcpy(ab+q_len, c_temp, q_len);
++			else
++				goto err;
++		}
++		kop.curve_type = ECC_BINARY;
++	} else
++		kop.curve_type = ECC_PRIME;
++
++	priv_key_len = r_len;
++
++	/*
++	 * If BN_num_bytes of priv_key returns less then r_len then
++	 * add padding bytes before the key
++	 */
++	if (spcf_bn2bin_ex((BIGNUM *)priv_key, &s, &priv_key_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	buflen = (EC_GROUP_get_degree(group) + 7)/8;
++	len = BN_num_bytes(x);
++	if (len > buflen || q_len < buflen) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_INTERNAL_ERROR);
++		goto err;
++	}
++
++	kop.crk_op = CRK_DH_COMPUTE_KEY;
++	kop.crk_param[0].crp_p = (void*) s;
++	kop.crk_param[0].crp_nbits = priv_key_len*8;
++	kop.crk_param[1].crp_p = (void*) w_xy;
++	kop.crk_param[1].crp_nbits = pub_key_len*8;
++	kop.crk_param[2].crp_p = (void*) q;
++	kop.crk_param[2].crp_nbits = q_len*8;
++	kop.crk_param[3].crp_p = (void*) ab;
++	kop.crk_param[3].crp_nbits = ab_len*8;
++	kop.crk_iparams = 4;
++	kop.crk_param[4].crp_p = (void*) out;
++	kop.crk_param[4].crp_nbits = q_len*8;
++	kop.crk_oparams = 1;
++	ret = q_len;
++	if (cryptodev_asym(&kop, 0, NULL, 0, NULL)) {
++		const ECDH_METHOD *meth = ECDH_OpenSSL();
++		ret = (meth->compute_key)(out, outlen, pub_key, ecdh, KDF);
++	} else
++		ret = q_len;
+ err:
+-	kop.crk_param[3].crp_p = NULL;
++	kop.crk_param[4].crp_p = NULL;
+ 	zapparams(&kop);
+-	return (dhret);
++	return ret;
+ }
+ 
++
+ static DH_METHOD cryptodev_dh = {
+ 	"cryptodev DH method",
+ 	NULL,				/* cryptodev_dh_generate_key */
+@@ -1518,6 +2516,14 @@ static DH_METHOD cryptodev_dh = {
+ 	NULL	/* app_data */
+ };
+ 
++static ECDH_METHOD cryptodev_ecdh = {
++	"cryptodev ECDH method",
++	NULL,	/* cryptodev_ecdh_compute_key */
++	NULL,
++	0,		/* flags */
++	NULL	/* app_data */
++};
++
+ /*
+  * ctrl right now is just a wrapper that doesn't do much
+  * but I expect we'll want some options soon.
+@@ -1602,25 +2608,42 @@ ENGINE_load_cryptodev(void)
+ 		memcpy(&cryptodev_dsa, meth, sizeof(DSA_METHOD));
+ 		if (cryptodev_asymfeat & CRF_DSA_SIGN)
+ 			cryptodev_dsa.dsa_do_sign = cryptodev_dsa_do_sign;
+-		if (cryptodev_asymfeat & CRF_MOD_EXP) {
+-			cryptodev_dsa.bn_mod_exp = cryptodev_dsa_bn_mod_exp;
+-			cryptodev_dsa.dsa_mod_exp = cryptodev_dsa_dsa_mod_exp;
+-		}
+ 		if (cryptodev_asymfeat & CRF_DSA_VERIFY)
+ 			cryptodev_dsa.dsa_do_verify = cryptodev_dsa_verify;
++		if (cryptodev_asymfeat & CRF_DSA_GENERATE_KEY)
++			cryptodev_dsa.dsa_keygen = cryptodev_dsa_keygen;
+ 	}
+ 
+ 	if (ENGINE_set_DH(engine, &cryptodev_dh)){
+ 		const DH_METHOD *dh_meth = DH_OpenSSL();
++		memcpy(&cryptodev_dh, dh_meth, sizeof(DH_METHOD));
++		if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY) {
++			cryptodev_dh.compute_key =
++				cryptodev_dh_compute_key;
++		}
++		if (cryptodev_asymfeat & CRF_DH_GENERATE_KEY) {
++			cryptodev_dh.generate_key =
++				cryptodev_dh_keygen;
++		}
++	}
+ 
+-		cryptodev_dh.generate_key = dh_meth->generate_key;
+-		cryptodev_dh.compute_key = dh_meth->compute_key;
+-		cryptodev_dh.bn_mod_exp = dh_meth->bn_mod_exp;
+-		if (cryptodev_asymfeat & CRF_MOD_EXP) {
+-			cryptodev_dh.bn_mod_exp = cryptodev_mod_exp_dh;
+-			if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY)
+-				cryptodev_dh.compute_key =
+-				    cryptodev_dh_compute_key;
++	if (ENGINE_set_ECDSA(engine, &cryptodev_ecdsa)) {
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++		memcpy(&cryptodev_ecdsa, meth, sizeof(ECDSA_METHOD));
++		if (cryptodev_asymfeat & CRF_DSA_SIGN) {
++			cryptodev_ecdsa.ecdsa_do_sign = cryptodev_ecdsa_do_sign;
++		}
++		if (cryptodev_asymfeat & CRF_DSA_VERIFY) {
++			cryptodev_ecdsa.ecdsa_do_verify =
++				cryptodev_ecdsa_verify;
++		}
++	}
++
++	if (ENGINE_set_ECDH(engine, &cryptodev_ecdh)) {
++		const ECDH_METHOD *ecdh_meth = ECDH_OpenSSL();
++		memcpy(&cryptodev_ecdh, ecdh_meth, sizeof(ECDH_METHOD));
++		if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY) {
++			cryptodev_ecdh.compute_key = cryptodev_ecdh_compute_key;
+ 		}
+ 	}
+ 
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0007-Added-hwrng-dev-file-as-source-of-RNG.patch b/recipes-connectivity/openssl/openssl-fsl/0007-Added-hwrng-dev-file-as-source-of-RNG.patch
new file mode 100644
index 0000000..afe9f7c
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0007-Added-hwrng-dev-file-as-source-of-RNG.patch
@@ -0,0 +1,28 @@
+From 6ee6f7acad9824244b32ac23248f1d12f2c2b201 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 11 Mar 2014 06:42:59 +0545
+Subject: [PATCH][fsl 07/15] Added hwrng dev file as source of RNG
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ e_os.h |    2 +-
+ 1 file changed, 1 insertion(+), 1 deletion(-)
+
+diff --git a/e_os.h b/e_os.h
+index 6a0aad1..57c0563 100644
+--- a/e_os.h
++++ b/e_os.h
+@@ -79,7 +79,7 @@ extern "C" {
+ #ifndef DEVRANDOM
+ /* set this to a comma-separated list of 'random' device files to try out.
+  * My default, we will try to read at least one of these files */
+-#define DEVRANDOM "/dev/urandom","/dev/random","/dev/srandom"
++#define DEVRANDOM "/dev/hwrng","/dev/urandom","/dev/random","/dev/srandom"
+ #endif
+ #ifndef DEVRANDOM_EGD
+ /* set this to a comma-seperated list of 'egd' sockets to try out. These
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0008-Asynchronous-interface-added-for-PKC-cryptodev-inter.patch b/recipes-connectivity/openssl/openssl-fsl/0008-Asynchronous-interface-added-for-PKC-cryptodev-inter.patch
new file mode 100644
index 0000000..d8b5d95
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0008-Asynchronous-interface-added-for-PKC-cryptodev-inter.patch
@@ -0,0 +1,2039 @@
+From 68f8054c5a1f72e40884782d2d548892406d6049 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 11 Mar 2014 07:14:30 +0545
+Subject: [PATCH][fsl 08/15] Asynchronous interface added for PKC cryptodev
+ interface
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+---
+ crypto/crypto.h               |   16 +
+ crypto/dh/dh.h                |    4 +-
+ crypto/dsa/dsa.h              |    5 +
+ crypto/ecdh/ech_locl.h        |    3 +
+ crypto/ecdsa/ecs_locl.h       |    5 +
+ crypto/engine/eng_cryptodev.c | 1578 +++++++++++++++++++++++++++++++++++++----
+ crypto/engine/eng_int.h       |   24 +-
+ crypto/engine/eng_lib.c       |   46 ++
+ crypto/engine/engine.h        |   24 +
+ crypto/rsa/rsa.h              |   23 +
+ 10 files changed, 1582 insertions(+), 146 deletions(-)
+
+diff --git a/crypto/crypto.h b/crypto/crypto.h
+index f92fc51..ce12731 100644
+--- a/crypto/crypto.h
++++ b/crypto/crypto.h
+@@ -605,6 +605,22 @@ void ERR_load_CRYPTO_strings(void);
+ #define CRYPTO_R_FIPS_MODE_NOT_SUPPORTED		 101
+ #define CRYPTO_R_NO_DYNLOCK_CREATE_CALLBACK		 100
+ 
++/* Additions for Asynchronous PKC Infrastructure */
++struct pkc_cookie_s {
++	void *cookie; /* To be filled by openssl library primitive method function caller */
++	void *eng_cookie; /* To be filled by Engine */
++	 /*
++	   * Callback handler to be provided by caller. Ensure to pass a
++	   * handler which takes the crypto operation to completion.
++	   * cookie: Container cookie from library
++	   * status: Status of the crypto Job completion.
++	   *		0: Job handled without any issue
++	   *		-EINVAL: Parameters Invalid
++	   */
++	void (*pkc_callback)(struct pkc_cookie_s *cookie, int status);
++	void *eng_handle;
++};
++
+ #ifdef  __cplusplus
+ }
+ #endif
+diff --git a/crypto/dh/dh.h b/crypto/dh/dh.h
+index ea59e61..20ffad2 100644
+--- a/crypto/dh/dh.h
++++ b/crypto/dh/dh.h
+@@ -118,7 +118,9 @@ struct dh_method
+ 	int (*bn_mod_exp)(const DH *dh, BIGNUM *r, const BIGNUM *a,
+ 				const BIGNUM *p, const BIGNUM *m, BN_CTX *ctx,
+ 				BN_MONT_CTX *m_ctx); /* Can be null */
+-
++	int (*compute_key_async)(unsigned char *key,const BIGNUM *pub_key,DH *dh,
++				struct pkc_cookie_s *cookie);
++	int (*generate_key_async)(DH *dh, struct pkc_cookie_s *cookie);
+ 	int (*init)(DH *dh);
+ 	int (*finish)(DH *dh);
+ 	int flags;
+diff --git a/crypto/dsa/dsa.h b/crypto/dsa/dsa.h
+index a6f6d0b..b04a029 100644
+--- a/crypto/dsa/dsa.h
++++ b/crypto/dsa/dsa.h
+@@ -140,6 +140,10 @@ struct dsa_method
+ 	int (*bn_mod_exp)(DSA *dsa, BIGNUM *r, BIGNUM *a, const BIGNUM *p,
+ 				const BIGNUM *m, BN_CTX *ctx,
+ 				BN_MONT_CTX *m_ctx); /* Can be null */
++	int (*dsa_do_sign_async)(const unsigned char *dgst, int dlen, DSA *dsa,
++				DSA_SIG *sig, struct pkc_cookie_s *cookie);
++	int (*dsa_do_verify_async)(const unsigned char *dgst, int dgst_len,
++			     DSA_SIG *sig, DSA *dsa, struct pkc_cookie_s *cookie);
+ 	int (*init)(DSA *dsa);
+ 	int (*finish)(DSA *dsa);
+ 	int flags;
+@@ -151,6 +155,7 @@ struct dsa_method
+ 			BN_GENCB *cb);
+ 	/* If this is non-NULL, it is used to generate DSA keys */
+ 	int (*dsa_keygen)(DSA *dsa);
++	int (*dsa_keygen_async)(DSA *dsa, struct pkc_cookie_s *cookie);
+ 	};
+ 
+ struct dsa_st
+diff --git a/crypto/ecdh/ech_locl.h b/crypto/ecdh/ech_locl.h
+index f6cad6a..adce6b3 100644
+--- a/crypto/ecdh/ech_locl.h
++++ b/crypto/ecdh/ech_locl.h
+@@ -67,6 +67,9 @@ struct ecdh_method
+ 	const char *name;
+ 	int (*compute_key)(void *key, size_t outlen, const EC_POINT *pub_key, EC_KEY *ecdh,
+ 	                   void *(*KDF)(const void *in, size_t inlen, void *out, size_t *outlen));
++	int (*compute_key_async)(void *key, size_t outlen, const EC_POINT *pub_key, EC_KEY *ecdh,
++	                   void *(*KDF)(const void *in, size_t inlen, void *out, size_t *outlen),
++	                   struct pkc_cookie_s *cookie);
+ #if 0
+ 	int (*init)(EC_KEY *eckey);
+ 	int (*finish)(EC_KEY *eckey);
+diff --git a/crypto/ecdsa/ecs_locl.h b/crypto/ecdsa/ecs_locl.h
+index cb3be13..eb0ebe0 100644
+--- a/crypto/ecdsa/ecs_locl.h
++++ b/crypto/ecdsa/ecs_locl.h
+@@ -74,6 +74,11 @@ struct ecdsa_method
+ 			BIGNUM **r);
+ 	int (*ecdsa_do_verify)(const unsigned char *dgst, int dgst_len, 
+ 			const ECDSA_SIG *sig, EC_KEY *eckey);
++	 int (*ecdsa_do_sign_async)(const unsigned char *dgst, int dgst_len,
++			const BIGNUM *inv, const BIGNUM *rp, EC_KEY *eckey,
++			ECDSA_SIG *sig, struct pkc_cookie_s *cookie);
++	int (*ecdsa_do_verify_async)(const unsigned char *dgst, int dgst_len,
++			const ECDSA_SIG *sig, EC_KEY *eckey, struct pkc_cookie_s *cookie);
+ #if 0
+ 	int (*init)(EC_KEY *eckey);
+ 	int (*finish)(EC_KEY *eckey);
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 88caec1..c5e8fb3 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -1248,6 +1248,56 @@ zapparams(struct crypt_kop *kop)
+ 	}
+ }
+ 
++/* Any PKC request has at max 2 output parameters and they are stored here to
++be used while copying in the check availability */
++struct cryptodev_cookie_s {
++	BIGNUM *r;
++	struct crparam r_param;
++	BIGNUM *s;
++	struct crparam s_param;
++	struct crypt_kop *kop;
++};
++
++static int
++cryptodev_asym_async(struct crypt_kop *kop, int rlen, BIGNUM *r, int slen,
++					BIGNUM *s)
++{
++	int fd;
++	struct pkc_cookie_s *cookie = kop->cookie;
++	struct cryptodev_cookie_s *eng_cookie;
++
++	fd = *(int *)cookie->eng_handle;
++
++	eng_cookie = malloc(sizeof(struct cryptodev_cookie_s));
++
++	if (eng_cookie) {
++		memset(eng_cookie, 0, sizeof(struct cryptodev_cookie_s));
++		if (r) {
++			kop->crk_param[kop->crk_iparams].crp_p = calloc(rlen, sizeof(char));
++			if (!kop->crk_param[kop->crk_iparams].crp_p)
++				return -ENOMEM;
++			kop->crk_param[kop->crk_iparams].crp_nbits = rlen * 8;
++			kop->crk_oparams++;
++			eng_cookie->r = r;
++			eng_cookie->r_param = kop->crk_param[kop->crk_iparams];
++		}
++		if (s) {
++			kop->crk_param[kop->crk_iparams+1].crp_p = calloc(slen, sizeof(char));
++			if (!kop->crk_param[kop->crk_iparams+1].crp_p)
++				return -ENOMEM;
++			kop->crk_param[kop->crk_iparams+1].crp_nbits = slen * 8;
++			kop->crk_oparams++;
++			eng_cookie->s = s;
++			eng_cookie->s_param = kop->crk_param[kop->crk_iparams + 1];
++		}
++	} else
++		return -ENOMEM;
++
++	eng_cookie->kop = kop;
++	cookie->eng_cookie = eng_cookie;
++	return ioctl(fd, CIOCASYMASYNCRYPT, kop);
++}
++
+ static int
+ cryptodev_asym(struct crypt_kop *kop, int rlen, BIGNUM *r, int slen, BIGNUM *s)
+ {
+@@ -1304,6 +1354,44 @@ void *cryptodev_init_instance(void)
+ 	return fd;
+ }
+ 
++#include <poll.h>
++
++/* Return 0 on success and 1 on failure */
++int cryptodev_check_availability(void *eng_handle)
++{
++	int fd = *(int *)eng_handle;
++	struct pkc_cookie_list_s cookie_list;
++	struct pkc_cookie_s *cookie;
++	int i;
++
++	/* FETCH COOKIE returns number of cookies extracted */
++	if (ioctl(fd, CIOCASYMFETCHCOOKIE, &cookie_list) <= 0)
++		return 1;
++
++	for (i = 0; i < cookie_list.cookie_available; i++) {
++		cookie = cookie_list.cookie[i];
++		if (cookie) {
++			struct cryptodev_cookie_s *eng_cookie = cookie->eng_cookie;
++			if (eng_cookie) {
++				struct crypt_kop *kop = eng_cookie->kop;
++
++				if (eng_cookie->r)
++					crparam2bn(&eng_cookie->r_param, eng_cookie->r);
++				if (eng_cookie->s)
++					crparam2bn(&eng_cookie->s_param, eng_cookie->s);
++				if (kop->crk_op == CRK_DH_COMPUTE_KEY)
++					kop->crk_oparams = 0;
++
++				zapparams(eng_cookie->kop);
++				free(eng_cookie->kop);
++				free (eng_cookie);
++			}
++			cookie->pkc_callback(cookie, cookie_list.status[i]);
++		}
++	}
++	return 0;
++}
++
+ static int
+ cryptodev_bn_mod_exp(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+     const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *in_mont)
+@@ -1349,6 +1437,63 @@ err:
+ }
+ 
+ static int
++cryptodev_bn_mod_exp_async(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
++    const BIGNUM *m, BN_CTX *ctx, BN_MONT_CTX *in_mont, struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int ret = 1;
++
++	/* Currently, we know we can do mod exp iff we can do any
++	 * asymmetric operations at all.
++	 */
++	if (cryptodev_asymfeat == 0 || !kop) {
++		ret = BN_mod_exp(r, a, p, m, ctx);
++		return (ret);
++	}
++
++	kop->crk_oparams = 0;
++	kop->crk_status = 0;
++	kop->crk_op = CRK_MOD_EXP;
++	kop->cookie = cookie;
++	/* inputs: a^p % m */
++	if (bn2crparam(a, &kop->crk_param[0]))
++		goto err;
++	if (bn2crparam(p, &kop->crk_param[1]))
++		goto err;
++	if (bn2crparam(m, &kop->crk_param[2]))
++		goto err;
++
++	kop->crk_iparams = 3;
++	if (cryptodev_asym_async(kop, BN_num_bytes(m), r, 0, NULL))
++		goto err;
++
++	return ret;
++err:
++	{
++		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
++
++		if (kop)
++			free(kop);
++		ret = meth->bn_mod_exp(r, a, p, m, ctx, in_mont);
++		if (ret)
++			/* Call the completion handler immediately */
++			cookie->pkc_callback(cookie, 0);
++	}
++	return ret;
++}
++
++static int
++cryptodev_rsa_nocrt_mod_exp_async(BIGNUM *r0, const BIGNUM *I,
++		RSA *rsa, BN_CTX *ctx, struct pkc_cookie_s *cookie)
++{
++	int r;
++	ctx = BN_CTX_new();
++	r = cryptodev_bn_mod_exp_async(r0, I, rsa->d, rsa->n, ctx, NULL, cookie);
++	BN_CTX_free(ctx);
++	return r;
++}
++
++static int
+ cryptodev_rsa_nocrt_mod_exp(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx)
+ {
+ 	int r;
+@@ -1413,6 +1558,62 @@ err:
+ 	return (ret);
+ }
+ 
++static int
++cryptodev_rsa_mod_exp_async(BIGNUM *r0, const BIGNUM *I, RSA *rsa, BN_CTX *ctx,
++				struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int ret = 1, f_len, p_len, q_len;
++	unsigned char *f = NULL, *p = NULL, *q = NULL, *dp = NULL, *dq = NULL, *c = NULL;
++
++	if (!rsa->p || !rsa->q || !rsa->dmp1 || !rsa->dmq1 || !rsa->iqmp || !kop) {
++		return (0);
++	}
++
++	kop->crk_oparams = 0;
++	kop->crk_status = 0;
++	kop->crk_op = CRK_MOD_EXP_CRT;
++	f_len = BN_num_bytes(rsa->n);
++	spcf_bn2bin_ex(I, &f, &f_len);
++	spcf_bn2bin(rsa->p, &p, &p_len);
++	spcf_bn2bin(rsa->q, &q, &q_len);
++	spcf_bn2bin_ex(rsa->dmp1, &dp, &p_len);
++	spcf_bn2bin_ex(rsa->iqmp, &c, &p_len);
++	spcf_bn2bin_ex(rsa->dmq1, &dq, &q_len);
++	/* inputs: rsa->p rsa->q I rsa->dmp1 rsa->dmq1 rsa->iqmp */
++	kop->crk_param[0].crp_p = p;
++	kop->crk_param[0].crp_nbits = p_len * 8;
++	kop->crk_param[1].crp_p = q;
++	kop->crk_param[1].crp_nbits = q_len * 8;
++	kop->crk_param[2].crp_p = f;
++	kop->crk_param[2].crp_nbits = f_len * 8;
++	kop->crk_param[3].crp_p = dp;
++	kop->crk_param[3].crp_nbits = p_len * 8;
++	/* dq must of length q, rest all of length p*/
++	kop->crk_param[4].crp_p = dq;
++	kop->crk_param[4].crp_nbits = q_len * 8;
++	kop->crk_param[5].crp_p = c;
++	kop->crk_param[5].crp_nbits = p_len * 8;
++	kop->crk_iparams = 6;
++	kop->cookie = cookie;
++	if (cryptodev_asym_async(kop, BN_num_bytes(rsa->n), r0, 0, NULL))
++		goto err;
++
++	return ret;
++err:
++	{
++		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
++
++		if (kop)
++			free(kop);
++		ret = (*meth->rsa_mod_exp)(r0, I, rsa, ctx);
++		if (ret)
++			/* Call user completion handler immediately */
++			cookie->pkc_callback(cookie, 0);
++	}
++	return (ret);
++}
++
+ static RSA_METHOD cryptodev_rsa = {
+ 	"cryptodev RSA method",
+ 	NULL,				/* rsa_pub_enc */
+@@ -1421,6 +1622,12 @@ static RSA_METHOD cryptodev_rsa = {
+ 	NULL,				/* rsa_priv_dec */
+ 	NULL,
+ 	NULL,
++	NULL,				/* rsa_pub_enc */
++	NULL,				/* rsa_pub_dec */
++	NULL,				/* rsa_priv_enc */
++	NULL,				/* rsa_priv_dec */
++	NULL,
++	NULL,
+ 	NULL,				/* init */
+ 	NULL,				/* finish */
+ 	0,				/* flags */
+@@ -1718,126 +1925,424 @@ sw_try:
+ 	return ret;
+ }
+ 
++/* Cryptodev DSA Key Gen routine */
++static int cryptodev_dsa_keygen_async(DSA *dsa,  struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int ret = 1, g_len;
++	unsigned char *g = NULL;
+ 
++	if (!kop)
++		goto sw_try;
+ 
+-static DSA_METHOD cryptodev_dsa = {
+-	"cryptodev DSA method",
+-	NULL,
+-	NULL,				/* dsa_sign_setup */
+-	NULL,
+-	NULL,				/* dsa_mod_exp */
+-	NULL,
+-	NULL,				/* init */
+-	NULL,				/* finish */
+-	0,	/* flags */
+-	NULL	/* app_data */
+-};
++	if (dsa->priv_key == NULL)	{
++		if ((dsa->priv_key=BN_new()) == NULL)
++			goto sw_try;
++	}
+ 
+-static ECDSA_METHOD cryptodev_ecdsa = {
+-	"cryptodev ECDSA method",
+-	NULL,
+-	NULL,				/* ecdsa_sign_setup */
+-	NULL,
+-	NULL,
+-	0,	/* flags */
+-	NULL	/* app_data */
+-};
++	if (dsa->pub_key == NULL) {
++		if ((dsa->pub_key=BN_new()) == NULL)
++			goto sw_try;
++	}
+ 
+-typedef enum ec_curve_s
+-{
+-	EC_PRIME,
+-	EC_BINARY
+-} ec_curve_t;
++	g_len = BN_num_bytes(dsa->p);
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
+ 
+-/* ENGINE handler for ECDSA Sign */
+-static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
+-	int dgst_len, const BIGNUM *in_kinv, const BIGNUM *in_r, EC_KEY *eckey)
+-{
+-	BIGNUM	*m = NULL, *p = NULL, *a = NULL;
+-	BIGNUM  *b = NULL, *x = NULL, *y = NULL;
+-	BN_CTX  *ctx = NULL;
+-	ECDSA_SIG *ret = NULL;
+-	ECDSA_DATA *ecdsa = NULL;
+-	unsigned char  * q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL;
+-	unsigned char  * s = NULL, *c = NULL, *d = NULL, *f = NULL, *tmp_dgst = NULL;
+-	int	i = 0, q_len = 0, priv_key_len = 0, r_len = 0;
+-	int	g_len = 0, d_len = 0, ab_len = 0;
+-	const BIGNUM   *order = NULL, *priv_key=NULL;
+-	const EC_GROUP *group = NULL;
+-	struct crypt_kop kop;
+-	ec_curve_t ec_crv = EC_PRIME;
++	memset(kop, 0, sizeof(struct crypt_kop));
++	kop->crk_op = CRK_DSA_GENERATE_KEY;
++	if (bn2crparam(dsa->p, &kop->crk_param[0]))
++		goto sw_try;
++	if (bn2crparam(dsa->q, &kop->crk_param[1]))
++		goto sw_try;
++	kop->crk_param[2].crp_p = g;
++	kop->crk_param[2].crp_nbits = g_len * 8;
++	kop->crk_iparams = 3;
++	kop->cookie = cookie;
+ 
+-	memset(&kop, 0, sizeof(kop));
+-	ecdsa = ecdsa_check(eckey);
+-	if (!ecdsa) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
+-		return NULL;
++	/* pub_key is or prime length while priv key is of length of order */
++	if (cryptodev_asym_async(kop, BN_num_bytes(dsa->p), dsa->pub_key,
++	    BN_num_bytes(dsa->q), dsa->priv_key))
++	    goto sw_try;
++
++	return ret;
++sw_try:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++
++		if (kop)
++			free(kop);
++		ret = (meth->dsa_keygen)(dsa);
++		cookie->pkc_callback(cookie, 0);
+ 	}
++	return ret;
++}
+ 
+-	group = EC_KEY_get0_group(eckey);
+-	priv_key = EC_KEY_get0_private_key(eckey);
++static int
++cryptodev_dsa_do_sign_async(const unsigned char *dgst, int dlen, DSA *dsa,
++			DSA_SIG *sig, struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	DSA_SIG *dsaret = NULL;
++	int q_len = 0, r_len = 0, g_len = 0;
++	int priv_key_len = 0, ret = 1;
++	unsigned char *q = NULL, *r = NULL, *g = NULL, *priv_key = NULL, *f = NULL;
+ 
+-	if (!group || !priv_key) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
+-		return NULL;
++	if (((sig->r = BN_new()) == NULL) || !kop) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
+ 	}
+ 
+-	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
+-		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
+-		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
+-		(y = BN_new()) == NULL) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++	if ((sig->s = BN_new()) == NULL) {
++		BN_free(sig->r);
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+ 	}
+ 
+-	order = &group->order;
+-	if (!order || BN_is_zero(order)) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ECDSA_R_MISSING_PARAMETERS);
++	if (spcf_bn2bin(dsa->p, &q, &q_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE);
+ 		goto err;
+ 	}
+ 
+-	i = BN_num_bits(order);
+-	/* Need to truncate digest if it is too long: first truncate whole
+-	 bytes */
+-	if (8 * dgst_len > i)
+-		dgst_len = (i + 7)/8;
++	/* Get order of the field of private keys into plain buffer */
++	if (spcf_bn2bin (dsa->q, &r, &r_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++ 	}
+ 
+-	if (!BN_bin2bn(dgst, dgst_len, m)) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++	/* sanity test */
++	if (dlen > r_len) {
++		DSAerr(DSA_F_DSA_DO_SIGN, DSA_R_DATA_TOO_LARGE_FOR_KEY_SIZE);
+ 		goto err;
+ 	}
+ 
+-	/* If still too long truncate remaining bits with a shift */
+-	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++	g_len = q_len;
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+ 	}
+ 
+-	/* copy the truncated bits into plain buffer */
+-	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len))  {
+-		fprintf(stderr, "%s:%d: OPENSSL_malloc failec\n", __FUNCTION__, __LINE__);
++	priv_key_len = r_len;
++	/**
++	 * Get private key into a plain buffer. If length is less than
++	 * r_len then add leading padding bytes.
++	 */
++	 if (spcf_bn2bin_ex(dsa->priv_key, &priv_key, &priv_key_len)) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+ 	}
+ 
+-	ret = ECDSA_SIG_new();
+-	if  (!ret) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++	/* Allocate memory to store hash. */
++	f = OPENSSL_malloc (r_len);
++	if (!f) {
++		DSAerr(DSA_F_DSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
+ 		goto err;
+ 	}
+ 
+-	/* check if this is prime or binary EC request */
+-	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_prime_field) {
+-		ec_crv = EC_PRIME;
+-		/* get the generator point pair */
+-		if (!EC_POINT_get_affine_coordinates_GFp (group, EC_GROUP_get0_generator(group),
+-			x, y,ctx)) {
+-			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
+-			goto err;
+-		}
++	/* Add padding, since SEC expects hash to of size r_len */
++	if (dlen < r_len)
++		memset(f, 0, r_len - dlen);
+ 
+-		/* get the ECC curve parameters */
+-		if (!EC_GROUP_get_curve_GFp(group, p, a, b , ctx)) {
+-			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len - dlen, dgst, dlen);
++
++	dlen = r_len;
++
++	memset(kop, 0, sizeof( struct crypt_kop));
++	kop->crk_op = CRK_DSA_SIGN;
++
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop->crk_param[0].crp_p = (void*)f;
++	kop->crk_param[0].crp_nbits = dlen * 8;
++	kop->crk_param[1].crp_p = (void*)q;
++	kop->crk_param[1].crp_nbits = q_len * 8;
++	kop->crk_param[2].crp_p = (void*)r;
++	kop->crk_param[2].crp_nbits = r_len * 8;
++	kop->crk_param[3].crp_p = (void*)g;
++	kop->crk_param[3].crp_nbits = g_len * 8;
++	kop->crk_param[4].crp_p = (void*)priv_key;
++	kop->crk_param[4].crp_nbits = priv_key_len * 8;
++	kop->crk_iparams = 5;
++	kop->cookie = cookie;
++
++	if (cryptodev_asym_async(kop, r_len, sig->r, r_len, sig->s))
++	    goto err;
++
++	return ret;
++err:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++
++		if (kop)
++			free(kop);
++		BN_free(sig->r);
++		BN_free(sig->s);
++		dsaret = (meth->dsa_do_sign)(dgst, dlen, dsa);
++		sig->r = dsaret->r;
++		sig->s = dsaret->s;
++		/* Call user callback immediately */
++		cookie->pkc_callback(cookie, 0);
++		ret = dsaret;
++	}
++	return ret;
++}
++
++static int
++cryptodev_dsa_verify_async(const unsigned char *dgst, int dlen,
++    DSA_SIG *sig, DSA *dsa, struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int q_len = 0, r_len = 0, g_len = 0;
++	int w_len = 0 ,c_len = 0, d_len = 0, ret = 1;
++	unsigned char   * q = NULL, * r = NULL, * w = NULL, * g = NULL;
++	unsigned char   *c = NULL, * d = NULL, *f = NULL;
++
++	if (!kop)
++		goto err;
++
++	if (spcf_bn2bin(dsa->p, &q, &q_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		return ret;
++	}
++
++	/* Get Order of field of private keys */
++	if (spcf_bn2bin(dsa->q, &r, &r_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	g_len = q_len;
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->g, &g, &g_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++	w_len = q_len;
++	/**
++	 * Get public key into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
++	 */
++	if (spcf_bn2bin_ex(dsa->pub_key, &w, &w_len)) {
++		DSAerr(DSA_F_DSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++	/**
++	 * Get the 1st part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	c_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->r, &c, &c_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/**
++	 * Get the 2nd part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	d_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++
++	/* Sanity test */
++	if (dlen > r_len) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Allocate memory to store hash. */
++	f = OPENSSL_malloc (r_len);
++	if (!f) {
++		DSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	if (dlen < r_len)
++		memset(f, 0, r_len - dlen);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len - dlen, dgst, dlen);
++
++	dlen = r_len;
++	memset(kop, 0, sizeof(struct crypt_kop));
++
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->pub_key sig->r sig->s */
++	kop->crk_param[0].crp_p = (void*)f;
++	kop->crk_param[0].crp_nbits = dlen * 8;
++	kop->crk_param[1].crp_p = q;
++	kop->crk_param[1].crp_nbits = q_len * 8;
++	kop->crk_param[2].crp_p = r;
++	kop->crk_param[2].crp_nbits = r_len * 8;
++	kop->crk_param[3].crp_p = g;
++	kop->crk_param[3].crp_nbits = g_len * 8;
++	kop->crk_param[4].crp_p = w;
++	kop->crk_param[4].crp_nbits = w_len * 8;
++	kop->crk_param[5].crp_p = c;
++	kop->crk_param[5].crp_nbits = c_len * 8;
++	kop->crk_param[6].crp_p = d;
++	kop->crk_param[6].crp_nbits = d_len * 8;
++	kop->crk_iparams = 7;
++	kop->crk_op = CRK_DSA_VERIFY;
++	kop->cookie = cookie;
++	if (cryptodev_asym_async(kop, 0, NULL, 0, NULL))
++		goto err;
++
++	return ret;
++err:
++	{
++		const DSA_METHOD *meth = DSA_OpenSSL();
++
++		if (kop)
++			free(kop);
++
++		ret = (meth->dsa_do_verify)(dgst, dlen, sig, dsa);
++		cookie->pkc_callback(cookie, 0);
++	}
++	return ret;
++}
++
++static DSA_METHOD cryptodev_dsa = {
++	"cryptodev DSA method",
++	NULL,
++	NULL,				/* dsa_sign_setup */
++	NULL,
++	NULL,				/* dsa_mod_exp */
++	NULL,
++	NULL,
++	NULL,
++	NULL,
++	NULL,				/* init */
++	NULL,				/* finish */
++	0,	/* flags */
++	NULL	/* app_data */
++};
++
++static ECDSA_METHOD cryptodev_ecdsa = {
++	"cryptodev ECDSA method",
++	NULL,
++	NULL,				/* ecdsa_sign_setup */
++	NULL,
++	NULL,
++	NULL,
++	NULL,
++	0,	/* flags */
++	NULL	/* app_data */
++};
++
++typedef enum ec_curve_s
++{
++	EC_PRIME,
++	EC_BINARY
++} ec_curve_t;
++
++/* ENGINE handler for ECDSA Sign */
++static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
++	int dgst_len, const BIGNUM *in_kinv, const BIGNUM *in_r, EC_KEY *eckey)
++{
++	BIGNUM	*m = NULL, *p = NULL, *a = NULL;
++	BIGNUM  *b = NULL, *x = NULL, *y = NULL;
++	BN_CTX  *ctx = NULL;
++	ECDSA_SIG *ret = NULL;
++	ECDSA_DATA *ecdsa = NULL;
++	unsigned char  * q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL;
++	unsigned char  * s = NULL, *c = NULL, *d = NULL, *f = NULL, *tmp_dgst = NULL;
++	int	i = 0, q_len = 0, priv_key_len = 0, r_len = 0;
++	int	g_len = 0, d_len = 0, ab_len = 0;
++	const BIGNUM   *order = NULL, *priv_key=NULL;
++	const EC_GROUP *group = NULL;
++	struct crypt_kop kop;
++	ec_curve_t ec_crv = EC_PRIME;
++
++	memset(&kop, 0, sizeof(kop));
++	ecdsa = ecdsa_check(eckey);
++	if (!ecdsa) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		return NULL;
++	}
++
++	group = EC_KEY_get0_group(eckey);
++	priv_key = EC_KEY_get0_private_key(eckey);
++
++	if (!group || !priv_key) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		return NULL;
++	}
++
++	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
++		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
++		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
++		(y = BN_new()) == NULL) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	order = &group->order;
++	if (!order || BN_is_zero(order)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ECDSA_R_MISSING_PARAMETERS);
++		goto err;
++	}
++
++	i = BN_num_bits(order);
++	/* Need to truncate digest if it is too long: first truncate whole
++	 bytes */
++	if (8 * dgst_len > i)
++		dgst_len = (i + 7)/8;
++
++	if (!BN_bin2bn(dgst, dgst_len, m)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* If still too long truncate remaining bits with a shift */
++	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* copy the truncated bits into plain buffer */
++	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len))  {
++		fprintf(stderr, "%s:%d: OPENSSL_malloc failec\n", __FUNCTION__, __LINE__);
++		goto err;
++	}
++
++	ret = ECDSA_SIG_new();
++	if  (!ret) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* check if this is prime or binary EC request */
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GFp (group, EC_GROUP_get0_generator(group),
++			x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
+ 			goto err;
+ 		}
+ 	} else if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_characteristic_two_field) {
+@@ -2162,63 +2667,581 @@ static int cryptodev_ecdsa_verify(const unsigned char *dgst, int dgst_len,
+ 	}
+ 
+ 	/**
+-	 * Get the 2nd part of signature into a flat buffer with
+-	 * appropriate padding
++	 * Get the 2nd part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	if (BN_num_bytes(sig->s) < r_len)
++		d_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* memory for message representative */
++	f = malloc(r_len);
++	if (!f) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	memset(f, 0, r_len-dgst_len);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len-dgst_len, tmp_dgst, dgst_len);
++	dgst_len += r_len-dgst_len;
++	kop.crk_op = CRK_DSA_VERIFY;
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop.crk_param[0].crp_p = f;
++	kop.crk_param[0].crp_nbits = dgst_len * 8;
++	kop.crk_param[1].crp_p = q;
++	kop.crk_param[1].crp_nbits = q_len * 8;
++	kop.crk_param[2].crp_p = r;
++	kop.crk_param[2].crp_nbits = r_len * 8;
++	kop.crk_param[3].crp_p = g_xy;
++	kop.crk_param[3].crp_nbits = g_len * 8;
++	kop.crk_param[4].crp_p = w_xy;
++	kop.crk_param[4].crp_nbits = pub_key_len * 8;
++	kop.crk_param[5].crp_p = ab;
++	kop.crk_param[5].crp_nbits = ab_len * 8;
++	kop.crk_param[6].crp_p = c;
++	kop.crk_param[6].crp_nbits = d_len * 8;
++	kop.crk_param[7].crp_p = d;
++	kop.crk_param[7].crp_nbits = d_len * 8;
++	kop.crk_iparams = 8;
++
++	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
++		/*OCF success value is 0, if not zero, change ret to fail*/
++		if(0 == kop.crk_status)
++			ret  = 1;
++	} else {
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++
++		ret = (meth->ecdsa_do_verify)(dgst, dgst_len, sig, eckey);
++	}
++	kop.crk_param[0].crp_p = NULL;
++	zapparams(&kop);
++
++err:
++	return ret;
++}
++
++static int cryptodev_ecdsa_do_sign_async( const unsigned char  *dgst,
++	int dgst_len, const BIGNUM *in_kinv, const BIGNUM *in_r, EC_KEY *eckey,
++	ECDSA_SIG *sig, struct pkc_cookie_s *cookie)
++{
++	BIGNUM	*m = NULL, *p = NULL, *a = NULL;
++	BIGNUM  *b = NULL, *x = NULL, *y = NULL;
++	BN_CTX  *ctx = NULL;
++	ECDSA_SIG *sig_ret = NULL;
++	ECDSA_DATA *ecdsa = NULL;
++	unsigned char  * q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL;
++	unsigned char  * s = NULL, *f = NULL, *tmp_dgst = NULL;
++	int	i = 0, q_len = 0, priv_key_len = 0, r_len = 0;
++	int	g_len = 0, ab_len = 0, ret = 1;
++	const BIGNUM   *order = NULL, *priv_key=NULL;
++	const EC_GROUP *group = NULL;
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	ec_curve_t ec_crv = EC_PRIME;
++
++	if (!(sig->r = BN_new()) || !kop)
++		goto err;
++	if ((sig->s = BN_new()) == NULL) {
++		BN_free(r);
++		goto err;
++	}
++
++	memset(kop, 0, sizeof(struct crypt_kop));
++	ecdsa = ecdsa_check(eckey);
++	if (!ecdsa) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		goto err;
++	}
++
++	group = EC_KEY_get0_group(eckey);
++	priv_key = EC_KEY_get0_private_key(eckey);
++
++	if (!group || !priv_key) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_PASSED_NULL_PARAMETER);
++		goto err;
++	}
++
++	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
++		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
++		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
++		(y = BN_new()) == NULL) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	order = &group->order;
++	if (!order || BN_is_zero(order)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ECDSA_R_MISSING_PARAMETERS);
++		goto err;
++	}
++
++	i = BN_num_bits(order);
++	/* Need to truncate digest if it is too long: first truncate whole
++	 bytes */
++	if (8 * dgst_len > i)
++		dgst_len = (i + 7)/8;
++
++	if (!BN_bin2bn(dgst, dgst_len, m)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* If still too long truncate remaining bits with a shift */
++	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* copy the truncated bits into plain buffer */
++	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len))  {
++		fprintf(stderr, "%s:%d: OPENSSL_malloc failec\n", __FUNCTION__, __LINE__);
++		goto err;
++	}
++
++	/* check if this is prime or binary EC request */
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group))
++				== NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GFp (group,
++			EC_GROUP_get0_generator(group), x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_characteristic_two_field) {
++		ec_crv = EC_BINARY;
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group), x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else {
++		printf("Unsupported Curve\n");
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++		goto err;
++	}
++
++	if (spcf_bn2bin(order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	priv_key_len = r_len;
++
++	/**
++	 * If BN_num_bytes of priv_key returns less then r_len then
++	 * add padding bytes before the key
++	 */
++	if (spcf_bn2bin_ex(priv_key, &s, &priv_key_len))  {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++	ab = eng_copy_curve_points(a, b, ab_len, q_len);
++	if (!ab) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		if (eng_ec_get_cparam(EC_GROUP_get_curve_name(group), ab+q_len, q_len))
++		{
++			unsigned char *c_temp = NULL;
++			int c_temp_len = q_len;
++			if (eng_ec_compute_cparam(b, p, &c_temp, &c_temp_len))
++				memcpy(ab+q_len, c_temp, q_len);
++			else
++				goto err;
++		}
++		kop->curve_type = ECC_BINARY;
++	}
++
++	/* Calculation of Generator point */
++	g_len = 2*q_len;
++	g_xy = eng_copy_curve_points(x, y, g_len, q_len);
++	if (!g_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* memory for message representative */
++	f = malloc(r_len);
++	if (!f) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	memset(f, 0, r_len - dgst_len);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f +  r_len - dgst_len, tmp_dgst, dgst_len);
++
++	dgst_len +=  r_len - dgst_len;
++
++	kop->crk_op = CRK_DSA_SIGN;
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop->crk_param[0].crp_p = f;
++	kop->crk_param[0].crp_nbits = dgst_len * 8;
++	kop->crk_param[1].crp_p = q;
++	kop->crk_param[1].crp_nbits = q_len * 8;
++	kop->crk_param[2].crp_p = r;
++	kop->crk_param[2].crp_nbits = r_len * 8;
++	kop->crk_param[3].crp_p = g_xy;
++	kop->crk_param[3].crp_nbits = g_len * 8;
++	kop->crk_param[4].crp_p = s;
++	kop->crk_param[4].crp_nbits = priv_key_len * 8;
++	kop->crk_param[5].crp_p = ab;
++	kop->crk_param[5].crp_nbits = ab_len * 8;
++	kop->crk_iparams = 6;
++	kop->cookie = cookie;
++
++	if (cryptodev_asym_async(kop, r_len, sig->r , r_len, sig->s))
++		goto err;
++
++	return ret;
++err:
++	{
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++		BN_free(sig->r);
++		BN_free(sig->s);
++		if (kop)
++			free(kop);
++		sig_ret = (meth->ecdsa_do_sign)(dgst, dgst_len, in_kinv, in_r, eckey);
++		sig->r = sig_ret->r;
++		sig->s = sig_ret->s;
++		cookie->pkc_callback(cookie, 0);
++	}
++	return ret;
++}
++
++static int cryptodev_ecdsa_verify_async(const unsigned char *dgst, int dgst_len,
++		const ECDSA_SIG *sig, EC_KEY *eckey, struct pkc_cookie_s *cookie)
++{
++	BIGNUM	*m = NULL, *p = NULL, *a = NULL, *b = NULL;
++	BIGNUM	*x = NULL, *y = NULL, *w_x = NULL, *w_y = NULL;
++  	BN_CTX	*ctx = NULL;
++	ECDSA_DATA	*ecdsa = NULL;
++	unsigned char *q = NULL, *r = NULL, *ab = NULL, *g_xy = NULL, *w_xy = NULL;
++	unsigned char *c = NULL, *d = NULL, *f = NULL, *tmp_dgst = NULL;
++	int	i = 0, q_len = 0, pub_key_len = 0, r_len = 0, c_len = 0, g_len = 0;
++	int	d_len = 0, ab_len = 0, ret = 1;
++	const EC_POINT *pub_key = NULL;
++	const BIGNUM   *order = NULL;
++	const EC_GROUP *group=NULL;
++	ec_curve_t       ec_crv = EC_PRIME;
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++
++	if (!kop)
++		goto err;
++
++	memset(kop, 0, sizeof(struct crypt_kop));
++	ecdsa = ecdsa_check(eckey);
++	if (!ecdsa) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_PASSED_NULL_PARAMETER);
++		goto err;
++	}
++
++	group    = EC_KEY_get0_group(eckey);
++	pub_key  = EC_KEY_get0_public_key(eckey);
++
++	if (!group || !pub_key) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_PASSED_NULL_PARAMETER);
++		goto err;
++	}
++
++	if ((ctx = BN_CTX_new()) == NULL || (m = BN_new()) == NULL ||
++		(a = BN_new()) == NULL || (b = BN_new()) == NULL ||
++		(p = BN_new()) == NULL || (x = BN_new()) == NULL ||
++		(y = BN_new()) == NULL || (w_x = BN_new()) == NULL ||
++		(w_y = BN_new()) == NULL) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	order = &group->order;
++	if (!order || BN_is_zero(order)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ECDSA_R_MISSING_PARAMETERS);
++		goto err;
++	}
++
++	i = BN_num_bits(order);
++	/* Need to truncate digest if it is too long: first truncate whole
++	* bytes */
++	if (8 * dgst_len > i)
++		dgst_len = (i + 7)/8;
++
++	if (!BN_bin2bn(dgst, dgst_len, m)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* If still too long truncate remaining bits with a shift */
++	if ((8 * dgst_len > i) && !BN_rshift(m, m, 8 - (i & 0x7))) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_BN_LIB);
++		goto err;
++	}
++	/* copy the truncated bits into plain buffer */
++	if (spcf_bn2bin(m, &tmp_dgst, &dgst_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* check if this is prime or binary EC request */
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GFp (group,
++			EC_GROUP_get0_generator(group), x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for prime curve */
++		if (!EC_POINT_get_affine_coordinates_GFp (group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b, ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++	} else if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) == NID_X9_62_characteristic_two_field){
++		ec_crv = EC_BINARY;
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the generator point pair */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group),x, y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for binary curve */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++			goto err;
++		}
++	}else {
++		printf("Unsupported Curve\n");
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_EC_LIB);
++		goto err;
++	}
++
++	/* Get the order of the subgroup of private keys */
++	if (spcf_bn2bin((BIGNUM*)order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the irreducible polynomial that creates the field */
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the public key into a flat buffer with appropriate padding */
++	pub_key_len = 2 * q_len;
++
++	w_xy = eng_copy_curve_points (w_x, w_y, pub_key_len, q_len);
++	if (!w_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++
++	ab = eng_copy_curve_points (a, b, ab_len, q_len);
++	if (!ab) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		/* copy b' i.e c(b), instead of only b */
++		eng_ec_get_cparam (EC_GROUP_get_curve_name(group),
++			ab+q_len, q_len);
++		kop->curve_type = ECC_BINARY;
++	}
++
++	/* Calculation of Generator point */
++	g_len = 2 * q_len;
++
++	g_xy = eng_copy_curve_points (x, y, g_len, q_len);
++	if (!g_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/**
++	 * Get the 1st part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	if (BN_num_bytes(sig->r) < r_len)
++		c_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->r, &c, &c_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/**
++	 * Get the 2nd part of signature into a flat buffer with
++	 * appropriate padding
++	 */
++	if (BN_num_bytes(sig->s) < r_len)
++		d_len = r_len;
++
++	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* memory for message representative */
++	f = malloc(r_len);
++	if (!f) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Add padding, since SEC expects hash to of size r_len */
++	memset(f, 0, r_len-dgst_len);
++
++	/* Skip leading bytes if dgst_len < r_len */
++	memcpy(f + r_len-dgst_len, tmp_dgst, dgst_len);
++
++	dgst_len += r_len-dgst_len;
++
++	kop->crk_op = CRK_DSA_VERIFY;
++	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
++	kop->crk_param[0].crp_p = f;
++	kop->crk_param[0].crp_nbits = dgst_len * 8;
++	kop->crk_param[1].crp_p = q;
++	kop->crk_param[1].crp_nbits = q_len * 8;
++	kop->crk_param[2].crp_p = r;
++	kop->crk_param[2].crp_nbits = r_len * 8;
++	kop->crk_param[3].crp_p = g_xy;
++	kop->crk_param[3].crp_nbits = g_len * 8;
++	kop->crk_param[4].crp_p = w_xy;
++	kop->crk_param[4].crp_nbits = pub_key_len * 8;
++	kop->crk_param[5].crp_p = ab;
++	kop->crk_param[5].crp_nbits = ab_len * 8;
++	kop->crk_param[6].crp_p = c;
++	kop->crk_param[6].crp_nbits = d_len * 8;
++	kop->crk_param[7].crp_p = d;
++	kop->crk_param[7].crp_nbits = d_len * 8;
++	kop->crk_iparams = 8;
++	kop->cookie = cookie;
++
++	if (cryptodev_asym_async(kop, 0, NULL, 0, NULL))
++		goto err;
++
++	return ret;
++err:
++	{
++		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++
++		if (kop)
++			free(kop);
++		ret = (meth->ecdsa_do_verify)(dgst, dgst_len, sig, eckey);
++		cookie->pkc_callback(cookie, 0);
++	}
++
++	return ret;
++}
++
++/* Cryptodev DH Key Gen routine */
++static int cryptodev_dh_keygen_async(DH *dh,  struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int ret = 1, g_len;
++	unsigned char *g = NULL;
++
++	if (!kop)
++		goto sw_try;
++
++	if (dh->priv_key == NULL)	{
++		if ((dh->priv_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	if (dh->pub_key == NULL) {
++		if ((dh->pub_key=BN_new()) == NULL)
++			goto sw_try;
++	}
++
++	g_len = BN_num_bytes(dh->p);
++	/**
++	 * Get generator into a plain buffer. If length is less than
++	 * q_len then add leading padding bytes.
+ 	 */
+-	if (BN_num_bytes(sig->s) < r_len)
+-		d_len = r_len;
+-
+-	if (spcf_bn2bin_ex(sig->s, &d, &d_len)) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+-		goto err;
+-	}
+-
+-	/* memory for message representative */
+-	f = malloc(r_len);
+-	if (!f) {
+-		ECDSAerr(ECDSA_F_ECDSA_DO_VERIFY, ERR_R_MALLOC_FAILURE);
+-		goto err;
++	if (spcf_bn2bin_ex(dh->g, &g, &g_len)) {
++		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
+ 	}
+ 
+-	/* Add padding, since SEC expects hash to of size r_len */
+-	memset(f, 0, r_len-dgst_len);
++	memset(kop, 0, sizeof(struct crypt_kop));
++	kop->crk_op = CRK_DH_GENERATE_KEY;
++	if (bn2crparam(dh->p, &kop->crk_param[0]))
++		goto sw_try;
++	if (bn2crparam(dh->q, &kop->crk_param[1]))
++		goto sw_try;
++	kop->crk_param[2].crp_p = g;
++	kop->crk_param[2].crp_nbits = g_len * 8;
++	kop->crk_iparams = 3;
++	kop->cookie = cookie;
+ 
+-	/* Skip leading bytes if dgst_len < r_len */
+-	memcpy(f + r_len-dgst_len, tmp_dgst, dgst_len);
+-	dgst_len += r_len-dgst_len;
+-	kop.crk_op = CRK_DSA_VERIFY;
+-	/* inputs: dgst dsa->p dsa->q dsa->g dsa->priv_key */
+-	kop.crk_param[0].crp_p = f;
+-	kop.crk_param[0].crp_nbits = dgst_len * 8;
+-	kop.crk_param[1].crp_p = q;
+-	kop.crk_param[1].crp_nbits = q_len * 8;
+-	kop.crk_param[2].crp_p = r;
+-	kop.crk_param[2].crp_nbits = r_len * 8;
+-	kop.crk_param[3].crp_p = g_xy;
+-	kop.crk_param[3].crp_nbits = g_len * 8;
+-	kop.crk_param[4].crp_p = w_xy;
+-	kop.crk_param[4].crp_nbits = pub_key_len * 8;
+-	kop.crk_param[5].crp_p = ab;
+-	kop.crk_param[5].crp_nbits = ab_len * 8;
+-	kop.crk_param[6].crp_p = c;
+-	kop.crk_param[6].crp_nbits = d_len * 8;
+-	kop.crk_param[7].crp_p = d;
+-	kop.crk_param[7].crp_nbits = d_len * 8;
+-	kop.crk_iparams = 8;
++	/* pub_key is or prime length while priv key is of length of order */
++	if (cryptodev_asym_async(kop, BN_num_bytes(dh->p), dh->pub_key,
++	    BN_num_bytes(dh->q), dh->priv_key))
++	    goto sw_try;
+ 
+-	if (cryptodev_asym(&kop, 0, NULL, 0, NULL) == 0) {
+-		/*OCF success value is 0, if not zero, change ret to fail*/
+-		if(0 == kop.crk_status)
+-			ret  = 1;
+-	} else {
+-		const ECDSA_METHOD *meth = ECDSA_OpenSSL();
++	return ret;
++sw_try:
++	{
++		const DH_METHOD *meth = DH_OpenSSL();
+ 
+-		ret = (meth->ecdsa_do_verify)(dgst, dgst_len, sig, eckey);
++		if (kop)
++			free(kop);
++		ret = (meth->generate_key)(dh);
++		cookie->pkc_callback(cookie, 0);
+ 	}
+-	kop.crk_param[0].crp_p = NULL;
+-	zapparams(&kop);
+-
+-err:
+ 	return ret;
+ }
+ 
+@@ -2327,6 +3350,54 @@ sw_try:
+ 	return (dhret);
+ }
+ 
++/* Return Length if successful and 0 on failure */
++static int
++cryptodev_dh_compute_key_async(unsigned char *key, const BIGNUM *pub_key,
++		DH *dh, struct pkc_cookie_s *cookie)
++{
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++	int ret = 1;
++	int fd, p_len;
++	unsigned char *padded_pub_key = NULL, *p = NULL;
++
++	fd = *(int *)cookie->eng_handle;
++
++	memset(kop, 0, sizeof(struct crypt_kop));
++	kop->crk_op = CRK_DH_COMPUTE_KEY;
++	/* inputs: dh->priv_key pub_key dh->p key */
++	spcf_bn2bin(dh->p, &p, &p_len);
++	spcf_bn2bin_ex(pub_key, &padded_pub_key, &p_len);
++
++	if (bn2crparam(dh->priv_key, &kop->crk_param[0]))
++		goto err;
++	kop->crk_param[1].crp_p = padded_pub_key;
++	kop->crk_param[1].crp_nbits = p_len * 8;
++	kop->crk_param[2].crp_p = p;
++	kop->crk_param[2].crp_nbits = p_len * 8;
++	kop->crk_iparams = 3;
++
++	kop->cookie = cookie;
++	kop->crk_param[3].crp_p = (void*) key;
++	kop->crk_param[3].crp_nbits = p_len * 8;
++	kop->crk_oparams = 1;
++
++	if (cryptodev_asym_async(kop, 0, NULL, 0, NULL))
++		goto err;
++
++	return p_len;
++err:
++	{
++		const DH_METHOD *meth = DH_OpenSSL();
++
++		if (kop)
++			free(kop);
++		ret = (meth->compute_key)(key, pub_key, dh);
++		/* Call user cookie handler */
++		cookie->pkc_callback(cookie, 0);
++	}
++	return (ret);
++}
++
+ int cryptodev_ecdh_compute_key(void *out, size_t outlen,
+ 	const EC_POINT *pub_key, EC_KEY *ecdh, void *(*KDF)(const void *in, size_t inlen,
+ 	void *out, size_t *outlen))
+@@ -2504,6 +3575,190 @@ err:
+ 	return ret;
+ }
+ 
++int cryptodev_ecdh_compute_key_async(void *out, size_t outlen,
++	const EC_POINT *pub_key, EC_KEY *ecdh, void *(*KDF)(const void *in, size_t inlen,
++	void *out, size_t *outlen), struct pkc_cookie_s *cookie)
++{
++	ec_curve_t       ec_crv = EC_PRIME;
++	unsigned char * q = NULL, *w_xy = NULL, *ab = NULL, *s = NULL, *r = NULL;
++	BIGNUM         * w_x = NULL, *w_y = NULL;
++	int q_len = 0, ab_len = 0, pub_key_len = 0, r_len = 0, priv_key_len = 0;
++	BIGNUM * p = NULL, *a = NULL, *b = NULL;
++	BN_CTX *ctx;
++	EC_POINT *tmp=NULL;
++	BIGNUM *x=NULL, *y=NULL;
++	const BIGNUM *priv_key;
++	const EC_GROUP* group = NULL;
++	int ret = 1;
++	size_t buflen, len;
++	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
++
++	if (!(ctx = BN_CTX_new()) || !kop)
++		 goto err;
++
++	memset(kop, 0, sizeof(struct crypt_kop));
++
++	BN_CTX_start(ctx);
++	x = BN_CTX_get(ctx);
++	y = BN_CTX_get(ctx);
++	p = BN_CTX_get(ctx);
++	a = BN_CTX_get(ctx);
++	b = BN_CTX_get(ctx);
++	w_x = BN_CTX_get(ctx);
++	w_y = BN_CTX_get(ctx);
++
++	if (!x || !y || !p || !a || !b || !w_x || !w_y) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	priv_key = EC_KEY_get0_private_key(ecdh);
++	if (priv_key == NULL) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_NO_PRIVATE_VALUE);
++		goto err;
++	}
++
++	group = EC_KEY_get0_group(ecdh);
++	if ((tmp=EC_POINT_new(group)) == NULL) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	if (EC_METHOD_get_field_type(EC_GROUP_method_of(group)) ==
++		NID_X9_62_prime_field) {
++		ec_crv = EC_PRIME;
++
++		if (!EC_POINT_get_affine_coordinates_GFp(group,
++			EC_GROUP_get0_generator(group), x, y, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_POINT_ARITHMETIC_FAILURE);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GFp(group, p, a, b, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for prime curve */
++		if (!EC_POINT_get_affine_coordinates_GFp (group, pub_key, w_x, w_y,ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++	} else {
++		ec_crv = EC_BINARY;
++
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			EC_GROUP_get0_generator(group), x, y, ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ECDH_R_POINT_ARITHMETIC_FAILURE);
++			goto err;
++		}
++
++		/* get the ECC curve parameters */
++		if (!EC_GROUP_get_curve_GF2m(group, p, a, b , ctx)) {
++			ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++			goto err;
++		}
++
++		/* get the public key pair for binary curve */
++		if (!EC_POINT_get_affine_coordinates_GF2m(group,
++			pub_key, w_x, w_y,ctx)) {
++			ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_EC_LIB);
++			goto err;
++		}
++	}
++
++	/* irreducible polynomial that creates the field */
++	if (spcf_bn2bin((BIGNUM*)&group->order, &r, &r_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Get the irreducible polynomial that creates the field */
++	if (spcf_bn2bin(p, &q, &q_len)) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++		goto err;
++	}
++
++	/* Get the public key into a flat buffer with appropriate padding */
++	pub_key_len = 2 * q_len;
++	w_xy = eng_copy_curve_points (w_x, w_y, pub_key_len, q_len);
++	if (!w_xy) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	/* Generation of ECC curve parameters */
++	ab_len = 2*q_len;
++	ab = eng_copy_curve_points (a, b, ab_len, q_len);
++	if (!ab) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY,ERR_R_BN_LIB);
++		goto err;
++	}
++
++	if (ec_crv == EC_BINARY) {
++		/* copy b' i.e c(b), instead of only b */
++		if (eng_ec_get_cparam(EC_GROUP_get_curve_name(group), ab+q_len, q_len))
++		{
++			unsigned char *c_temp = NULL;
++			int c_temp_len = q_len;
++			if (eng_ec_compute_cparam(b, p, &c_temp, &c_temp_len))
++				memcpy(ab+q_len, c_temp, q_len);
++			else
++				goto err;
++		}
++		kop->curve_type = ECC_BINARY;
++	} else
++		kop->curve_type = ECC_PRIME;
++
++	priv_key_len = r_len;
++
++	/*
++	 * If BN_num_bytes of priv_key returns less then r_len then
++	 * add padding bytes before the key
++	 */
++	if (spcf_bn2bin_ex((BIGNUM *)priv_key, &s, &priv_key_len)) {
++		ECDSAerr(ECDSA_F_ECDSA_DO_SIGN, ERR_R_MALLOC_FAILURE);
++		goto err;
++	}
++
++	buflen = (EC_GROUP_get_degree(group) + 7)/8;
++	len = BN_num_bytes(x);
++	if (len > buflen || q_len < buflen) {
++		ECDHerr(ECDH_F_ECDH_COMPUTE_KEY, ERR_R_INTERNAL_ERROR);
++		goto err;
++	}
++
++	kop->crk_op = CRK_DH_COMPUTE_KEY;
++	kop->crk_param[0].crp_p = (void *) s;
++	kop->crk_param[0].crp_nbits = priv_key_len*8;
++	kop->crk_param[1].crp_p = (void *) w_xy;
++	kop->crk_param[1].crp_nbits = pub_key_len*8;
++	kop->crk_param[2].crp_p = (void *) q;
++	kop->crk_param[2].crp_nbits = q_len*8;
++	kop->crk_param[3].crp_p = (void *) ab;
++	kop->crk_param[3].crp_nbits = ab_len*8;
++	kop->crk_iparams = 4;
++	kop->crk_param[4].crp_p = (void *) out;
++	kop->crk_param[4].crp_nbits = q_len*8;
++	kop->crk_oparams = 1;
++	kop->cookie = cookie;
++	if (cryptodev_asym_async(kop, 0, NULL, 0, NULL))
++		goto err;
++
++	return q_len;
++err:
++	{
++		const ECDH_METHOD *meth = ECDH_OpenSSL();
++
++		if (kop)
++			free(kop);
++		ret = (meth->compute_key)(out, outlen, pub_key, ecdh, KDF);
++		/* Call user cookie handler */
++		cookie->pkc_callback(cookie, 0);
++	}
++	return ret;
++}
+ 
+ static DH_METHOD cryptodev_dh = {
+ 	"cryptodev DH method",
+@@ -2512,6 +3767,8 @@ static DH_METHOD cryptodev_dh = {
+ 	NULL,
+ 	NULL,
+ 	NULL,
++	NULL,
++	NULL,
+ 	0,	/* flags */
+ 	NULL	/* app_data */
+ };
+@@ -2520,6 +3777,7 @@ static ECDH_METHOD cryptodev_ecdh = {
+ 	"cryptodev ECDH method",
+ 	NULL,	/* cryptodev_ecdh_compute_key */
+ 	NULL,
++	NULL,
+ 	0,		/* flags */
+ 	NULL	/* app_data */
+ };
+@@ -2593,12 +3851,19 @@ ENGINE_load_cryptodev(void)
+ 		cryptodev_rsa.rsa_priv_dec = rsa_meth->rsa_priv_dec;
+ 		if (cryptodev_asymfeat & CRF_MOD_EXP) {
+ 			cryptodev_rsa.bn_mod_exp = cryptodev_bn_mod_exp;
+-			if (cryptodev_asymfeat & CRF_MOD_EXP_CRT)
++			cryptodev_rsa.bn_mod_exp_async =
++				 cryptodev_bn_mod_exp_async;
++			if (cryptodev_asymfeat & CRF_MOD_EXP_CRT) {
+ 				cryptodev_rsa.rsa_mod_exp =
+ 				    cryptodev_rsa_mod_exp;
+-			else
++				cryptodev_rsa.rsa_mod_exp_async =
++				    cryptodev_rsa_mod_exp_async;
++			} else {
+ 				cryptodev_rsa.rsa_mod_exp =
+ 				    cryptodev_rsa_nocrt_mod_exp;
++				cryptodev_rsa.rsa_mod_exp_async =
++				    cryptodev_rsa_nocrt_mod_exp_async;
++			}
+ 		}
+ 	}
+ 
+@@ -2606,12 +3871,21 @@ ENGINE_load_cryptodev(void)
+ 		const DSA_METHOD *meth = DSA_OpenSSL();
+ 
+ 		memcpy(&cryptodev_dsa, meth, sizeof(DSA_METHOD));
+-		if (cryptodev_asymfeat & CRF_DSA_SIGN)
++		if (cryptodev_asymfeat & CRF_DSA_SIGN) {
+ 			cryptodev_dsa.dsa_do_sign = cryptodev_dsa_do_sign;
+-		if (cryptodev_asymfeat & CRF_DSA_VERIFY)
++			cryptodev_dsa.dsa_do_sign_async =
++				 cryptodev_dsa_do_sign_async;
++		}
++		if (cryptodev_asymfeat & CRF_DSA_VERIFY) {
+ 			cryptodev_dsa.dsa_do_verify = cryptodev_dsa_verify;
+-		if (cryptodev_asymfeat & CRF_DSA_GENERATE_KEY)
++			cryptodev_dsa.dsa_do_verify_async =
++				 cryptodev_dsa_verify_async;
++		}
++		if (cryptodev_asymfeat & CRF_DSA_GENERATE_KEY) {
+ 			cryptodev_dsa.dsa_keygen = cryptodev_dsa_keygen;
++			cryptodev_dsa.dsa_keygen_async =
++				 cryptodev_dsa_keygen_async;
++		}
+ 	}
+ 
+ 	if (ENGINE_set_DH(engine, &cryptodev_dh)){
+@@ -2620,10 +3894,15 @@ ENGINE_load_cryptodev(void)
+ 		if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY) {
+ 			cryptodev_dh.compute_key =
+ 				cryptodev_dh_compute_key;
++			cryptodev_dh.compute_key_async =
++				cryptodev_dh_compute_key_async;
+ 		}
+ 		if (cryptodev_asymfeat & CRF_DH_GENERATE_KEY) {
+ 			cryptodev_dh.generate_key =
+ 				cryptodev_dh_keygen;
++			cryptodev_dh.generate_key_async =
++				cryptodev_dh_keygen_async;
++
+ 		}
+ 	}
+ 
+@@ -2632,10 +3911,14 @@ ENGINE_load_cryptodev(void)
+ 		memcpy(&cryptodev_ecdsa, meth, sizeof(ECDSA_METHOD));
+ 		if (cryptodev_asymfeat & CRF_DSA_SIGN) {
+ 			cryptodev_ecdsa.ecdsa_do_sign = cryptodev_ecdsa_do_sign;
++			cryptodev_ecdsa.ecdsa_do_sign_async =
++				cryptodev_ecdsa_do_sign_async;
+ 		}
+ 		if (cryptodev_asymfeat & CRF_DSA_VERIFY) {
+ 			cryptodev_ecdsa.ecdsa_do_verify =
+ 				cryptodev_ecdsa_verify;
++			cryptodev_ecdsa.ecdsa_do_verify_async =
++				cryptodev_ecdsa_verify_async;
+ 		}
+ 	}
+ 
+@@ -2644,9 +3927,16 @@ ENGINE_load_cryptodev(void)
+ 		memcpy(&cryptodev_ecdh, ecdh_meth, sizeof(ECDH_METHOD));
+ 		if (cryptodev_asymfeat & CRF_DH_COMPUTE_KEY) {
+ 			cryptodev_ecdh.compute_key = cryptodev_ecdh_compute_key;
++			cryptodev_ecdh.compute_key_async =
++				 cryptodev_ecdh_compute_key_async;
+ 		}
+ 	}
+ 
++	ENGINE_set_check_pkc_availability(engine, cryptodev_check_availability);
++	ENGINE_set_close_instance(engine, cryptodev_close_instance);
++	ENGINE_set_init_instance(engine, cryptodev_init_instance);
++	ENGINE_set_async_map(engine, ENGINE_ALLPKC_ASYNC);
++
+ 	ENGINE_add(engine);
+ 	ENGINE_free(engine);
+ 	ERR_clear_error();
+diff --git a/crypto/engine/eng_int.h b/crypto/engine/eng_int.h
+index 451ef8f..8fc3077 100644
+--- a/crypto/engine/eng_int.h
++++ b/crypto/engine/eng_int.h
+@@ -181,7 +181,29 @@ struct engine_st
+ 	ENGINE_LOAD_KEY_PTR load_pubkey;
+ 
+ 	ENGINE_SSL_CLIENT_CERT_PTR load_ssl_client_cert;
+-
++	/*
++	 * Instantiate Engine handle to be passed in check_pkc_availability
++	 * Ensure that Engine is instantiated before any pkc asynchronous call.
++	 */
++	void *(*engine_init_instance)(void);
++	/*
++	 * Instantiated Engine handle will be closed with this call.
++	 * Ensure that no pkc asynchronous call is made after this call
++	 */
++	void (*engine_close_instance)(void *handle);
++	/*
++	 * Check availability will extract the data from kernel.
++	 * eng_handle: This is the Engine handle corresponds to which
++	 * the cookies needs to be polled.
++	 * return 0 if cookie available else 1
++	 */
++	int (*check_pkc_availability)(void *eng_handle);
++	/*
++	 * The following map is used to check if the engine supports asynchronous implementation
++	 * ENGINE_ASYNC_FLAG* for available bitmap. Any application checking for asynchronous
++	 * implementation need to check this features using "int ENGINE_get_async_map(engine *)";
++	 */
++	int async_map;
+ 	const ENGINE_CMD_DEFN *cmd_defns;
+ 	int flags;
+ 	/* reference count on the structure itself */
+diff --git a/crypto/engine/eng_lib.c b/crypto/engine/eng_lib.c
+index 18a6664..6fa621c 100644
+--- a/crypto/engine/eng_lib.c
++++ b/crypto/engine/eng_lib.c
+@@ -98,7 +98,11 @@ void engine_set_all_null(ENGINE *e)
+ 	e->ctrl = NULL;
+ 	e->load_privkey = NULL;
+ 	e->load_pubkey = NULL;
++	e->check_pkc_availability = NULL;
++	e->engine_init_instance = NULL;
++	e->engine_close_instance = NULL;
+ 	e->cmd_defns = NULL;
++	e->async_map = 0;
+ 	e->flags = 0;
+ 	}
+ 
+@@ -233,6 +237,48 @@ int ENGINE_set_id(ENGINE *e, const char *id)
+ 	return 1;
+ 	}
+ 
++void ENGINE_set_init_instance(ENGINE *e, void *(*engine_init_instance)(void))
++	{
++		e->engine_init_instance = engine_init_instance;
++	}
++
++void ENGINE_set_close_instance(ENGINE *e,
++	void (*engine_close_instance)(void *))
++	{
++		e->engine_close_instance = engine_close_instance;
++	}
++
++void ENGINE_set_async_map(ENGINE *e, int async_map)
++	{
++		e->async_map = async_map;
++	}
++
++void *ENGINE_init_instance(ENGINE *e)
++	{
++		return e->engine_init_instance();
++	}
++
++void ENGINE_close_instance(ENGINE *e, void *eng_handle)
++	{
++		e->engine_close_instance(eng_handle);
++	}
++
++int ENGINE_get_async_map(ENGINE *e)
++	{
++		return e->async_map;
++	}
++
++void ENGINE_set_check_pkc_availability(ENGINE *e,
++	int (*check_pkc_availability)(void *eng_handle))
++	{
++		e->check_pkc_availability = check_pkc_availability;
++	}
++
++int ENGINE_check_pkc_availability(ENGINE *e, void *eng_handle)
++	{
++		return e->check_pkc_availability(eng_handle);
++	}
++
+ int ENGINE_set_name(ENGINE *e, const char *name)
+ 	{
+ 	if(name == NULL)
+diff --git a/crypto/engine/engine.h b/crypto/engine/engine.h
+index 237a6c9..ccff86a 100644
+--- a/crypto/engine/engine.h
++++ b/crypto/engine/engine.h
+@@ -473,6 +473,30 @@ ENGINE *ENGINE_new(void);
+ int ENGINE_free(ENGINE *e);
+ int ENGINE_up_ref(ENGINE *e);
+ int ENGINE_set_id(ENGINE *e, const char *id);
++void ENGINE_set_init_instance(ENGINE *e, void *(*engine_init_instance)(void));
++void ENGINE_set_close_instance(ENGINE *e,
++	void (*engine_free_instance)(void *));
++/*
++ * Following FLAGS are bitmap store in async_map to set asynchronous interface capability
++ *of the engine
++ */
++#define ENGINE_RSA_ASYNC 0x0001
++#define ENGINE_DSA_ASYNC 0x0002
++#define ENGINE_DH_ASYNC 0x0004
++#define ENGINE_ECDSA_ASYNC 0x0008
++#define ENGINE_ECDH_ASYNC 0x0010
++#define ENGINE_ALLPKC_ASYNC 0x001F
++/* Engine implementation will set the bitmap based on above flags using following API */
++void ENGINE_set_async_map(ENGINE *e, int async_map);
++ /* Application need to check the bitmap based on above flags using following API
++  * to confirm asynchronous methods supported
++  */
++int ENGINE_get_async_map(ENGINE *e);
++void *ENGINE_init_instance(ENGINE *e);
++void ENGINE_close_instance(ENGINE *e, void *eng_handle);
++void ENGINE_set_check_pkc_availability(ENGINE *e,
++	int (*check_pkc_availability)(void *eng_handle));
++int ENGINE_check_pkc_availability(ENGINE *e, void *eng_handle);
+ int ENGINE_set_name(ENGINE *e, const char *name);
+ int ENGINE_set_RSA(ENGINE *e, const RSA_METHOD *rsa_meth);
+ int ENGINE_set_DSA(ENGINE *e, const DSA_METHOD *dsa_meth);
+diff --git a/crypto/rsa/rsa.h b/crypto/rsa/rsa.h
+index 5f269e5..6ef1b15 100644
+--- a/crypto/rsa/rsa.h
++++ b/crypto/rsa/rsa.h
+@@ -101,6 +101,29 @@ struct rsa_meth_st
+ 	int (*bn_mod_exp)(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
+ 			  const BIGNUM *m, BN_CTX *ctx,
+ 			  BN_MONT_CTX *m_ctx); /* Can be null */
++	/*
++	 * Cookie in the following _async variant must be allocated before
++	 * submission and can be freed once its corresponding callback
++	 * handler is called
++	 */
++	int (*rsa_pub_enc_asyn)(int flen,const unsigned char *from,
++			   unsigned char *to, RSA *rsa, int padding,
++			   struct pkc_cookie_s *cookie);
++	int (*rsa_pub_dec_async)(int flen,const unsigned char *from,
++			   unsigned char *to, RSA *rsa, int padding,
++			   struct pkc_cookie_s *cookie);
++	int (*rsa_priv_enc_async)(int flen,const unsigned char *from,
++			    unsigned char *to, RSA *rsa, int padding,
++			    struct pkc_cookie_s *cookie);
++	int (*rsa_priv_dec_async)(int flen,const unsigned char *from,
++			    unsigned char *to, RSA *rsa, int padding,
++			    struct pkc_cookie_s *cookie);
++	int (*rsa_mod_exp_async)(BIGNUM *r0, const BIGNUM *I, RSA *rsa,
++			    BN_CTX *ctx, struct pkc_cookie_s *cookie);
++	int (*bn_mod_exp_async)(BIGNUM *r, const BIGNUM *a, const BIGNUM *p,
++			  const BIGNUM *m, BN_CTX *ctx,
++			  BN_MONT_CTX *m_ctx, struct pkc_cookie_s *cookie);
++
+ 	int (*init)(RSA *rsa);		/* called at new */
+ 	int (*finish)(RSA *rsa);	/* called at free */
+ 	int flags;			/* RSA_METHOD_FLAG_* things */
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0009-eng_cryptodev-extend-TLS-offload-with-new-algorithms.patch b/recipes-connectivity/openssl/openssl-fsl/0009-eng_cryptodev-extend-TLS-offload-with-new-algorithms.patch
new file mode 100644
index 0000000..a417884
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0009-eng_cryptodev-extend-TLS-offload-with-new-algorithms.patch
@@ -0,0 +1,106 @@
+From 6555c11c9f62fc37c60bb335cfeb5c9d641e493a Mon Sep 17 00:00:00 2001
+From: Cristian Stoica <cristian.stoica at freescale.com>
+Date: Fri, 21 Mar 2014 16:22:27 +0200
+Subject: [PATCH][fsl 09/15] eng_cryptodev: extend TLS offload with new
+ algorithms
+
+Upstream-status: Pending
+
+- aes-192-cbc-hmac-sha1
+- aes-256-cbc-hmac-sha1
+
+Signed-off-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |   41 +++++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 41 insertions(+)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index c5e8fb3..e2d4c53 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -248,6 +248,8 @@ static struct {
+ 	{ CRYPTO_CAST_CBC,      NID_cast5_cbc,    8,  16, 0},
+ 	{ CRYPTO_SKIPJACK_CBC,  NID_undef,        0,  0,  0},
+ 	{ CRYPTO_TLS10_AES_CBC_HMAC_SHA1, NID_aes_128_cbc_hmac_sha1, 16, 16, 20},
++	{ CRYPTO_TLS10_AES_CBC_HMAC_SHA1, NID_aes_192_cbc_hmac_sha1, 16, 24, 20},
++	{ CRYPTO_TLS10_AES_CBC_HMAC_SHA1, NID_aes_256_cbc_hmac_sha1, 16, 32, 20},
+ 	{ 0, NID_undef,	0, 0, 0},
+ };
+ 
+@@ -536,6 +538,8 @@ static int cryptodev_aead_cipher(EVP_CIPHER_CTX *ctx, unsigned char *out,
+ 	/* TODO: make a seamless integration with cryptodev flags */
+ 	switch (ctx->cipher->nid) {
+ 	case NID_aes_128_cbc_hmac_sha1:
++	case NID_aes_192_cbc_hmac_sha1:
++	case NID_aes_256_cbc_hmac_sha1:
+ 		cryp.flags = COP_FLAG_AEAD_TLS_TYPE;
+ 	}
+ 	cryp.ses = sess->ses;
+@@ -729,6 +733,8 @@ static int cryptodev_cbc_hmac_sha1_ctrl(EVP_CIPHER_CTX *ctx, int type, int arg,
+ 		/* TODO: this should be an extension of EVP_CIPHER struct */
+ 		switch (ctx->cipher->nid) {
+ 		case NID_aes_128_cbc_hmac_sha1:
++		case NID_aes_192_cbc_hmac_sha1:
++		case NID_aes_256_cbc_hmac_sha1:
+ 			maclen = SHA_DIGEST_LENGTH;
+ 		}
+ 
+@@ -871,6 +877,33 @@ const EVP_CIPHER cryptodev_aes_128_cbc_hmac_sha1 = {
+ 	NULL
+ };
+ 
++const EVP_CIPHER cryptodev_aes_192_cbc_hmac_sha1 = {
++	NID_aes_192_cbc_hmac_sha1,
++	16, 24, 16,
++	EVP_CIPH_CBC_MODE | EVP_CIPH_FLAG_AEAD_CIPHER,
++	cryptodev_init_aead_key,
++	cryptodev_aead_cipher,
++	cryptodev_cleanup,
++	sizeof(struct dev_crypto_state),
++	EVP_CIPHER_set_asn1_iv,
++	EVP_CIPHER_get_asn1_iv,
++	cryptodev_cbc_hmac_sha1_ctrl,
++	NULL
++};
++
++const EVP_CIPHER cryptodev_aes_256_cbc_hmac_sha1 = {
++	NID_aes_256_cbc_hmac_sha1,
++	16, 32, 16,
++	EVP_CIPH_CBC_MODE | EVP_CIPH_FLAG_AEAD_CIPHER,
++	cryptodev_init_aead_key,
++	cryptodev_aead_cipher,
++	cryptodev_cleanup,
++	sizeof(struct dev_crypto_state),
++	EVP_CIPHER_set_asn1_iv,
++	EVP_CIPHER_get_asn1_iv,
++	cryptodev_cbc_hmac_sha1_ctrl,
++	NULL
++};
+ /*
+  * Registered by the ENGINE when used to find out how to deal with
+  * a particular NID in the ENGINE. this says what we'll do at the
+@@ -911,6 +944,12 @@ cryptodev_engine_ciphers(ENGINE *e, const EVP_CIPHER **cipher,
+ 	case NID_aes_128_cbc_hmac_sha1:
+ 		*cipher = &cryptodev_aes_128_cbc_hmac_sha1;
+ 		break;
++	case NID_aes_192_cbc_hmac_sha1:
++		*cipher = &cryptodev_aes_192_cbc_hmac_sha1;
++		break;
++	case NID_aes_256_cbc_hmac_sha1:
++		*cipher = &cryptodev_aes_256_cbc_hmac_sha1;
++		break;
+ 	default:
+ 		*cipher = NULL;
+ 		break;
+@@ -3830,6 +3869,8 @@ ENGINE_load_cryptodev(void)
+ 	put_dev_crypto(fd);
+ 
+ 	EVP_add_cipher(&cryptodev_aes_128_cbc_hmac_sha1);
++	EVP_add_cipher(&cryptodev_aes_192_cbc_hmac_sha1);
++	EVP_add_cipher(&cryptodev_aes_256_cbc_hmac_sha1);
+ 	if (!ENGINE_set_id(engine, "cryptodev") ||
+ 	    !ENGINE_set_name(engine, "BSD cryptodev engine") ||
+ 	    !ENGINE_set_ciphers(engine, cryptodev_engine_ciphers) ||
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0010-Add-RSA-keygen-operation-and-support-gendsa-command-.patch b/recipes-connectivity/openssl/openssl-fsl/0010-Add-RSA-keygen-operation-and-support-gendsa-command-.patch
new file mode 100644
index 0000000..4eaaeaa
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0010-Add-RSA-keygen-operation-and-support-gendsa-command-.patch
@@ -0,0 +1,153 @@
+From a08f27a22d2c78f058b63dd2565925ca92ad08b2 Mon Sep 17 00:00:00 2001
+From: Hou Zhiqiang <B48286 at freescale.com>
+Date: Wed, 2 Apr 2014 16:10:43 +0800
+Subject: [PATCH][fsl 10/15] Add RSA keygen operation and support gendsa
+ command with hardware engine
+
+Upstream-status: Pending
+
+Signed-off-by: Hou Zhiqiang <B48286 at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |  118 +++++++++++++++++++++++++++++++++++++++++
+ 1 file changed, 118 insertions(+)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index e2d4c53..0a6567c 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -1912,6 +1912,121 @@ err:
+ 	return dsaret;
+ }
+ 
++/* Cryptodev RSA Key Gen routine */
++static int cryptodev_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
++{
++	struct crypt_kop kop;
++	int ret, fd;
++	int p_len, q_len;
++	int i;
++
++	if ((fd = get_asym_dev_crypto()) < 0)
++		return fd;
++
++	if(!rsa->n && ((rsa->n=BN_new()) == NULL)) goto err;
++	if(!rsa->d && ((rsa->d=BN_new()) == NULL)) goto err;
++	if(!rsa->e && ((rsa->e=BN_new()) == NULL)) goto err;
++	if(!rsa->p && ((rsa->p=BN_new()) == NULL)) goto err;
++	if(!rsa->q && ((rsa->q=BN_new()) == NULL)) goto err;
++	if(!rsa->dmp1 && ((rsa->dmp1=BN_new()) == NULL)) goto err;
++	if(!rsa->dmq1 && ((rsa->dmq1=BN_new()) == NULL)) goto err;
++	if(!rsa->iqmp && ((rsa->iqmp=BN_new()) == NULL)) goto err;
++
++	BN_copy(rsa->e, e);
++
++	p_len = (bits+1) / (2 * 8);
++	q_len = (bits - p_len * 8) / 8;
++	memset(&kop, 0, sizeof kop);
++	kop.crk_op = CRK_RSA_GENERATE_KEY;
++
++	/* p length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = p_len * 8;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, p_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* q length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(q_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = q_len * 8;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, q_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* n length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + q_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = bits;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0x00, p_len + q_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* d length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + q_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = bits;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, p_len + q_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* dp1 length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = p_len * 8;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, p_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* dq1 length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(q_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = q_len * 8;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, q_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++	/* i length */
++	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + 1, sizeof(char));
++	if (!kop.crk_param[kop.crk_iparams].crp_p)
++		goto err;
++	kop.crk_param[kop.crk_iparams].crp_nbits = p_len * 8;
++	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, p_len + 1);
++	kop.crk_iparams++;
++	kop.crk_oparams++;
++
++	if (ioctl(fd, CIOCKEY, &kop) == 0) {
++		BN_bin2bn(kop.crk_param[0].crp_p,
++				p_len, rsa->p);
++		BN_bin2bn(kop.crk_param[1].crp_p,
++				q_len, rsa->q);
++		BN_bin2bn(kop.crk_param[2].crp_p,
++				bits / 8, rsa->n);
++		BN_bin2bn(kop.crk_param[3].crp_p,
++				bits / 8, rsa->d);
++		BN_bin2bn(kop.crk_param[4].crp_p,
++				p_len, rsa->dmp1);
++		BN_bin2bn(kop.crk_param[5].crp_p,
++				q_len, rsa->dmq1);
++		BN_bin2bn(kop.crk_param[6].crp_p,
++				p_len, rsa->iqmp);
++		return 1;
++	}
++sw_try:
++	{
++		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
++		ret = (meth->rsa_keygen)(rsa, bits, e, cb);
++	}
++	return ret;
++
++err:
++	for (i = 0; i < CRK_MAXPARAM; i++)
++		free(kop.crk_param[i].crp_p);
++	return 0;
++
++}
++
+ /* Cryptodev DSA Key Gen routine */
+ static int cryptodev_dsa_keygen(DSA *dsa)
+ {
+@@ -3905,6 +4020,9 @@ ENGINE_load_cryptodev(void)
+ 				cryptodev_rsa.rsa_mod_exp_async =
+ 				    cryptodev_rsa_nocrt_mod_exp_async;
+ 			}
++			if (cryptodev_asymfeat & CRF_RSA_GENERATE_KEY)
++				cryptodev_rsa.rsa_keygen =
++					cryptodev_rsa_keygen;
+ 		}
+ 	}
+ 
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0011-RSA-Keygen-Fix.patch b/recipes-connectivity/openssl/openssl-fsl/0011-RSA-Keygen-Fix.patch
new file mode 100644
index 0000000..b2d636a
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0011-RSA-Keygen-Fix.patch
@@ -0,0 +1,64 @@
+From f44fc935d5bc601cd625a64a366e64b19f2bb730 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Wed, 16 Apr 2014 22:53:04 +0545
+Subject: [PATCH][fsl 11/15] RSA Keygen Fix
+
+Upstream-status: Pending
+
+If Kernel driver doesn't support RSA Keygen or same returns
+error handling the keygen operation, the keygen is gracefully
+handled by software supported rsa_keygen handler
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |   12 +++++++-----
+ 1 file changed, 7 insertions(+), 5 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 0a6567c..5d54f7e 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -1921,7 +1921,7 @@ static int cryptodev_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
+ 	int i;
+ 
+ 	if ((fd = get_asym_dev_crypto()) < 0)
+-		return fd;
++		goto sw_try;
+ 
+ 	if(!rsa->n && ((rsa->n=BN_new()) == NULL)) goto err;
+ 	if(!rsa->d && ((rsa->d=BN_new()) == NULL)) goto err;
+@@ -1942,7 +1942,7 @@ static int cryptodev_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
+ 	/* p length */
+ 	kop.crk_param[kop.crk_iparams].crp_p = calloc(p_len + 1, sizeof(char));
+ 	if (!kop.crk_param[kop.crk_iparams].crp_p)
+-		goto err;
++		goto sw_try;
+ 	kop.crk_param[kop.crk_iparams].crp_nbits = p_len * 8;
+ 	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, p_len + 1);
+ 	kop.crk_iparams++;
+@@ -1950,7 +1950,7 @@ static int cryptodev_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
+ 	/* q length */
+ 	kop.crk_param[kop.crk_iparams].crp_p = calloc(q_len + 1, sizeof(char));
+ 	if (!kop.crk_param[kop.crk_iparams].crp_p)
+-		goto err;
++		goto sw_try;
+ 	kop.crk_param[kop.crk_iparams].crp_nbits = q_len * 8;
+ 	memset(kop.crk_param[kop.crk_iparams].crp_p, 0xff, q_len + 1);
+ 	kop.crk_iparams++;
+@@ -2015,8 +2015,10 @@ static int cryptodev_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
+ 	}
+ sw_try:
+ 	{
+-		const RSA_METHOD *meth = RSA_PKCS1_SSLeay();
+-		ret = (meth->rsa_keygen)(rsa, bits, e, cb);
++		const RSA_METHOD *meth = rsa->meth;
++		rsa->meth = RSA_PKCS1_SSLeay();
++		ret = RSA_generate_key_ex(rsa, bits, e, cb);
++		rsa->meth = meth;
+ 	}
+ 	return ret;
+ 
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0012-Removed-local-copy-of-curve_t-type.patch b/recipes-connectivity/openssl/openssl-fsl/0012-Removed-local-copy-of-curve_t-type.patch
new file mode 100644
index 0000000..077b08e
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0012-Removed-local-copy-of-curve_t-type.patch
@@ -0,0 +1,164 @@
+From 7a6848210c3b2f42aed4de60646e0e63c0e35fcb Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Thu, 17 Apr 2014 06:57:59 +0545
+Subject: [PATCH][fsl 12/15] Removed local copy of curve_t type
+
+Upstream-status: Pending
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c    |   34 ++++++++++++++--------------------
+ crypto/engine/eng_cryptodev_ec.h |    7 -------
+ 2 files changed, 14 insertions(+), 27 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 5d54f7e..33447c8 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -2404,12 +2404,6 @@ static ECDSA_METHOD cryptodev_ecdsa = {
+ 	NULL	/* app_data */
+ };
+ 
+-typedef enum ec_curve_s
+-{
+-	EC_PRIME,
+-	EC_BINARY
+-} ec_curve_t;
+-
+ /* ENGINE handler for ECDSA Sign */
+ static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
+ 	int dgst_len, const BIGNUM *in_kinv, const BIGNUM *in_r, EC_KEY *eckey)
+@@ -2426,7 +2420,7 @@ static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
+ 	const BIGNUM   *order = NULL, *priv_key=NULL;
+ 	const EC_GROUP *group = NULL;
+ 	struct crypt_kop kop;
+-	ec_curve_t ec_crv = EC_PRIME;
++	enum ec_curve_t ec_crv = EC_PRIME;
+ 
+ 	memset(&kop, 0, sizeof(kop));
+ 	ecdsa = ecdsa_check(eckey);
+@@ -2559,7 +2553,7 @@ static ECDSA_SIG *cryptodev_ecdsa_do_sign( const unsigned char  *dgst,
+ 			else
+ 				goto err;
+ 		}
+-		kop.curve_type = ECC_BINARY;
++		kop.curve_type = EC_BINARY;
+ 	}
+ 
+ 	/* Calculation of Generator point */
+@@ -2653,7 +2647,7 @@ static int cryptodev_ecdsa_verify(const unsigned char *dgst, int dgst_len,
+ 	const EC_POINT *pub_key = NULL;
+ 	const BIGNUM   *order = NULL;
+ 	const EC_GROUP *group=NULL;
+-	ec_curve_t       ec_crv = EC_PRIME;
++	enum ec_curve_t       ec_crv = EC_PRIME;
+ 	struct crypt_kop kop;
+ 
+ 	memset(&kop, 0, sizeof kop);
+@@ -2798,7 +2792,7 @@ static int cryptodev_ecdsa_verify(const unsigned char *dgst, int dgst_len,
+ 			else
+ 				goto err;
+ 		}
+-		kop.curve_type = ECC_BINARY;
++		kop.curve_type = EC_BINARY;
+ 	}
+ 
+ 	/* Calculation of Generator point */
+@@ -2899,7 +2893,7 @@ static int cryptodev_ecdsa_do_sign_async( const unsigned char  *dgst,
+ 	const BIGNUM   *order = NULL, *priv_key=NULL;
+ 	const EC_GROUP *group = NULL;
+ 	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
+-	ec_curve_t ec_crv = EC_PRIME;
++	enum ec_curve_t ec_crv = EC_PRIME;
+ 
+ 	if (!(sig->r = BN_new()) || !kop)
+ 		goto err;
+@@ -3035,7 +3029,7 @@ static int cryptodev_ecdsa_do_sign_async( const unsigned char  *dgst,
+ 			else
+ 				goto err;
+ 		}
+-		kop->curve_type = ECC_BINARY;
++		kop->curve_type = EC_BINARY;
+ 	}
+ 
+ 	/* Calculation of Generator point */
+@@ -3111,7 +3105,7 @@ static int cryptodev_ecdsa_verify_async(const unsigned char *dgst, int dgst_len,
+ 	const EC_POINT *pub_key = NULL;
+ 	const BIGNUM   *order = NULL;
+ 	const EC_GROUP *group=NULL;
+-	ec_curve_t       ec_crv = EC_PRIME;
++	enum ec_curve_t       ec_crv = EC_PRIME;
+ 	struct crypt_kop *kop = malloc(sizeof(struct crypt_kop));
+ 
+ 	if (!kop)
+@@ -3253,7 +3247,7 @@ static int cryptodev_ecdsa_verify_async(const unsigned char *dgst, int dgst_len,
+ 		/* copy b' i.e c(b), instead of only b */
+ 		eng_ec_get_cparam (EC_GROUP_get_curve_name(group),
+ 			ab+q_len, q_len);
+-		kop->curve_type = ECC_BINARY;
++		kop->curve_type = EC_BINARY;
+ 	}
+ 
+ 	/* Calculation of Generator point */
+@@ -3558,7 +3552,7 @@ int cryptodev_ecdh_compute_key(void *out, size_t outlen,
+ 	const EC_POINT *pub_key, EC_KEY *ecdh, void *(*KDF)(const void *in, size_t inlen,
+ 	void *out, size_t *outlen))
+ {
+-	ec_curve_t       ec_crv = EC_PRIME;
++	enum ec_curve_t       ec_crv = EC_PRIME;
+ 	unsigned char * q = NULL, *w_xy = NULL, *ab = NULL, *s = NULL, *r = NULL;
+ 	BIGNUM         * w_x = NULL, *w_y = NULL;
+ 	int q_len = 0, ab_len = 0, pub_key_len = 0, r_len = 0, priv_key_len = 0;
+@@ -3684,9 +3678,9 @@ int cryptodev_ecdh_compute_key(void *out, size_t outlen,
+ 			else
+ 				goto err;
+ 		}
+-		kop.curve_type = ECC_BINARY;
++		kop.curve_type = EC_BINARY;
+ 	} else
+-		kop.curve_type = ECC_PRIME;
++		kop.curve_type = EC_PRIME;
+ 
+ 	priv_key_len = r_len;
+ 
+@@ -3735,7 +3729,7 @@ int cryptodev_ecdh_compute_key_async(void *out, size_t outlen,
+ 	const EC_POINT *pub_key, EC_KEY *ecdh, void *(*KDF)(const void *in, size_t inlen,
+ 	void *out, size_t *outlen), struct pkc_cookie_s *cookie)
+ {
+-	ec_curve_t       ec_crv = EC_PRIME;
++	enum ec_curve_t       ec_crv = EC_PRIME;
+ 	unsigned char * q = NULL, *w_xy = NULL, *ab = NULL, *s = NULL, *r = NULL;
+ 	BIGNUM         * w_x = NULL, *w_y = NULL;
+ 	int q_len = 0, ab_len = 0, pub_key_len = 0, r_len = 0, priv_key_len = 0;
+@@ -3863,9 +3857,9 @@ int cryptodev_ecdh_compute_key_async(void *out, size_t outlen,
+ 			else
+ 				goto err;
+ 		}
+-		kop->curve_type = ECC_BINARY;
++		kop->curve_type = EC_BINARY;
+ 	} else
+-		kop->curve_type = ECC_PRIME;
++		kop->curve_type = EC_PRIME;
+ 
+ 	priv_key_len = r_len;
+ 
+diff --git a/crypto/engine/eng_cryptodev_ec.h b/crypto/engine/eng_cryptodev_ec.h
+index 77aee71..a4b8da5 100644
+--- a/crypto/engine/eng_cryptodev_ec.h
++++ b/crypto/engine/eng_cryptodev_ec.h
+@@ -286,11 +286,4 @@ static inline unsigned char *eng_copy_curve_points(BIGNUM * x, BIGNUM * y,
+ 
+ 	return xy;
+ }
+-
+-enum curve_t {
+-	DISCRETE_LOG,
+-	ECC_PRIME,
+-	ECC_BINARY,
+-	MAX_ECC_TYPE
+-};
+ #endif
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0013-Modulus-parameter-is-not-populated-by-dhparams.patch b/recipes-connectivity/openssl/openssl-fsl/0013-Modulus-parameter-is-not-populated-by-dhparams.patch
new file mode 100644
index 0000000..11f0622
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0013-Modulus-parameter-is-not-populated-by-dhparams.patch
@@ -0,0 +1,43 @@
+From 8aabfeb1308188a46d3f370cd757de130e73eb9b Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Tue, 22 Apr 2014 22:58:33 +0545
+Subject: [PATCH][fsl 13/15] Modulus parameter is not populated by dhparams
+
+Upstream-status: Pending
+
+When dhparams are created, modulus parameter required for
+private key generation is not populated. So, falling back
+to software for proper population of modulus parameters followed
+by private key generation
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |    4 ++--
+ 1 file changed, 2 insertions(+), 2 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 33447c8..8de8f09 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -3370,7 +3370,7 @@ static int cryptodev_dh_keygen_async(DH *dh,  struct pkc_cookie_s *cookie)
+ 	kop->crk_op = CRK_DH_GENERATE_KEY;
+ 	if (bn2crparam(dh->p, &kop->crk_param[0]))
+ 		goto sw_try;
+-	if (bn2crparam(dh->q, &kop->crk_param[1]))
++	if (!dh->q || bn2crparam(dh->q, &kop->crk_param[1]))
+ 		goto sw_try;
+ 	kop->crk_param[2].crp_p = g;
+ 	kop->crk_param[2].crp_nbits = g_len * 8;
+@@ -3425,7 +3425,7 @@ static int cryptodev_dh_keygen(DH *dh)
+ 	kop.crk_op = CRK_DH_GENERATE_KEY;
+ 	if (bn2crparam(dh->p, &kop.crk_param[0]))
+ 		goto sw_try;
+-	if (bn2crparam(dh->q, &kop.crk_param[1]))
++	if (!dh->q || bn2crparam(dh->q, &kop.crk_param[1]))
+ 		goto sw_try;
+ 	kop.crk_param[2].crp_p = g;
+ 	kop.crk_param[2].crp_nbits = g_len * 8;
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0014-SW-Backoff-mechanism-for-dsa-keygen.patch b/recipes-connectivity/openssl/openssl-fsl/0014-SW-Backoff-mechanism-for-dsa-keygen.patch
new file mode 100644
index 0000000..e5aa1ba
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0014-SW-Backoff-mechanism-for-dsa-keygen.patch
@@ -0,0 +1,53 @@
+From 8b1ed323d08dce8b6e303ce63a82337543e9187f Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Thu, 24 Apr 2014 00:35:34 +0545
+Subject: [PATCH][fsl 14/15] SW Backoff mechanism for dsa keygen
+
+Upstream-status: Pending
+
+DSA Keygen is not handled in default openssl dsa method. Due to
+same null function pointer in SW DSA method, the backoff for dsa
+keygen gives segmentation fault.
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |   12 ++++++++----
+ 1 file changed, 8 insertions(+), 4 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 8de8f09..7c2661f 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -2075,8 +2075,10 @@ static int cryptodev_dsa_keygen(DSA *dsa)
+ 	return ret;
+ sw_try:
+ 	{
+-		const DSA_METHOD *meth = DSA_OpenSSL();
+-		ret = (meth->dsa_keygen)(dsa);
++		const DSA_METHOD *meth = dsa->meth;
++		dsa->meth = DSA_OpenSSL();
++		ret = DSA_generate_key(dsa);
++		dsa->meth = meth;
+ 	}
+ 	return ret;
+ }
+@@ -2130,11 +2132,13 @@ static int cryptodev_dsa_keygen_async(DSA *dsa,  struct pkc_cookie_s *cookie)
+ 	return ret;
+ sw_try:
+ 	{
+-		const DSA_METHOD *meth = DSA_OpenSSL();
++		const DSA_METHOD *meth = dsa->meth;
+ 
++		dsa->meth = DSA_OpenSSL();
+ 		if (kop)
+ 			free(kop);
+-		ret = (meth->dsa_keygen)(dsa);
++		ret = DSA_generate_key(dsa);
++		dsa->meth = meth;
+ 		cookie->pkc_callback(cookie, 0);
+ 	}
+ 	return ret;
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl-fsl/0015-Fixed-DH-keygen-pair-generator.patch b/recipes-connectivity/openssl/openssl-fsl/0015-Fixed-DH-keygen-pair-generator.patch
new file mode 100644
index 0000000..99e6094
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl-fsl/0015-Fixed-DH-keygen-pair-generator.patch
@@ -0,0 +1,100 @@
+From 9dfc18846063a110070782ede699c513b30257e5 Mon Sep 17 00:00:00 2001
+From: Yashpal Dutta <yashpal.dutta at freescale.com>
+Date: Thu, 1 May 2014 06:35:45 +0545
+Subject: [PATCH][fsl 15/15] Fixed DH keygen pair generator
+
+Upstream-status: Pending
+
+Wrong Padding results into keygen length error
+
+Signed-off-by: Yashpal Dutta <yashpal.dutta at freescale.com>
+Tested-by: Cristian Stoica <cristian.stoica at freescale.com>
+---
+ crypto/engine/eng_cryptodev.c |   50 +++++++++++++++++++++++++++--------------
+ 1 file changed, 33 insertions(+), 17 deletions(-)
+
+diff --git a/crypto/engine/eng_cryptodev.c b/crypto/engine/eng_cryptodev.c
+index 7c2661f..703eee4 100644
+--- a/crypto/engine/eng_cryptodev.c
++++ b/crypto/engine/eng_cryptodev.c
+@@ -3402,44 +3402,60 @@ sw_try:
+ static int cryptodev_dh_keygen(DH *dh)
+ {
+ 	struct crypt_kop kop;
+-	int ret = 1, g_len;
+-	unsigned char *g = NULL;
++	int ret = 1, q_len = 0;
++	unsigned char *q = NULL, *g = NULL, *s = NULL, *w = NULL;
++	BIGNUM *pub_key = NULL, *priv_key = NULL;
++	int generate_new_key = 1;
+ 
+-	if (dh->priv_key == NULL)	{
+-		if ((dh->priv_key=BN_new()) == NULL)
+-			goto sw_try;
+-	}
++	if (dh->priv_key)
++		priv_key = dh->priv_key;
+ 
+-	if (dh->pub_key == NULL) {
+-		if ((dh->pub_key=BN_new()) == NULL)
+-			goto sw_try;
+-	}
++	if (dh->pub_key)
++		pub_key = dh->pub_key;
+ 
+-	g_len = BN_num_bytes(dh->p);
++	q_len = BN_num_bytes(dh->p);
+ 	/**
+ 	 * Get generator into a plain buffer. If length is less than
+ 	 * q_len then add leading padding bytes.
+ 	 */
+-	if (spcf_bn2bin_ex(dh->g, &g, &g_len)) {
++	if (spcf_bn2bin_ex(dh->g, &g, &q_len)) {
++		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
++
++	if (spcf_bn2bin_ex(dh->p, &q, &q_len)) {
+ 		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
+ 		goto sw_try;
+ 	}
+ 
+ 	memset(&kop, 0, sizeof kop);
+ 	kop.crk_op = CRK_DH_GENERATE_KEY;
+-	if (bn2crparam(dh->p, &kop.crk_param[0]))
+-		goto sw_try;
++	kop.crk_param[0].crp_p = q;
++	kop.crk_param[0].crp_nbits = q_len * 8;
+ 	if (!dh->q || bn2crparam(dh->q, &kop.crk_param[1]))
+ 		goto sw_try;
+ 	kop.crk_param[2].crp_p = g;
+-	kop.crk_param[2].crp_nbits = g_len * 8;
++	kop.crk_param[2].crp_nbits = q_len * 8;
+ 	kop.crk_iparams = 3;
+ 
++	s = OPENSSL_malloc (q_len);
++	if (!s) {
++		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
++
++	w = OPENSSL_malloc (q_len);
++	if (!w) {
++		DSAerr(DH_F_DH_GENERATE_KEY, ERR_R_MALLOC_FAILURE);
++		goto sw_try;
++	}
++
+ 	/* pub_key is or prime length while priv key is of length of order */
+-	if (cryptodev_asym(&kop, BN_num_bytes(dh->p), dh->pub_key,
+-	    BN_num_bytes(dh->q), dh->priv_key))
++	if (cryptodev_asym(&kop, q_len, w, q_len, s))
+ 	    goto sw_try;
+ 
++	dh->pub_key = BN_bin2bn(w, q_len, pub_key);
++	dh->pub_key = BN_bin2bn(s, q_len, priv_key);
+ 	return ret;
+ sw_try:
+ 	{
+-- 
+1.7.9.7
+
diff --git a/recipes-connectivity/openssl/openssl_1.0.1g.bbappend b/recipes-connectivity/openssl/openssl_1.0.1g.bbappend
new file mode 100644
index 0000000..f3e49ae
--- /dev/null
+++ b/recipes-connectivity/openssl/openssl_1.0.1g.bbappend
@@ -0,0 +1,59 @@
+FILESEXTRAPATHS_prepend := "${THISDIR}/openssl-fsl"
+
+RDEPENDS_${PN}_class-target += "cryptodev-module"
+
+# base package is taken from Freescale repository
+SRCBRANCH = "OpenSSL_1_0_1-stable"
+SRC_URI = "git://git.openssl.org/openssl.git;branch=${SRCBRANCH} \
+    file://0001-remove-double-initialization-of-cryptodev-engine.patch \
+    file://0002-ECC-Support-header-for-Cryptodev-Engine.patch \
+    file://0003-add-support-for-TLS-algorithms-offload.patch \
+    file://0004-Fixed-private-key-support-for-DH.patch \
+    file://0005-Fixed-private-key-support-for-DH.patch \
+    file://0006-Initial-support-for-PKC-in-cryptodev-engine.patch \
+    file://0007-Added-hwrng-dev-file-as-source-of-RNG.patch \
+    file://0008-Asynchronous-interface-added-for-PKC-cryptodev-inter.patch \
+    file://0009-eng_cryptodev-extend-TLS-offload-with-new-algorithms.patch \
+    file://0010-Add-RSA-keygen-operation-and-support-gendsa-command-.patch \
+    file://0011-RSA-Keygen-Fix.patch \
+    file://0012-Removed-local-copy-of-curve_t-type.patch \
+    file://0013-Modulus-parameter-is-not-populated-by-dhparams.patch \
+    file://0014-SW-Backoff-mechanism-for-dsa-keygen.patch \
+    file://0015-Fixed-DH-keygen-pair-generator.patch \
+"
+SRCREV = "b2d951e4232d2f90168f9a3dd0b7df9ecf2d81a8"
+
+SRC_URI += "file://configure-targets.patch \
+            file://shared-libs.patch \
+            file://oe-ldflags.patch \
+            file://engines-install-in-libdir-ssl.patch \
+            file://openssl-fix-link.patch \
+            file://debian/version-script.patch \
+            file://debian/pic.patch \
+            file://debian/c_rehash-compat.patch \
+            file://debian/ca.patch \
+            file://debian/make-targets.patch \
+            file://debian/no-rpath.patch \
+            file://debian/man-dir.patch \
+            file://debian/man-section.patch \
+            file://debian/no-symbolic.patch \
+            file://debian/debian-targets.patch \
+            file://openssl_fix_for_x32.patch \
+            file://openssl-fix-doc.patch \
+            file://fix-cipher-des-ede3-cfb1.patch \
+            file://openssl-avoid-NULL-pointer-dereference-in-EVP_DigestInit_ex.patch \
+            file://openssl-avoid-NULL-pointer-dereference-in-dh_pub_encode.patch \
+            file://initial-aarch64-bits.patch \
+            file://find.pl \
+            file://openssl-fix-des.pod-error.patch \
+           "
+S = "${WORKDIR}/git"
+
+# Digest offloading through cryptodev is not recommended because of the
+# performance penalty of the Openssl engine interface. Openssl generates a huge
+# number of calls to digest functions for even a small amount of work data.
+# For example there are 70 calls to cipher code and over 10000 to digest code
+# when downloading only 10 files of 700 bytes each.
+# Do not build OpenSSL with cryptodev digest support until engine digest
+# interface gets some rework:
+CFLAG := "${@'${CFLAG}'.replace('-DUSE_CRYPTODEV_DIGESTS', '')}"
-- 
1.7.9.7



More information about the meta-freescale mailing list