restore the server's transport parameters from the session ticket

This commit is contained in:
Marten Seemann
2019-08-09 15:32:57 +07:00
parent 1f8a47af02
commit 44aa12850e
5 changed files with 124 additions and 41 deletions

View File

@@ -67,6 +67,7 @@ type cryptoSetup struct {
messageChan chan []byte
ourParams *TransportParameters
peerParams *TransportParameters
paramsChan <-chan []byte
runner handshakeRunner
@@ -77,8 +78,9 @@ type cryptoSetup struct {
// is closed when Close() is called
closeChan chan struct{}
zeroRTTParameters *TransportParameters
clientHelloWritten bool
clientHelloWrittenChan chan struct{}
clientHelloWrittenChan chan *TransportParameters
receivedWriteKey chan struct{}
receivedReadKey chan struct{}
@@ -131,7 +133,7 @@ func NewCryptoSetupClient(
enable0RTT bool,
rttStats *congestion.RTTStats,
logger utils.Logger,
) (CryptoSetup, <-chan struct{} /* ClientHello written */) {
) (CryptoSetup, <-chan *TransportParameters /* ClientHello written. Receive nil for non-0-RTT */) {
cs, clientHelloWritten := newCryptoSetup(
initialStream,
handshakeStream,
@@ -192,7 +194,7 @@ func newCryptoSetup(
rttStats *congestion.RTTStats,
logger utils.Logger,
perspective protocol.Perspective,
) (*cryptoSetup, <-chan struct{} /* ClientHello written */) {
) (*cryptoSetup, <-chan *TransportParameters /* ClientHello written. Receive nil for non-0-RTT */) {
initialSealer, initialOpener := NewInitialAEAD(connID, perspective)
extHandler := newExtensionHandler(tp.Marshal(), perspective)
cs := &cryptoSetup{
@@ -211,14 +213,14 @@ func newCryptoSetup(
perspective: perspective,
handshakeDone: make(chan struct{}),
alertChan: make(chan uint8),
clientHelloWrittenChan: make(chan struct{}),
clientHelloWrittenChan: make(chan *TransportParameters, 1),
messageChan: make(chan []byte, 100),
receivedReadKey: make(chan struct{}),
receivedWriteKey: make(chan struct{}),
writeRecord: make(chan struct{}, 1),
closeChan: make(chan struct{}),
}
qtlsConf := tlsConfigToQtlsConfig(tlsConf, cs, extHandler, cs.accept0RTT, enable0RTT)
qtlsConf := tlsConfigToQtlsConfig(tlsConf, cs, extHandler, cs.marshalPeerParamsForSessionState, cs.handlePeerParamsFromSessionState, cs.accept0RTT, enable0RTT)
cs.tlsConf = qtlsConf
return cs, cs.clientHelloWrittenChan
}
@@ -436,7 +438,22 @@ func (h *cryptoSetup) handleTransportParameters(data []byte) {
if err := tp.Unmarshal(data, h.perspective.Opposite()); err != nil {
h.runner.OnError(qerr.Error(qerr.TransportParameterError, err.Error()))
}
h.runner.OnReceivedParams(&tp)
h.peerParams = &tp
h.runner.OnReceivedParams(h.peerParams)
}
// must be called after receiving the transport parameters
func (h *cryptoSetup) marshalPeerParamsForSessionState() []byte {
return h.peerParams.MarshalForSessionTicket()
}
func (h *cryptoSetup) handlePeerParamsFromSessionState(data []byte) {
var tp TransportParameters
if err := tp.Unmarshal(data, protocol.PerspectiveServer); err != nil {
h.logger.Debugf("Restoring of transport parameters from session ticket failed: %s", err.Error())
return
}
h.zeroRTTParameters = &tp
}
// only valid for the server
@@ -569,7 +586,13 @@ func (h *cryptoSetup) WriteRecord(p []byte) (int, error) {
n, err := h.initialStream.Write(p)
if !h.clientHelloWritten && h.perspective == protocol.PerspectiveClient {
h.clientHelloWritten = true
close(h.clientHelloWrittenChan)
if h.zeroRTTSealer != nil && h.zeroRTTParameters != nil {
h.logger.Debugf("Doing 0-RTT.")
h.clientHelloWrittenChan <- h.zeroRTTParameters
} else {
h.logger.Debugf("Not doing 0-RTT. Has Sealer: %t, has params: %t", h.zeroRTTSealer != nil, h.zeroRTTParameters != nil)
h.clientHelloWrittenChan <- nil
}
} else {
// We need additional signaling to properly detect HelloRetryRequests.
// For servers: when the ServerHello is written.