httpd-dev mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From Dr Stephen Henson <shen...@opensslfoundation.com>
Subject Re: svn commit: r1160863 - in /httpd/httpd/trunk: docs/manual/mod/ modules/ssl/
Date Sat, 03 Sep 2011 11:15:42 GMT
On 23/08/2011 20:35, druggeri@apache.org wrote:
> Author: druggeri
> Date: Tue Aug 23 19:35:07 2011
> New Revision: 1160863
> 
> URL: http://svn.apache.org/viewvc?rev=1160863&view=rev
> Log:
> Add SSLProxyMachineCertificateChainFile directive and documentation for bug 50812
>
> Modified: httpd/httpd/trunk/modules/ssl/ssl_util_ssl.c
> URL: http://svn.apache.org/viewvc/httpd/httpd/trunk/modules/ssl/ssl_util_ssl.c?rev=1160863&r1=1160862&r2=1160863&view=diff
> ==============================================================================
> --- httpd/httpd/trunk/modules/ssl/ssl_util_ssl.c (original)
> +++ httpd/httpd/trunk/modules/ssl/ssl_util_ssl.c Tue Aug 23 19:35:07 2011
> @@ -434,6 +434,45 @@ BOOL SSL_X509_INFO_load_path(apr_pool_t 
>      return ok;
>  }
>  
> +/*
> + * Construct a stack of X509_INFO containing only certificates
> + * that have signed the provided certificate or are an intermediary
> + * signer of the certificate
> +*/
> +int SSL_X509_INFO_create_chain(const X509 *x509,
> +                             STACK_OF(X509_INFO) *ca_certs,
> +                             STACK_OF(X509_INFO) *chain)
> +{
> +    int can_proceed=1;
> +    int len=0;
> +    int i;
> +    X509 *certificate = (X509 *)x509;
> +    X509_INFO *info;
> +    X509_NAME *cert_issuer_name, *ca_name, *ca_issuer_name;
> +
> +    while (can_proceed) {
> +        can_proceed = 0;
> +        cert_issuer_name = X509_get_issuer_name(certificate);
> +
> +        for (i = 0; i < sk_X509_INFO_num(ca_certs); i++) {
> +            info = sk_X509_INFO_value(ca_certs, i);
> +            ca_name = X509_get_subject_name(info->x509);
> +            ca_issuer_name = X509_get_issuer_name(info->x509);
> +
> +            if (X509_NAME_cmp(cert_issuer_name, ca_name) == 0) {
> +                /* Check for a self-signed cert (no issuer) */
> +                can_proceed=X509_NAME_cmp(ca_name, ca_issuer_name) == 0 ? 0 : 1;
> +                len++;
> +                certificate = info->x509;
> +                sk_X509_INFO_unshift(chain, info);
> +                break;
> +            }
> +        }
> +    }
> +
> +    return len;
> +}
> +
> 

The above code is manually building up a certificate chain. While it will work
for the simpler cases it cannot handle more complex chains. For example those
where several certificates have the same subject name and indicate preferences
using SKID/AKID. Also certificates can appear higher in the chain and be "self
issued" (matching subject/issuer) but not self signed. Admittedly such cases are
comparatively rare outside compliance tests...

So instead of manually building the chain why not handle it automatically or at
least have the option to do so? The X509_verify_cert function in OpenSSL can do
this. This has the advantage that the chain is also checked for validity (expiry
for example) and you can't send an invalid chain and have to trace why the peer
is rejecting it with a (possibly obscure) error.

Steve.
-- 
Dr Stephen Henson. OpenSSL Software Foundation, Inc.
1829 Mount Ephraim Road
Adamstown, MD 21710
+1 877-673-6775
shenson@opensslfoundation.com

Mime
View raw message