summarylogtreecommitdiffstats
diff options
context:
space:
mode:
authorMantas Mikulėnas2021-01-24 18:45:46 +0200
committerMantas Mikulėnas2021-01-24 18:45:46 +0200
commite01ea4d3c17d8d2877f4f19ba7fc4110812c9dce (patch)
tree50d4bd64c250dea4e4a4b1d8d068a8757f002de9
parent60be0072bb3c1a8a9d7286e2fea6c9bfe2cfebe9 (diff)
downloadaur-openssl-tpm-engine.tar.gz
import patches from James Bottomley's fork
-rw-r--r--.SRCINFO10
-rw-r--r--0001-try-well-known-authority-for-SRK-first.patch107
-rw-r--r--0002-Handle-EVP-keys.patch54
-rw-r--r--0003-Add-option-for-random-migration-authority.patch117
-rw-r--r--0004-e_tpm-reduce-TPM-connection-time.patch1016
-rw-r--r--PKGBUILD20
6 files changed, 1319 insertions, 5 deletions
diff --git a/.SRCINFO b/.SRCINFO
index 9fbdfbdbefa9..8b8ee783febd 100644
--- a/.SRCINFO
+++ b/.SRCINFO
@@ -1,6 +1,6 @@
pkgbase = openssl-tpm-engine
pkgdesc = OpenSSL engine for TPM 1.2 hardware-backed keys
- pkgver = 0.5.0
+ pkgver = 0.5.0+jejb
pkgrel = 1
url = https://github.com/mgerstner/openssl_tpm_engine
arch = i686
@@ -9,6 +9,14 @@ pkgbase = openssl-tpm-engine
depends = openssl
depends = trousers
source = openssl-tpm-engine::git+https://github.com/mgerstner/openssl_tpm_engine#commit=b28de5065e6eb9aa5d5afe2276904f7624c2cbaf
+ source = 0001-try-well-known-authority-for-SRK-first.patch
+ source = 0002-Handle-EVP-keys.patch
+ source = 0003-Add-option-for-random-migration-authority.patch
+ source = 0004-e_tpm-reduce-TPM-connection-time.patch
sha256sums = SKIP
+ sha256sums = b713c5e46e6ea26bee50234786a8d24da154b52f078c5580508c72f644c45083
+ sha256sums = 5eeb49e0af7f393bfcabc7a82f6b4d13c57e7bbc4219e7cca4316bc2ec0e5bb1
+ sha256sums = 95489c2c01544081bc19ac9a9210227ebe17f97e72e83be38579cf6a19dfbbe0
+ sha256sums = 682da7346e3351b8e63ce165d610331f04d558b57cd585f09336666fc827cf31
pkgname = openssl-tpm-engine
diff --git a/0001-try-well-known-authority-for-SRK-first.patch b/0001-try-well-known-authority-for-SRK-first.patch
new file mode 100644
index 000000000000..95ecf4257427
--- /dev/null
+++ b/0001-try-well-known-authority-for-SRK-first.patch
@@ -0,0 +1,107 @@
+From 2d55917522a1a1e1a5159462a78d38334555ece0 Mon Sep 17 00:00:00 2001
+From: James Bottomley <James.Bottomley@HansenPartnership.com>
+Date: Tue, 8 Nov 2016 08:27:33 -0800
+Subject: [PATCH 1/4] try well known authority for SRK first
+
+There's no way to give the well known authority via the password prompt, so
+try it first. If that succeeds, we have the key authority and if not, we can
+prompt for a password.
+
+This allows the engine and create_tpm_key to work on systems where the SRK has
+the well known authority value.
+
+Signed-off-by: James Bottomley <jejb@linux.vnet.ibm.com>
+---
+ src/create_tpm_key.c | 28 ++++++++++++++++++++--------
+ src/e_tpm.c | 9 +++++++++
+ 2 files changed, 29 insertions(+), 8 deletions(-)
+
+diff --git a/src/create_tpm_key.c b/src/create_tpm_key.c
+index a73d549..1f959c8 100644
+--- a/src/create_tpm_key.c
++++ b/src/create_tpm_key.c
+@@ -83,6 +83,7 @@ usage(char *argv0)
+ }
+
+ TSS_UUID SRK_UUID = TSS_UUID_SRK;
++static BYTE well_known[] = TSS_WELL_KNOWN_SECRET;
+
+ void
+ openssl_print_errors()
+@@ -299,20 +300,29 @@ int main(int argc, char **argv)
+ }
+
+ if (srk_authusage) {
+- char *authdata = calloc(1, 128);
+-
+- if (!authdata) {
+- fprintf(stderr, "malloc failed.\n");
+- Tspi_Context_Close(hContext);
+- exit(result);
+- }
++ char *authdata;
+
+ if ((result = Tspi_GetPolicyObject(hSRK, TSS_POLICY_USAGE,
+ &srkUsagePolicy))) {
+ print_error("Tspi_GetPolicyObject", result);
+ Tspi_Context_CloseObject(hContext, hKey);
+ Tspi_Context_Close(hContext);
+- free(authdata);
++ exit(result);
++ }
++
++ /* first try the well known secret */
++ if (Tspi_Policy_SetSecret(srkUsagePolicy,
++ TSS_SECRET_MODE_SHA1,
++ sizeof(well_known),
++ well_known)
++ == TSS_SUCCESS)
++ goto found_secret;
++
++ authdata = calloc(1, 128);
++
++ if (!authdata) {
++ fprintf(stderr, "malloc failed.\n");
++ Tspi_Context_Close(hContext);
+ exit(result);
+ }
+
+@@ -335,6 +345,8 @@ int main(int argc, char **argv)
+ }
+
+ free(authdata);
++ found_secret:
++ ;
+ }
+
+ if (auth) {
+diff --git a/src/e_tpm.c b/src/e_tpm.c
+index f671771..9f6b0c6 100644
+--- a/src/e_tpm.c
++++ b/src/e_tpm.c
+@@ -111,6 +111,7 @@ static TSS_HKEY hSRK = NULL_HKEY;
+ static TSS_HPOLICY hSRKPolicy = NULL_HPOLICY;
+ static TSS_HTPM hTPM = NULL_HTPM;
+ static TSS_UUID SRK_UUID = TSS_UUID_SRK;
++static BYTE well_known[] = TSS_WELL_KNOWN_SECRET;
+ static UINT32 secret_mode = TSS_SECRET_MODE_PLAIN;
+
+ /* varibles used to get/set CRYPTO_EX_DATA values */
+@@ -313,6 +314,14 @@ int tpm_load_srk(UI_METHOD *ui, void *cb_data)
+ return 0;
+ }
+
++ /* first try the well known secret */
++ if (Tspi_Policy_SetSecret(hSRKPolicy,
++ TSS_SECRET_MODE_SHA1,
++ sizeof(well_known),
++ well_known)
++ == TSS_SUCCESS)
++ return 1;
++
+ if (!tpm_engine_get_auth(ui, (char *)auth, 128, "SRK authorization: ",
+ cb_data)) {
+ Tspi_Context_CloseObject(hContext, hSRK);
+--
+2.30.0
+
diff --git a/0002-Handle-EVP-keys.patch b/0002-Handle-EVP-keys.patch
new file mode 100644
index 000000000000..6a057257edb1
--- /dev/null
+++ b/0002-Handle-EVP-keys.patch
@@ -0,0 +1,54 @@
+From 73d2a32fc05286ee6429f100232701568d818389 Mon Sep 17 00:00:00 2001
+From: James Bottomley <James.Bottomley@HansenPartnership.com>
+Date: Wed, 9 Nov 2016 17:14:16 -0800
+Subject: [PATCH 2/4] Handle EVP keys
+
+EVP keys have a variable encryption envelope, which is used by openssh, so
+adding EVP key support allows create_tpm_key to read ssh v2 keys
+
+Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
+---
+ src/create_tpm_key.c | 8 +++++++-
+ 1 file changed, 7 insertions(+), 1 deletion(-)
+
+diff --git a/src/create_tpm_key.c b/src/create_tpm_key.c
+index 1f959c8..449d152 100644
+--- a/src/create_tpm_key.c
++++ b/src/create_tpm_key.c
+@@ -97,6 +97,7 @@ RSA *
+ openssl_read_key(char *filename)
+ {
+ BIO *b = NULL;
++ EVP_PKEY *pkey;
+ RSA *rsa = NULL;
+
+ b = BIO_new_file(filename, "r");
+@@ -105,12 +106,14 @@ openssl_read_key(char *filename)
+ return NULL;
+ }
+
+- if ((rsa = PEM_read_bio_RSAPrivateKey(b, NULL, 0, NULL)) == NULL) {
++ if ((pkey = PEM_read_bio_PrivateKey(b, NULL, PEM_def_callback, NULL)) == NULL) {
+ fprintf(stderr, "Reading key %s from disk failed.\n", filename);
+ openssl_print_errors();
+ }
+ BIO_free(b);
+
++ rsa = EVP_PKEY_get1_RSA(pkey);
++
+ return rsa;
+ }
+
+@@ -413,6 +416,9 @@ int main(int argc, char **argv)
+ unsigned int size_n, size_p;
+ BYTE *pubSRK;
+
++ /* may be needed to decrypt the key */
++ OpenSSL_add_all_ciphers();
++
+ /*Set migration policy needed to wrap the key*/
+ if ((result = Tspi_Context_CreateObject(hContext,
+ TSS_OBJECT_TYPE_POLICY,
+--
+2.30.0
+
diff --git a/0003-Add-option-for-random-migration-authority.patch b/0003-Add-option-for-random-migration-authority.patch
new file mode 100644
index 000000000000..8bd67dfba7dd
--- /dev/null
+++ b/0003-Add-option-for-random-migration-authority.patch
@@ -0,0 +1,117 @@
+From 0ec233c5bdd751973afc85de7d77e1cdc07f3733 Mon Sep 17 00:00:00 2001
+From: James Bottomley <James.Bottomley@HansenPartnership.com>
+Date: Thu, 10 Nov 2016 11:04:10 -0800
+Subject: [PATCH 3/4] Add option for random migration authority
+
+This is used to generate keys which can never be extracted from the TPM
+into which they're inserted. As long as no-one knows (and it's impossible to
+guess) the migration authority of the key, there is no way to extract it from
+a TPM.
+
+Signed-off-by: James Bottomley <jejb@linux.vnet.ibm.com>
+---
+ src/create_tpm_key.c | 34 ++++++++++++++++++++++++----------
+ 1 file changed, 24 insertions(+), 10 deletions(-)
+
+diff --git a/src/create_tpm_key.c b/src/create_tpm_key.c
+index 449d152..3b865e0 100644
+--- a/src/create_tpm_key.c
++++ b/src/create_tpm_key.c
+@@ -42,6 +42,7 @@
+ #include <openssl/pem.h>
+ #include <openssl/evp.h>
+ #include <openssl/err.h>
++#include <openssl/rand.h>
+
+ #include <trousers/tss.h>
+ #include <trousers/trousers.h>
+@@ -60,6 +61,7 @@ static struct option long_options[] = {
+ {"popup", 0, 0, 'p'},
+ {"wrap", 1, 0, 'w'},
+ {"help", 0, 0, 'h'},
++ {"random-migration", 0, 0, 'm'},
+ {0, 0, 0, 0}
+ };
+
+@@ -76,6 +78,7 @@ usage(char *argv0)
+ "\t\t-p|--popup use TSS GUI popup dialogs to get the password "
+ "for the\n\t\t\t\t key [NO] (implies --auth)\n"
+ "\t\t-w|--wrap [file] wrap an existing openssl PEM key\n"
++ "\t\t-m|--random-migration set a random migration auth\n"
+ "\t\t-h|--help print this help message\n"
+ "\nReport bugs to %s\n",
+ argv0, argv0, PACKAGE_BUGREPORT);
+@@ -157,7 +160,7 @@ int main(int argc, char **argv)
+ unsigned char *blob_asn1 = NULL;
+ int asn1_len;
+ char *filename, c, *openssl_key = NULL;
+- int option_index, auth = 0, popup = 0, wrap = 0;
++ int option_index, auth = 0, popup = 0, wrap = 0, rndm = 0;
+ UINT32 enc_scheme = TSS_ES_RSAESPKCSV15;
+ UINT32 sig_scheme = TSS_SS_RSASSAPKCS1V15_DER;
+ UINT32 key_size = 2048;
+@@ -165,7 +168,7 @@ int main(int argc, char **argv)
+
+ while (1) {
+ option_index = 0;
+- c = getopt_long(argc, argv, "pe:q:s:ahw:",
++ c = getopt_long(argc, argv, "pe:q:s:ahw:m",
+ long_options, &option_index);
+ if (c == -1)
+ break;
+@@ -205,6 +208,10 @@ int main(int argc, char **argv)
+ wrap = 1;
+ openssl_key = optarg;
+ break;
++ case 'm':
++ initFlags |= TSS_KEY_MIGRATABLE;
++ rndm = 1;
++ break;
+ default:
+ usage(argv[0]);
+ break;
+@@ -428,8 +435,9 @@ int main(int argc, char **argv)
+ Tspi_Context_Close(hContext);
+ exit(result);
+ }
+- if (auth) {
++ if (auth || rndm) {
+ char *authdata = calloc(1, 128);
++ int authlen;
+
+ if (!authdata) {
+ fprintf(stderr, "malloc failed.\n");
+@@ -437,17 +445,23 @@ int main(int argc, char **argv)
+ exit(result);
+ }
+
+- if (EVP_read_pw_string(authdata, 128,
+- "Enter Key Migration Password: ", 1)) {
+- printf("Passwords do not match.\n");
+- free(authdata);
+- Tspi_Context_Close(hContext);
+- exit(result);
++ if (rndm) {
++ authlen = 20;
++ RAND_bytes(authdata, authlen);
++ } else {
++
++ if (EVP_read_pw_string(authdata, 128,
++ "Enter Key Migration Password: ", 1)) {
++ printf("Passwords do not match.\n");
++ free(authdata);
++ Tspi_Context_Close(hContext);
++ exit(result);
++ }
+ }
+
+ if ((result = Tspi_Policy_SetSecret(keyMigrationPolicy,
+ TSS_SECRET_MODE_PLAIN,
+- strlen(authdata),
++ authlen,
+ (BYTE *)authdata))) {
+ print_error("Tspi_Policy_SetSecret", result);
+ Tspi_Context_Close(hContext);
+--
+2.30.0
+
diff --git a/0004-e_tpm-reduce-TPM-connection-time.patch b/0004-e_tpm-reduce-TPM-connection-time.patch
new file mode 100644
index 000000000000..0885b09b0803
--- /dev/null
+++ b/0004-e_tpm-reduce-TPM-connection-time.patch
@@ -0,0 +1,1016 @@
+From f5c5c1464ead3dda6f53f4b41a951f4436d3f7ce Mon Sep 17 00:00:00 2001
+From: James Bottomley <James.Bottomley@HansenPartnership.com>
+Date: Fri, 10 Nov 2017 06:52:34 -0800
+Subject: [PATCH 4/4] e_tpm: reduce TPM connection time.
+
+The current engine keeps a connection to the tcsd open throughout the
+engine lifetime by connecting on init and disconnecting on finish. If
+the tcsd crashes this connection dies and the program needs to be
+restarted. A partial fix for this is to eliminate this static
+connection and open one dynamic connection per key.
+
+Since this is all about key handling, eliminate the random number
+generator piece and the key gen part which isn't complete.
+
+Signed-off-by: James Bottomley <James.Bottomley@HansenPartnership.com>
+---
+ src/e_tpm.c | 621 ++++++++--------------------------------------------
+ src/e_tpm.h | 1 +
+ 2 files changed, 96 insertions(+), 526 deletions(-)
+
+diff --git a/src/e_tpm.c b/src/e_tpm.c
+index 9f6b0c6..e5c5b46 100644
+--- a/src/e_tpm.c
++++ b/src/e_tpm.c
+@@ -38,13 +38,10 @@
+ #include "e_tpm.h"
+ #include "ssl_compat.h"
+
+-//#define DLOPEN_TSPI
+-
+ #ifndef OPENSSL_NO_HW
+ #ifndef OPENSSL_NO_HW_TPM
+
+ /* engine specific functions */
+-static int tpm_engine_destroy(ENGINE *);
+ static int tpm_engine_init(ENGINE *);
+ static int tpm_engine_finish(ENGINE *);
+ static int tpm_engine_ctrl(ENGINE *, int, long, void *, void (*)());
+@@ -60,14 +57,8 @@ static int tpm_rsa_pub_enc(int, const unsigned char *, unsigned char *, RSA *, i
+ static int tpm_rsa_priv_dec(int, const unsigned char *, unsigned char *, RSA *, int);
+ static int tpm_rsa_priv_enc(int, const unsigned char *, unsigned char *, RSA *, int);
+ //static int tpm_rsa_sign(int, const unsigned char *, unsigned int, unsigned char *, unsigned int *, const RSA *);
+-static int tpm_rsa_keygen(RSA *, int, BIGNUM *, BN_GENCB *);
+ #endif
+
+-/* random functions */
+-static int tpm_rand_bytes(unsigned char *, int);
+-static int tpm_rand_status(void);
+-static RAND_SEED_RET_TYPE tpm_rand_seed(const void *, int);
+-
+ /* The definitions for control commands specific to this engine */
+ #define TPM_CMD_SO_PATH ENGINE_CMD_BASE
+ #define TPM_CMD_PIN ENGINE_CMD_BASE+1
+@@ -91,25 +82,10 @@ static const ENGINE_CMD_DEFN tpm_cmd_defns[] = {
+ static RSA_METHOD *tpm_rsa;
+ static const RSA_METHOD *ssl_rsa;
+
+-static RAND_METHOD tpm_rand = {
+- /* "TPM RAND method", */
+- tpm_rand_seed,
+- tpm_rand_bytes,
+- NULL,
+- NULL,
+- tpm_rand_bytes,
+- tpm_rand_status,
+-};
+-
+ /* Constants used when creating the ENGINE */
+ static const char *engine_tpm_id = "tpm";
+ static const char *engine_tpm_name = "TPM hardware engine support";
+-static const char *TPM_LIBNAME = "tspi";
+
+-static TSS_HCONTEXT hContext = NULL_HCONTEXT;
+-static TSS_HKEY hSRK = NULL_HKEY;
+-static TSS_HPOLICY hSRKPolicy = NULL_HPOLICY;
+-static TSS_HTPM hTPM = NULL_HTPM;
+ static TSS_UUID SRK_UUID = TSS_UUID_SRK;
+ static BYTE well_known[] = TSS_WELL_KNOWN_SECRET;
+ static UINT32 secret_mode = TSS_SECRET_MODE_PLAIN;
+@@ -117,69 +93,6 @@ static UINT32 secret_mode = TSS_SECRET_MODE_PLAIN;
+ /* varibles used to get/set CRYPTO_EX_DATA values */
+ int ex_app_data = TPM_ENGINE_EX_DATA_UNINIT;
+
+-#ifdef DLOPEN_TSPI
+-/* This is a process-global DSO handle used for loading and unloading
+- * the TSS library. NB: This is only set (or unset) during an
+- * init() or finish() call (reference counts permitting) and they're
+- * operating with global locks, so this should be thread-safe
+- * implicitly. */
+-
+-static DSO *tpm_dso = NULL;
+-
+-/* These are the function pointers that are (un)set when the library has
+- * successfully (un)loaded. */
+-static unsigned int (*p_tspi_Context_Create)();
+-static unsigned int (*p_tspi_Context_Close)();
+-static unsigned int (*p_tspi_Context_Connect)();
+-static unsigned int (*p_tspi_Context_FreeMemory)();
+-static unsigned int (*p_tspi_Context_CreateObject)();
+-static unsigned int (*p_tspi_Context_LoadKeyByUUID)();
+-static unsigned int (*p_tspi_Context_LoadKeyByBlob)();
+-static unsigned int (*p_tspi_Context_GetTpmObject)();
+-static unsigned int (*p_tspi_TPM_GetRandom)();
+-static unsigned int (*p_tspi_TPM_StirRandom)();
+-static unsigned int (*p_tspi_Key_CreateKey)();
+-static unsigned int (*p_tspi_Key_LoadKey)();
+-static unsigned int (*p_tspi_Data_Bind)();
+-static unsigned int (*p_tspi_Data_Unbind)();
+-static unsigned int (*p_tspi_GetAttribData)();
+-static unsigned int (*p_tspi_SetAttribData)();
+-static unsigned int (*p_tspi_SetAttribUint32)();
+-static unsigned int (*p_tspi_GetAttribUint32)();
+-static unsigned int (*p_tspi_Context_CloseObject)();
+-static unsigned int (*p_tspi_Hash_Sign)();
+-static unsigned int (*p_tspi_Hash_SetHashValue)();
+-static unsigned int (*p_tspi_GetPolicyObject)();
+-static unsigned int (*p_tspi_Policy_SetSecret)();
+-static unsigned int (*p_tspi_Policy_AssignToObject)();
+-
+-/* Override the real function calls to use our indirect pointers */
+-#define Tspi_Context_Create p_tspi_Context_Create
+-#define Tspi_Context_Close p_tspi_Context_Close
+-#define Tspi_Context_Connect p_tspi_Context_Connect
+-#define Tspi_Context_CreateObject p_tspi_Context_CreateObject
+-#define Tspi_Context_CloseObject p_tspi_Context_CloseObject
+-#define Tspi_Context_FreeMemory p_tspi_Context_FreeMemory
+-#define Tspi_Context_LoadKeyByBlob p_tspi_Context_LoadKeyByBlob
+-#define Tspi_Context_LoadKeyByUUID p_tspi_Context_LoadKeyByUUID
+-#define Tspi_Context_GetTpmObject p_tspi_Context_GetTpmObject
+-#define Tspi_TPM_GetRandom p_tspi_TPM_GetRandom
+-#define Tspi_TPM_StirRandom p_tspi_TPM_StirRandom
+-#define Tspi_Key_CreateKey p_tspi_Key_CreateKey
+-#define Tspi_Key_LoadKey p_tspi_Key_LoadKey
+-#define Tspi_Data_Bind p_tspi_Data_Bind
+-#define Tspi_Data_Unbind p_tspi_Data_Unbind
+-#define Tspi_GetAttribData p_tspi_GetAttribData
+-#define Tspi_SetAttribData p_tspi_SetAttribData
+-#define Tspi_GetAttribUint32 p_tspi_GetAttribUint32
+-#define Tspi_SetAttribUint32 p_tspi_SetAttribUint32
+-#define Tspi_GetPolicyObject p_tspi_GetPolicyObject
+-#define Tspi_Hash_Sign p_tspi_Hash_Sign
+-#define Tspi_Hash_SetHashValue p_tspi_Hash_SetHashValue
+-#define Tspi_Policy_SetSecret p_tspi_Policy_SetSecret
+-#define Tspi_Policy_AssignToObject p_tspi_Policy_AssignToObject
+-#endif /* DLOPEN_TSPI */
+-
+ static int setup_rsa_method()
+ {
+ tpm_rsa = RSA_meth_new("TPM RSA method", 0);
+@@ -194,8 +107,7 @@ static int setup_rsa_method()
+ !RSA_meth_set_priv_dec(tpm_rsa, tpm_rsa_priv_dec) ||
+ !RSA_meth_set_bn_mod_exp(tpm_rsa, BN_mod_exp_mont) ||
+ !RSA_meth_set_init(tpm_rsa, tpm_rsa_init) ||
+- !RSA_meth_set_finish(tpm_rsa, tpm_rsa_finish) ||
+- !RSA_meth_set_keygen(tpm_rsa, tpm_rsa_keygen))
++ !RSA_meth_set_finish(tpm_rsa, tpm_rsa_finish))
+ {
+ RSA_meth_free(tpm_rsa);
+ tpm_rsa = NULL;
+@@ -205,8 +117,6 @@ static int setup_rsa_method()
+ return 1;
+ }
+
+-/* This internal function is used by ENGINE_tpm() and possibly by the
+- * "dynamic" ENGINE support too */
+ static int bind_helper(ENGINE * e)
+ {
+ if (!setup_rsa_method())
+@@ -216,11 +126,6 @@ static int bind_helper(ENGINE * e)
+
+ if (!ENGINE_set_id(e, engine_tpm_id) ||
+ !ENGINE_set_name(e, engine_tpm_name) ||
+-#ifndef OPENSSL_NO_RSA
+- !ENGINE_set_RSA(e, tpm_rsa) ||
+-#endif
+- !ENGINE_set_RAND(e, &tpm_rand) ||
+- !ENGINE_set_destroy_function(e, tpm_engine_destroy) ||
+ !ENGINE_set_init_function(e, tpm_engine_init) ||
+ !ENGINE_set_finish_function(e, tpm_engine_finish) ||
+ !ENGINE_set_ctrl_function(e, tpm_engine_ctrl) ||
+@@ -234,51 +139,28 @@ static int bind_helper(ENGINE * e)
+ return 1;
+ }
+
+-static ENGINE *engine_tpm(void)
+-{
+- ENGINE *ret = ENGINE_new();
+- DBG("%s", __FUNCTION__);
+- if (!ret)
+- return NULL;
+- if (!bind_helper(ret)) {
+- ENGINE_free(ret);
+- return NULL;
+- }
+- return ret;
+-}
+-
+-void ENGINE_load_tpm(void)
+-{
+- /* Copied from eng_[openssl|dyn].c */
+- ENGINE *toadd = engine_tpm();
+- if (!toadd)
+- return;
+- ENGINE_add(toadd);
+- ENGINE_free(toadd);
+- ERR_clear_error();
+-}
+-
+-int tpm_load_srk(UI_METHOD *ui, void *cb_data)
++int tpm_load_srk(UI_METHOD *ui, void *cb_data, TSS_HKEY *hSRK, TSS_HCONTEXT ctx)
+ {
+ TSS_RESULT result;
+ UINT32 authusage;
+ BYTE *auth;
++ TSS_HPOLICY hSRKPolicy;
+
+- if (hSRK != NULL_HKEY) {
++ if (*hSRK != NULL_HKEY) {
+ DBGFN("SRK is already loaded.");
+ return 1;
+ }
+
+- if ((result = Tspi_Context_LoadKeyByUUID(hContext, TSS_PS_TYPE_SYSTEM,
+- SRK_UUID, &hSRK))) {
++ if ((result = Tspi_Context_LoadKeyByUUID(ctx, TSS_PS_TYPE_SYSTEM,
++ SRK_UUID, hSRK))) {
+ TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+ return 0;
+ }
+
+- if ((result = Tspi_GetAttribUint32(hSRK, TSS_TSPATTRIB_KEY_INFO,
++ if ((result = Tspi_GetAttribUint32(*hSRK, TSS_TSPATTRIB_KEY_INFO,
+ TSS_TSPATTRIB_KEYINFO_AUTHUSAGE,
+ &authusage))) {
+- Tspi_Context_CloseObject(hContext, hSRK);
++ Tspi_Context_CloseObject(ctx, *hSRK);
+ TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+ return 0;
+ }
+@@ -288,23 +170,9 @@ int tpm_load_srk(UI_METHOD *ui, void *cb_data)
+ return 1;
+ }
+
+- /* If hSRKPolicy is non 0, then a policy object for the SRK has already
+- * been set up by engine pre/post commands. Just assign it to the SRK.
+- * Otherwise, we need to get the SRK's implicit policy and prompt for a
+- * secret */
+- if (hSRKPolicy) {
+- DBG("Found an already initialized SRK policy, using it");
+- if ((result = Tspi_Policy_AssignToObject(hSRKPolicy, hSRK))) {
+- TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- return 1;
+- }
+-
+- if ((result = Tspi_GetPolicyObject(hSRK, TSS_POLICY_USAGE,
++ if ((result = Tspi_GetPolicyObject(*hSRK, TSS_POLICY_USAGE,
+ &hSRKPolicy))) {
+- Tspi_Context_CloseObject(hContext, hSRK);
++ Tspi_Context_CloseObject(ctx, *hSRK);
+ TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+ return 0;
+ }
+@@ -324,7 +192,8 @@ int tpm_load_srk(UI_METHOD *ui, void *cb_data)
+
+ if (!tpm_engine_get_auth(ui, (char *)auth, 128, "SRK authorization: ",
+ cb_data)) {
+- Tspi_Context_CloseObject(hContext, hSRK);
++ Tspi_Context_CloseObject(ctx, *hSRK);
++ *hSRK = NULL_HKEY;
+ free(auth);
+ TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+ return 0;
+@@ -334,7 +203,8 @@ int tpm_load_srk(UI_METHOD *ui, void *cb_data)
+ * commands. By default, its set to TSS_SECRET_MODE_PLAIN */
+ if ((result = Tspi_Policy_SetSecret(hSRKPolicy, secret_mode,
+ strlen((char *)auth), auth))) {
+- Tspi_Context_CloseObject(hContext, hSRK);
++ Tspi_Context_CloseObject(ctx, *hSRK);
++ *hSRK = NULL_HKEY;
+ free(auth);
+ TSSerr(TPM_F_TPM_LOAD_SRK, TPM_R_REQUEST_FAILED);
+ return 0;
+@@ -346,123 +216,12 @@ int tpm_load_srk(UI_METHOD *ui, void *cb_data)
+ }
+
+
+-/* Destructor (complements the "ENGINE_tpm()" constructor) */
+-static int tpm_engine_destroy(ENGINE * e)
+-{
+- /* Unload the tpm error strings so any error state including our
+- * functs or reasons won't lead to a segfault (they simply get displayed
+- * without corresponding string data because none will be found). */
+- ERR_unload_TPM_strings();
+- return 1;
+-}
+-
+ /* initialisation function */
+ static int tpm_engine_init(ENGINE * e)
+ {
+- TSS_RESULT result;
+-
+ DBG("%s", __FUNCTION__);
+
+-#ifdef DLOPEN_TSPI
+- if (tpm_dso != NULL) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_ALREADY_LOADED);
+- return 1;
+- }
+-
+- if ((tpm_dso = DSO_load(NULL, TPM_LIBNAME, NULL, 0)) == NULL) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_DSO_FAILURE);
+- goto err;
+- }
+-
+-#define bind_tspi_func(dso, func) (p_tspi_##func = (void *)DSO_bind_func(dso, "Tspi_" #func))
+-
+- if (!bind_tspi_func(tpm_dso, Context_Create) ||
+- !bind_tspi_func(tpm_dso, Context_Close) ||
+- !bind_tspi_func(tpm_dso, Context_Connect) ||
+- !bind_tspi_func(tpm_dso, TPM_GetRandom) ||
+- !bind_tspi_func(tpm_dso, Key_CreateKey) ||
+- !bind_tspi_func(tpm_dso, Data_Bind) ||
+- !bind_tspi_func(tpm_dso, Data_Unbind) ||
+- !bind_tspi_func(tpm_dso, Context_CreateObject) ||
+- !bind_tspi_func(tpm_dso, Context_FreeMemory) ||
+- !bind_tspi_func(tpm_dso, Key_LoadKey) ||
+- !bind_tspi_func(tpm_dso, Context_LoadKeyByUUID) ||
+- !bind_tspi_func(tpm_dso, GetAttribData) ||
+- !bind_tspi_func(tpm_dso, Hash_Sign) ||
+- !bind_tspi_func(tpm_dso, Context_CloseObject) ||
+- !bind_tspi_func(tpm_dso, Hash_SetHashValue) ||
+- !bind_tspi_func(tpm_dso, SetAttribUint32) ||
+- !bind_tspi_func(tpm_dso, GetPolicyObject) ||
+- !bind_tspi_func(tpm_dso, Policy_SetSecret) ||
+- !bind_tspi_func(tpm_dso, TPM_StirRandom) ||
+- !bind_tspi_func(tpm_dso, Context_LoadKeyByBlob) ||
+- !bind_tspi_func(tpm_dso, Context_GetTpmObject) ||
+- !bind_tspi_func(tpm_dso, GetAttribUint32) ||
+- !bind_tspi_func(tpm_dso, SetAttribData) ||
+- !bind_tspi_func(tpm_dso, Policy_AssignToObject)
+- ) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_DSO_FAILURE);
+- goto err;
+- }
+-#endif /* DLOPEN_TSPI */
+-
+- if ((result = Tspi_Context_Create(&hContext))) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_UNIT_FAILURE);
+- goto err;
+- }
+-
+- /* XXX allow dest to be specified through pre commands */
+- if ((result = Tspi_Context_Connect(hContext, NULL))) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_UNIT_FAILURE);
+- goto err;
+- }
+-
+- if ((result = Tspi_Context_GetTpmObject(hContext, &hTPM))) {
+- TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_UNIT_FAILURE);
+- goto err;
+- }
+-
+- RSA_meth_set_mod_exp(tpm_rsa, RSA_meth_get_mod_exp(ssl_rsa));
+-
+ return 1;
+-err:
+- if (hContext != NULL_HCONTEXT) {
+- Tspi_Context_Close(hContext);
+- hContext = NULL_HCONTEXT;
+- hTPM = NULL_HTPM;
+- }
+-
+-#ifdef DLOPEN_TSPI
+- if (tpm_dso) {
+- DSO_free(tpm_dso);
+- tpm_dso = NULL;
+- }
+-
+- p_tspi_Context_Create = NULL;
+- p_tspi_Context_Close = NULL;
+- p_tspi_Context_Connect = NULL;
+- p_tspi_Context_FreeMemory = NULL;
+- p_tspi_Context_LoadKeyByBlob = NULL;
+- p_tspi_Context_LoadKeyByUUID = NULL;
+- p_tspi_Context_GetTpmObject = NULL;
+- p_tspi_Context_CloseObject = NULL;
+- p_tspi_Key_CreateKey = NULL;
+- p_tspi_Key_LoadKey = NULL;
+- p_tspi_Data_Bind = NULL;
+- p_tspi_Data_Unbind = NULL;
+- p_tspi_Hash_SetHashValue = NULL;
+- p_tspi_Hash_Sign = NULL;
+- p_tspi_GetAttribData = NULL;
+- p_tspi_SetAttribData = NULL;
+- p_tspi_GetAttribUint32 = NULL;
+- p_tspi_SetAttribUint32 = NULL;
+- p_tspi_GetPolicyObject = NULL;
+- p_tspi_Policy_SetSecret = NULL;
+- p_tspi_Policy_AssignToObject = NULL;
+- p_tspi_TPM_StirRandom = NULL;
+- p_tspi_TPM_GetRandom = NULL;
+-#endif
+- return 0;
+ }
+
+ static char *tpm_engine_get_auth(UI_METHOD *ui_method, char *auth, int maxlen,
+@@ -497,29 +256,10 @@ static int tpm_engine_finish(ENGINE * e)
+ {
+ DBG("%s", __FUNCTION__);
+
+-#ifdef DLOPEN_TSPI
+- if (tpm_dso == NULL) {
+- TSSerr(TPM_F_TPM_ENGINE_FINISH, TPM_R_NOT_LOADED);
+- return 0;
+- }
+-#endif
+- if (hContext != NULL_HCONTEXT) {
+- Tspi_Context_Close(hContext);
+- hContext = NULL_HCONTEXT;
+- }
+-#ifdef DLOPEN_TSPI
+- if (!DSO_free(tpm_dso)) {
+- TSSerr(TPM_F_TPM_ENGINE_FINISH, TPM_R_DSO_FAILURE);
+- return 0;
+- }
+- tpm_dso = NULL;
+-#endif
+- RSA_meth_free(tpm_rsa);
+- tpm_rsa = NULL;
+ return 1;
+ }
+
+-int fill_out_rsa_object(RSA *rsa, TSS_HKEY hKey)
++int fill_out_rsa_object(RSA *rsa, TSS_HKEY hKey, TSS_HCONTEXT ctx)
+ {
+ TSS_RESULT result;
+ UINT32 pubkey_len, encScheme, sigScheme;
+@@ -552,12 +292,12 @@ int fill_out_rsa_object(RSA *rsa, TSS_HKEY hKey)
+ }
+
+ if ((n = BN_bin2bn(pubkey, pubkey_len, n)) == NULL) {
+- Tspi_Context_FreeMemory(hContext, pubkey);
++ Tspi_Context_FreeMemory(ctx, pubkey);
+ TSSerr(TPM_F_TPM_FILL_RSA_OBJECT, TPM_R_BN_CONVERSION_FAILED);
+ return 0;
+ }
+
+- Tspi_Context_FreeMemory(hContext, pubkey);
++ Tspi_Context_FreeMemory(ctx, pubkey);
+
+ /* set e in the RSA object */
+ if (((e = BN_new()) == NULL)) {
+@@ -588,6 +328,7 @@ int fill_out_rsa_object(RSA *rsa, TSS_HKEY hKey)
+ app_data->hKey = hKey;
+ app_data->encScheme = encScheme;
+ app_data->sigScheme = sigScheme;
++ app_data->context = ctx;
+ RSA_set_ex_data(rsa, ex_app_data, app_data);
+
+ return 1;
+@@ -609,24 +350,35 @@ static EVP_PKEY *tpm_engine_load_key(ENGINE *e, const char *key_id,
+ RSA *rsa;
+ EVP_PKEY *pkey;
+ BIO *bf;
+-
++ TSS_HKEY hSRK = NULL_HKEY;
++ TSS_HCONTEXT ctx;
+
+ DBG("%s", __FUNCTION__);
+
++ if (Tspi_Context_Create(&ctx)) {
++ TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_UNIT_FAILURE);
++ return NULL;
++ }
++
++ if (Tspi_Context_Connect(ctx, NULL)) {
++ TSSerr(TPM_F_TPM_ENGINE_INIT, TPM_R_UNIT_FAILURE);
++ return NULL;
++ }
++
+ if (!key_id) {
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, ERR_R_PASSED_NULL_PARAMETER);
+- return NULL;
++ goto err_context_free;
+ }
+
+- if (!tpm_load_srk(ui, cb_data)) {
++ if (!tpm_load_srk(ui, cb_data, &hSRK, ctx)) {
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_SRK_LOAD_FAILED);
+- return NULL;
++ goto err_context_free;
+ }
+
+ if ((bf = BIO_new_file(key_id, "r")) == NULL) {
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY,
+ TPM_R_FILE_NOT_FOUND);
+- return NULL;
++ goto err_context_free;
+ }
+
+ blobstr = PEM_ASN1_read_bio((void *)d2i_ASN1_OCTET_STRING,
+@@ -635,12 +387,12 @@ static EVP_PKEY *tpm_engine_load_key(ENGINE *e, const char *key_id,
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY,
+ TPM_R_FILE_READ_FAILED);
+ BIO_free(bf);
+- return NULL;
++ goto err_context_free;
+ }
+
+ BIO_free(bf);
+ DBG("Loading blob of size: %d", blobstr->length);
+- if ((result = Tspi_Context_LoadKeyByBlob(hContext, hSRK,
++ if ((result = Tspi_Context_LoadKeyByBlob(ctx, hSRK,
+ blobstr->length,
+ blobstr->data, &hKey))) {
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY,
+@@ -652,10 +404,10 @@ static EVP_PKEY *tpm_engine_load_key(ENGINE *e, const char *key_id,
+ if ((result = Tspi_GetAttribUint32(hKey, TSS_TSPATTRIB_KEY_INFO,
+ TSS_TSPATTRIB_KEYINFO_AUTHUSAGE,
+ &authusage))) {
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY,
+ TPM_R_REQUEST_FAILED);
+- return NULL;
++ goto err_context_free;
+ }
+
+ if (authusage) {
+@@ -663,46 +415,46 @@ static EVP_PKEY *tpm_engine_load_key(ENGINE *e, const char *key_id,
+ BYTE *auth;
+
+ if ((auth = calloc(1, 128)) == NULL) {
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, ERR_R_MALLOC_FAILURE);
+- return NULL;
++ goto err_context_free;
+ }
+
+ if (!tpm_engine_get_auth(ui, (char *)auth, 128,
+ "TPM Key Password: ",
+ cb_data)) {
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ free(auth);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return NULL;
++ goto err_context_free;
+ }
+
+- if ((result = Tspi_Context_CreateObject(hContext,
++ if ((result = Tspi_Context_CreateObject(ctx,
+ TSS_OBJECT_TYPE_POLICY,
+ TSS_POLICY_USAGE,
+ &hPolicy))) {
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ free(auth);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return 0;
++ goto err_context_free;
+ }
+
+ if ((result = Tspi_Policy_AssignToObject(hPolicy, hKey))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- Tspi_Context_CloseObject(hContext, hPolicy);
++ Tspi_Context_CloseObject(ctx, hKey);
++ Tspi_Context_CloseObject(ctx, hPolicy);
+ free(auth);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return 0;
++ goto err_context_free;
+ }
+
+ if ((result = Tspi_Policy_SetSecret(hPolicy,
+ TSS_SECRET_MODE_PLAIN,
+ strlen((char *)auth), auth))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- Tspi_Context_CloseObject(hContext, hPolicy);
++ Tspi_Context_CloseObject(ctx, hKey);
++ Tspi_Context_CloseObject(ctx, hPolicy);
+ free(auth);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return 0;
++ goto err_context_free;
+ }
+
+ free(auth);
+@@ -710,90 +462,48 @@ static EVP_PKEY *tpm_engine_load_key(ENGINE *e, const char *key_id,
+
+ /* create the new objects to return */
+ if ((pkey = EVP_PKEY_new()) == NULL) {
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, ERR_R_MALLOC_FAILURE);
+- return NULL;
++ goto err_context_free;
+ }
+
+ if ((rsa = RSA_new()) == NULL) {
+ EVP_PKEY_free(pkey);
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, ERR_R_MALLOC_FAILURE);
+- return NULL;
++ goto err_context_free;
+ }
+
+ RSA_set_method(rsa, tpm_rsa);
+
+- if (!fill_out_rsa_object(rsa, hKey)) {
++ if (!fill_out_rsa_object(rsa, hKey, ctx)) {
+ EVP_PKEY_free(pkey);
+ RSA_free(rsa);
+- Tspi_Context_CloseObject(hContext, hKey);
++ Tspi_Context_CloseObject(ctx, hKey);
+ TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return NULL;
++ goto err_context_free;
+ }
+
+ EVP_PKEY_assign_RSA(pkey, rsa);
+
+ return pkey;
+-}
+
+-static int tpm_create_srk_policy(void *secret)
+-{
+- TSS_RESULT result;
+- UINT32 secret_len;
+-
+- if (secret_mode == TSS_SECRET_MODE_SHA1)
+- secret_len = SHA_DIGEST_LENGTH;
+- else {
+- secret_len = (secret == NULL) ? 0 : strlen((char *)secret);
+- DBG("Using SRK secret = %s", (BYTE *)secret);
+- }
+-
+- if (hSRKPolicy == NULL_HPOLICY) {
+- DBG("Creating SRK policy");
+- if ((result = Tspi_Context_CreateObject(hContext,
+- TSS_OBJECT_TYPE_POLICY,
+- TSS_POLICY_USAGE,
+- &hSRKPolicy))) {
+- TSSerr(TPM_F_TPM_CREATE_SRK_POLICY,
+- TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+- }
+-
+- if ((result = Tspi_Policy_SetSecret(hSRKPolicy, secret_mode,
+- secret_len, (BYTE *)secret))) {
+- TSSerr(TPM_F_TPM_CREATE_SRK_POLICY, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
++ err_context_free:
++ Tspi_Context_Close(ctx);
+
+- return 1;
++ return NULL;
+ }
+
+ static int tpm_engine_ctrl(ENGINE * e, int cmd, long i, void *p, void (*f) ())
+ {
+- int initialised = !!hContext;
+ DBG("%s", __FUNCTION__);
+
+ switch (cmd) {
+- case TPM_CMD_SO_PATH:
+- if (p == NULL) {
+- TSSerr(TPM_F_TPM_ENGINE_CTRL,
+- ERR_R_PASSED_NULL_PARAMETER);
+- return 0;
+- }
+- if (initialised) {
+- TSSerr(TPM_F_TPM_ENGINE_CTRL,
+- TPM_R_ALREADY_LOADED);
+- return 0;
+- }
+- TPM_LIBNAME = (const char *) p;
+- return 1;
+ case TPM_CMD_SECRET_MODE:
+ switch ((UINT32)i) {
+ case TSS_SECRET_MODE_POPUP:
+ secret_mode = (UINT32)i;
+- return tpm_create_srk_policy(p);
++ return 0; //tpm_create_srk_policy(p);
+ case TSS_SECRET_MODE_SHA1:
+ /* fall through */
+ case TSS_SECRET_MODE_PLAIN:
+@@ -807,7 +517,7 @@ static int tpm_engine_ctrl(ENGINE * e, int cmd, long i, void *p, void (*f) ())
+ }
+ return 1;
+ case TPM_CMD_PIN:
+- return tpm_create_srk_policy(p);
++ return 0; //tpm_create_srk_policy(p);
+ default:
+ break;
+ }
+@@ -817,12 +527,29 @@ static int tpm_engine_ctrl(ENGINE * e, int cmd, long i, void *p, void (*f) ())
+ }
+
+ #ifndef OPENSSL_NO_RSA
++static void tpm_rsa_free(void *parent, void *ptr, CRYPTO_EX_DATA *ad,
++ int idx, long argl, void *argp)
++{
++ struct rsa_app_data *app_data = ptr;
++ TSS_HCONTEXT ctx;
++
++ if (!app_data)
++ return;
++
++ ctx = app_data->context;
++
++ OPENSSL_free(app_data);
++
++ Tspi_Context_Close(ctx);
++}
++
++
+ static int tpm_rsa_init(RSA *rsa)
+ {
+ DBG("%s", __FUNCTION__);
+
+ if (ex_app_data == TPM_ENGINE_EX_DATA_UNINIT)
+- ex_app_data = RSA_get_ex_new_index(0, NULL, NULL, NULL, NULL);
++ ex_app_data = RSA_get_ex_new_index(0, NULL, NULL, NULL, tpm_rsa_free);
+
+ if (ex_app_data == TPM_ENGINE_EX_DATA_UNINIT) {
+ TSSerr(TPM_F_TPM_RSA_INIT, TPM_R_REQUEST_FAILED);
+@@ -835,6 +562,7 @@ static int tpm_rsa_init(RSA *rsa)
+ static int tpm_rsa_finish(RSA *rsa)
+ {
+ struct rsa_app_data *app_data = RSA_get_ex_data(rsa, ex_app_data);
++ TSS_HCONTEXT ctx = app_data->context;
+
+ DBG("%s", __FUNCTION__);
+
+@@ -842,21 +570,24 @@ static int tpm_rsa_finish(RSA *rsa)
+ return 1;
+
+ if (app_data->hHash) {
+- Tspi_Context_CloseObject(hContext, app_data->hHash);
++ Tspi_Context_CloseObject(ctx, app_data->hHash);
+ app_data->hHash = NULL_HHASH;
+ }
+
+ if (app_data->hKey) {
+- Tspi_Context_CloseObject(hContext, app_data->hKey);
++ Tspi_Context_CloseObject(ctx, app_data->hKey);
+ app_data->hKey = NULL_HKEY;
+ }
+
+ if (app_data->hEncData) {
+- Tspi_Context_CloseObject(hContext, app_data->hEncData);
++ Tspi_Context_CloseObject(ctx, app_data->hEncData);
+ app_data->hEncData = NULL_HENCDATA;
+ }
+
++ Tspi_Context_Close(ctx);
++
+ OPENSSL_free(app_data);
++ RSA_set_ex_data(rsa, ex_app_data, NULL);
+
+ return 1;
+ }
+@@ -887,6 +618,7 @@ static int tpm_rsa_priv_dec(int flen,
+ int padding)
+ {
+ struct rsa_app_data *app_data = RSA_get_ex_data(rsa, ex_app_data);
++ TSS_HCONTEXT ctx = app_data->context;
+ TSS_RESULT result;
+ UINT32 out_len, in_len;
+ BYTE *out;
+@@ -911,7 +643,7 @@ static int tpm_rsa_priv_dec(int flen,
+ }
+
+ if (app_data->hEncData == NULL_HENCDATA) {
+- if ((result = Tspi_Context_CreateObject(hContext,
++ if ((result = Tspi_Context_CreateObject(ctx,
+ TSS_OBJECT_TYPE_ENCDATA,
+ TSS_ENCDATA_BIND,
+ &app_data->hEncData))) {
+@@ -952,7 +684,7 @@ static int tpm_rsa_priv_dec(int flen,
+ DBG("%s: writing out %d bytes as a signature", __FUNCTION__, out_len);
+
+ memcpy(to, out, out_len);
+- Tspi_Context_FreeMemory(hContext, out);
++ Tspi_Context_FreeMemory(ctx, out);
+
+ return out_len;
+ }
+@@ -988,7 +720,7 @@ static int tpm_rsa_pub_enc(int flen,
+ }
+
+ if (app_data->hEncData == NULL_HENCDATA) {
+- if ((result = Tspi_Context_CreateObject(hContext,
++ if ((result = Tspi_Context_CreateObject(app_data->context,
+ TSS_OBJECT_TYPE_ENCDATA,
+ TSS_ENCDATA_BIND,
+ &app_data->hEncData))) {
+@@ -1059,7 +791,7 @@ static int tpm_rsa_pub_enc(int flen,
+ DBG("%s: writing out %d bytes as bound data", __FUNCTION__, out_len);
+
+ memcpy(to, out, out_len);
+- Tspi_Context_FreeMemory(hContext, out);
++ Tspi_Context_FreeMemory(app_data->context, out);
+
+ return out_len;
+ }
+@@ -1100,7 +832,7 @@ static int tpm_rsa_priv_enc(int flen,
+ }
+
+ if (app_data->hHash == NULL_HHASH) {
+- if ((result = Tspi_Context_CreateObject(hContext,
++ if ((result = Tspi_Context_CreateObject(app_data->context,
+ TSS_OBJECT_TYPE_HASH,
+ TSS_HASH_OTHER,
+ &app_data->hHash))) {
+@@ -1141,176 +873,13 @@ static int tpm_rsa_priv_enc(int flen,
+ DBG("%s: writing out %d bytes as a signature", __FUNCTION__, sig_len);
+
+ memcpy(to, sig, sig_len);
+- Tspi_Context_FreeMemory(hContext, sig);
++ Tspi_Context_FreeMemory(app_data->context, sig);
+
+ return sig_len;
+ }
+
+-/* create a new key. we need a way to specify creation of a key with OAEP
+- * padding as well as PKCSv1.5, since signatures will need to be done on
+- * data larger than 20 bytes, which is the max size *regardless of key size*
+- * for an OAEP key signing using the TPM */
+-static int tpm_rsa_keygen(RSA *rsa, int bits, BIGNUM *e, BN_GENCB *cb)
+-{
+- TSS_RESULT result;
+- TSS_FLAG initFlags = TSS_KEY_TYPE_LEGACY;
+- UINT32 encScheme, sigScheme;
+- TSS_HKEY hKey;
+-
+- /* XXX allow this to be specified through pre commands */
+- sigScheme = TSS_SS_RSASSAPKCS1V15_DER;
+- encScheme = TSS_ES_RSAESPKCSV15;
+-
+- DBG("%s", __FUNCTION__);
+-
+- if (!BN_is_word(e, 65537)) {
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_INVALID_EXPONENT);
+- return 0;
+- }
+-
+- switch (bits) {
+- case 512:
+- initFlags |= TSS_KEY_SIZE_512;
+- break;
+- case 1024:
+- initFlags |= TSS_KEY_SIZE_1024;
+- break;
+- case 2048:
+- initFlags |= TSS_KEY_SIZE_2048;
+- break;
+- case 4096:
+- initFlags |= TSS_KEY_SIZE_4096;
+- break;
+- case 8192:
+- initFlags |= TSS_KEY_SIZE_8192;
+- break;
+- case 16384:
+- initFlags |= TSS_KEY_SIZE_16384;
+- break;
+- default:
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_INVALID_KEY_SIZE);
+- return 0;
+- }
+-
+- /* Load the parent key (SRK) which will wrap the new key */
+- if (!tpm_load_srk(NULL, NULL)) {
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_SRK_LOAD_FAILED);
+- return 0;
+- }
+-
+- /* Create the new key object */
+- if ((result = Tspi_Context_CreateObject(hContext,
+- TSS_OBJECT_TYPE_RSAKEY,
+- initFlags, &hKey))) {
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- /* set the signature scheme */
+- if ((result = Tspi_SetAttribUint32(hKey, TSS_TSPATTRIB_KEY_INFO,
+- TSS_TSPATTRIB_KEYINFO_SIGSCHEME,
+- sigScheme))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- /* set the encryption scheme */
+- if ((result = Tspi_SetAttribUint32(hKey, TSS_TSPATTRIB_KEY_INFO,
+- TSS_TSPATTRIB_KEYINFO_ENCSCHEME,
+- encScheme))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- /* Call create key using the new object */
+- if ((result = Tspi_Key_CreateKey(hKey, hSRK, NULL_HPCRS))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- if (!fill_out_rsa_object(rsa, hKey)) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- TSSerr(TPM_F_TPM_RSA_KEYGEN, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- /* Load the key into the chip so other functions don't need to */
+- if ((result = Tspi_Key_LoadKey(hKey, hSRK))) {
+- Tspi_Context_CloseObject(hContext, hKey);
+- TSSerr(TPM_F_TPM_ENGINE_LOAD_KEY, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- return 1;
+-}
+ #endif
+
+-static int tpm_rand_bytes(unsigned char *buf, int num)
+-{
+- TSS_RESULT result;
+- BYTE *rand_data;
+- UINT32 total_requested = 0;
+-
+- DBG("%s getting %d bytes", __FUNCTION__, num);
+-
+- if (num - total_requested > 4096) {
+- if ((result = Tspi_TPM_GetRandom(hTPM, 4096, &rand_data))) {
+- TSSerr(TPM_F_TPM_RAND_BYTES, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- memcpy(&buf[total_requested], rand_data, 4096);
+- Tspi_Context_FreeMemory(hContext, rand_data);
+- total_requested += 4096;
+- }
+-
+- if ((result = Tspi_TPM_GetRandom(hTPM, num - total_requested, &rand_data))) {
+- TSSerr(TPM_F_TPM_RAND_BYTES, TPM_R_REQUEST_FAILED);
+- return 0;
+- }
+-
+- memcpy(buf + total_requested, rand_data, num - total_requested);
+- Tspi_Context_FreeMemory(hContext, rand_data);
+-
+- return 1;
+-}
+-
+-static int tpm_rand_status(void)
+-{
+- DBG("%s", __FUNCTION__);
+- return 1;
+-}
+-
+-static RAND_SEED_RET_TYPE tpm_rand_seed(const void *buf, int num)
+-{
+- TSS_RESULT result;
+- UINT32 total_stirred = 0;
+-
+- DBG("%s", __FUNCTION__);
+-
+- /* There's a hard maximum of 255 bytes allowed to be sent to the TPM on a TPM_StirRandom
+- * call. Use all the bytes in buf, but break them in to 255 or smaller byte chunks */
+- while (num - total_stirred > 255) {
+- if ((result = Tspi_TPM_StirRandom(hTPM, 255,
+- ((BYTE*)buf) + total_stirred))) {
+- TSSerr(TPM_F_TPM_RAND_SEED, TPM_R_REQUEST_FAILED);
+- return RAND_SEED_BAD_RETURN;
+- }
+-
+- total_stirred += 255;
+- }
+-
+- if ((result = Tspi_TPM_StirRandom(hTPM, num - total_stirred,
+- ((BYTE*)buf) + total_stirred))) {
+- TSSerr(TPM_F_TPM_RAND_SEED, TPM_R_REQUEST_FAILED);
+- }
+-
+- return RAND_SEED_GOOD_RETURN;
+-}
+-
+ /* This stuff is needed if this ENGINE is being compiled into a self-contained
+ * shared-library. */
+ static int bind_fn(ENGINE * e, const char *id)
+diff --git a/src/e_tpm.h b/src/e_tpm.h
+index 6316e0b..b592dc2 100644
+--- a/src/e_tpm.h
++++ b/src/e_tpm.h
+@@ -105,6 +105,7 @@ struct rsa_app_data
+ TSS_HENCDATA hEncData;
+ UINT32 encScheme;
+ UINT32 sigScheme;
++ TSS_HCONTEXT context;
+ };
+
+ #define TPM_ENGINE_EX_DATA_UNINIT -1
+--
+2.30.0
+
diff --git a/PKGBUILD b/PKGBUILD
index 01c3fbd04adf..1b759e213a5f 100644
--- a/PKGBUILD
+++ b/PKGBUILD
@@ -1,6 +1,6 @@
# Maintainer: Mantas Mikulėnas <grawity@gmail.com>
pkgname=openssl-tpm-engine
-pkgver=0.5.0
+pkgver=0.5.0+jejb
pkgrel=1
pkgdesc="OpenSSL engine for TPM 1.2 hardware-backed keys"
arch=(i686 x86_64)
@@ -8,16 +8,28 @@ url="https://github.com/mgerstner/openssl_tpm_engine"
license=(custom:openssl)
depends=(openssl trousers)
_commit=b28de5065e6eb9aa5d5afe2276904f7624c2cbaf
-source=("$pkgname::git+https://github.com/mgerstner/openssl_tpm_engine#commit=$_commit")
-sha256sums=('SKIP')
+source=("$pkgname::git+https://github.com/mgerstner/openssl_tpm_engine#commit=$_commit"
+ 0001-try-well-known-authority-for-SRK-first.patch
+ 0002-Handle-EVP-keys.patch
+ 0003-Add-option-for-random-migration-authority.patch
+ 0004-e_tpm-reduce-TPM-connection-time.patch)
+sha256sums=('SKIP'
+ 'b713c5e46e6ea26bee50234786a8d24da154b52f078c5580508c72f644c45083'
+ '5eeb49e0af7f393bfcabc7a82f6b4d13c57e7bbc4219e7cca4316bc2ec0e5bb1'
+ '95489c2c01544081bc19ac9a9210227ebe17f97e72e83be38579cf6a19dfbbe0'
+ '682da7346e3351b8e63ce165d610331f04d558b57cd585f09336666fc827cf31')
pkgver() {
cd $pkgname
- git describe --tags | sed "s/^v//; s/-/.r/; s/-/./"
+ git describe --tags | sed "s/^v//; s/-/.r/; s/-/./; s/$/+jejb/"
}
prepare() {
cd $pkgname
+ patch -Np1 < ../0001-try-well-known-authority-for-SRK-first.patch
+ patch -Np1 < ../0002-Handle-EVP-keys.patch
+ patch -Np1 < ../0003-Add-option-for-random-migration-authority.patch
+ patch -Np1 < ../0004-e_tpm-reduce-TPM-connection-time.patch
sh bootstrap.sh
}