Add new "valid_flags" field to CERT_PKEY structure which determines what
the certificate can be used for (if anything). Set valid_flags field in new tls1_check_chain function. Simplify ssl_set_cert_masks which used to have similar checks in it. Add new "cert_flags" field to CERT structure and include a "strict mode". This enforces some TLS certificate requirements (such as only permitting certificate signature algorithms contained in the supported algorithms extension) which some implementations ignore: this option should be used with caution as it could cause interoperability issues.
This commit is contained in:
@@ -1128,6 +1128,10 @@ long SSL_ctrl(SSL *s,int cmd,long larg,void *parg)
|
||||
if (s->s3)
|
||||
return s->s3->send_connection_binding;
|
||||
else return 0;
|
||||
case SSL_CTRL_CERT_FLAGS:
|
||||
return(s->cert->cert_flags|=larg);
|
||||
case SSL_CTRL_CLEAR_CERT_FLAGS:
|
||||
return(s->cert->cert_flags &=~larg);
|
||||
default:
|
||||
return(s->method->ssl_ctrl(s,cmd,larg,parg));
|
||||
}
|
||||
@@ -1225,6 +1229,10 @@ long SSL_CTX_ctrl(SSL_CTX *ctx,int cmd,long larg,void *parg)
|
||||
return 0;
|
||||
ctx->max_send_fragment = larg;
|
||||
return 1;
|
||||
case SSL_CTRL_CERT_FLAGS:
|
||||
return(ctx->cert->cert_flags|=larg);
|
||||
case SSL_CTRL_CLEAR_CERT_FLAGS:
|
||||
return(ctx->cert->cert_flags &=~larg);
|
||||
default:
|
||||
return(ctx->method->ssl_ctx_ctrl(ctx,cmd,larg,parg));
|
||||
}
|
||||
@@ -2078,21 +2086,21 @@ void ssl_set_cert_masks(CERT *c, const SSL_CIPHER *cipher)
|
||||
have_ecdh_tmp=(c->ecdh_tmp || c->ecdh_tmp_cb || c->ecdh_tmp_auto);
|
||||
#endif
|
||||
cpk= &(c->pkeys[SSL_PKEY_RSA_ENC]);
|
||||
rsa_enc= (cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
rsa_enc= cpk->valid_flags;
|
||||
rsa_enc_export=(rsa_enc && EVP_PKEY_size(cpk->privatekey)*8 <= kl);
|
||||
cpk= &(c->pkeys[SSL_PKEY_RSA_SIGN]);
|
||||
rsa_sign=(cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
rsa_sign= (cpk->valid_flags & CERT_PKEY_SIGN);
|
||||
cpk= &(c->pkeys[SSL_PKEY_DSA_SIGN]);
|
||||
dsa_sign=(cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
dsa_sign= (cpk->valid_flags & CERT_PKEY_SIGN);
|
||||
cpk= &(c->pkeys[SSL_PKEY_DH_RSA]);
|
||||
dh_rsa= (cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
dh_rsa= cpk->valid_flags;
|
||||
dh_rsa_export=(dh_rsa && EVP_PKEY_size(cpk->privatekey)*8 <= kl);
|
||||
cpk= &(c->pkeys[SSL_PKEY_DH_DSA]);
|
||||
/* FIX THIS EAY EAY EAY */
|
||||
dh_dsa= (cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
dh_dsa= cpk->valid_flags;
|
||||
dh_dsa_export=(dh_dsa && EVP_PKEY_size(cpk->privatekey)*8 <= kl);
|
||||
cpk= &(c->pkeys[SSL_PKEY_ECC]);
|
||||
have_ecc_cert= (cpk->x509 != NULL && cpk->privatekey != NULL);
|
||||
have_ecc_cert= cpk->valid_flags;
|
||||
mask_k=0;
|
||||
mask_a=0;
|
||||
emask_k=0;
|
||||
@@ -2174,13 +2182,16 @@ void ssl_set_cert_masks(CERT *c, const SSL_CIPHER *cipher)
|
||||
*/
|
||||
if (have_ecc_cert)
|
||||
{
|
||||
cpk = &c->pkeys[SSL_PKEY_ECC];
|
||||
x = cpk->x509;
|
||||
/* This call populates extension flags (ex_flags) */
|
||||
x = (c->pkeys[SSL_PKEY_ECC]).x509;
|
||||
X509_check_purpose(x, -1, 0);
|
||||
ecdh_ok = (x->ex_flags & EXFLAG_KUSAGE) ?
|
||||
(x->ex_kusage & X509v3_KU_KEY_AGREEMENT) : 1;
|
||||
ecdsa_ok = (x->ex_flags & EXFLAG_KUSAGE) ?
|
||||
(x->ex_kusage & X509v3_KU_DIGITAL_SIGNATURE) : 1;
|
||||
if (!(cpk->valid_flags & CERT_PKEY_SIGN))
|
||||
ecdsa_ok = 0;
|
||||
ecc_pkey = X509_get_pubkey(x);
|
||||
ecc_pkey_size = (ecc_pkey != NULL) ?
|
||||
EVP_PKEY_bits(ecc_pkey) : 0;
|
||||
|
Reference in New Issue
Block a user