📄 s3_enc.c
字号:
int num; int ret = 0; SSL_COMP *comp; if (s->s3->tmp.key_block_length != 0) return(1); if (!ssl_cipher_get_evp(s->session,&c,&hash,&comp)) { SSLerr(SSL_F_SSL3_SETUP_KEY_BLOCK,SSL_R_CIPHER_OR_HASH_UNAVAILABLE); return(0); } s->s3->tmp.new_sym_enc=c; s->s3->tmp.new_hash=hash;#ifdef OPENSSL_NO_COMP s->s3->tmp.new_compression=NULL;#else s->s3->tmp.new_compression=comp;#endif num=EVP_CIPHER_key_length(c)+EVP_MD_size(hash)+EVP_CIPHER_iv_length(c); num*=2; ssl3_cleanup_key_block(s); if ((p=OPENSSL_malloc(num)) == NULL) goto err; s->s3->tmp.key_block_length=num; s->s3->tmp.key_block=p; ret = ssl3_generate_key_block(s,p,num); if (!(s->options & SSL_OP_DONT_INSERT_EMPTY_FRAGMENTS)) { /* enable vulnerability countermeasure for CBC ciphers with * known-IV problem (http://www.openssl.org/~bodo/tls-cbc.txt) */ s->s3->need_empty_fragments = 1; if (s->session->cipher != NULL) { if ((s->session->cipher->algorithms & SSL_ENC_MASK) == SSL_eNULL) s->s3->need_empty_fragments = 0; #ifndef OPENSSL_NO_RC4 if ((s->session->cipher->algorithms & SSL_ENC_MASK) == SSL_RC4) s->s3->need_empty_fragments = 0;#endif } } return ret; err: SSLerr(SSL_F_SSL3_SETUP_KEY_BLOCK,ERR_R_MALLOC_FAILURE); return(0); }void ssl3_cleanup_key_block(SSL *s) { if (s->s3->tmp.key_block != NULL) { OPENSSL_cleanse(s->s3->tmp.key_block, s->s3->tmp.key_block_length); OPENSSL_free(s->s3->tmp.key_block); s->s3->tmp.key_block=NULL; } s->s3->tmp.key_block_length=0; }int ssl3_enc(SSL *s, int send) { SSL3_RECORD *rec; EVP_CIPHER_CTX *ds; unsigned long l; int bs,i; const EVP_CIPHER *enc; if (send) { ds=s->enc_write_ctx; rec= &(s->s3->wrec); if (s->enc_write_ctx == NULL) enc=NULL; else enc=EVP_CIPHER_CTX_cipher(s->enc_write_ctx); } else { ds=s->enc_read_ctx; rec= &(s->s3->rrec); if (s->enc_read_ctx == NULL) enc=NULL; else enc=EVP_CIPHER_CTX_cipher(s->enc_read_ctx); } if ((s->session == NULL) || (ds == NULL) || (enc == NULL)) { memmove(rec->data,rec->input,rec->length); rec->input=rec->data; } else { l=rec->length; bs=EVP_CIPHER_block_size(ds->cipher); /* COMPRESS */ if ((bs != 1) && send) { i=bs-((int)l%bs); /* we need to add 'i-1' padding bytes */ l+=i; rec->length+=i; rec->input[l-1]=(i-1); } if (!send) { if (l == 0 || l%bs != 0) { SSLerr(SSL_F_SSL3_ENC,SSL_R_BLOCK_CIPHER_PAD_IS_WRONG); ssl3_send_alert(s,SSL3_AL_FATAL,SSL_AD_DECRYPTION_FAILED); return 0; } /* otherwise, rec->length >= bs */ } EVP_Cipher(ds,rec->data,rec->input,l); if ((bs != 1) && !send) { i=rec->data[l-1]+1; /* SSL 3.0 bounds the number of padding bytes by the block size; * padding bytes (except the last one) are arbitrary */ if (i > bs) { /* Incorrect padding. SSLerr() and ssl3_alert are done * by caller: we don't want to reveal whether this is * a decryption error or a MAC verification failure * (see http://www.openssl.org/~bodo/tls-cbc.txt) */ return -1; } /* now i <= bs <= rec->length */ rec->length-=i; } } return(1); }void ssl3_init_finished_mac(SSL *s) { EVP_DigestInit_ex(&(s->s3->finish_dgst1),s->ctx->md5, NULL); EVP_DigestInit_ex(&(s->s3->finish_dgst2),s->ctx->sha1, NULL); }void ssl3_finish_mac(SSL *s, const unsigned char *buf, int len) { EVP_DigestUpdate(&(s->s3->finish_dgst1),buf,len); EVP_DigestUpdate(&(s->s3->finish_dgst2),buf,len); }int ssl3_cert_verify_mac(SSL *s, EVP_MD_CTX *ctx, unsigned char *p) { return(ssl3_handshake_mac(s,ctx,NULL,0,p)); }int ssl3_final_finish_mac(SSL *s, EVP_MD_CTX *ctx1, EVP_MD_CTX *ctx2, const char *sender, int len, unsigned char *p) { int ret; ret=ssl3_handshake_mac(s,ctx1,sender,len,p); p+=ret; ret+=ssl3_handshake_mac(s,ctx2,sender,len,p); return(ret); }static int ssl3_handshake_mac(SSL *s, EVP_MD_CTX *in_ctx, const char *sender, int len, unsigned char *p) { unsigned int ret; int npad,n; unsigned int i; unsigned char md_buf[EVP_MAX_MD_SIZE]; EVP_MD_CTX ctx; EVP_MD_CTX_init(&ctx); EVP_MD_CTX_copy_ex(&ctx,in_ctx); n=EVP_MD_CTX_size(&ctx); npad=(48/n)*n; if (sender != NULL) EVP_DigestUpdate(&ctx,sender,len); EVP_DigestUpdate(&ctx,s->session->master_key, s->session->master_key_length); EVP_DigestUpdate(&ctx,ssl3_pad_1,npad); EVP_DigestFinal_ex(&ctx,md_buf,&i); EVP_DigestInit_ex(&ctx,EVP_MD_CTX_md(&ctx), NULL); EVP_DigestUpdate(&ctx,s->session->master_key, s->session->master_key_length); EVP_DigestUpdate(&ctx,ssl3_pad_2,npad); EVP_DigestUpdate(&ctx,md_buf,i); EVP_DigestFinal_ex(&ctx,p,&ret); EVP_MD_CTX_cleanup(&ctx); return((int)ret); }int ssl3_mac(SSL *ssl, unsigned char *md, int send) { SSL3_RECORD *rec; unsigned char *mac_sec,*seq; EVP_MD_CTX md_ctx; const EVP_MD *hash; unsigned char *p,rec_char; unsigned int md_size; int npad; if (send) { rec= &(ssl->s3->wrec); mac_sec= &(ssl->s3->write_mac_secret[0]); seq= &(ssl->s3->write_sequence[0]); hash=ssl->write_hash; } else { rec= &(ssl->s3->rrec); mac_sec= &(ssl->s3->read_mac_secret[0]); seq= &(ssl->s3->read_sequence[0]); hash=ssl->read_hash; } md_size=EVP_MD_size(hash); npad=(48/md_size)*md_size; /* Chop the digest off the end :-) */ EVP_MD_CTX_init(&md_ctx); EVP_DigestInit_ex( &md_ctx,hash, NULL); EVP_DigestUpdate(&md_ctx,mac_sec,md_size); EVP_DigestUpdate(&md_ctx,ssl3_pad_1,npad); EVP_DigestUpdate(&md_ctx,seq,8); rec_char=rec->type; EVP_DigestUpdate(&md_ctx,&rec_char,1); p=md; s2n(rec->length,p); EVP_DigestUpdate(&md_ctx,md,2); EVP_DigestUpdate(&md_ctx,rec->input,rec->length); EVP_DigestFinal_ex( &md_ctx,md,NULL); EVP_DigestInit_ex( &md_ctx,hash, NULL); EVP_DigestUpdate(&md_ctx,mac_sec,md_size); EVP_DigestUpdate(&md_ctx,ssl3_pad_2,npad); EVP_DigestUpdate(&md_ctx,md,md_size); EVP_DigestFinal_ex( &md_ctx,md,&md_size); EVP_MD_CTX_cleanup(&md_ctx); ssl3_record_sequence_update(seq); return(md_size); }void ssl3_record_sequence_update(unsigned char *seq) { int i; for (i=7; i>=0; i--) { ++seq[i]; if (seq[i] != 0) break; } }int ssl3_generate_master_secret(SSL *s, unsigned char *out, unsigned char *p, int len) { static const unsigned char *salt[3]={#ifndef CHARSET_EBCDIC (const unsigned char *)"A", (const unsigned char *)"BB", (const unsigned char *)"CCC",#else (const unsigned char *)"\x41", (const unsigned char *)"\x42\x42", (const unsigned char *)"\x43\x43\x43",#endif }; unsigned char buf[EVP_MAX_MD_SIZE]; EVP_MD_CTX ctx; int i,ret=0; unsigned int n; EVP_MD_CTX_init(&ctx); for (i=0; i<3; i++) { EVP_DigestInit_ex(&ctx,s->ctx->sha1, NULL); EVP_DigestUpdate(&ctx,salt[i],strlen((const char *)salt[i])); EVP_DigestUpdate(&ctx,p,len); EVP_DigestUpdate(&ctx,&(s->s3->client_random[0]), SSL3_RANDOM_SIZE); EVP_DigestUpdate(&ctx,&(s->s3->server_random[0]), SSL3_RANDOM_SIZE); EVP_DigestFinal_ex(&ctx,buf,&n); EVP_DigestInit_ex(&ctx,s->ctx->md5, NULL); EVP_DigestUpdate(&ctx,p,len); EVP_DigestUpdate(&ctx,buf,n); EVP_DigestFinal_ex(&ctx,out,&n); out+=n; ret+=n; } EVP_MD_CTX_cleanup(&ctx); return(ret); }int ssl3_alert_code(int code) { switch (code) { case SSL_AD_CLOSE_NOTIFY: return(SSL3_AD_CLOSE_NOTIFY); case SSL_AD_UNEXPECTED_MESSAGE: return(SSL3_AD_UNEXPECTED_MESSAGE); case SSL_AD_BAD_RECORD_MAC: return(SSL3_AD_BAD_RECORD_MAC); case SSL_AD_DECRYPTION_FAILED: return(SSL3_AD_BAD_RECORD_MAC); case SSL_AD_RECORD_OVERFLOW: return(SSL3_AD_BAD_RECORD_MAC); case SSL_AD_DECOMPRESSION_FAILURE:return(SSL3_AD_DECOMPRESSION_FAILURE); case SSL_AD_HANDSHAKE_FAILURE: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_NO_CERTIFICATE: return(SSL3_AD_NO_CERTIFICATE); case SSL_AD_BAD_CERTIFICATE: return(SSL3_AD_BAD_CERTIFICATE); case SSL_AD_UNSUPPORTED_CERTIFICATE:return(SSL3_AD_UNSUPPORTED_CERTIFICATE); case SSL_AD_CERTIFICATE_REVOKED:return(SSL3_AD_CERTIFICATE_REVOKED); case SSL_AD_CERTIFICATE_EXPIRED:return(SSL3_AD_CERTIFICATE_EXPIRED); case SSL_AD_CERTIFICATE_UNKNOWN:return(SSL3_AD_CERTIFICATE_UNKNOWN); case SSL_AD_ILLEGAL_PARAMETER: return(SSL3_AD_ILLEGAL_PARAMETER); case SSL_AD_UNKNOWN_CA: return(SSL3_AD_BAD_CERTIFICATE); case SSL_AD_ACCESS_DENIED: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_DECODE_ERROR: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_DECRYPT_ERROR: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_EXPORT_RESTRICTION: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_PROTOCOL_VERSION: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_INSUFFICIENT_SECURITY:return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_INTERNAL_ERROR: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_USER_CANCELLED: return(SSL3_AD_HANDSHAKE_FAILURE); case SSL_AD_NO_RENEGOTIATION: return(-1); /* Don't send it :-) */ default: return(-1); } }
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -