summaryrefslogtreecommitdiff
path: root/src/lib/libcrypto/pem
diff options
context:
space:
mode:
authorbeck <>2000-03-19 11:13:58 +0000
committerbeck <>2000-03-19 11:13:58 +0000
commit796d609550df3a33fc11468741c5d2f6d3df4c11 (patch)
tree6c6d539061caa20372dad0ac4ddb1dfae2fbe7fe /src/lib/libcrypto/pem
parent5be3114c1fd7e0dfea1e38d3abb4cbba75244419 (diff)
downloadopenbsd-796d609550df3a33fc11468741c5d2f6d3df4c11.tar.gz
openbsd-796d609550df3a33fc11468741c5d2f6d3df4c11.tar.bz2
openbsd-796d609550df3a33fc11468741c5d2f6d3df4c11.zip
OpenSSL 0.9.5 merge
*warning* this bumps shared lib minors for libssl and libcrypto from 2.1 to 2.2 if you are using the ssl26 packages for ssh and other things to work you will need to get new ones (see ~beck/libsslsnap/<arch>) on cvs or ~beck/src-patent.tar.gz on cvs
Diffstat (limited to 'src/lib/libcrypto/pem')
-rw-r--r--src/lib/libcrypto/pem/pem.h38
-rw-r--r--src/lib/libcrypto/pem/pem_all.c94
-rw-r--r--src/lib/libcrypto/pem/pem_err.c3
-rw-r--r--src/lib/libcrypto/pem/pem_info.c11
-rw-r--r--src/lib/libcrypto/pem/pem_lib.c222
-rw-r--r--src/lib/libcrypto/pem/pem_seal.c6
6 files changed, 341 insertions, 33 deletions
diff --git a/src/lib/libcrypto/pem/pem.h b/src/lib/libcrypto/pem/pem.h
index fc333e42c8..e4bae0b4aa 100644
--- a/src/lib/libcrypto/pem/pem.h
+++ b/src/lib/libcrypto/pem/pem.h
@@ -103,13 +103,16 @@ extern "C" {
103 103
104#define PEM_STRING_X509_OLD "X509 CERTIFICATE" 104#define PEM_STRING_X509_OLD "X509 CERTIFICATE"
105#define PEM_STRING_X509 "CERTIFICATE" 105#define PEM_STRING_X509 "CERTIFICATE"
106#define PEM_STRING_X509_TRUSTED "TRUSTED CERTIFICATE"
106#define PEM_STRING_X509_REQ_OLD "NEW CERTIFICATE REQUEST" 107#define PEM_STRING_X509_REQ_OLD "NEW CERTIFICATE REQUEST"
107#define PEM_STRING_X509_REQ "CERTIFICATE REQUEST" 108#define PEM_STRING_X509_REQ "CERTIFICATE REQUEST"
108#define PEM_STRING_X509_CRL "X509 CRL" 109#define PEM_STRING_X509_CRL "X509 CRL"
109#define PEM_STRING_EVP_PKEY "ANY PRIVATE KEY" 110#define PEM_STRING_EVP_PKEY "ANY PRIVATE KEY"
111#define PEM_STRING_PUBLIC "PUBLIC KEY"
110#define PEM_STRING_RSA "RSA PRIVATE KEY" 112#define PEM_STRING_RSA "RSA PRIVATE KEY"
111#define PEM_STRING_RSA_PUBLIC "RSA PUBLIC KEY" 113#define PEM_STRING_RSA_PUBLIC "RSA PUBLIC KEY"
112#define PEM_STRING_DSA "DSA PRIVATE KEY" 114#define PEM_STRING_DSA "DSA PRIVATE KEY"
115#define PEM_STRING_DSA_PUBLIC "DSA PUBLIC KEY"
113#define PEM_STRING_PKCS7 "PKCS7" 116#define PEM_STRING_PKCS7 "PKCS7"
114#define PEM_STRING_PKCS8 "ENCRYPTED PRIVATE KEY" 117#define PEM_STRING_PKCS8 "ENCRYPTED PRIVATE KEY"
115#define PEM_STRING_PKCS8INF "PRIVATE KEY" 118#define PEM_STRING_PKCS8INF "PRIVATE KEY"
@@ -528,7 +531,10 @@ void PEM_dek_info(char *buf, const char *type, int len, char *str);
528 531
529DECLARE_PEM_rw(X509, X509) 532DECLARE_PEM_rw(X509, X509)
530 533
534DECLARE_PEM_rw(X509_AUX, X509)
535
531DECLARE_PEM_rw(X509_REQ, X509_REQ) 536DECLARE_PEM_rw(X509_REQ, X509_REQ)
537DECLARE_PEM_write(X509_REQ_NEW, X509_REQ)
532 538
533DECLARE_PEM_rw(X509_CRL, X509_CRL) 539DECLARE_PEM_rw(X509_CRL, X509_CRL)
534 540
@@ -545,6 +551,7 @@ DECLARE_PEM_rw(PKCS8_PRIV_KEY_INFO, PKCS8_PRIV_KEY_INFO)
545DECLARE_PEM_rw_cb(RSAPrivateKey, RSA) 551DECLARE_PEM_rw_cb(RSAPrivateKey, RSA)
546 552
547DECLARE_PEM_rw(RSAPublicKey, RSA) 553DECLARE_PEM_rw(RSAPublicKey, RSA)
554DECLARE_PEM_rw(RSA_PUBKEY, RSA)
548 555
549#endif 556#endif
550 557
@@ -552,6 +559,8 @@ DECLARE_PEM_rw(RSAPublicKey, RSA)
552 559
553DECLARE_PEM_rw_cb(DSAPrivateKey, DSA) 560DECLARE_PEM_rw_cb(DSAPrivateKey, DSA)
554 561
562DECLARE_PEM_rw(DSA_PUBKEY, DSA)
563
555DECLARE_PEM_rw(DSAparams, DSA) 564DECLARE_PEM_rw(DSAparams, DSA)
556 565
557#endif 566#endif
@@ -564,10 +573,36 @@ DECLARE_PEM_rw(DHparams, DH)
564 573
565DECLARE_PEM_rw_cb(PrivateKey, EVP_PKEY) 574DECLARE_PEM_rw_cb(PrivateKey, EVP_PKEY)
566 575
576DECLARE_PEM_rw(PUBKEY, EVP_PKEY)
577
578int PEM_write_bio_PKCS8PrivateKey_nid(BIO *bp, EVP_PKEY *x, int nid,
579 char *kstr, int klen,
580 pem_password_cb *cb, void *u);
567int PEM_write_bio_PKCS8PrivateKey(BIO *, EVP_PKEY *, const EVP_CIPHER *, 581int PEM_write_bio_PKCS8PrivateKey(BIO *, EVP_PKEY *, const EVP_CIPHER *,
568 char *, int, pem_password_cb *, void *); 582 char *, int, pem_password_cb *, void *);
583int i2d_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc,
584 char *kstr, int klen,
585 pem_password_cb *cb, void *u);
586int i2d_PKCS8PrivateKey_nid_bio(BIO *bp, EVP_PKEY *x, int nid,
587 char *kstr, int klen,
588 pem_password_cb *cb, void *u);
589EVP_PKEY *d2i_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY **x, pem_password_cb *cb, void *u);
590
591int i2d_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc,
592 char *kstr, int klen,
593 pem_password_cb *cb, void *u);
594int i2d_PKCS8PrivateKey_nid_fp(FILE *fp, EVP_PKEY *x, int nid,
595 char *kstr, int klen,
596 pem_password_cb *cb, void *u);
597int PEM_write_PKCS8PrivateKey_nid(FILE *fp, EVP_PKEY *x, int nid,
598 char *kstr, int klen,
599 pem_password_cb *cb, void *u);
600
601EVP_PKEY *d2i_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY **x, pem_password_cb *cb, void *u);
602
569int PEM_write_PKCS8PrivateKey(FILE *fp,EVP_PKEY *x,const EVP_CIPHER *enc, 603int PEM_write_PKCS8PrivateKey(FILE *fp,EVP_PKEY *x,const EVP_CIPHER *enc,
570 char *kstr,int klen, pem_password_cb *cd, void *u); 604 char *kstr,int klen, pem_password_cb *cd, void *u);
605
571#endif /* SSLEAY_MACROS */ 606#endif /* SSLEAY_MACROS */
572 607
573 608
@@ -579,6 +614,8 @@ int PEM_write_PKCS8PrivateKey(FILE *fp,EVP_PKEY *x,const EVP_CIPHER *enc,
579/* Error codes for the PEM functions. */ 614/* Error codes for the PEM functions. */
580 615
581/* Function codes. */ 616/* Function codes. */
617#define PEM_F_D2I_PKCS8PRIVATEKEY_BIO 120
618#define PEM_F_D2I_PKCS8PRIVATEKEY_FP 121
582#define PEM_F_DEF_CALLBACK 100 619#define PEM_F_DEF_CALLBACK 100
583#define PEM_F_LOAD_IV 101 620#define PEM_F_LOAD_IV 101
584#define PEM_F_PEM_ASN1_READ 102 621#define PEM_F_PEM_ASN1_READ 102
@@ -586,6 +623,7 @@ int PEM_write_PKCS8PrivateKey(FILE *fp,EVP_PKEY *x,const EVP_CIPHER *enc,
586#define PEM_F_PEM_ASN1_WRITE 104 623#define PEM_F_PEM_ASN1_WRITE 104
587#define PEM_F_PEM_ASN1_WRITE_BIO 105 624#define PEM_F_PEM_ASN1_WRITE_BIO 105
588#define PEM_F_PEM_DO_HEADER 106 625#define PEM_F_PEM_DO_HEADER 106
626#define PEM_F_PEM_F_DO_PK8KEY_FP 122
589#define PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY 118 627#define PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY 118
590#define PEM_F_PEM_GET_EVP_CIPHER_INFO 107 628#define PEM_F_PEM_GET_EVP_CIPHER_INFO 107
591#define PEM_F_PEM_READ 108 629#define PEM_F_PEM_READ 108
diff --git a/src/lib/libcrypto/pem/pem_all.c b/src/lib/libcrypto/pem/pem_all.c
index bc473f3cff..dc9c35b4b4 100644
--- a/src/lib/libcrypto/pem/pem_all.c
+++ b/src/lib/libcrypto/pem/pem_all.c
@@ -65,10 +65,21 @@
65#include <openssl/pkcs7.h> 65#include <openssl/pkcs7.h>
66#include <openssl/pem.h> 66#include <openssl/pem.h>
67 67
68#ifndef NO_RSA
69static RSA *pkey_get_rsa(EVP_PKEY *key, RSA **rsa);
70#endif
71#ifndef NO_DSA
72static DSA *pkey_get_dsa(EVP_PKEY *key, DSA **dsa);
73#endif
74
68IMPLEMENT_PEM_rw(X509, X509, PEM_STRING_X509, X509) 75IMPLEMENT_PEM_rw(X509, X509, PEM_STRING_X509, X509)
69 76
77IMPLEMENT_PEM_rw(X509_AUX, X509, PEM_STRING_X509_TRUSTED, X509_AUX)
78
70IMPLEMENT_PEM_rw(X509_REQ, X509_REQ, PEM_STRING_X509_REQ, X509_REQ) 79IMPLEMENT_PEM_rw(X509_REQ, X509_REQ, PEM_STRING_X509_REQ, X509_REQ)
71 80
81IMPLEMENT_PEM_write(X509_REQ_NEW, X509_REQ, PEM_STRING_X509_REQ_OLD, X509_REQ)
82
72IMPLEMENT_PEM_rw(X509_CRL, X509_CRL, PEM_STRING_X509_CRL, X509_CRL) 83IMPLEMENT_PEM_rw(X509_CRL, X509_CRL, PEM_STRING_X509_CRL, X509_CRL)
73 84
74IMPLEMENT_PEM_rw(PKCS7, PKCS7, PEM_STRING_PKCS7, PKCS7) 85IMPLEMENT_PEM_rw(PKCS7, PKCS7, PEM_STRING_PKCS7, PKCS7)
@@ -82,15 +93,92 @@ IMPLEMENT_PEM_rw(PKCS8_PRIV_KEY_INFO, PKCS8_PRIV_KEY_INFO, PEM_STRING_PKCS8INF,
82 93
83#ifndef NO_RSA 94#ifndef NO_RSA
84 95
85IMPLEMENT_PEM_rw_cb(RSAPrivateKey, RSA, PEM_STRING_RSA, RSAPrivateKey) 96/* We treat RSA or DSA private keys as a special case.
97 *
98 * For private keys we read in an EVP_PKEY structure with
99 * PEM_read_bio_PrivateKey() and extract the relevant private
100 * key: this means can handle "traditional" and PKCS#8 formats
101 * transparently.
102 */
103
104static RSA *pkey_get_rsa(EVP_PKEY *key, RSA **rsa)
105{
106 RSA *rtmp;
107 if(!key) return NULL;
108 rtmp = EVP_PKEY_get1_RSA(key);
109 EVP_PKEY_free(key);
110 if(!rtmp) return NULL;
111 if(rsa) {
112 RSA_free(*rsa);
113 *rsa = rtmp;
114 }
115 return rtmp;
116}
117
118RSA *PEM_read_bio_RSAPrivateKey(BIO *bp, RSA **rsa, pem_password_cb *cb,
119 void *u)
120{
121 EVP_PKEY *pktmp;
122 pktmp = PEM_read_bio_PrivateKey(bp, NULL, cb, u);
123 return pkey_get_rsa(pktmp, rsa);
124}
125
126#ifndef NO_FP_API
127
128RSA *PEM_read_RSAPrivateKey(FILE *fp, RSA **rsa, pem_password_cb *cb,
129 void *u)
130{
131 EVP_PKEY *pktmp;
132 pktmp = PEM_read_PrivateKey(fp, NULL, cb, u);
133 return pkey_get_rsa(pktmp, rsa);
134}
135
136#endif
86 137
138IMPLEMENT_PEM_write_cb(RSAPrivateKey, RSA, PEM_STRING_RSA, RSAPrivateKey)
87IMPLEMENT_PEM_rw(RSAPublicKey, RSA, PEM_STRING_RSA_PUBLIC, RSAPublicKey) 139IMPLEMENT_PEM_rw(RSAPublicKey, RSA, PEM_STRING_RSA_PUBLIC, RSAPublicKey)
140IMPLEMENT_PEM_rw(RSA_PUBKEY, RSA, PEM_STRING_PUBLIC, RSA_PUBKEY)
88 141
89#endif 142#endif
90 143
91#ifndef NO_DSA 144#ifndef NO_DSA
92 145
93IMPLEMENT_PEM_rw_cb(DSAPrivateKey, DSA, PEM_STRING_DSA, DSAPrivateKey) 146static DSA *pkey_get_dsa(EVP_PKEY *key, DSA **dsa)
147{
148 DSA *dtmp;
149 if(!key) return NULL;
150 dtmp = EVP_PKEY_get1_DSA(key);
151 EVP_PKEY_free(key);
152 if(!dtmp) return NULL;
153 if(dsa) {
154 DSA_free(*dsa);
155 *dsa = dtmp;
156 }
157 return dtmp;
158}
159
160DSA *PEM_read_bio_DSAPrivateKey(BIO *bp, DSA **dsa, pem_password_cb *cb,
161 void *u)
162{
163 EVP_PKEY *pktmp;
164 pktmp = PEM_read_bio_PrivateKey(bp, NULL, cb, u);
165 return pkey_get_dsa(pktmp, dsa);
166}
167
168IMPLEMENT_PEM_write_cb(DSAPrivateKey, DSA, PEM_STRING_DSA, DSAPrivateKey)
169IMPLEMENT_PEM_rw(DSA_PUBKEY, DSA, PEM_STRING_PUBLIC, DSA_PUBKEY)
170
171#ifndef NO_FP_API
172
173DSA *PEM_read_DSAPrivateKey(FILE *fp, DSA **dsa, pem_password_cb *cb,
174 void *u)
175{
176 EVP_PKEY *pktmp;
177 pktmp = PEM_read_PrivateKey(fp, NULL, cb, u);
178 return pkey_get_dsa(pktmp, dsa);
179}
180
181#endif
94 182
95IMPLEMENT_PEM_rw(DSAparams, DSA, PEM_STRING_DSAPARAMS, DSAparams) 183IMPLEMENT_PEM_rw(DSAparams, DSA, PEM_STRING_DSAPARAMS, DSAparams)
96 184
@@ -111,3 +199,5 @@ IMPLEMENT_PEM_rw(DHparams, DH, PEM_STRING_DHPARAMS, DHparams)
111 */ 199 */
112IMPLEMENT_PEM_read(PrivateKey, EVP_PKEY, PEM_STRING_EVP_PKEY, PrivateKey) 200IMPLEMENT_PEM_read(PrivateKey, EVP_PKEY, PEM_STRING_EVP_PKEY, PrivateKey)
113IMPLEMENT_PEM_write_cb(PrivateKey, EVP_PKEY, ((x->type == EVP_PKEY_DSA)?PEM_STRING_DSA:PEM_STRING_RSA), PrivateKey) 201IMPLEMENT_PEM_write_cb(PrivateKey, EVP_PKEY, ((x->type == EVP_PKEY_DSA)?PEM_STRING_DSA:PEM_STRING_RSA), PrivateKey)
202
203IMPLEMENT_PEM_rw(PUBKEY, EVP_PKEY, PEM_STRING_PUBLIC, PUBKEY)
diff --git a/src/lib/libcrypto/pem/pem_err.c b/src/lib/libcrypto/pem/pem_err.c
index fa70f60998..642129da20 100644
--- a/src/lib/libcrypto/pem/pem_err.c
+++ b/src/lib/libcrypto/pem/pem_err.c
@@ -65,6 +65,8 @@
65#ifndef NO_ERR 65#ifndef NO_ERR
66static ERR_STRING_DATA PEM_str_functs[]= 66static ERR_STRING_DATA PEM_str_functs[]=
67 { 67 {
68{ERR_PACK(0,PEM_F_D2I_PKCS8PRIVATEKEY_BIO,0), "d2i_PKCS8PrivateKey_bio"},
69{ERR_PACK(0,PEM_F_D2I_PKCS8PRIVATEKEY_FP,0), "d2i_PKCS8PrivateKey_fp"},
68{ERR_PACK(0,PEM_F_DEF_CALLBACK,0), "DEF_CALLBACK"}, 70{ERR_PACK(0,PEM_F_DEF_CALLBACK,0), "DEF_CALLBACK"},
69{ERR_PACK(0,PEM_F_LOAD_IV,0), "LOAD_IV"}, 71{ERR_PACK(0,PEM_F_LOAD_IV,0), "LOAD_IV"},
70{ERR_PACK(0,PEM_F_PEM_ASN1_READ,0), "PEM_ASN1_read"}, 72{ERR_PACK(0,PEM_F_PEM_ASN1_READ,0), "PEM_ASN1_read"},
@@ -72,6 +74,7 @@ static ERR_STRING_DATA PEM_str_functs[]=
72{ERR_PACK(0,PEM_F_PEM_ASN1_WRITE,0), "PEM_ASN1_write"}, 74{ERR_PACK(0,PEM_F_PEM_ASN1_WRITE,0), "PEM_ASN1_write"},
73{ERR_PACK(0,PEM_F_PEM_ASN1_WRITE_BIO,0), "PEM_ASN1_write_bio"}, 75{ERR_PACK(0,PEM_F_PEM_ASN1_WRITE_BIO,0), "PEM_ASN1_write_bio"},
74{ERR_PACK(0,PEM_F_PEM_DO_HEADER,0), "PEM_do_header"}, 76{ERR_PACK(0,PEM_F_PEM_DO_HEADER,0), "PEM_do_header"},
77{ERR_PACK(0,PEM_F_PEM_F_DO_PK8KEY_FP,0), "PEM_F_DO_PK8KEY_FP"},
75{ERR_PACK(0,PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY,0), "PEM_F_PEM_WRITE_PKCS8PRIVATEKEY"}, 78{ERR_PACK(0,PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY,0), "PEM_F_PEM_WRITE_PKCS8PRIVATEKEY"},
76{ERR_PACK(0,PEM_F_PEM_GET_EVP_CIPHER_INFO,0), "PEM_get_EVP_CIPHER_INFO"}, 79{ERR_PACK(0,PEM_F_PEM_GET_EVP_CIPHER_INFO,0), "PEM_get_EVP_CIPHER_INFO"},
77{ERR_PACK(0,PEM_F_PEM_READ,0), "PEM_read"}, 80{ERR_PACK(0,PEM_F_PEM_READ,0), "PEM_read"},
diff --git a/src/lib/libcrypto/pem/pem_info.c b/src/lib/libcrypto/pem/pem_info.c
index fec18a4c2e..b65239a920 100644
--- a/src/lib/libcrypto/pem/pem_info.c
+++ b/src/lib/libcrypto/pem/pem_info.c
@@ -132,6 +132,17 @@ start:
132 } 132 }
133 pp=(char **)&(xi->x509); 133 pp=(char **)&(xi->x509);
134 } 134 }
135 else if ((strcmp(name,PEM_STRING_X509_TRUSTED) == 0))
136 {
137 d2i=(char *(*)())d2i_X509_AUX;
138 if (xi->x509 != NULL)
139 {
140 if (!sk_X509_INFO_push(ret,xi)) goto err;
141 if ((xi=X509_INFO_new()) == NULL) goto err;
142 goto start;
143 }
144 pp=(char **)&(xi->x509);
145 }
135 else if (strcmp(name,PEM_STRING_X509_CRL) == 0) 146 else if (strcmp(name,PEM_STRING_X509_CRL) == 0)
136 { 147 {
137 d2i=(char *(*)())d2i_X509_CRL; 148 d2i=(char *(*)())d2i_X509_CRL;
diff --git a/src/lib/libcrypto/pem/pem_lib.c b/src/lib/libcrypto/pem/pem_lib.c
index 90f02011ba..072211ba0f 100644
--- a/src/lib/libcrypto/pem/pem_lib.c
+++ b/src/lib/libcrypto/pem/pem_lib.c
@@ -75,8 +75,17 @@ const char *PEM_version="PEM" OPENSSL_VERSION_PTEXT;
75 75
76static int def_callback(char *buf, int num, int w, void *userdata); 76static int def_callback(char *buf, int num, int w, void *userdata);
77static int load_iv(unsigned char **fromp,unsigned char *to, int num); 77static int load_iv(unsigned char **fromp,unsigned char *to, int num);
78 78static int check_pem(const char *nm, const char *name);
79static int def_callback(char *buf, int num, int w, void *userdata) 79static int do_pk8pkey(BIO *bp, EVP_PKEY *x, int isder,
80 int nid, const EVP_CIPHER *enc,
81 char *kstr, int klen,
82 pem_password_cb *cb, void *u);
83static int do_pk8pkey_fp(FILE *bp, EVP_PKEY *x, int isder,
84 int nid, const EVP_CIPHER *enc,
85 char *kstr, int klen,
86 pem_password_cb *cb, void *u);
87
88static int def_callback(char *buf, int num, int w, void *key)
80 { 89 {
81#ifdef NO_FP_API 90#ifdef NO_FP_API
82 /* We should not ever call the default callback routine from 91 /* We should not ever call the default callback routine from
@@ -86,6 +95,12 @@ static int def_callback(char *buf, int num, int w, void *userdata)
86#else 95#else
87 int i,j; 96 int i,j;
88 const char *prompt; 97 const char *prompt;
98 if(key) {
99 i=strlen(key);
100 i=(i > num)?num:i;
101 memcpy(buf,key,i);
102 return(i);
103 }
89 104
90 prompt=EVP_get_pw_prompt(); 105 prompt=EVP_get_pw_prompt();
91 if (prompt == NULL) 106 if (prompt == NULL)
@@ -168,6 +183,47 @@ char *PEM_ASN1_read(char *(*d2i)(), const char *name, FILE *fp, char **x,
168 } 183 }
169#endif 184#endif
170 185
186static int check_pem(const char *nm, const char *name)
187{
188 /* Normal matching nm and name */
189 if (!strcmp(nm,name)) return 1;
190
191 /* Make PEM_STRING_EVP_PKEY match any private key */
192
193 if(!strcmp(nm,PEM_STRING_PKCS8) &&
194 !strcmp(name,PEM_STRING_EVP_PKEY)) return 1;
195
196 if(!strcmp(nm,PEM_STRING_PKCS8INF) &&
197 !strcmp(name,PEM_STRING_EVP_PKEY)) return 1;
198
199 if(!strcmp(nm,PEM_STRING_RSA) &&
200 !strcmp(name,PEM_STRING_EVP_PKEY)) return 1;
201
202 if(!strcmp(nm,PEM_STRING_DSA) &&
203 !strcmp(name,PEM_STRING_EVP_PKEY)) return 1;
204
205 /* Permit older strings */
206
207 if(!strcmp(nm,PEM_STRING_X509_OLD) &&
208 !strcmp(name,PEM_STRING_X509)) return 1;
209
210 if(!strcmp(nm,PEM_STRING_X509_REQ_OLD) &&
211 !strcmp(name,PEM_STRING_X509_REQ)) return 1;
212
213 /* Allow normal certs to be read as trusted certs */
214 if(!strcmp(nm,PEM_STRING_X509) &&
215 !strcmp(name,PEM_STRING_X509_TRUSTED)) return 1;
216
217 if(!strcmp(nm,PEM_STRING_X509_OLD) &&
218 !strcmp(name,PEM_STRING_X509_TRUSTED)) return 1;
219
220 /* Some CAs use PKCS#7 with CERTIFICATE headers */
221 if(!strcmp(nm, PEM_STRING_X509) &&
222 !strcmp(name, PEM_STRING_PKCS7)) return 1;
223
224 return 0;
225}
226
171char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x, 227char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x,
172 pem_password_cb *cb, void *u) 228 pem_password_cb *cb, void *u)
173 { 229 {
@@ -179,22 +235,13 @@ char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x,
179 235
180 for (;;) 236 for (;;)
181 { 237 {
182 if (!PEM_read_bio(bp,&nm,&header,&data,&len)) return(NULL); 238 if (!PEM_read_bio(bp,&nm,&header,&data,&len)) {
183 if ( (strcmp(nm,name) == 0) || 239 if(ERR_GET_REASON(ERR_peek_error()) ==
184 ((strcmp(nm,PEM_STRING_RSA) == 0) && 240 PEM_R_NO_START_LINE)
185 (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || 241 ERR_add_error_data(2, "Expecting: ", name);
186 ((strcmp(nm,PEM_STRING_DSA) == 0) && 242 return(NULL);
187 (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || 243 }
188 ((strcmp(nm,PEM_STRING_PKCS8) == 0) && 244 if(check_pem(nm, name)) break;
189 (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) ||
190 ((strcmp(nm,PEM_STRING_PKCS8INF) == 0) &&
191 (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) ||
192 ((strcmp(nm,PEM_STRING_X509_OLD) == 0) &&
193 (strcmp(name,PEM_STRING_X509) == 0)) ||
194 ((strcmp(nm,PEM_STRING_X509_REQ_OLD) == 0) &&
195 (strcmp(name,PEM_STRING_X509_REQ) == 0))
196 )
197 break;
198 Free(nm); 245 Free(nm);
199 Free(header); 246 Free(header);
200 Free(data); 247 Free(data);
@@ -218,7 +265,7 @@ char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x,
218 X509_SIG *p8; 265 X509_SIG *p8;
219 int klen; 266 int klen;
220 char psbuf[PEM_BUFSIZE]; 267 char psbuf[PEM_BUFSIZE];
221 p8 = d2i_X509_SIG((X509_SIG **)x, &p, len); 268 p8 = d2i_X509_SIG(NULL, &p, len);
222 if(!p8) goto p8err; 269 if(!p8) goto p8err;
223 if (cb) klen=cb(psbuf,PEM_BUFSIZE,0,u); 270 if (cb) klen=cb(psbuf,PEM_BUFSIZE,0,u);
224 else klen=def_callback(psbuf,PEM_BUFSIZE,0,u); 271 else klen=def_callback(psbuf,PEM_BUFSIZE,0,u);
@@ -231,6 +278,10 @@ char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x,
231 X509_SIG_free(p8); 278 X509_SIG_free(p8);
232 if(!p8inf) goto p8err; 279 if(!p8inf) goto p8err;
233 ret = (char *)EVP_PKCS82PKEY(p8inf); 280 ret = (char *)EVP_PKCS82PKEY(p8inf);
281 if(x) {
282 if(*x) EVP_PKEY_free((EVP_PKEY *)*x);
283 *x = ret;
284 }
234 PKCS8_PRIV_KEY_INFO_free(p8inf); 285 PKCS8_PRIV_KEY_INFO_free(p8inf);
235 } 286 }
236 } else ret=d2i(x,&p,len); 287 } else ret=d2i(x,&p,len);
@@ -321,8 +372,9 @@ int PEM_ASN1_write_bio(int (*i2d)(), const char *name, BIO *bp, char *x,
321#endif 372#endif
322 kstr=(unsigned char *)buf; 373 kstr=(unsigned char *)buf;
323 } 374 }
324 RAND_seed(data,i);/* put in the RSA key. */ 375 RAND_add(data,i,0);/* put in the RSA key. */
325 RAND_bytes(iv,8); /* Generate a salt */ 376 if (RAND_bytes(iv,8) <= 0) /* Generate a salt */
377 goto err;
326 /* The 'iv' is used as the iv and as a salt. It is 378 /* The 'iv' is used as the iv and as a salt. It is
327 * NOT taken from the BytesToKey function */ 379 * NOT taken from the BytesToKey function */
328 EVP_BytesToKey(enc,EVP_md5(),iv,kstr,klen,1,key,NULL); 380 EVP_BytesToKey(enc,EVP_md5(),iv,kstr,klen,1,key,NULL);
@@ -743,16 +795,44 @@ err:
743 return(0); 795 return(0);
744 } 796 }
745 797
746/* This function writes a private key in PKCS#8 format: it is a "drop in" 798/* These functions write a private key in PKCS#8 format: it is a "drop in"
747 * replacement for PEM_write_bio_PrivateKey(). As usual if 'enc' is NULL then 799 * replacement for PEM_write_bio_PrivateKey() and friends. As usual if 'enc'
748 * it uses the unencrypted private key form. It uses PKCS#5 v2.0 password based 800 * is NULL then it uses the unencrypted private key form. The 'nid' versions
749 * encryption algorithms. 801 * uses PKCS#5 v1.5 PBE algorithms whereas the others use PKCS#5 v2.0.
750 */ 802 */
751 803
804int PEM_write_bio_PKCS8PrivateKey_nid(BIO *bp, EVP_PKEY *x, int nid,
805 char *kstr, int klen,
806 pem_password_cb *cb, void *u)
807{
808 return do_pk8pkey(bp, x, 0, nid, NULL, kstr, klen, cb, u);
809}
810
752int PEM_write_bio_PKCS8PrivateKey(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc, 811int PEM_write_bio_PKCS8PrivateKey(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc,
753 char *kstr, int klen, 812 char *kstr, int klen,
754 pem_password_cb *cb, void *u) 813 pem_password_cb *cb, void *u)
755{ 814{
815 return do_pk8pkey(bp, x, 0, -1, enc, kstr, klen, cb, u);
816}
817
818int i2d_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc,
819 char *kstr, int klen,
820 pem_password_cb *cb, void *u)
821{
822 return do_pk8pkey(bp, x, 1, -1, enc, kstr, klen, cb, u);
823}
824
825int i2d_PKCS8PrivateKey_nid_bio(BIO *bp, EVP_PKEY *x, int nid,
826 char *kstr, int klen,
827 pem_password_cb *cb, void *u)
828{
829 return do_pk8pkey(bp, x, 1, nid, NULL, kstr, klen, cb, u);
830}
831
832static int do_pk8pkey(BIO *bp, EVP_PKEY *x, int isder, int nid, const EVP_CIPHER *enc,
833 char *kstr, int klen,
834 pem_password_cb *cb, void *u)
835{
756 X509_SIG *p8; 836 X509_SIG *p8;
757 PKCS8_PRIV_KEY_INFO *p8inf; 837 PKCS8_PRIV_KEY_INFO *p8inf;
758 char buf[PEM_BUFSIZE]; 838 char buf[PEM_BUFSIZE];
@@ -762,7 +842,7 @@ int PEM_write_bio_PKCS8PrivateKey(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc,
762 PEM_R_ERROR_CONVERTING_PRIVATE_KEY); 842 PEM_R_ERROR_CONVERTING_PRIVATE_KEY);
763 return 0; 843 return 0;
764 } 844 }
765 if(enc) { 845 if(enc || (nid != -1)) {
766 if(!kstr) { 846 if(!kstr) {
767 if(!cb) klen = def_callback(buf, PEM_BUFSIZE, 1, u); 847 if(!cb) klen = def_callback(buf, PEM_BUFSIZE, 1, u);
768 else klen = cb(buf, PEM_BUFSIZE, 1, u); 848 else klen = cb(buf, PEM_BUFSIZE, 1, u);
@@ -775,29 +855,109 @@ int PEM_write_bio_PKCS8PrivateKey(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc,
775 855
776 kstr = buf; 856 kstr = buf;
777 } 857 }
778 p8 = PKCS8_encrypt(-1, enc, kstr, klen, NULL, 0, 0, p8inf); 858 p8 = PKCS8_encrypt(nid, enc, kstr, klen, NULL, 0, 0, p8inf);
779 if(kstr == buf) memset(buf, 0, klen); 859 if(kstr == buf) memset(buf, 0, klen);
780 PKCS8_PRIV_KEY_INFO_free(p8inf); 860 PKCS8_PRIV_KEY_INFO_free(p8inf);
781 ret = PEM_write_bio_PKCS8(bp, p8); 861 if(isder) ret = i2d_PKCS8_bio(bp, p8);
862 else ret = PEM_write_bio_PKCS8(bp, p8);
782 X509_SIG_free(p8); 863 X509_SIG_free(p8);
783 return ret; 864 return ret;
784 } else { 865 } else {
785 ret = PEM_write_bio_PKCS8_PRIV_KEY_INFO(bp, p8inf); 866 if(isder) ret = i2d_PKCS8_PRIV_KEY_INFO_bio(bp, p8inf);
867 else ret = PEM_write_bio_PKCS8_PRIV_KEY_INFO(bp, p8inf);
786 PKCS8_PRIV_KEY_INFO_free(p8inf); 868 PKCS8_PRIV_KEY_INFO_free(p8inf);
787 return ret; 869 return ret;
788 } 870 }
789} 871}
790 872
873/* Finally the DER version to read PKCS#8 encrypted private keys. It has to be
874 * here to access the default callback.
875 */
876
877EVP_PKEY *d2i_PKCS8PrivateKey_bio(BIO *bp, EVP_PKEY **x, pem_password_cb *cb, void *u)
878{
879 PKCS8_PRIV_KEY_INFO *p8inf = NULL;
880 X509_SIG *p8 = NULL;
881 int klen;
882 EVP_PKEY *ret;
883 char psbuf[PEM_BUFSIZE];
884 p8 = d2i_PKCS8_bio(bp, NULL);
885 if(!p8) return NULL;
886 if (cb) klen=cb(psbuf,PEM_BUFSIZE,0,u);
887 else klen=def_callback(psbuf,PEM_BUFSIZE,0,u);
888 if (klen <= 0) {
889 PEMerr(PEM_F_D2I_PKCS8PRIVATEKEY_BIO, PEM_R_BAD_PASSWORD_READ);
890 X509_SIG_free(p8);
891 return NULL;
892 }
893 p8inf = M_PKCS8_decrypt(p8, psbuf, klen);
894 X509_SIG_free(p8);
895 if(!p8inf) return NULL;
896 ret = EVP_PKCS82PKEY(p8inf);
897 PKCS8_PRIV_KEY_INFO_free(p8inf);
898 if(!ret) return NULL;
899 if(x) {
900 if(*x) EVP_PKEY_free(*x);
901 *x = ret;
902 }
903 return ret;
904}
905
906#ifndef NO_FP_API
907
908int i2d_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc,
909 char *kstr, int klen,
910 pem_password_cb *cb, void *u)
911{
912 return do_pk8pkey_fp(fp, x, 1, -1, enc, kstr, klen, cb, u);
913}
914
915int i2d_PKCS8PrivateKey_nid_fp(FILE *fp, EVP_PKEY *x, int nid,
916 char *kstr, int klen,
917 pem_password_cb *cb, void *u)
918{
919 return do_pk8pkey_fp(fp, x, 1, nid, NULL, kstr, klen, cb, u);
920}
921
922int PEM_write_PKCS8PrivateKey_nid(FILE *fp, EVP_PKEY *x, int nid,
923 char *kstr, int klen,
924 pem_password_cb *cb, void *u)
925{
926 return do_pk8pkey_fp(fp, x, 0, nid, NULL, kstr, klen, cb, u);
927}
928
791int PEM_write_PKCS8PrivateKey(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc, 929int PEM_write_PKCS8PrivateKey(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc,
792 char *kstr, int klen, pem_password_cb *cb, void *u) 930 char *kstr, int klen, pem_password_cb *cb, void *u)
793{ 931{
932 return do_pk8pkey_fp(fp, x, 0, -1, enc, kstr, klen, cb, u);
933}
934
935static int do_pk8pkey_fp(FILE *fp, EVP_PKEY *x, int isder, int nid, const EVP_CIPHER *enc,
936 char *kstr, int klen,
937 pem_password_cb *cb, void *u)
938{
794 BIO *bp; 939 BIO *bp;
795 int ret; 940 int ret;
796 if(!(bp = BIO_new_fp(fp, BIO_NOCLOSE))) { 941 if(!(bp = BIO_new_fp(fp, BIO_NOCLOSE))) {
797 PEMerr(PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY,ERR_R_BUF_LIB); 942 PEMerr(PEM_F_PEM_F_DO_PK8KEY_FP,ERR_R_BUF_LIB);
798 return(0); 943 return(0);
799 } 944 }
800 ret = PEM_write_bio_PKCS8PrivateKey(bp, x, enc, kstr, klen, cb, u); 945 ret = do_pk8pkey(bp, x, isder, nid, enc, kstr, klen, cb, u);
801 BIO_free(bp); 946 BIO_free(bp);
802 return ret; 947 return ret;
803} 948}
949
950EVP_PKEY *d2i_PKCS8PrivateKey_fp(FILE *fp, EVP_PKEY **x, pem_password_cb *cb, void *u)
951{
952 BIO *bp;
953 EVP_PKEY *ret;
954 if(!(bp = BIO_new_fp(fp, BIO_NOCLOSE))) {
955 PEMerr(PEM_F_D2I_PKCS8PRIVATEKEY_FP,ERR_R_BUF_LIB);
956 return NULL;
957 }
958 ret = d2i_PKCS8PrivateKey_bio(bp, x, cb, u);
959 BIO_free(bp);
960 return ret;
961}
962
963#endif
diff --git a/src/lib/libcrypto/pem/pem_seal.c b/src/lib/libcrypto/pem/pem_seal.c
index 23f95beb1e..126e29d375 100644
--- a/src/lib/libcrypto/pem/pem_seal.c
+++ b/src/lib/libcrypto/pem/pem_seal.c
@@ -175,4 +175,10 @@ err:
175 if (s != NULL) Free(s); 175 if (s != NULL) Free(s);
176 return(ret); 176 return(ret);
177 } 177 }
178#else /* !NO_RSA */
179
180# if PEDANTIC
181static void *dummy=&dummy;
182# endif
183
178#endif 184#endif