diff options
author | beck <> | 1999-09-29 04:37:45 +0000 |
---|---|---|
committer | beck <> | 1999-09-29 04:37:45 +0000 |
commit | de8f24ea083384bb66b32ec105dc4743c5663cdf (patch) | |
tree | 1412176ae62a3cab2cf2b0b92150fcbceaac6092 /src/lib/libcrypto/pem/pem_lib.c | |
parent | cb929d29896bcb87c2a97417fbd03e50078fc178 (diff) | |
download | openbsd-de8f24ea083384bb66b32ec105dc4743c5663cdf.tar.gz openbsd-de8f24ea083384bb66b32ec105dc4743c5663cdf.tar.bz2 openbsd-de8f24ea083384bb66b32ec105dc4743c5663cdf.zip |
OpenSSL 0.9.4 merge
Diffstat (limited to 'src/lib/libcrypto/pem/pem_lib.c')
-rw-r--r-- | src/lib/libcrypto/pem/pem_lib.c | 273 |
1 files changed, 157 insertions, 116 deletions
diff --git a/src/lib/libcrypto/pem/pem_lib.c b/src/lib/libcrypto/pem/pem_lib.c index 7a2c0ad83b..90f02011ba 100644 --- a/src/lib/libcrypto/pem/pem_lib.c +++ b/src/lib/libcrypto/pem/pem_lib.c | |||
@@ -58,36 +58,25 @@ | |||
58 | 58 | ||
59 | #include <stdio.h> | 59 | #include <stdio.h> |
60 | #include "cryptlib.h" | 60 | #include "cryptlib.h" |
61 | #include "buffer.h" | 61 | #include <openssl/buffer.h> |
62 | #include "objects.h" | 62 | #include <openssl/objects.h> |
63 | #include "evp.h" | 63 | #include <openssl/evp.h> |
64 | #include "rand.h" | 64 | #include <openssl/rand.h> |
65 | #include "x509.h" | 65 | #include <openssl/x509.h> |
66 | #include "pem.h" | 66 | #include <openssl/pem.h> |
67 | #include <openssl/pkcs12.h> | ||
67 | #ifndef NO_DES | 68 | #ifndef NO_DES |
68 | #include "des.h" | 69 | #include <openssl/des.h> |
69 | #endif | 70 | #endif |
70 | 71 | ||
71 | char *PEM_version="PEM part of SSLeay 0.9.0b 29-Jun-1998"; | 72 | const char *PEM_version="PEM" OPENSSL_VERSION_PTEXT; |
72 | 73 | ||
73 | #define MIN_LENGTH 4 | 74 | #define MIN_LENGTH 4 |
74 | 75 | ||
75 | /* PEMerr(PEM_F_PEM_WRITE_BIO,ERR_R_MALLOC_FAILURE); | 76 | static int def_callback(char *buf, int num, int w, void *userdata); |
76 | * PEMerr(PEM_F_PEM_READ_BIO,ERR_R_MALLOC_FAILURE); | ||
77 | */ | ||
78 | |||
79 | #ifndef NOPROTO | ||
80 | static int def_callback(char *buf, int num, int w); | ||
81 | static int load_iv(unsigned char **fromp,unsigned char *to, int num); | 77 | static int load_iv(unsigned char **fromp,unsigned char *to, int num); |
82 | #else | ||
83 | static int def_callback(); | ||
84 | static int load_iv(); | ||
85 | #endif | ||
86 | 78 | ||
87 | static int def_callback(buf, num, w) | 79 | static int def_callback(char *buf, int num, int w, void *userdata) |
88 | char *buf; | ||
89 | int num; | ||
90 | int w; | ||
91 | { | 80 | { |
92 | #ifdef NO_FP_API | 81 | #ifdef NO_FP_API |
93 | /* We should not ever call the default callback routine from | 82 | /* We should not ever call the default callback routine from |
@@ -96,7 +85,7 @@ int w; | |||
96 | return(-1); | 85 | return(-1); |
97 | #else | 86 | #else |
98 | int i,j; | 87 | int i,j; |
99 | char *prompt; | 88 | const char *prompt; |
100 | 89 | ||
101 | prompt=EVP_get_pw_prompt(); | 90 | prompt=EVP_get_pw_prompt(); |
102 | if (prompt == NULL) | 91 | if (prompt == NULL) |
@@ -123,11 +112,9 @@ int w; | |||
123 | #endif | 112 | #endif |
124 | } | 113 | } |
125 | 114 | ||
126 | void PEM_proc_type(buf, type) | 115 | void PEM_proc_type(char *buf, int type) |
127 | char *buf; | ||
128 | int type; | ||
129 | { | 116 | { |
130 | char *str; | 117 | const char *str; |
131 | 118 | ||
132 | if (type == PEM_TYPE_ENCRYPTED) | 119 | if (type == PEM_TYPE_ENCRYPTED) |
133 | str="ENCRYPTED"; | 120 | str="ENCRYPTED"; |
@@ -143,11 +130,7 @@ int type; | |||
143 | strcat(buf,"\n"); | 130 | strcat(buf,"\n"); |
144 | } | 131 | } |
145 | 132 | ||
146 | void PEM_dek_info(buf, type, len, str) | 133 | void PEM_dek_info(char *buf, const char *type, int len, char *str) |
147 | char *buf; | ||
148 | char *type; | ||
149 | int len; | ||
150 | char *str; | ||
151 | { | 134 | { |
152 | static unsigned char map[17]="0123456789ABCDEF"; | 135 | static unsigned char map[17]="0123456789ABCDEF"; |
153 | long i; | 136 | long i; |
@@ -167,12 +150,8 @@ char *str; | |||
167 | } | 150 | } |
168 | 151 | ||
169 | #ifndef NO_FP_API | 152 | #ifndef NO_FP_API |
170 | char *PEM_ASN1_read(d2i,name,fp, x, cb) | 153 | char *PEM_ASN1_read(char *(*d2i)(), const char *name, FILE *fp, char **x, |
171 | char *(*d2i)(); | 154 | pem_password_cb *cb, void *u) |
172 | char *name; | ||
173 | FILE *fp; | ||
174 | char **x; | ||
175 | int (*cb)(); | ||
176 | { | 155 | { |
177 | BIO *b; | 156 | BIO *b; |
178 | char *ret; | 157 | char *ret; |
@@ -183,18 +162,14 @@ int (*cb)(); | |||
183 | return(0); | 162 | return(0); |
184 | } | 163 | } |
185 | BIO_set_fp(b,fp,BIO_NOCLOSE); | 164 | BIO_set_fp(b,fp,BIO_NOCLOSE); |
186 | ret=PEM_ASN1_read_bio(d2i,name,b,x,cb); | 165 | ret=PEM_ASN1_read_bio(d2i,name,b,x,cb,u); |
187 | BIO_free(b); | 166 | BIO_free(b); |
188 | return(ret); | 167 | return(ret); |
189 | } | 168 | } |
190 | #endif | 169 | #endif |
191 | 170 | ||
192 | char *PEM_ASN1_read_bio(d2i,name,bp, x, cb) | 171 | char *PEM_ASN1_read_bio(char *(*d2i)(), const char *name, BIO *bp, char **x, |
193 | char *(*d2i)(); | 172 | pem_password_cb *cb, void *u) |
194 | char *name; | ||
195 | BIO *bp; | ||
196 | char **x; | ||
197 | int (*cb)(); | ||
198 | { | 173 | { |
199 | EVP_CIPHER_INFO cipher; | 174 | EVP_CIPHER_INFO cipher; |
200 | char *nm=NULL,*header=NULL; | 175 | char *nm=NULL,*header=NULL; |
@@ -210,10 +185,14 @@ int (*cb)(); | |||
210 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || | 185 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || |
211 | ((strcmp(nm,PEM_STRING_DSA) == 0) && | 186 | ((strcmp(nm,PEM_STRING_DSA) == 0) && |
212 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || | 187 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || |
188 | ((strcmp(nm,PEM_STRING_PKCS8) == 0) && | ||
189 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || | ||
190 | ((strcmp(nm,PEM_STRING_PKCS8INF) == 0) && | ||
191 | (strcmp(name,PEM_STRING_EVP_PKEY) == 0)) || | ||
213 | ((strcmp(nm,PEM_STRING_X509_OLD) == 0) && | 192 | ((strcmp(nm,PEM_STRING_X509_OLD) == 0) && |
214 | (strcmp(name,PEM_STRING_X509) == 0)) || | 193 | (strcmp(name,PEM_STRING_X509) == 0)) || |
215 | ((strcmp(nm,PEM_STRING_X509_REQ_OLD) == 0) && | 194 | ((strcmp(nm,PEM_STRING_X509_REQ_OLD) == 0) && |
216 | (strcmp(name,PEM_STRING_X509_REQ) == 0)) | 195 | (strcmp(name,PEM_STRING_X509_REQ) == 0)) |
217 | ) | 196 | ) |
218 | break; | 197 | break; |
219 | Free(nm); | 198 | Free(nm); |
@@ -221,17 +200,41 @@ int (*cb)(); | |||
221 | Free(data); | 200 | Free(data); |
222 | } | 201 | } |
223 | if (!PEM_get_EVP_CIPHER_INFO(header,&cipher)) goto err; | 202 | if (!PEM_get_EVP_CIPHER_INFO(header,&cipher)) goto err; |
224 | if (!PEM_do_header(&cipher,data,&len,cb)) goto err; | 203 | if (!PEM_do_header(&cipher,data,&len,cb,u)) goto err; |
225 | p=data; | 204 | p=data; |
226 | if (strcmp(name,PEM_STRING_EVP_PKEY) == 0) | 205 | if (strcmp(name,PEM_STRING_EVP_PKEY) == 0) { |
227 | { | ||
228 | if (strcmp(nm,PEM_STRING_RSA) == 0) | 206 | if (strcmp(nm,PEM_STRING_RSA) == 0) |
229 | ret=d2i(EVP_PKEY_RSA,x,&p,len); | 207 | ret=d2i(EVP_PKEY_RSA,x,&p,len); |
230 | else if (strcmp(nm,PEM_STRING_DSA) == 0) | 208 | else if (strcmp(nm,PEM_STRING_DSA) == 0) |
231 | ret=d2i(EVP_PKEY_DSA,x,&p,len); | 209 | ret=d2i(EVP_PKEY_DSA,x,&p,len); |
210 | else if (strcmp(nm,PEM_STRING_PKCS8INF) == 0) { | ||
211 | PKCS8_PRIV_KEY_INFO *p8inf; | ||
212 | p8inf=d2i_PKCS8_PRIV_KEY_INFO( | ||
213 | (PKCS8_PRIV_KEY_INFO **) x, &p, len); | ||
214 | ret = (char *)EVP_PKCS82PKEY(p8inf); | ||
215 | PKCS8_PRIV_KEY_INFO_free(p8inf); | ||
216 | } else if (strcmp(nm,PEM_STRING_PKCS8) == 0) { | ||
217 | PKCS8_PRIV_KEY_INFO *p8inf; | ||
218 | X509_SIG *p8; | ||
219 | int klen; | ||
220 | char psbuf[PEM_BUFSIZE]; | ||
221 | p8 = d2i_X509_SIG((X509_SIG **)x, &p, len); | ||
222 | if(!p8) goto p8err; | ||
223 | if (cb) klen=cb(psbuf,PEM_BUFSIZE,0,u); | ||
224 | else klen=def_callback(psbuf,PEM_BUFSIZE,0,u); | ||
225 | if (klen <= 0) { | ||
226 | PEMerr(PEM_F_PEM_ASN1_READ_BIO, | ||
227 | PEM_R_BAD_PASSWORD_READ); | ||
228 | goto err; | ||
229 | } | ||
230 | p8inf = M_PKCS8_decrypt(p8, psbuf, klen); | ||
231 | X509_SIG_free(p8); | ||
232 | if(!p8inf) goto p8err; | ||
233 | ret = (char *)EVP_PKCS82PKEY(p8inf); | ||
234 | PKCS8_PRIV_KEY_INFO_free(p8inf); | ||
232 | } | 235 | } |
233 | else | 236 | } else ret=d2i(x,&p,len); |
234 | ret=d2i(x,&p,len); | 237 | p8err: |
235 | if (ret == NULL) | 238 | if (ret == NULL) |
236 | PEMerr(PEM_F_PEM_ASN1_READ_BIO,ERR_R_ASN1_LIB); | 239 | PEMerr(PEM_F_PEM_ASN1_READ_BIO,ERR_R_ASN1_LIB); |
237 | err: | 240 | err: |
@@ -242,15 +245,9 @@ err: | |||
242 | } | 245 | } |
243 | 246 | ||
244 | #ifndef NO_FP_API | 247 | #ifndef NO_FP_API |
245 | int PEM_ASN1_write(i2d,name,fp, x, enc, kstr, klen, callback) | 248 | int PEM_ASN1_write(int (*i2d)(), const char *name, FILE *fp, char *x, |
246 | int (*i2d)(); | 249 | const EVP_CIPHER *enc, unsigned char *kstr, int klen, |
247 | char *name; | 250 | pem_password_cb *callback, void *u) |
248 | FILE *fp; | ||
249 | char *x; | ||
250 | EVP_CIPHER *enc; | ||
251 | unsigned char *kstr; | ||
252 | int klen; | ||
253 | int (*callback)(); | ||
254 | { | 251 | { |
255 | BIO *b; | 252 | BIO *b; |
256 | int ret; | 253 | int ret; |
@@ -261,27 +258,20 @@ int (*callback)(); | |||
261 | return(0); | 258 | return(0); |
262 | } | 259 | } |
263 | BIO_set_fp(b,fp,BIO_NOCLOSE); | 260 | BIO_set_fp(b,fp,BIO_NOCLOSE); |
264 | ret=PEM_ASN1_write_bio(i2d,name,b,x,enc,kstr,klen,callback); | 261 | ret=PEM_ASN1_write_bio(i2d,name,b,x,enc,kstr,klen,callback,u); |
265 | BIO_free(b); | 262 | BIO_free(b); |
266 | return(ret); | 263 | return(ret); |
267 | } | 264 | } |
268 | #endif | 265 | #endif |
269 | 266 | ||
270 | int PEM_ASN1_write_bio(i2d,name,bp, x, enc, kstr, klen, callback) | 267 | int PEM_ASN1_write_bio(int (*i2d)(), const char *name, BIO *bp, char *x, |
271 | int (*i2d)(); | 268 | const EVP_CIPHER *enc, unsigned char *kstr, int klen, |
272 | char *name; | 269 | pem_password_cb *callback, void *u) |
273 | BIO *bp; | ||
274 | char *x; | ||
275 | EVP_CIPHER *enc; | ||
276 | unsigned char *kstr; | ||
277 | int klen; | ||
278 | int (*callback)(); | ||
279 | { | 270 | { |
280 | EVP_CIPHER_CTX ctx; | 271 | EVP_CIPHER_CTX ctx; |
281 | int dsize=0,i,j,ret=0; | 272 | int dsize=0,i,j,ret=0; |
282 | unsigned char *p,*data=NULL; | 273 | unsigned char *p,*data=NULL; |
283 | char *objstr=NULL; | 274 | const char *objstr=NULL; |
284 | #define PEM_BUFSIZE 1024 | ||
285 | char buf[PEM_BUFSIZE]; | 275 | char buf[PEM_BUFSIZE]; |
286 | unsigned char key[EVP_MAX_KEY_LENGTH]; | 276 | unsigned char key[EVP_MAX_KEY_LENGTH]; |
287 | unsigned char iv[EVP_MAX_IV_LENGTH]; | 277 | unsigned char iv[EVP_MAX_IV_LENGTH]; |
@@ -317,14 +307,18 @@ int (*callback)(); | |||
317 | if (kstr == NULL) | 307 | if (kstr == NULL) |
318 | { | 308 | { |
319 | if (callback == NULL) | 309 | if (callback == NULL) |
320 | klen=def_callback(buf,PEM_BUFSIZE,1); | 310 | klen=def_callback(buf,PEM_BUFSIZE,1,u); |
321 | else | 311 | else |
322 | klen=(*callback)(buf,PEM_BUFSIZE,1); | 312 | klen=(*callback)(buf,PEM_BUFSIZE,1,u); |
323 | if (klen <= 0) | 313 | if (klen <= 0) |
324 | { | 314 | { |
325 | PEMerr(PEM_F_PEM_ASN1_WRITE_BIO,PEM_R_READ_KEY); | 315 | PEMerr(PEM_F_PEM_ASN1_WRITE_BIO,PEM_R_READ_KEY); |
326 | goto err; | 316 | goto err; |
327 | } | 317 | } |
318 | #ifdef CHARSET_EBCDIC | ||
319 | /* Convert the pass phrase from EBCDIC */ | ||
320 | ebcdic2ascii(buf, buf, klen); | ||
321 | #endif | ||
328 | kstr=(unsigned char *)buf; | 322 | kstr=(unsigned char *)buf; |
329 | } | 323 | } |
330 | RAND_seed(data,i);/* put in the RSA key. */ | 324 | RAND_seed(data,i);/* put in the RSA key. */ |
@@ -363,11 +357,8 @@ err: | |||
363 | return(ret); | 357 | return(ret); |
364 | } | 358 | } |
365 | 359 | ||
366 | int PEM_do_header(cipher, data, plen, callback) | 360 | int PEM_do_header(EVP_CIPHER_INFO *cipher, unsigned char *data, long *plen, |
367 | EVP_CIPHER_INFO *cipher; | 361 | pem_password_cb *callback,void *u) |
368 | unsigned char *data; | ||
369 | long *plen; | ||
370 | int (*callback)(); | ||
371 | { | 362 | { |
372 | int i,j,o,klen; | 363 | int i,j,o,klen; |
373 | long len; | 364 | long len; |
@@ -379,14 +370,19 @@ int (*callback)(); | |||
379 | 370 | ||
380 | if (cipher->cipher == NULL) return(1); | 371 | if (cipher->cipher == NULL) return(1); |
381 | if (callback == NULL) | 372 | if (callback == NULL) |
382 | klen=def_callback(buf,PEM_BUFSIZE,0); | 373 | klen=def_callback(buf,PEM_BUFSIZE,0,u); |
383 | else | 374 | else |
384 | klen=callback(buf,PEM_BUFSIZE,0); | 375 | klen=callback(buf,PEM_BUFSIZE,0,u); |
385 | if (klen <= 0) | 376 | if (klen <= 0) |
386 | { | 377 | { |
387 | PEMerr(PEM_F_PEM_DO_HEADER,PEM_R_BAD_PASSWORD_READ); | 378 | PEMerr(PEM_F_PEM_DO_HEADER,PEM_R_BAD_PASSWORD_READ); |
388 | return(0); | 379 | return(0); |
389 | } | 380 | } |
381 | #ifdef CHARSET_EBCDIC | ||
382 | /* Convert the pass phrase from EBCDIC */ | ||
383 | ebcdic2ascii(buf, buf, klen); | ||
384 | #endif | ||
385 | |||
390 | EVP_BytesToKey(cipher->cipher,EVP_md5(),&(cipher->iv[0]), | 386 | EVP_BytesToKey(cipher->cipher,EVP_md5(),&(cipher->iv[0]), |
391 | (unsigned char *)buf,klen,1,key,NULL); | 387 | (unsigned char *)buf,klen,1,key,NULL); |
392 | 388 | ||
@@ -407,12 +403,10 @@ int (*callback)(); | |||
407 | return(1); | 403 | return(1); |
408 | } | 404 | } |
409 | 405 | ||
410 | int PEM_get_EVP_CIPHER_INFO(header,cipher) | 406 | int PEM_get_EVP_CIPHER_INFO(char *header, EVP_CIPHER_INFO *cipher) |
411 | char *header; | ||
412 | EVP_CIPHER_INFO *cipher; | ||
413 | { | 407 | { |
414 | int o; | 408 | int o; |
415 | EVP_CIPHER *enc=NULL; | 409 | const EVP_CIPHER *enc=NULL; |
416 | char *p,c; | 410 | char *p,c; |
417 | 411 | ||
418 | cipher->cipher=NULL; | 412 | cipher->cipher=NULL; |
@@ -438,9 +432,15 @@ EVP_CIPHER_INFO *cipher; | |||
438 | for (;;) | 432 | for (;;) |
439 | { | 433 | { |
440 | c= *header; | 434 | c= *header; |
435 | #ifndef CHARSET_EBCDIC | ||
441 | if (!( ((c >= 'A') && (c <= 'Z')) || (c == '-') || | 436 | if (!( ((c >= 'A') && (c <= 'Z')) || (c == '-') || |
442 | ((c >= '0') && (c <= '9')))) | 437 | ((c >= '0') && (c <= '9')))) |
443 | break; | 438 | break; |
439 | #else | ||
440 | if (!( isupper(c) || (c == '-') || | ||
441 | isdigit(c))) | ||
442 | break; | ||
443 | #endif | ||
444 | header++; | 444 | header++; |
445 | } | 445 | } |
446 | *header='\0'; | 446 | *header='\0'; |
@@ -459,9 +459,7 @@ EVP_CIPHER_INFO *cipher; | |||
459 | return(1); | 459 | return(1); |
460 | } | 460 | } |
461 | 461 | ||
462 | static int load_iv(fromp,to,num) | 462 | static int load_iv(unsigned char **fromp, unsigned char *to, int num) |
463 | unsigned char **fromp,*to; | ||
464 | int num; | ||
465 | { | 463 | { |
466 | int v,i; | 464 | int v,i; |
467 | unsigned char *from; | 465 | unsigned char *from; |
@@ -491,12 +489,8 @@ int num; | |||
491 | } | 489 | } |
492 | 490 | ||
493 | #ifndef NO_FP_API | 491 | #ifndef NO_FP_API |
494 | int PEM_write(fp, name, header, data,len) | 492 | int PEM_write(FILE *fp, char *name, char *header, unsigned char *data, |
495 | FILE *fp; | 493 | long len) |
496 | char *name; | ||
497 | char *header; | ||
498 | unsigned char *data; | ||
499 | long len; | ||
500 | { | 494 | { |
501 | BIO *b; | 495 | BIO *b; |
502 | int ret; | 496 | int ret; |
@@ -513,12 +507,8 @@ long len; | |||
513 | } | 507 | } |
514 | #endif | 508 | #endif |
515 | 509 | ||
516 | int PEM_write_bio(bp, name, header, data,len) | 510 | int PEM_write_bio(BIO *bp, const char *name, char *header, unsigned char *data, |
517 | BIO *bp; | 511 | long len) |
518 | char *name; | ||
519 | char *header; | ||
520 | unsigned char *data; | ||
521 | long len; | ||
522 | { | 512 | { |
523 | int nlen,n,i,j,outl; | 513 | int nlen,n,i,j,outl; |
524 | unsigned char *buf; | 514 | unsigned char *buf; |
@@ -573,12 +563,8 @@ err: | |||
573 | } | 563 | } |
574 | 564 | ||
575 | #ifndef NO_FP_API | 565 | #ifndef NO_FP_API |
576 | int PEM_read(fp, name, header, data,len) | 566 | int PEM_read(FILE *fp, char **name, char **header, unsigned char **data, |
577 | FILE *fp; | 567 | long *len) |
578 | char **name; | ||
579 | char **header; | ||
580 | unsigned char **data; | ||
581 | long *len; | ||
582 | { | 568 | { |
583 | BIO *b; | 569 | BIO *b; |
584 | int ret; | 570 | int ret; |
@@ -595,12 +581,8 @@ long *len; | |||
595 | } | 581 | } |
596 | #endif | 582 | #endif |
597 | 583 | ||
598 | int PEM_read_bio(bp, name, header, data, len) | 584 | int PEM_read_bio(BIO *bp, char **name, char **header, unsigned char **data, |
599 | BIO *bp; | 585 | long *len) |
600 | char **name; | ||
601 | char **header; | ||
602 | unsigned char **data; | ||
603 | long *len; | ||
604 | { | 586 | { |
605 | EVP_ENCODE_CTX ctx; | 587 | EVP_ENCODE_CTX ctx; |
606 | int end=0,i,k,bl=0,hl=0,nohead=0; | 588 | int end=0,i,k,bl=0,hl=0,nohead=0; |
@@ -643,7 +625,7 @@ long *len; | |||
643 | PEMerr(PEM_F_PEM_READ_BIO,ERR_R_MALLOC_FAILURE); | 625 | PEMerr(PEM_F_PEM_READ_BIO,ERR_R_MALLOC_FAILURE); |
644 | goto err; | 626 | goto err; |
645 | } | 627 | } |
646 | strncpy(nameB->data,&(buf[11]),(unsigned int)i-6); | 628 | memcpy(nameB->data,&(buf[11]),i-6); |
647 | nameB->data[i-6]='\0'; | 629 | nameB->data[i-6]='\0'; |
648 | break; | 630 | break; |
649 | } | 631 | } |
@@ -668,7 +650,7 @@ long *len; | |||
668 | nohead=1; | 650 | nohead=1; |
669 | break; | 651 | break; |
670 | } | 652 | } |
671 | strncpy(&(headerB->data[hl]),buf,(unsigned int)i); | 653 | memcpy(&(headerB->data[hl]),buf,i); |
672 | headerB->data[hl+i]='\0'; | 654 | headerB->data[hl+i]='\0'; |
673 | hl+=i; | 655 | hl+=i; |
674 | } | 656 | } |
@@ -696,7 +678,7 @@ long *len; | |||
696 | PEMerr(PEM_F_PEM_READ_BIO,ERR_R_MALLOC_FAILURE); | 678 | PEMerr(PEM_F_PEM_READ_BIO,ERR_R_MALLOC_FAILURE); |
697 | goto err; | 679 | goto err; |
698 | } | 680 | } |
699 | strncpy(&(dataB->data[bl]),buf,(unsigned int)i); | 681 | memcpy(&(dataB->data[bl]),buf,i); |
700 | dataB->data[bl+i]='\0'; | 682 | dataB->data[bl+i]='\0'; |
701 | bl+=i; | 683 | bl+=i; |
702 | if (end) | 684 | if (end) |
@@ -721,7 +703,7 @@ long *len; | |||
721 | } | 703 | } |
722 | i=strlen(nameB->data); | 704 | i=strlen(nameB->data); |
723 | if ( (strncmp(buf,"-----END ",9) != 0) || | 705 | if ( (strncmp(buf,"-----END ",9) != 0) || |
724 | (strncmp(nameB->data,&(buf[9]),(unsigned int)i) != 0) || | 706 | (strncmp(nameB->data,&(buf[9]),i) != 0) || |
725 | (strncmp(&(buf[9+i]),"-----\n",6) != 0)) | 707 | (strncmp(&(buf[9+i]),"-----\n",6) != 0)) |
726 | { | 708 | { |
727 | PEMerr(PEM_F_PEM_READ_BIO,PEM_R_BAD_END_LINE); | 709 | PEMerr(PEM_F_PEM_READ_BIO,PEM_R_BAD_END_LINE); |
@@ -760,3 +742,62 @@ err: | |||
760 | BUF_MEM_free(dataB); | 742 | BUF_MEM_free(dataB); |
761 | return(0); | 743 | return(0); |
762 | } | 744 | } |
745 | |||
746 | /* This function writes 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 | ||
748 | * it uses the unencrypted private key form. It uses PKCS#5 v2.0 password based | ||
749 | * encryption algorithms. | ||
750 | */ | ||
751 | |||
752 | int PEM_write_bio_PKCS8PrivateKey(BIO *bp, EVP_PKEY *x, const EVP_CIPHER *enc, | ||
753 | char *kstr, int klen, | ||
754 | pem_password_cb *cb, void *u) | ||
755 | { | ||
756 | X509_SIG *p8; | ||
757 | PKCS8_PRIV_KEY_INFO *p8inf; | ||
758 | char buf[PEM_BUFSIZE]; | ||
759 | int ret; | ||
760 | if(!(p8inf = EVP_PKEY2PKCS8(x))) { | ||
761 | PEMerr(PEM_F_PEM_WRITE_BIO_PKCS8PRIVATEKEY, | ||
762 | PEM_R_ERROR_CONVERTING_PRIVATE_KEY); | ||
763 | return 0; | ||
764 | } | ||
765 | if(enc) { | ||
766 | if(!kstr) { | ||
767 | if(!cb) klen = def_callback(buf, PEM_BUFSIZE, 1, u); | ||
768 | else klen = cb(buf, PEM_BUFSIZE, 1, u); | ||
769 | if(klen <= 0) { | ||
770 | PEMerr(PEM_F_PEM_WRITE_BIO_PKCS8PRIVATEKEY, | ||
771 | PEM_R_READ_KEY); | ||
772 | PKCS8_PRIV_KEY_INFO_free(p8inf); | ||
773 | return 0; | ||
774 | } | ||
775 | |||
776 | kstr = buf; | ||
777 | } | ||
778 | p8 = PKCS8_encrypt(-1, enc, kstr, klen, NULL, 0, 0, p8inf); | ||
779 | if(kstr == buf) memset(buf, 0, klen); | ||
780 | PKCS8_PRIV_KEY_INFO_free(p8inf); | ||
781 | ret = PEM_write_bio_PKCS8(bp, p8); | ||
782 | X509_SIG_free(p8); | ||
783 | return ret; | ||
784 | } else { | ||
785 | ret = PEM_write_bio_PKCS8_PRIV_KEY_INFO(bp, p8inf); | ||
786 | PKCS8_PRIV_KEY_INFO_free(p8inf); | ||
787 | return ret; | ||
788 | } | ||
789 | } | ||
790 | |||
791 | int PEM_write_PKCS8PrivateKey(FILE *fp, EVP_PKEY *x, const EVP_CIPHER *enc, | ||
792 | char *kstr, int klen, pem_password_cb *cb, void *u) | ||
793 | { | ||
794 | BIO *bp; | ||
795 | int ret; | ||
796 | if(!(bp = BIO_new_fp(fp, BIO_NOCLOSE))) { | ||
797 | PEMerr(PEM_F_PEM_F_PEM_WRITE_PKCS8PRIVATEKEY,ERR_R_BUF_LIB); | ||
798 | return(0); | ||
799 | } | ||
800 | ret = PEM_write_bio_PKCS8PrivateKey(bp, x, enc, kstr, klen, cb, u); | ||
801 | BIO_free(bp); | ||
802 | return ret; | ||
803 | } | ||