Sure Xuelei. Filed 9067508 for the client issue, and 9067509 for the server one. Thanks! Daniel
sob., 31 paź 2020 o 17:23 Xue-Lei Fan <xuelei....@oracle.com> napisał(a): > Hi Daniel, > > Would you mind file a bug for the tracking? > > Xuelei > > On Oct 31, 2020, at 5:45 AM, Daniel Jeliński <djelins...@gmail.com> wrote: > > Verified that this behavior is still observed with JDK 16 EA 22. > > Client side code responsible for server certificate validation is located > in EndEntityChecker.checkTLSServer [1]. That code is not executed when the > certificate is trusted [2]. I believe this is a bug - I wouldn't choose to > accept a server certificate when that certificate was only meant for > signing other certificates, for example. > > Server side code responsible for cipher selection may need some > refactoring; currently the server selects the first cipher that passes > validation checks and for which keyManager.chooseServerAlias(keyType,...) > returns a key. The key manager does not have information about the intended > key usage (keyType is "EC" for both ECDH and ECDSA, and we don't know which > cipher is being checked), so it returns the same certificate when querying > for ECDH and ECDSA. > > Fortunately ECDH is not popular, and most clients won't even try to > negotiate it. Still, I believe this is a bug that should be addressed. > > As far as I could tell, there were no bugs reported for this in the bug > system. Should I report them there? > > If someone is interested in the server code, here's the interesting > portion of stack trace: > > chooseServerAlias:260, SunX509KeyManagerImpl (sun.security.ssl) > createServerPossession:288, X509Authentication$X509PossessionGenerator > (sun.security.ssl) > createPossession:214, X509Authentication$X509PossessionGenerator > (sun.security.ssl) > createPossession:90, X509Authentication (sun.security.ssl) > createPossessions:51, SSLKeyExchange (sun.security.ssl) > chooseCipherSuite:443, ServerHello$T12ServerHelloProducer (sun.security.ssl) > > > [1] > http://hg.openjdk.java.net/jdk/jdk/file/ee1d592a9f53/src/java.base/share/classes/sun/security/validator/EndEntityChecker.java#l276 > [2] > http://hg.openjdk.java.net/jdk/jdk/file/ee1d592a9f53/src/java.base/share/classes/sun/security/validator/Validator.java#l267 > > wt., 27 paź 2020 o 18:44 Daniel Jeliński <djelins...@gmail.com> > napisał(a): > >> Hi all, >> >> TL;DR: both SSL server and client ignore KeyUsage certificate extension >> when determining the list of available cipher suites. They shouldn't; >> KeyUsage is the only differentiator between ECDH and ECDSA certificates. >> >> Long version: >> I'm experimenting with ECC certificates on my Jetty server; when I >> created an ECC certificate and tested the server with nmap, I found that >> both ECDSA and ECDH cipher suites are enabled. I don't want ECDH ciphers, >> but I don't want to add explicit excludes either. >> >> Reading into NIST recommendations [1] I found that ECDSA certificates >> should define KeyUsage extension with value digitalSignature, vs ECDH which >> should use keyAgreement value. >> I experimented with both combinations of KeyValue, both resulted in the >> same set of ciphers being offered by the server. The client doesn't seem to >> care about KeyUsage either - it accepts connections even when the selected >> cipher doesn't match KeyUsage. >> >> Chrome browser doesn't support ECDH ciphers, but it does support ECDSA. >> When connecting to a Java server using ECDH certificate, it displays the >> error "ERR_SSL_KEY_USAGE_INCOMPATIBLE"; the server offers an ECDSA >> cipher suite, which is rejected by the browser. >> >> The issue was already reported by Bernd Eckenfels here [2], but as far as >> I can tell, it is not addressed yet; I was able to reproduce it using >> slightly modified code of this gist [3]. Certificates were generated using >> keytool commands: >> >> ECDSA: >> keytool -genkeypair -alias ec -keyalg EC -keysize 256 -sigalg >> SHA256withECDSA -validity 365 -dname >> "CN=localhost,OU=Unknown,O=Unknown,L=Unknown,S=Unknown,C=Unknown" >> -storetype JKS -keystore ectest.jks -storepass 123456 -ext >> KeyUsage:c=digitalSignature,keyCertSign >> >> ECDH: >> keytool -genkeypair -alias ec -keyalg EC -keysize 256 -sigalg >> SHA256withECDSA -validity 365 -dname >> "CN=localhost,OU=Unknown,O=Unknown,L=Unknown,S=Unknown,C=Unknown" >> -storetype JKS -keystore ectest.jks -storepass 123456 -ext >> KeyUsage:c=keyAgreement,keyCertSign >> >> I'm not sure if keyCertSign is required on self-signed certificates, >> added it just in case. >> >> Tested on OpenJDK 11.0.6. >> >> Regards, >> Daniel Jeliński >> >> >> [1] >> https://nvlpubs.nist.gov/nistpubs/SpecialPublications/NIST.SP.800-52r2.pdf >> [2] >> http://mail.openjdk.java.net/pipermail/security-dev/2017-May/015902.html >> [3] https://gist.github.com/djelinski/b4543a3eb7ea66306044c08b41bba00f >> > >