Openssl s_client -verify -CApath always gives "unable to get local issuer certificate"

I haven’t used openssl s_client -verify in a long time, but it seems like some essential behavior has changed since then, because this used to work.

This fails:

openssl s_client -CApath /etc/pki/tls -verify 1 -showcerts -connect imap.gmail.com:993

But this works:

openssl s_client -verify 1 -showcerts -connect imap.gmail.com:993

That doesn’t make any sense to me because, according to openssl, /etc/pki/tls is the correct path for certs:

openssl version -d
OPENSSLDIR: "/etc/pki/tls"

It’s as if the “correct” way to use openssl is not to specify the CApath. But, then, how can you tell if CApath option works at all?

This also works:
openssl s_client -CAfile /etc/pki/tls/cert.pem -verify 1 -connect imap.gmail.com:993

So, CAfile seems to work as before, but not CApath.

Here are my questions:

  1. Can someone tell me what is going wrong? What am I missing?

  2. In the past, a program that wanted to use openssl had to know and pass to openssl the system-wide cert bundle path. This was a known issue because systems don’t all share the same default CA path. This new behavior breaks that old paradigm because CApath doesn’t seem to work at all anymore, even if you pass it the correct value. Is that “okay” because we shouldn’t use CApath any more, or is it a bug? If the former, how can you specify a local directory of CA certs (I’m assuming this broken, but I didn’t test)?

Buzz

Which is the error? I mean, in both cases “* OK Gimap ready for…” is being shown.

openssl s_client -CApath /etc/pki/tls -verify 1 -showcerts -connect imap.gmail.com:993

UPDATE:
https://www.openssl.org/docs/man1.1.1/man1/openssl-s_client.html

-CApath directory

  • The directory to use for server certificate verification. This directory must be in “hash format”, see verify(1) for more information. These are also used when building the client certificate chain.

Have no idea why this (dnf install openssl-perl, c_rehash, etc…) not working for me.

Well, I think that answers one of my questions: you’re saying that CApath no longer accepts the system path because those certs are not in the required “hash format”. Is that right?

Regarding your original question, the error is that verification fails. When I say “this fails”, I mean the result of the -verify command is the return code 20 “unable to get local issuer certificate”. So, it’s saying that certificate verification of imap.gmail.com:993 fails; it’s NOT a valid cert.

So, this is not a bug, that’s clear, although it is inconsistent behavior with past operation, IIRC.

I’d be interested in more history on this, if anyone knows. When did this change? Why?