Commit 15d21c2d authored by Ralf S. Engelschall's avatar Ralf S. Engelschall
Browse files

Add a bunch of SSL_xxx() functions for configuring the temporary RSA and DH

private keys and/or callback functions which directly correspond to their
SSL_CTX_xxx() counterparts but work on a per-connection basis. This is needed
for applications which have to configure certificates on a per-connection
basis (e.g. Apache+mod_ssl) instead of a per-context basis (e.g.
s_server).

For the RSA certificate situation is makes no difference, but for the DSA
certificate situation this fixes the "no shared cipher" problem where the
OpenSSL cipher selection procedure failed because the temporary keys were not
overtaken from the context and the API provided no way to reconfigure them.

The new functions now let applications reconfigure the stuff and they are in
detail: SSL_need_tmp_RSA, SSL_set_tmp_rsa, SSL_set_tmp_dh,
SSL_set_tmp_rsa_callback and SSL_set_tmp_dh_callback.  Additionally a new
non-public-API function ssl_cert_instantiate() is used as a helper function
and also to reduce code redundancy inside ssl_rsa.c.

Submitted by: Ralf S. Engelschall
Reviewed by: Ben Laurie
parent ea14a91f
Loading
Loading
Loading
Loading
+18 −0
Original line number Diff line number Diff line
@@ -5,6 +5,24 @@

 Changes between 0.9.1c and 0.9.2

  *) Add a bunch of SSL_xxx() functions for configuring the temporary RSA and
     DH private keys and/or callback functions which directly correspond to
     their SSL_CTX_xxx() counterparts but work on a per-connection basis. This
     is needed for applications which have to configure certificates on a
     per-connection basis (e.g. Apache+mod_ssl) instead of a per-context basis
     (e.g. s_server). 
        For the RSA certificate situation is makes no difference, but
     for the DSA certificate situation this fixes the "no shared cipher"
     problem where the OpenSSL cipher selection procedure failed because the
     temporary keys were not overtaken from the context and the API provided
     no way to reconfigure them. 
        The new functions now let applications reconfigure the stuff and they
     are in detail: SSL_need_tmp_RSA, SSL_set_tmp_rsa, SSL_set_tmp_dh,
     SSL_set_tmp_rsa_callback and SSL_set_tmp_dh_callback.  Additionally a new
     non-public-API function ssl_cert_instantiate() is used as a helper
     function and also to reduce code redundancy inside ssl_rsa.c.
     [Ralf S. Engelschall]

  *) Move s_server -dcert and -dkey options out of the undocumented feature
     area because they are useful for the DSA situation and should be
     recognized by the users.
