summaryrefslogtreecommitdiffstats
path: root/crypto/openssl/apps/pkcs12.c
diff options
context:
space:
mode:
Diffstat (limited to 'crypto/openssl/apps/pkcs12.c')
-rw-r--r--crypto/openssl/apps/pkcs12.c211
1 files changed, 152 insertions, 59 deletions
diff --git a/crypto/openssl/apps/pkcs12.c b/crypto/openssl/apps/pkcs12.c
index 5defdde..bf76864 100644
--- a/crypto/openssl/apps/pkcs12.c
+++ b/crypto/openssl/apps/pkcs12.c
@@ -61,12 +61,12 @@
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
-#include <openssl/des.h>
-#include <openssl/pem.h>
+#include "apps.h"
+#include <openssl/crypto.h>
#include <openssl/err.h>
+#include <openssl/pem.h>
#include <openssl/pkcs12.h>
-#include "apps.h"
#define PROG pkcs12_main
EVP_CIPHER *enc;
@@ -79,14 +79,16 @@ EVP_CIPHER *enc;
#define CACERTS 0x10
int get_cert_chain(X509 *cert, STACK_OF(X509) **chain);
-int dump_cert_text (BIO *out, X509 *x);
-int dump_certs_keys_p12(BIO *out, PKCS12 *p12, char *pass, int passlen, int options);
-int dump_certs_pkeys_bags(BIO *out, STACK *bags, char *pass, int passlen, int options);
-int dump_certs_pkeys_bag(BIO *out, PKCS12_SAFEBAG *bags, char *pass, int passlen, int options);
+int dump_certs_keys_p12(BIO *out, PKCS12 *p12, char *pass, int passlen, int options, char *pempass);
+int dump_certs_pkeys_bags(BIO *out, STACK *bags, char *pass, int passlen, int options, char *pempass);
+int dump_certs_pkeys_bag(BIO *out, PKCS12_SAFEBAG *bags, char *pass, int passlen, int options, char *pempass);
int print_attribs(BIO *out, STACK_OF(X509_ATTRIBUTE) *attrlst, char *name);
void hex_prin(BIO *out, unsigned char *buf, int len);
int alg_print(BIO *x, X509_ALGOR *alg);
int cert_load(BIO *in, STACK_OF(X509) *sk);
+
+int MAIN(int, char **);
+
int MAIN(int argc, char **argv)
{
char *infile=NULL, *outfile=NULL, *keyname = NULL;
@@ -101,15 +103,19 @@ int MAIN(int argc, char **argv)
int chain = 0;
int badarg = 0;
int iter = PKCS12_DEFAULT_ITER;
- int maciter = 1;
+ int maciter = PKCS12_DEFAULT_ITER;
int twopass = 0;
int keytype = 0;
int cert_pbe = NID_pbe_WithSHA1And40BitRC2_CBC;
+ int key_pbe = NID_pbe_WithSHA1And3_Key_TripleDES_CBC;
int ret = 1;
int macver = 1;
int noprompt = 0;
STACK *canames = NULL;
char *cpass = NULL, *mpass = NULL;
+ char *passargin = NULL, *passargout = NULL, *passarg = NULL;
+ char *passin = NULL, *passout = NULL;
+ char *inrand = NULL;
apps_startup();
@@ -143,8 +149,35 @@ int MAIN(int argc, char **argv)
else if (!strcmp (*args, "-noiter")) iter = 1;
else if (!strcmp (*args, "-maciter"))
maciter = PKCS12_DEFAULT_ITER;
+ else if (!strcmp (*args, "-nomaciter"))
+ maciter = 1;
else if (!strcmp (*args, "-nodes")) enc=NULL;
- else if (!strcmp (*args, "-inkey")) {
+ else if (!strcmp (*args, "-certpbe")) {
+ if (args[1]) {
+ args++;
+ cert_pbe=OBJ_txt2nid(*args);
+ if(cert_pbe == NID_undef) {
+ BIO_printf(bio_err,
+ "Unknown PBE algorithm %s\n", *args);
+ badarg = 1;
+ }
+ } else badarg = 1;
+ } else if (!strcmp (*args, "-keypbe")) {
+ if (args[1]) {
+ args++;
+ key_pbe=OBJ_txt2nid(*args);
+ if(key_pbe == NID_undef) {
+ BIO_printf(bio_err,
+ "Unknown PBE algorithm %s\n", *args);
+ badarg = 1;
+ }
+ } else badarg = 1;
+ } else if (!strcmp (*args, "-rand")) {
+ if (args[1]) {
+ args++;
+ inrand = *args;
+ } else badarg = 1;
+ } else if (!strcmp (*args, "-inkey")) {
if (args[1]) {
args++;
keyname = *args;
@@ -175,20 +208,20 @@ int MAIN(int argc, char **argv)
args++;
outfile = *args;
} else badarg = 1;
- } else if (!strcmp (*args, "-envpass")) {
+ } else if (!strcmp(*args,"-passin")) {
if (args[1]) {
args++;
- if(!(cpass = getenv(*args))) {
- BIO_printf(bio_err,
- "Can't read environment variable %s\n", *args);
- goto end;
- }
- noprompt = 1;
+ passargin = *args;
+ } else badarg = 1;
+ } else if (!strcmp(*args,"-passout")) {
+ if (args[1]) {
+ args++;
+ passargout = *args;
} else badarg = 1;
} else if (!strcmp (*args, "-password")) {
if (args[1]) {
args++;
- cpass = *args;
+ passarg = *args;
noprompt = 1;
} else badarg = 1;
} else badarg = 1;
@@ -225,21 +258,54 @@ int MAIN(int argc, char **argv)
BIO_printf (bio_err, "-maciter use MAC iteration\n");
BIO_printf (bio_err, "-twopass separate MAC, encryption passwords\n");
BIO_printf (bio_err, "-descert encrypt PKCS#12 certificates with triple DES (default RC2-40)\n");
+ BIO_printf (bio_err, "-certpbe alg specify certificate PBE algorithm (default RC2-40)\n");
+ BIO_printf (bio_err, "-keypbe alg specify private key PBE algorithm (default 3DES)\n");
BIO_printf (bio_err, "-keyex set MS key exchange type\n");
BIO_printf (bio_err, "-keysig set MS key signature type\n");
- BIO_printf (bio_err, "-password p set import/export password (NOT RECOMMENDED)\n");
- BIO_printf (bio_err, "-envpass p set import/export password from environment\n");
+ BIO_printf (bio_err, "-password p set import/export password source\n");
+ BIO_printf (bio_err, "-passin p input file pass phrase source\n");
+ BIO_printf (bio_err, "-passout p output file pass phrase source\n");
+ BIO_printf(bio_err, "-rand file%cfile%c...\n", LIST_SEPARATOR_CHAR, LIST_SEPARATOR_CHAR);
+ BIO_printf(bio_err, " load the file (or the files in the directory) into\n");
+ BIO_printf(bio_err, " the random number generator\n");
goto end;
}
- if(cpass) mpass = cpass;
- else {
+ if(passarg) {
+ if(export_cert) passargout = passarg;
+ else passargin = passarg;
+ }
+
+ if(!app_passwd(bio_err, passargin, passargout, &passin, &passout)) {
+ BIO_printf(bio_err, "Error getting passwords\n");
+ goto end;
+ }
+
+ if(!cpass) {
+ if(export_cert) cpass = passout;
+ else cpass = passin;
+ }
+
+ if(cpass) {
+ mpass = cpass;
+ noprompt = 1;
+ } else {
cpass = pass;
mpass = macpass;
}
+ if(export_cert || inrand) {
+ app_RAND_load_file(NULL, bio_err, (inrand != NULL));
+ if (inrand != NULL)
+ BIO_printf(bio_err,"%ld semi-random bytes loaded\n",
+ app_RAND_load_files(inrand));
+ }
ERR_load_crypto_strings();
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("read files");
+#endif
+
if (!infile) in = BIO_new_fp(stdin, BIO_NOCLOSE);
else in = BIO_new_file(infile, "rb");
if (!in) {
@@ -265,6 +331,11 @@ int MAIN(int argc, char **argv)
}
}
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+ CRYPTO_push_info("write files");
+#endif
+
if (!outfile) out = BIO_new_fp(stdout, BIO_NOCLOSE);
else out = BIO_new_file(outfile, "wb");
if (!out) {
@@ -274,27 +345,38 @@ int MAIN(int argc, char **argv)
goto end;
}
if (twopass) {
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("read MAC password");
+#endif
if(EVP_read_pw_string (macpass, 50, "Enter MAC Password:", export_cert))
{
BIO_printf (bio_err, "Can't read Password\n");
goto end;
}
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+#endif
}
-if (export_cert) {
+ if (export_cert) {
EVP_PKEY *key;
STACK *bags, *safes;
PKCS12_SAFEBAG *bag;
PKCS8_PRIV_KEY_INFO *p8;
PKCS7 *authsafe;
- X509 *cert = NULL, *ucert = NULL;
- STACK_OF(X509) *certs;
+ X509 *ucert = NULL;
+ STACK_OF(X509) *certs=NULL;
char *catmp;
int i;
unsigned char keyid[EVP_MAX_MD_SIZE];
unsigned int keyidlen = 0;
- key = PEM_read_bio_PrivateKey(inkey ? inkey : in, NULL, NULL, NULL);
+
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("process -export_cert");
+#endif
+ key = PEM_read_bio_PrivateKey(inkey ? inkey : in, NULL, NULL, passin);
if (!inkey) (void) BIO_reset(in);
+ else BIO_free(inkey);
if (!key) {
BIO_printf (bio_err, "Error loading private key\n");
ERR_print_errors(bio_err);
@@ -313,7 +395,7 @@ if (export_cert) {
for(i = 0; i < sk_X509_num(certs); i++) {
ucert = sk_X509_value(certs, i);
if(X509_check_private_key(ucert, key)) {
- X509_digest(cert, EVP_sha1(), keyid, &keyidlen);
+ X509_digest(ucert, EVP_sha1(), keyid, &keyidlen);
break;
}
}
@@ -354,6 +436,7 @@ if (export_cert) {
/* We now have loads of certificates: include them all */
for(i = 0; i < sk_X509_num(certs); i++) {
+ X509 *cert = NULL;
cert = sk_X509_value(certs, i);
bag = M_PKCS12_x5092certbag(cert);
/* If it matches private key set id */
@@ -364,7 +447,7 @@ if (export_cert) {
PKCS12_add_friendlyname(bag, catmp, -1);
sk_push(bags, (char *)bag);
}
-
+ sk_X509_pop_free(certs, X509_free);
if (canames) sk_free(canames);
if(!noprompt &&
@@ -390,8 +473,7 @@ if (export_cert) {
p8 = EVP_PKEY2PKCS8 (key);
EVP_PKEY_free(key);
if(keytype) PKCS8_add_keyusage(p8, keytype);
- bag = PKCS12_MAKE_SHKEYBAG(NID_pbe_WithSHA1And3_Key_TripleDES_CBC,
- cpass, -1, NULL, 0, iter, p8);
+ bag = PKCS12_MAKE_SHKEYBAG(key_pbe, cpass, -1, NULL, 0, iter, p8);
PKCS8_PRIV_KEY_INFO_free(p8);
if (name) PKCS12_add_friendlyname (bag, name, -1);
PKCS12_add_localkeyid (bag, keyid, keyidlen);
@@ -415,6 +497,10 @@ if (export_cert) {
PKCS12_free(p12);
ret = 0;
+
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+#endif
goto end;
}
@@ -424,50 +510,61 @@ if (export_cert) {
goto end;
}
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("read import password");
+#endif
if(!noprompt && EVP_read_pw_string(pass, 50, "Enter Import Password:", 0)) {
BIO_printf (bio_err, "Can't read Password\n");
goto end;
}
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+#endif
if (!twopass) strcpy(macpass, pass);
if (options & INFO) BIO_printf (bio_err, "MAC Iteration %ld\n", p12->mac->iter ? ASN1_INTEGER_get (p12->mac->iter) : 1);
if(macver) {
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("verify MAC");
+#endif
if (!PKCS12_verify_mac (p12, mpass, -1)) {
- BIO_printf (bio_err, "Mac verify errror: invalid password?\n");
+ BIO_printf (bio_err, "Mac verify error: invalid password?\n");
ERR_print_errors (bio_err);
goto end;
} else BIO_printf (bio_err, "MAC verified OK\n");
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+#endif
}
- if (!dump_certs_keys_p12 (out, p12, cpass, -1, options)) {
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_push_info("output keys and certificates");
+#endif
+ if (!dump_certs_keys_p12 (out, p12, cpass, -1, options, passout)) {
BIO_printf(bio_err, "Error outputting keys and certificates\n");
ERR_print_errors (bio_err);
goto end;
}
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_pop_info();
+#endif
PKCS12_free(p12);
ret = 0;
end:
+ if(export_cert || inrand) app_RAND_write_file(NULL, bio_err);
+#ifdef CRYPTO_MDEBUG
+ CRYPTO_remove_all_info();
+#endif
+ BIO_free(in);
BIO_free(out);
+ if(passin) Free(passin);
+ if(passout) Free(passout);
EXIT(ret);
}
-int dump_cert_text (BIO *out, X509 *x)
-{
- char buf[256];
- X509_NAME_oneline(X509_get_subject_name(x),buf,256);
- BIO_puts(out,"subject=");
- BIO_puts(out,buf);
-
- X509_NAME_oneline(X509_get_issuer_name(x),buf,256);
- BIO_puts(out,"\nissuer= ");
- BIO_puts(out,buf);
- BIO_puts(out,"\n");
- return 0;
-}
-
int dump_certs_keys_p12 (BIO *out, PKCS12 *p12, char *pass,
- int passlen, int options)
+ int passlen, int options, char *pempass)
{
STACK *asafes, *bags;
int i, bagnid;
@@ -489,7 +586,7 @@ int dump_certs_keys_p12 (BIO *out, PKCS12 *p12, char *pass,
} else continue;
if (!bags) return 0;
if (!dump_certs_pkeys_bags (out, bags, pass, passlen,
- options)) {
+ options, pempass)) {
sk_pop_free (bags, PKCS12_SAFEBAG_free);
return 0;
}
@@ -500,19 +597,19 @@ int dump_certs_keys_p12 (BIO *out, PKCS12 *p12, char *pass,
}
int dump_certs_pkeys_bags (BIO *out, STACK *bags, char *pass,
- int passlen, int options)
+ int passlen, int options, char *pempass)
{
int i;
for (i = 0; i < sk_num (bags); i++) {
if (!dump_certs_pkeys_bag (out,
(PKCS12_SAFEBAG *)sk_value (bags, i), pass, passlen,
- options)) return 0;
+ options, pempass)) return 0;
}
return 1;
}
int dump_certs_pkeys_bag (BIO *out, PKCS12_SAFEBAG *bag, char *pass,
- int passlen, int options)
+ int passlen, int options, char *pempass)
{
EVP_PKEY *pkey;
PKCS8_PRIV_KEY_INFO *p8;
@@ -527,7 +624,7 @@ int dump_certs_pkeys_bag (BIO *out, PKCS12_SAFEBAG *bag, char *pass,
p8 = bag->value.keybag;
if (!(pkey = EVP_PKCS82PKEY (p8))) return 0;
print_attribs (out, p8->attributes, "Key Attributes");
- PEM_write_bio_PrivateKey (out, pkey, enc, NULL, 0, NULL, NULL);
+ PEM_write_bio_PrivateKey (out, pkey, enc, NULL, 0, NULL, pempass);
EVP_PKEY_free(pkey);
break;
@@ -543,7 +640,7 @@ int dump_certs_pkeys_bag (BIO *out, PKCS12_SAFEBAG *bag, char *pass,
if (!(pkey = EVP_PKCS82PKEY (p8))) return 0;
print_attribs (out, p8->attributes, "Key Attributes");
PKCS8_PRIV_KEY_INFO_free(p8);
- PEM_write_bio_PrivateKey (out, pkey, enc, NULL, 0, NULL, NULL);
+ PEM_write_bio_PrivateKey (out, pkey, enc, NULL, 0, NULL, pempass);
EVP_PKEY_free(pkey);
break;
@@ -566,7 +663,7 @@ int dump_certs_pkeys_bag (BIO *out, PKCS12_SAFEBAG *bag, char *pass,
if (options & INFO) BIO_printf (bio_err, "Safe Contents bag\n");
print_attribs (out, bag->attrib, "Bag Attributes");
return dump_certs_pkeys_bags (out, bag->value.safes, pass,
- passlen, options);
+ passlen, options, pempass);
default:
BIO_printf (bio_err, "Warning unsupported bag type: ");
@@ -588,7 +685,7 @@ int get_cert_chain (X509 *cert, STACK_OF(X509) **chain)
X509_STORE_CTX store_ctx;
STACK_OF(X509) *chn;
int i;
- X509 *x;
+
store = X509_STORE_new ();
X509_STORE_set_default_paths (store);
X509_STORE_CTX_init(&store_ctx, store, cert, NULL);
@@ -596,11 +693,7 @@ int get_cert_chain (X509 *cert, STACK_OF(X509) **chain)
i = X509_STORE_CTX_get_error (&store_ctx);
goto err;
}
- chn = sk_X509_dup(X509_STORE_CTX_get_chain (&store_ctx));
- for (i = 0; i < sk_X509_num(chn); i++) {
- x = sk_X509_value(chn, i);
- CRYPTO_add(&x->references,1,CRYPTO_LOCK_X509);
- }
+ chn = X509_STORE_CTX_get1_chain(&store_ctx);
i = 0;
*chain = chn;
err:
OpenPOWER on IntegriCloud