X-Git-Url: https://git.openssl.org/gitweb/?a=blobdiff_plain;f=crypto%2Fpem%2Fpem_lib.c;h=5e41d85a6ab539729879cbde9b2174a2e92c47f2;hb=9f10e9293bd34e9b6269b1d2030e61b56f48841b;hp=9631ee2d5dd34b6dfe781f70c045e7258b27edca;hpb=3e4585c8fd0b23f884d775462736502599146af6;p=openssl.git diff --git a/crypto/pem/pem_lib.c b/crypto/pem/pem_lib.c index 9631ee2d5d..5e41d85a6a 100644 --- a/crypto/pem/pem_lib.c +++ b/crypto/pem/pem_lib.c @@ -70,8 +70,11 @@ #ifndef OPENSSL_NO_DES #include #endif +#ifndef OPENSSL_NO_ENGINE +#include +#endif -const char *PEM_version="PEM" OPENSSL_VERSION_PTEXT; +const char PEM_version[]="PEM" OPENSSL_VERSION_PTEXT; #define MIN_LENGTH 4 @@ -102,7 +105,7 @@ int PEM_def_callback(char *buf, int num, int w, void *key) for (;;) { - i=EVP_read_pw_string(buf,num,prompt,w); + i=EVP_read_pw_string_min(buf,MIN_LENGTH,num,prompt,w); if (i != 0) { PEMerr(PEM_F_PEM_DEF_CALLBACK,PEM_R_PROBLEMS_GETTING_PASSWORD); @@ -197,7 +200,11 @@ static int check_pem(const char *nm, const char *name) slen = pem_check_suffix(nm, "PRIVATE KEY"); if (slen > 0) { - ameth = EVP_PKEY_asn1_find_str(nm, slen); + /* NB: ENGINE implementations wont contain + * a deprecated old private key decode function + * so don't look for them. + */ + ameth = EVP_PKEY_asn1_find_str(NULL, nm, slen); if (ameth && ameth->old_priv_decode) return 1; } @@ -211,12 +218,27 @@ static int check_pem(const char *nm, const char *name) slen = pem_check_suffix(nm, "PARAMETERS"); if (slen > 0) { - ameth = EVP_PKEY_asn1_find_str(nm, slen); - if (ameth && ameth->param_decode) - return 1; + ENGINE *e; + ameth = EVP_PKEY_asn1_find_str(&e, nm, slen); + if (ameth) + { + int r; + if (ameth->param_decode) + r = 1; + else + r = 0; +#ifndef OPENSSL_NO_ENGINE + if (e) + ENGINE_finish(e); +#endif + return r; + } } return 0; } + /* If reading DH parameters handle X9.42 DH format too */ + if(!strcmp(nm,PEM_STRING_DHXPARAMS) && + !strcmp(name,PEM_STRING_DHPARAMS)) return 1; /* Permit older strings */ @@ -237,6 +259,17 @@ static int check_pem(const char *nm, const char *name) if(!strcmp(nm, PEM_STRING_X509) && !strcmp(name, PEM_STRING_PKCS7)) return 1; + if(!strcmp(nm, PEM_STRING_PKCS7_SIGNED) && + !strcmp(name, PEM_STRING_PKCS7)) return 1; + +#ifndef OPENSSL_NO_CMS + if(!strcmp(nm, PEM_STRING_X509) && + !strcmp(name, PEM_STRING_CMS)) return 1; + /* Allow CMS to be read from PKCS#7 headers */ + if(!strcmp(nm, PEM_STRING_PKCS7) && + !strcmp(name, PEM_STRING_CMS)) return 1; +#endif + return 0; } @@ -282,7 +315,7 @@ err: #ifndef OPENSSL_NO_FP_API int PEM_ASN1_write(i2d_of_void *i2d, const char *name, FILE *fp, - char *x, const EVP_CIPHER *enc, unsigned char *kstr, + void *x, const EVP_CIPHER *enc, unsigned char *kstr, int klen, pem_password_cb *callback, void *u) { BIO *b; @@ -301,7 +334,7 @@ int PEM_ASN1_write(i2d_of_void *i2d, const char *name, FILE *fp, #endif int PEM_ASN1_write_bio(i2d_of_void *i2d, const char *name, BIO *bp, - char *x, const EVP_CIPHER *enc, unsigned char *kstr, + void *x, const EVP_CIPHER *enc, unsigned char *kstr, int klen, pem_password_cb *callback, void *u) { EVP_CIPHER_CTX ctx; @@ -364,7 +397,8 @@ int PEM_ASN1_write_bio(i2d_of_void *i2d, const char *name, BIO *bp, goto err; /* The 'iv' is used as the iv and as a salt. It is * NOT taken from the BytesToKey function */ - EVP_BytesToKey(enc,EVP_md5(),iv,kstr,klen,1,key,NULL); + if (!EVP_BytesToKey(enc,EVP_md5(),iv,kstr,klen,1,key,NULL)) + goto err; if (kstr == (unsigned char *)buf) OPENSSL_cleanse(buf,PEM_BUFSIZE); @@ -376,12 +410,15 @@ int PEM_ASN1_write_bio(i2d_of_void *i2d, const char *name, BIO *bp, /* k=strlen(buf); */ EVP_CIPHER_CTX_init(&ctx); - EVP_EncryptInit_ex(&ctx,enc,NULL,key,iv); - EVP_EncryptUpdate(&ctx,data,&j,data,i); - EVP_EncryptFinal_ex(&ctx,&(data[j]),&i); + ret = 1; + if (!EVP_EncryptInit_ex(&ctx,enc,NULL,key,iv) + || !EVP_EncryptUpdate(&ctx,data,&j,data,i) + || !EVP_EncryptFinal_ex(&ctx,&(data[j]),&i)) + ret = 0; EVP_CIPHER_CTX_cleanup(&ctx); + if (ret == 0) + goto err; i+=j; - ret=1; } else { @@ -429,14 +466,17 @@ int PEM_do_header(EVP_CIPHER_INFO *cipher, unsigned char *data, long *plen, ebcdic2ascii(buf, buf, klen); #endif - EVP_BytesToKey(cipher->cipher,EVP_md5(),&(cipher->iv[0]), - (unsigned char *)buf,klen,1,key,NULL); + if (!EVP_BytesToKey(cipher->cipher,EVP_md5(),&(cipher->iv[0]), + (unsigned char *)buf,klen,1,key,NULL)) + return 0; j=(int)len; EVP_CIPHER_CTX_init(&ctx); - EVP_DecryptInit_ex(&ctx,cipher->cipher,NULL, key,&(cipher->iv[0])); - EVP_DecryptUpdate(&ctx,data,&i,data,j); - o=EVP_DecryptFinal_ex(&ctx,&(data[i]),&j); + o = EVP_DecryptInit_ex(&ctx,cipher->cipher,NULL, key,&(cipher->iv[0])); + if (o) + o = EVP_DecryptUpdate(&ctx,data,&i,data,j); + if (o) + o = EVP_DecryptFinal_ex(&ctx,&(data[i]),&j); EVP_CIPHER_CTX_cleanup(&ctx); OPENSSL_cleanse((char *)buf,sizeof(buf)); OPENSSL_cleanse((char *)key,sizeof(key)); @@ -452,7 +492,6 @@ int PEM_do_header(EVP_CIPHER_INFO *cipher, unsigned char *data, long *plen, int PEM_get_EVP_CIPHER_INFO(char *header, EVP_CIPHER_INFO *cipher) { - int o; const EVP_CIPHER *enc=NULL; char *p,c; char **header_pp = &header; @@ -492,7 +531,6 @@ int PEM_get_EVP_CIPHER_INFO(char *header, EVP_CIPHER_INFO *cipher) header++; } *header='\0'; - o=OBJ_sn2nid(p); cipher->cipher=enc=EVP_get_cipherbyname(p); *header=c; header++; @@ -538,8 +576,8 @@ static int load_iv(char **fromp, unsigned char *to, int num) } #ifndef OPENSSL_NO_FP_API -int PEM_write(FILE *fp, char *name, char *header, unsigned char *data, - long len) +int PEM_write(FILE *fp, const char *name, const char *header, + const unsigned char *data, long len) { BIO *b; int ret; @@ -556,8 +594,8 @@ int PEM_write(FILE *fp, char *name, char *header, unsigned char *data, } #endif -int PEM_write_bio(BIO *bp, const char *name, char *header, unsigned char *data, - long len) +int PEM_write_bio(BIO *bp, const char *name, const char *header, + const unsigned char *data, long len) { int nlen,n,i,j,outl; unsigned char *buf = NULL; @@ -600,6 +638,7 @@ int PEM_write_bio(BIO *bp, const char *name, char *header, unsigned char *data, } EVP_EncodeFinal(&ctx,buf,&outl); if ((outl > 0) && (BIO_write(bp,(char *)buf,outl) != outl)) goto err; + OPENSSL_cleanse(buf, PEM_BUFSIZE*8); OPENSSL_free(buf); buf = NULL; if ( (BIO_write(bp,"-----END ",9) != 9) || @@ -608,8 +647,10 @@ int PEM_write_bio(BIO *bp, const char *name, char *header, unsigned char *data, goto err; return(i+outl); err: - if (buf) + if (buf) { + OPENSSL_cleanse(buf, PEM_BUFSIZE*8); OPENSSL_free(buf); + } PEMerr(PEM_F_PEM_WRITE_BIO,reason); return(0); }