Description
First of all, I want to say, I have found a bug in version 2.0.19, which is no problem in version 2.0.16. Comparing the org.apache.mina.filter.ssl.SslHandle.java betwen two version, in the unwrap() method, handshakeStatus is a temporary variable in version 2.0.16, and this temporary variable is changed to a member variable in 2.0.19.
The problem is that when the session is established, if the server immediately sends a message, the handshakeStatus will remain in the NOT_HANDSHAKING state at this time, and will never go to FINISHED.
//2.0.19 has a bug private SSLEngineResult unwrap() throws SSLException { *** SSLEngineResult res; Status status; do { *** handshakeStatus = res.getHandshakeStatus(); *** }
//2.0.16 is ok private SSLEngineResult unwrap() throws SSLException { *** SSLEngineResult res; Status status; HandshakeStatus handshakeStatus = null; do { *** handshakeStatus = res.getHandshakeStatus(); *** }
The following is my positioning process, please refer to.
1. In the handshake method of SslHandler.java, add a sentence to print.
//2.0.19 /void handshake(NextFilter nextFilter) throws SSLException { for (;;) { switch (handshakeStatus) { System.out.println(handshakeStatus); case FINISHED:
When creating an ssl connection, the 2.0.19 print sequence is as follows: NOT_HANDSHAKING
NEED_UNWRAP
NEED_UNWRAP
NEED_TASK
NEED_WRAP
NEED_WRAP
NEED_WRAP
NEED_UNWRAP
NEED_UNWRAP
NEED_UNWRAP
NEED_UNWRAP
NOT_HANDSHAKING
NOT_HANDSHAKING
And 2.0.16 can be ended correctly.
NEED_WRAP
NEED_UNWRAP
NEED_UNWRAP
NEED_TASK
NEED_WRAP
NEED_WRAP
NEED_WRAP
NEED_UNWRAP
NEED_UNWRAP
NEED_UNWRAP
NEED_UNWRAP
FINISHED
2. We can find thar there is a problem in the last NEED_UNWRAP. By debugging the code in 2.0.16 and 2.0.19 respectively, When the unwrapHandshake method is tracked , the handshakeStatus variable is changed after the unwrap() method. However, when viewing the unwrap() method, there is no reassignment of the variables to the handshakeStatus, so I guess the reference address was changed. By printing the memory address of the handshakeStatus, it was found that the change did occur. As for where to change, I didn't understand at the moment, so I compared the modification points of the SslHandler.java files in 2.0.16 and 2.0.19 , then found that the temporary variable in 2.0.19 was wrongly changed to member variable ,maybe due to the name is same.
//2.0.19 private SSLEngineResult.Status unwrapHandshake(NextFilter nextFilter) throws SSLException { *** // If handshake finished, no data was produced, and the status is still // ok, try to unwrap more if ((handshakeStatus == SSLEngineResult.HandshakeStatus.FINISHED) && (res.getStatus() == SSLEngineResult.Status.OK) && inNetBuffer.hasRemaining()) { res = unwrap(); ***
3. Try to change handshakeStatus to a temporary variable, I found that the problem was fixed.
//2.0.19 private SSLEngineResult unwrap() throws SSLException { *** SSLEngineResult res; Status status; HandshakeStatus handshakeStatus = null; do { *** handshakeStatus = res.getHandshakeStatus(); *** }
Therefore, please help to track down the problem and solve it as soon as possible. This problem is conditional appearance, thank you.