diff options
author | Kenny Root <kroot@google.com> | 2012-03-15 09:42:07 -0700 |
---|---|---|
committer | Kenny Root <kroot@google.com> | 2012-03-26 14:52:55 -0700 |
commit | c1b51d45a7363d6fa58b59bf6f12182993a7c1d0 (patch) | |
tree | afb89cab2b7f5f2f0f0a3adce51c8791dfb9726b | |
parent | c91307af2622f6625525f3c1f9c954376df950ad (diff) | |
download | ipsec-tools-c1b51d45a7363d6fa58b59bf6f12182993a7c1d0.tar.gz |
Add support for OpenSSL ENGINE for keystore
keystore now has an OpenSSL ENGINE frontend that can be used to ask for
private keys or public keys to be loaded and also signing operations to
take place. Use that instead of the crazy byte-array marshalling of the
private key material that is used for the "privsep" stuff.
Change-Id: I6171ca1fb0e77e338c19f04d8c34ad7744984b63
-rw-r--r-- | Android.mk | 4 | ||||
-rw-r--r-- | main.c | 16 | ||||
-rw-r--r-- | src/racoon/oakley.c | 45 |
3 files changed, 63 insertions, 2 deletions
@@ -62,7 +62,7 @@ LOCAL_STATIC_LIBRARIES := libipsec LOCAL_SHARED_LIBRARIES := libcutils libcrypto -LOCAL_CFLAGS := -DANDROID_CHANGES -DHAVE_CONFIG_H +LOCAL_CFLAGS := -DANDROID_CHANGES -DHAVE_CONFIG_H -DHAVE_OPENSSL_ENGINE_H LOCAL_CFLAGS += -Wno-sign-compare -Wno-missing-field-initializers @@ -78,7 +78,7 @@ LOCAL_SRC_FILES := \ src/libipsec/pfkey.c \ src/libipsec/ipsec_strerror.c -LOCAL_CFLAGS := -DHAVE_CONFIG_H +LOCAL_CFLAGS := -DHAVE_CONFIG_H -DHAVE_OPENSSL_ENGINE_H LOCAL_CFLAGS += -Wno-sign-compare -Wno-missing-field-initializers @@ -27,6 +27,8 @@ #ifdef ANDROID_CHANGES +#include <openssl/engine.h> + #include <string.h> #include <sys/types.h> #include <sys/socket.h> @@ -156,9 +158,17 @@ int main(int argc, char **argv) { #ifdef ANDROID_CHANGES int control = android_get_control_and_arguments(&argc, &argv); + ENGINE *e; if (control != -1) { pname = "%p"; monitor_fd(control, NULL); + + ENGINE_load_dynamic(); + e = ENGINE_by_id("keystore"); + if (!e || !ENGINE_init(e)) { + do_plog(LLV_ERROR, "ipsec-tools: cannot load keystore engine"); + exit(1); + } } #endif @@ -194,6 +204,12 @@ int main(int argc, char **argv) } } } +#ifdef ANDROID_CHANGES + if (e) { + ENGINE_finish(e); + ENGINE_free(e); + } +#endif return 0; } diff --git a/src/racoon/oakley.c b/src/racoon/oakley.c index 183ac2f..c446bbb 100644 --- a/src/racoon/oakley.c +++ b/src/racoon/oakley.c @@ -40,6 +40,9 @@ #include <openssl/pkcs7.h> #include <openssl/x509.h> +#ifdef ANDROID_CHANGES +#include <openssl/engine.h> +#endif #include <stdlib.h> #include <stdio.h> @@ -1799,6 +1802,44 @@ end: } #endif +#ifdef ANDROID_CHANGES +static vchar_t* keystore_sign(vchar_t* src, const char* path) { + vchar_t* sig = NULL; + + ENGINE* e = ENGINE_by_id("keystore"); + if (!e) { + return NULL; + } + + if (!ENGINE_init(e)) { + ENGINE_free(e); + return NULL; + } + + const char *key_id; + if (sscanf(path, pname, &key_id) != 1) { + do_plog(LLV_ERROR, "couldn't read private key info\n"); + return NULL; + } + + EVP_PKEY* evp = ENGINE_load_private_key(e, key_id, NULL, NULL); + if (!evp) { + do_plog(LLV_ERROR, "couldn't retrieve private key"); + ERR_clear_error(); + return NULL; + } + + sig = eay_rsa_sign(src, evp->pkey.rsa); + + EVP_PKEY_free(evp); + + ENGINE_finish(e); + ENGINE_free(e); + + return sig; +} +#endif + /* get signature */ int oakley_getsign(iph1) @@ -1820,6 +1861,9 @@ oakley_getsign(iph1) getpathname(path, sizeof(path), LC_PATHTYPE_CERT, iph1->rmconf->myprivfile); +#ifdef ANDROID_CHANGES + iph1->sig = keystore_sign(iph1->hash, path); +#else privkey = privsep_eay_get_pkcs1privkey(path); if (privkey == NULL) { plog(LLV_ERROR, LOCATION, NULL, @@ -1830,6 +1874,7 @@ oakley_getsign(iph1) plogdump(LLV_DEBUG2, privkey->v, privkey->l); iph1->sig = eay_get_x509sign(iph1->hash, privkey); +#endif break; #ifndef ANDROID_PATCHED case ISAKMP_CERT_PLAINRSA: |