|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
|
|
package sun.security.ssl; |
|
|
|
import java.io.IOException; |
|
import java.nio.ByteBuffer; |
|
import sun.security.ssl.SSLHandshake.HandshakeMessage; |
|
|
|
|
|
|
|
*/ |
|
final class HelloRequest { |
|
static final SSLProducer kickstartProducer = |
|
new HelloRequestKickstartProducer(); |
|
|
|
static final SSLConsumer handshakeConsumer = |
|
new HelloRequestConsumer(); |
|
static final HandshakeProducer handshakeProducer = |
|
new HelloRequestProducer(); |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
static final class HelloRequestMessage extends HandshakeMessage { |
|
HelloRequestMessage(HandshakeContext handshakeContext) { |
|
super(handshakeContext); |
|
} |
|
|
|
HelloRequestMessage(HandshakeContext handshakeContext, |
|
ByteBuffer m) throws IOException { |
|
super(handshakeContext); |
|
if (m.hasRemaining()) { |
|
handshakeContext.conContext.fatal(Alert.ILLEGAL_PARAMETER, |
|
"Error parsing HelloRequest message: not empty"); |
|
} |
|
} |
|
|
|
@Override |
|
public SSLHandshake handshakeType() { |
|
return SSLHandshake.HELLO_REQUEST; |
|
} |
|
|
|
@Override |
|
public int messageLength() { |
|
return 0; |
|
} |
|
|
|
@Override |
|
public void send(HandshakeOutStream s) throws IOException { |
|
// empty, nothing to send |
|
} |
|
|
|
@Override |
|
public String toString() { |
|
return "<empty>"; |
|
} |
|
} |
|
|
|
|
|
|
|
*/ |
|
private static final |
|
class HelloRequestKickstartProducer implements SSLProducer { |
|
|
|
private HelloRequestKickstartProducer() { |
|
// blank |
|
} |
|
|
|
@Override |
|
public byte[] produce(ConnectionContext context) throws IOException { |
|
|
|
ServerHandshakeContext shc = (ServerHandshakeContext)context; |
|
|
|
HelloRequestMessage hrm = new HelloRequestMessage(shc); |
|
if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { |
|
SSLLogger.fine("Produced HelloRequest handshake message", hrm); |
|
} |
|
|
|
|
|
hrm.write(shc.handshakeOutput); |
|
shc.handshakeOutput.flush(); |
|
|
|
// update the context |
|
|
|
|
|
shc.handshakeConsumers.put( |
|
SSLHandshake.CLIENT_HELLO.id, SSLHandshake.CLIENT_HELLO); |
|
|
|
|
|
return null; |
|
} |
|
} |
|
|
|
|
|
|
|
*/ |
|
private static final class HelloRequestProducer |
|
implements HandshakeProducer { |
|
|
|
private HelloRequestProducer() { |
|
// blank |
|
} |
|
|
|
@Override |
|
public byte[] produce(ConnectionContext context, |
|
HandshakeMessage message) throws IOException { |
|
|
|
ServerHandshakeContext shc = (ServerHandshakeContext)context; |
|
|
|
HelloRequestMessage hrm = new HelloRequestMessage(shc); |
|
if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { |
|
SSLLogger.fine("Produced HelloRequest handshake message", hrm); |
|
} |
|
|
|
|
|
hrm.write(shc.handshakeOutput); |
|
shc.handshakeOutput.flush(); |
|
|
|
// update the context |
|
|
|
|
|
shc.handshakeConsumers.put( |
|
SSLHandshake.CLIENT_HELLO.id, SSLHandshake.CLIENT_HELLO); |
|
|
|
|
|
return null; |
|
} |
|
} |
|
|
|
|
|
|
|
*/ |
|
private static final class HelloRequestConsumer |
|
implements SSLConsumer { |
|
|
|
|
|
private HelloRequestConsumer() { |
|
// blank |
|
} |
|
|
|
@Override |
|
public void consume(ConnectionContext context, |
|
ByteBuffer message) throws IOException { |
|
|
|
ClientHandshakeContext chc = (ClientHandshakeContext)context; |
|
|
|
// For TLS 1.2 and prior versions, the HelloRequest message MAY |
|
// be sent by the server at any time. Please don't clean up this |
|
|
|
HelloRequestMessage hrm = new HelloRequestMessage(chc, message); |
|
if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { |
|
SSLLogger.fine( |
|
"Consuming HelloRequest handshake message", hrm); |
|
} |
|
|
|
if (!chc.kickstartMessageDelivered) { |
|
if (!chc.conContext.secureRenegotiation && |
|
!HandshakeContext.allowUnsafeRenegotiation) { |
|
chc.conContext.fatal(Alert.HANDSHAKE_FAILURE, |
|
"Unsafe renegotiation is not allowed"); |
|
} |
|
|
|
if (!chc.conContext.secureRenegotiation) { |
|
if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { |
|
SSLLogger.warning( |
|
"Continue with insecure renegotiation"); |
|
} |
|
} |
|
|
|
|
|
chc.handshakeProducers.put( |
|
SSLHandshake.CLIENT_HELLO.id, |
|
SSLHandshake.CLIENT_HELLO); |
|
|
|
// |
|
// produce response handshake message |
|
|
|
SSLHandshake.CLIENT_HELLO.produce(context, hrm); |
|
} else { |
|
if (SSLLogger.isOn && SSLLogger.isOn("ssl,handshake")) { |
|
SSLLogger.fine( |
|
"Ingore HelloRequest, handshaking is in progress"); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|