[openssl-users] SSL_CTX_load_verify_locations only with CAPath

David Thompson dthompson at cardconnect.com
Sun Jul 5 12:19:27 UTC 2015

From: openssl-users On Behalf Of Dr. Roger Cuypers
Sent: Friday, July 03, 2015 11:01
> I'm trying to do peer client verification using the SSL_CTX_load_verify_locations function
<snip: CAfile works>
> However, setting only CAPath will not: <snip>
> This will result in a X509_V_ERR_UNABLE_TO_GET_ISSUER_CERT_LOCALLY error.
> The cert directory D:\\certs looks like this:
> -.wikipedia.org.crt
> ca_client.jks
> ca_server.jks
> My expectation would be that the library uses -.wikipedia.org.crt
> As it is the only certificate available or am I doing something wrong?

A truststore generally can contain many certs, not just one. OpenSSL needs to
find the correct one(s) for each connection and uses special names for this.

>From manpage https://www.openssl.org/docs/ssl/SSL_CTX_load_verify_locations.html

If CApath is not NULL, it points to a directory containing CA certificates in PEM format.
The files each contain one CA certificate. The files are looked up by the
CA subject name hash value, which must hence be available. If more than
one CA certificate with the same name hash value exist, the extension
must be different (e.g. 9d66eef0.0, 9d66eef0.1 etc). The search is performed
in the ordering of the extension number, regardless of other properties
of the certificates. Use the c_rehash utility to create the necessary links.

The semantically similar https://www.openssl.org/docs/apps/verify.html
-CApath option is slightly briefer:

    A directory of trusted certificates. The certificates should have names of the form:
hash.0 or have symbolic links to them of this form ("hash" is the hashed certificate
subject name: see the -hash option of the x509 utility). Under Unix the c_rehash
script will automatically create symbolic links to a directory of certificates.

Note c_rehash  only works on Unix, or quasi-Unix like Cygwin/Windows.
For native Windows one or two is easiest done by hand:
  openssl x509 -in certfile.pem -noout -subject_hash
  (outputs hex number call it xxxxxxxx)
  mklink /h xxxxxxxx.0 certfile.pem
To do it automatically you need a trick to capture the value, something like
  for %f in (*.pem) do for /v %h ('openssl x509 -in %f -noout -subject_hash') ^
  do mklink /h %v.0 %f
except that doesn't handle errors or collisions intelligently. (And if you want
to make it a .bat file, remember all "local" % must be doubled in .bat.)

Note this *method* hasn't changed for at least a decade, but the *hash*
used for -subject_hash did change between 0.9.8 and 1.0.0. If you create
hashlinks with 0.9.8 they won't work for 1.0.0 and up, and vice versa.

And note only *one* cert per file in CApath is used. If your wikipedia.crt
file has multiple certs, using it as CAfile puts them *all* in the truststore
and uses them if needed, but for CApath you must split out separate file
for each needed cert, each with a hashlink (or name) as above.

But the server I get for wikipedia.org:443 ( (as it should)
provides full chain up to but excluding GlobalSign Root CA, so that root
is the only cert you should need regardless of store format.


THIS MESSAGE IS CONFIDENTIAL. This e-mail message and any attachments are proprietary and confidential information protected from disclosure and intended only for the use of the recipient(s) named above. If the reader of this message is not the intended recipient, or an employee or agent responsible for delivering this message to the intended recipient, you are hereby notified that any dissemination, distribution or copying of this message or any attachments is strictly prohibited. If you have received this communication in error, please notify CardConnect immediately by replying to this message and then delete this message and any attachments from your computer.

More information about the openssl-users mailing list