NullPointerException at org.bouncycastle.crypto.signers.PSSSigner.generateSignature on Tomcat server. ERR_SSL_PROTOCOL_ERROR on chrome

Viewed 5219

Tomcat server starts successfully. But as soon as it hits https://localhost:8443, I see repeated error on server (logs below). On chrome browser I see This site can’t provide a secure connection, localhost sent an invalid response ERR_SSL_PROTOCOL_ERROR. Some how I managed to run localhost in safari but chrome still has issue. Any help would be appreciated. Thanks

SEVERE [https-jsse-nio-8443-exec-7] org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun 
    java.lang.NullPointerException
        at org.bouncycastle.crypto.signers.PSSSigner.generateSignature(Unknown Source)
        at org.bouncycastle.jcajce.provider.asymmetric.rsa.PSSSignatureSpi.engineSign(Unknown Source)
        at java.security.Signature$Delegate.engineSign(Signature.java:1382)
        at java.security.Signature.sign(Signature.java:698)
        at sun.security.ssl.CertificateVerify$T13CertificateVerifyMessage.<init>(CertificateVerify.java:931)
        at sun.security.ssl.CertificateVerify$T13CertificateVerifyProducer.onProduceCertificateVerify(CertificateVerify.java:1105)
        at sun.security.ssl.CertificateVerify$T13CertificateVerifyProducer.produce(CertificateVerify.java:1098)
        at sun.security.ssl.SSLHandshake.produce(SSLHandshake.java:420)
        at sun.security.ssl.ClientHello$T13ClientHelloConsumer.goServerHello(ClientHello.java:1096)
        at sun.security.ssl.ClientHello$T13ClientHelloConsumer.consume(ClientHello.java:1032)
        at sun.security.ssl.ClientHello$ClientHelloConsumer.onClientHello(ClientHello.java:716)
        at sun.security.ssl.ClientHello$ClientHelloConsumer.consume(ClientHello.java:683)
        at sun.security.ssl.SSLHandshake.consume(SSLHandshake.java:376)
        at sun.security.ssl.HandshakeContext.dispatch(HandshakeContext.java:444)
        at sun.security.ssl.SSLEngineImpl$DelegatedTask$DelegatedAction.run(SSLEngineImpl.java:983)
        at sun.security.ssl.SSLEngineImpl$DelegatedTask$DelegatedAction.run(SSLEngineImpl.java:970)
        at java.security.AccessController.doPrivileged(Native Method)
        at sun.security.ssl.SSLEngineImpl$DelegatedTask.run(SSLEngineImpl.java:917)
        at org.apache.tomcat.util.net.SecureNioChannel.tasks(SecureNioChannel.java:423)
        at org.apache.tomcat.util.net.SecureNioChannel.handshakeUnwrap(SecureNioChannel.java:483)
        at org.apache.tomcat.util.net.SecureNioChannel.handshake(SecureNioChannel.java:238)
        at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1475)
        at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
        at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
        at java.lang.Thread.run(Thread.java:748)
3 Answers

I came accross this issue when updating to openjdk-1.8.0_275 . Disabling "RSASSA-PSS" in java.security resolved the problem for me.

Open ${JAVA_HOME}/jre/lib/security/java.security and find jdk.certpath.disabledAlgorithms add RSASSA-PSS to the end of the list:

jdk.tls.disabledAlgorithms=SSLv3, RC4, DES, MD5withRSA, DH keySize < 1024, \
EC keySize < 224, 3DES_EDE_CBC, anon, NULL, RSASSA-PSS

I've also seen other people having to disable TLS1.3 in tomcat but I didn't need to.

note: This should be a temporary work around. Supporting and using TLSv1.3 is the ideal scenario - for me that's not possible right now due to restrictions from my client.

It is an unfortunate mix of events. In my case, I upgraded JDK to 1.8.0_282 because I wanted to start working with TLS v1.3 in Tomcat, and it depends on the underlying Java Runtime to be able to work.

So everything pointed at JDK, but the exception is thrown at a Bouncy Castle component which is not part of JDK. Some Tomcat implementations (my case: TomEE 8.0.1) include a Bouncy Castle library within (version 1.63).

It turns out that when Java invokes the verification of the signature of the certificate, the implementation that covers the best algorithm appears to be from the Bouncy Castle implementation, and it had a bug in earlier versions (up to 1.64) by which the NullPointerException is thrown after receiving a null value from a randomizer.

As pointed out in Carles Barrobès reference Bouncy Castle Tracker, the issue was found and fixed after version 1.65.

So you have to find the Bouncy Castle jar in your Tomcat lib directory (named bcprov-jdk15on-1.63.jar in my case - look for a similar file name with probably a different version) and substitute it with a new one from Bouncy Castle web site (bcprov-jdk15to18-168.jar at the moment of this writing).

Note: Use the "-jdk15to18-" file instead of the "-jdk15on-" since the latter was designed for newer versions of JDK (post 1.8) and the whole problem is precisely with JDK 1.8.

Related