+83 −0
Original line number Diff line number Diff line
@@ -546,6 +546,26 @@ char *parg;
	{
	int ret=0;

#if !defined(NO_DSA) || !defined(NO_RSA)
	if (
#ifndef NO_RSA
	    cmd == SSL_CTRL_SET_TMP_RSA ||
	    cmd == SSL_CTRL_SET_TMP_RSA_CB ||
#endif
#ifndef NO_DSA
	    cmd == SSL_CTRL_SET_TMP_DH ||
	    cmd == SSL_CTRL_SET_TMP_DH_CB ||
#endif
		0)
		{
		if (!ssl_cert_instantiate(&s->cert, s->ctx->default_cert)) 
		    	{
			SSLerr(SSL_F_SSL3_CTRL, ERR_R_MALLOC_FAILURE);
			return(0);
			}
		}
#endif

	switch (cmd)
		{
	case SSL_CTRL_GET_SESSION_REUSED:
@@ -566,6 +586,69 @@ char *parg;
	case SSL_CTRL_GET_FLAGS:
		ret=(int)(s->s3->flags);
		break;
#ifndef NO_RSA
	case SSL_CTRL_NEED_TMP_RSA:
		if ((s->cert != NULL) && (s->cert->rsa_tmp == NULL) &&
		    ((s->cert->pkeys[SSL_PKEY_RSA_ENC].privatekey == NULL) ||
		     (EVP_PKEY_size(s->cert->pkeys[SSL_PKEY_RSA_ENC].privatekey) > (512/8))))
			ret = 1;
		break;
	case SSL_CTRL_SET_TMP_RSA:
		{
			RSA *rsa = (RSA *)parg;
			if (rsa == NULL) {
				SSLerr(SSL_F_SSL3_CTRL, ERR_R_PASSED_NULL_PARAMETER);
				return(ret);
			}
			if ((rsa = RSAPrivateKey_dup(rsa)) == NULL) {
				SSLerr(SSL_F_SSL3_CTRL, ERR_R_RSA_LIB);
				return(ret);
			}
			if (s->cert->rsa_tmp != NULL)
				RSA_free(s->cert->rsa_tmp);
			s->cert->rsa_tmp = rsa;
			ret = 1;
		}
		break;
	case SSL_CTRL_SET_TMP_RSA_CB:
#ifndef NOPROTO
		s->cert->rsa_tmp_cb = (RSA *(*)(SSL *, int, int))parg;
#else
		s->cert->rsa_tmp_cb = (RSA *(*)())parg;
#endif
		break;
#endif
#ifndef NO_DH
	case SSL_CTRL_SET_TMP_DH:
		{
			DH *dh = (DH *)parg;
			if (dh == NULL) {
				SSLerr(SSL_F_SSL3_CTRL, ERR_R_PASSED_NULL_PARAMETER);
				return(ret);
			}
			if ((dh = DHparams_dup(dh)) == NULL) {
				SSLerr(SSL_F_SSL3_CTRL, ERR_R_DH_LIB);
				return(ret);
			}
			if (!DH_generate_key(dh)) {
				DH_free(dh);
				SSLerr(SSL_F_SSL3_CTRL, ERR_R_DH_LIB);
				return(ret);
			}
			if (s->cert->dh_tmp != NULL)
				DH_free(s->cert->dh_tmp);
			s->cert->dh_tmp = dh;
			ret = 1;
		}
		break;
	case SSL_CTRL_SET_TMP_DH_CB:
#ifndef NOPROTO
		s->cert->dh_tmp_cb = (DH *(*)(SSL *, int, int))parg;
#else
		s->cert->dh_tmp_cb = (DH *(*)())parg;
#endif
		break;
#endif
	default:
		break;
		}
+2 −0
Original line number Diff line number Diff line
@@ -113,6 +113,8 @@
#define SSL_F_TLS1_ENC					 210
#define SSL_F_TLS1_SETUP_KEY_BLOCK			 211
#define SSL_F_WRITE_PENDING				 212
#define SSL_F_SSL3_CTRL					 213
#define SSL_F_SSL_CERT_INSTANTIATE			 214

/* Reason codes. */
#define SSL_R_APP_DATA_IN_HANDSHAKE			 100
+18 −0
Original line number Diff line number Diff line
@@ -784,6 +784,13 @@ struct ssl_st
#define SSL_CTX_set_tmp_dh(ctx,dh) \
	SSL_CTX_ctrl(ctx,SSL_CTRL_SET_TMP_DH,0,(char *)dh)

#define SSL_need_tmp_RSA(ssl) \
	SSL_ctrl(ssl,SSL_CTRL_NEED_TMP_RSA,0,NULL)
#define SSL_set_tmp_rsa(ssl,rsa) \
	SSL_ctrl(ssl,SSL_CTRL_SET_TMP_RSA,0,(char *)rsa)
#define SSL_set_tmp_dh(ssl,dh) \
	SSL_ctrl(ssl,SSL_CTRL_SET_TMP_DH,0,(char *)dh)

#define SSL_CTX_add_extra_chain_cert(ctx,x509) \
	SSL_CTX_ctrl(ctx,SSL_CTRL_EXTRA_CHAIN_CERT,0,(char *)x509)

@@ -1029,6 +1036,12 @@ void SSL_CTX_set_tmp_rsa_callback(SSL_CTX *ctx,
void SSL_CTX_set_tmp_dh_callback(SSL_CTX *ctx,
				 DH *(*dh)(SSL *ssl,int export,int keylength));

void SSL_set_tmp_rsa_callback(SSL *ssl,
				  RSA *(*cb)(SSL *ssl,int export,
					     int keylength));
void SSL_set_tmp_dh_callback(SSL *ssl,
				 DH *(*dh)(SSL *ssl,int export,int keylength));

#ifdef HEADER_COMP_H
int SSL_COMP_add_compression_method(int id,COMP_METHOD *cm);
#else
@@ -1258,6 +1271,9 @@ int SSL_COMP_add_compression_method();
void SSL_CTX_set_tmp_rsa_callback();
void SSL_CTX_set_tmp_dh_callback();

void SSL_set_tmp_rsa_callback();
void SSL_set_tmp_dh_callback();

/* #endif */

#endif
@@ -1378,6 +1394,8 @@ void SSL_CTX_set_tmp_dh_callback();
#define SSL_F_TLS1_ENC					 210
#define SSL_F_TLS1_SETUP_KEY_BLOCK			 211
#define SSL_F_WRITE_PENDING				 212
#define SSL_F_SSL3_CTRL					 213
#define SSL_F_SSL_CERT_INSTANTIATE			 214

/* Reason codes. */
#define SSL_R_APP_DATA_IN_HANDSHAKE			 100
+21 −0
Original line number Diff line number Diff line
@@ -144,6 +144,27 @@ CERT *c;
	Free(c);
	}

int ssl_cert_instantiate(CERT **o, CERT *d)
	{
	CERT *n;
	if (o == NULL) 
		{
		SSLerr(SSL_F_SSL_CERT_INSTANTIATE, ERR_R_PASSED_NULL_PARAMETER);
		return(0);
		}
	if (*o != NULL && d != NULL && *o != d)
	    return(1);
	if ((n = ssl_cert_new()) == NULL) 
		{
		SSLerr(SSL_F_SSL_CERT_INSTANTIATE, ERR_R_MALLOC_FAILURE);
		return(0);
		}
	if (*o != NULL) 
		ssl_cert_free(*o);
	*o = n;
	return(1);
	}

int ssl_set_cert_type(c, type)
CERT *c;
int type;
Loading