Hi Chris, On Fri, Oct 19, 2018 at 2:14 AM Christopher Schultz < ch...@christopherschultz.net> wrote:
> -----BEGIN PGP SIGNED MESSAGE----- > Hash: SHA256 > > Igor, > > On 10/16/18 17:03, Igor Cicimov wrote: > > On Tue, Oct 16, 2018 at 8:56 PM Igor Cicimov <icici...@gmail.com> > > wrote: > > > >> Hi Jose, > >> > >> On Tue, Oct 16, 2018 at 5:52 PM Jose María Zaragoza > >> <demablo...@gmail.com> wrote: > >> > >>> Hi > >>> > >>> El mar., 16 oct. 2018 a las 1:49, Igor Cicimov > >>> (<icici...@gmail.com>) escribió: > >>>> > >>>> Hi all, > >>>> > >>>> I just want to clarify something that I've been seeing > >>>> behave > >>> differently > >>>> on various Java versions during the years. In case we have > >>>> the following setting: > >>>> > >>>> -Djavax.net.ssl.trustStore=/keystore/truststore.jks" > >>>> > >>>> in Tomcat's default config file, is JVM suppose to fall back > >>>> to the > >>> global > >>>> CA store on the server under /etc/ssl/certs for verification > >>>> in case > >>> *any* > >>>> of the certificates returned by a trusted domain are not > >>>> present in the above JKS store? By any I mean, all the certs > >>>> in the chain returned by > >>> the > >>>> SSL handshake. > >>>> > >>>> For example, lets say we have a situation like this: > >>>> > >>>> DigiCert Global Root G2 -> RapidSSL TLS RSA CA G1 -> > >>>> CN=*.mydomain.com > >>>> > >>>> Lets say I have imported the *CN=*.mydomain.com > >>>> <http://mydomain.com>* certificate in the truststore.jks, the > >>>> question is is JVM going to look under /etc/ssl/certs for > >>>> RapidSSL in order to validate the CN signature > >>> and > >>>> then for DigiCert to validate the RapidSSL cert? > >>>> > >>>> As I said I had a mixed luck with this over the years, > >>>> sometimes it > >>> works > >>>> as (I) expect it to work i.e. verify the certs by looking at > >>>> the system > >>> CA > >>>> store and sometimes this is not the case. > >>> > >>> My experience is that if you store a server certificate in the > >>> truststore.jks , don't search anyone more. > >>> > >> > >> That's my experience too ... most of the time. But what happens > >> when lets say the domain returns multiple certificates in the > >> handshake, like the intermediate and the domain certificate? For > >> the example above I gave: > >> > >> DigiCert Global Root G2 -> RapidSSL TLS RSA CA G1 -> > >> CN=*.mydomain.com > >> > >> what if what is sent back are the Intermediate (RapidSSL TLS RSA > >> CA G1) and the domain one (*.mydomain.com) cert in the chain? Is > >> Java going to need to validate the Intermediate cert now too? > >> There is only the domain cert in the truststore so how is it > >> going to validate the Intermediate in this case? Is the > >> Intermediate ignored maybe since the domain one validates > >> anyway? > >> > >> This behaviour makes sense for me because you are saying that > >> you > >>> trust in that certificate because you verified ( by other means > >>> ) it before Even if certificate is expired ( and server send it > >>> expired too, obviously ) , I think that is validated as > >>> trusted > >>> > >>> Regards > >>> > >>> > > To make it more clear, with a custom trusted keystore how do the > > certs that are not trusted get validated? Now Java needs to > > validate the whole chain so where does it look for the CAs? In its > > own keystore $JAVA_HOME/jre/lib/security/cacerts or under > > /etc/ssl/certs ? > > Java has no notion of CAs, nor does any trust store, really. Correct, but by loading all CAs in the trust store it kinda does, indirectly. A > certificate is trusted if it is present in the trust store, full stop. > It not need be a "CA". The oly thing being a CA gets you is ... in > everyone's default trust stores. > > The system property javax.net.ssl.trustStore only sets the default > trust store for the JVM and any components which choose to use it. For > example, if you use HttpURLConnection without any explicit > configuration, it will use that. Same with Apache httpclient. > > But both of those can be configured to use a different trust store, > which case they will *not* fall-back to the built-in trust store (the > one in JAVA_HOME/lib/security/cacerts. > > Well I see couple of issues with this approach of the trsutstore being the only source of truth. First is the obvious one, when using a custom trust store I have to load *all* CA certificates that already exist somewhere else on the server (and in multiple places) in the trust store too otherwise no certificate will ever get validated. > When overriding the default trust store for the JVM, the trust store > you specify should be the ONLY trust store consulted. It should not > fall back. I can confirm this is the case on Java 8 - 11, at least the > ones I happen to be using. Any other behavior would be a security proble > m. > > Not sure I can agree with this reasoning too. All apps on the server use the default system CA store so should we consider them insecure? I see no harm of Java looking in the default location(s) on the server when a cert can not be validated by looking in the trust store. Otherwise as noted above in case of custom trust store we need to load all those certificates anyway ending up with same certificates stored in multiple places, making the size of the trust store unnecessary big. > The proper way to validate a certificate chain is to perform the > following algorithm: > > 0. Start with the server's certificate (the leaf) > 1. Is the certificate in the trust store? > Yes: chain is valid; stop > 2. Is the certificate signed by a cert in the trust store? > Yes: chain is valid; stop > 3. Is the certificate signed by the next cert in the chain? > No: chain is invalid; stop > 4. Move to the next cert in the chain > 5. Go to step 1 > > So if you use an empty trust store and try to connect to > https://www.google.com, you should find that you get an exception > thrown. Something like this: > > Exception in thread "main" javax.net.ssl.SSLHandshakeException: > sun.security.validator.ValidatorException: PKIX path building failed: > sun.security.provider.certpath.SunCertPathBuilderException: unable to > find valid certification path to requested target > > To conclude, the way I would expect the trust store to be used and the whole validation done: 1. I use custom trust store because I need to load self signed certificates that I need to validate when connecting to lets say partner APIs that use self signed certificates and I know I can trust 2. I would expect nothing else needed in this store as every other valid certificate under the sun is already located in default locations on the server Java is running on 3. In case JAVA_HOME/lib/security/cacerts is my trust store (the default) I would expect Java to use the system store(s) too in case a certificate can not be validated simply because a CA is missing in the Java store. Example, DigiCert Global Root G2 CA is missing in the Java versions older than 8u91 causing inexplicable PKIX exceptions but can be found in the system store, both under /etc/ssl/certs and /usr/share/ca-certificates which are (much) more frequently updated with new certs than Java versions. This actually applies to the case of custom trust store even more so Thoughts? Cheers, Igor - -chris > -----BEGIN PGP SIGNATURE----- > Comment: Using GnuPG with Thunderbird - https://www.enigmail.net/ > > iQIzBAEBCAAdFiEEMmKgYcQvxMe7tcJcHPApP6U8pFgFAlvIo24ACgkQHPApP6U8 > pFgJSBAAw/Q8vRyj5w4cB0cBx8EeNpBamr89jVvNQj5jHeuXOn6htATILjCQZpm9 > FL1Ikn5lxkWvMn1Ru+x7br3F3cxTdkVvRWXH4KcksVh6KkPGcp0PEogl7sscjf4X > pSpnYocNKiCBfnlXG3bJV2u4VS4J9m9pXAh9proxnBxY1fg5NgtUp+uq4kF4q1z+ > uopesloM9RdKoLREJVjXsZemBXQyF3tKGziOb0+u3Meq1eG+N+P+gSZr7AsQndCx > KQmdlKK5NyD8NhrCi8EGfGR8992JgrsvOG43gPokqfzOJ0IHXZs6vrCU8yrl7KVX > RcKtc+mBI+8biAW+41ut5cPIqM5p7h9ZMCn9KH7vLz26HuFeQYhhE+WOQ8QRt07A > QiNL2uqIbBG1wVaBzmB664wu0ifbWdUfzVq39T56Rzd9HUFDn26GaO7+IO4kfdpt > UdklRvf+Ldw/SCuXYtTI7nArrhfCFN0ALUVBkY81hUcdKNXdWrE7DEp0KLm7LD61 > aFl3M/HWNSSJnGvgyT5OJ1Q1Z8wVaisccPe9vBDJ6EmE9u868uPkquY6I6jnsC1X > 4Q9wGzf3OsPYQ0vzSNhN1At8kMHj6C/5RRTVAUIXW1M3FE9YiiELy25CWOdaF95f > aFNRSoiEHzRTWcAVh8M5KXb0G3rtq8b6WjWgMCPJ5Kh33uRShWM= > =g3kh > -----END PGP SIGNATURE----- > > --------------------------------------------------------------------- > To unsubscribe, e-mail: users-unsubscr...@tomcat.apache.org > For additional commands, e-mail: users-h...@tomcat.apache.org > >