I have a unusual case where, as a server, I need the client to provide a
SSL cert, however, I am not interested in verifying it. In order to
convince the client to provide a cert, the SSL_VERIFY_PEER param is
passed to the context using SSL_CTX_set_verify function. This happens
in the function ngx_ssl_client_certificate in “ngx_event_openssl.c”
(configured by setting ssl_verify_client to ‘ask’)
…
ngx_int_t
ngx_ssl_client_certificate(ngx_conf_t *cf, ngx_ssl_t *ssl, ngx_str_t
*cert,
ngx_int_t depth)
{
STACK_OF(X509_NAME) *list;
SSL_CTX_set_verify(ssl->ctx, SSL_VERIFY_PEER,
ngx_http_ssl_verify_callback);
SSL_CTX_set_verify_depth(ssl->ctx, depth);
if (cert->len == 0) {
return NGX_OK;
}
…
However, in order to get into that code, I have to first call
ngx_http_ssl_merge_srv_conf in “ngx_http_ssl_module.c”:
…
if (conf->verify) {
if (conf->client_certificate.len == 0) {
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
"no ssl_client_certificate for
ssl_client_verify");
return NGX_CONF_ERROR;
}
if (ngx_ssl_client_certificate(cf, &conf->ssl,
&conf->client_certificate,
conf->verify_depth)
!= NGX_OK)
{
return NGX_CONF_ERROR;
}
}
…
The problem is that if (conf->verify) is non-zero, but the
(conf->client_certificate.len == 0), the function is aborted. This will
happen when verify is turned on, but the ca_cert is not supplied in the
configuration. I can get around this by commenting out that check, and
the code works fine.
…
if (conf->verify) {
/* if (conf->client_certificate.len == 0) {
ngx_log_error(NGX_LOG_EMERG, cf->log, 0,
“no ssl_client_certificate for
ssl_client_verify”);
return NGX_CONF_ERROR;
}
*/
if (ngx_ssl_client_certificate(cf, &conf->ssl,
&conf->client_certificate,
conf->verify_depth)
!= NGX_OK)
{
return NGX_CONF_ERROR;
}
}
…
My question is, does nginx need to return a NGX_CONF_ERROR if the
ssl_client_certificate (ie. ca_cert) is not provided? It already
correct checks for an empty ca_cert in “ngx_ssl_client_certificate” and
returns NGX_OK in that case.
Posted at Nginx Forum: