Skip to content

Commit fe3a675

Browse files
taosodaenney
authored andcommitted
Make sure clean the stored session
We need to delete the stored session when any fatal errors occurs. This operation should be taken in the Conn.notify function.
1 parent 04c1634 commit fe3a675

8 files changed

Lines changed: 28 additions & 30 deletions

File tree

conn.go

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -676,14 +676,6 @@ func (c *Conn) handleIncomingPacket(buf []byte, enqueue bool) (bool, *alert.Aler
676676
var err error
677677
buf, err = c.state.cipherSuite.Decrypt(buf)
678678
if err != nil {
679-
if len(c.state.SessionID) > 0 {
680-
// According to the RFC, we need to delete the stored session.
681-
// https://datatracker.ietf.org/doc/html/rfc5246#section-7.2
682-
if delErr := c.fsm.cfg.sessionStore.Del(c.state.SessionID); delErr != nil {
683-
return false, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, delErr
684-
}
685-
return false, &alert.Alert{Level: alert.Fatal, Description: alert.DecryptError}, err
686-
}
687679
c.log.Debugf("%s: decrypt failed: %s", srvCliStr(c.state.isClient), err)
688680
return false, nil, nil
689681
}
@@ -764,6 +756,16 @@ func (c *Conn) recvHandshake() <-chan chan struct{} {
764756
}
765757

766758
func (c *Conn) notify(ctx context.Context, level alert.Level, desc alert.Description) error {
759+
if level == alert.Fatal && len(c.state.SessionID) > 0 {
760+
// According to the RFC, we need to delete the stored session.
761+
// https://datatracker.ietf.org/doc/html/rfc5246#section-7.2
762+
if ss := c.fsm.cfg.sessionStore; ss != nil {
763+
c.log.Tracef("clean invalid session: %s", c.state.SessionID)
764+
if err := ss.Del(c.sessionKey()); err != nil {
765+
return err
766+
}
767+
}
768+
}
767769
return c.writePackets(ctx, []*packet{
768770
{
769771
record: &recordlayer.RecordLayer{
@@ -960,6 +962,16 @@ func (c *Conn) RemoteAddr() net.Addr {
960962
return c.nextConn.RemoteAddr()
961963
}
962964

965+
func (c *Conn) sessionKey() []byte {
966+
if c.state.isClient {
967+
// As ServerName can be like 0.example.com, it's better to add
968+
// delimiter character which is not allowed to be in
969+
// neither address or domain name.
970+
return []byte(c.nextConn.RemoteAddr().String() + "_" + c.fsm.cfg.serverName)
971+
}
972+
return c.state.SessionID
973+
}
974+
963975
// SetDeadline implements net.Conn.SetDeadline
964976
func (c *Conn) SetDeadline(t time.Time) error {
965977
c.readDeadline.Set(t)

conn_test.go

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2153,7 +2153,7 @@ func TestSessionResume(t *testing.T) {
21532153
report := test.CheckRoutines(t)
21542154
defer report()
21552155

2156-
t.Run("session resumption old", func(t *testing.T) {
2156+
t.Run("resumed", func(t *testing.T) {
21572157
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
21582158
defer cancel()
21592159

@@ -2173,7 +2173,7 @@ func TestSessionResume(t *testing.T) {
21732173
ca, cb := dpipe.Pipe()
21742174

21752175
_ = ss.Set(id, s)
2176-
_ = ss.Set([]byte(ca.RemoteAddr().String()+"example.com"), s)
2176+
_ = ss.Set([]byte(ca.RemoteAddr().String()+"_example.com"), s)
21772177

21782178
go func() {
21792179
config := &Config{
@@ -2217,7 +2217,7 @@ func TestSessionResume(t *testing.T) {
22172217
_ = res.c.Close()
22182218
})
22192219

2220-
t.Run("session resumption new", func(t *testing.T) {
2220+
t.Run("new session", func(t *testing.T) {
22212221
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
22222222
defer cancel()
22232223

@@ -2263,7 +2263,7 @@ func TestSessionResume(t *testing.T) {
22632263
if res.err != nil {
22642264
t.Fatal(res.err)
22652265
}
2266-
cs, _ := s1.Get([]byte(ca.RemoteAddr().String() + "example.com"))
2266+
cs, _ := s1.Get([]byte(ca.RemoteAddr().String() + "_example.com"))
22672267
if !bytes.Equal(actualMasterSecret, cs.Secret) {
22682268
t.Errorf("TestSessionResumetion: masterSecret Mismatch: expected(%v) actual(%v)", ss.Secret, actualMasterSecret)
22692269
}

flight1handler.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -92,8 +92,7 @@ func flight1Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
9292

9393
if cfg.sessionStore != nil {
9494
cfg.log.Tracef("[handshake] try to resume session")
95-
key := []byte(c.RemoteAddr().String() + cfg.serverName)
96-
if s, err := cfg.sessionStore.Get(key); err != nil {
95+
if s, err := cfg.sessionStore.Get(c.sessionKey()); err != nil {
9796
return nil, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
9897
} else if s.ID != nil {
9998
cfg.log.Tracef("[handshake] get saved session: %x", s.ID)

flight3handler.go

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -171,11 +171,6 @@ func handleResumption(ctx context.Context, c flightConn, state *State, cache *ha
171171
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
172172
}
173173
if !bytes.Equal(expectedVerifyData, finished.VerifyData) {
174-
cfg.log.Tracef("[handshake] clean invalid session: %s", state.SessionID)
175-
if err := cfg.sessionStore.Del(state.SessionID); err != nil {
176-
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
177-
}
178-
179174
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, errVerifyDataMismatch
180175
}
181176

flight4bhandler.go

Lines changed: 0 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -34,11 +34,6 @@ func flight4bParse(ctx context.Context, c flightConn, state *State, cache *hands
3434

3535
expectedVerifyData, err := prf.VerifyDataClient(state.masterSecret, plainText, state.cipherSuite.HashFunc())
3636
if err != nil {
37-
cfg.log.Tracef("[handshake] clean invalid session: %s", state.SessionID)
38-
if delErr := cfg.sessionStore.Del(state.SessionID); delErr != nil {
39-
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, delErr
40-
}
41-
4237
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
4338
}
4439
if !bytes.Equal(expectedVerifyData, finished.VerifyData) {

flight5handler.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -54,8 +54,7 @@ func flight5Parse(ctx context.Context, c flightConn, state *State, cache *handsh
5454
Secret: state.masterSecret,
5555
}
5656
cfg.log.Tracef("[handshake] save new session: %x", s.ID)
57-
key := []byte(c.RemoteAddr().String() + cfg.serverName)
58-
if err := cfg.sessionStore.Set(key, s); err != nil {
57+
if err := cfg.sessionStore.Set(c.sessionKey(), s); err != nil {
5958
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
6059
}
6160
}

handshaker.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,6 @@ import (
66
"crypto/x509"
77
"fmt"
88
"io"
9-
"net"
109
"sync"
1110
"time"
1211

@@ -122,7 +121,7 @@ type flightConn interface {
122121
recvHandshake() <-chan chan struct{}
123122
setLocalEpoch(epoch uint16)
124123
handleQueuedPackets(context.Context) error
125-
RemoteAddr() net.Addr
124+
sessionKey() []byte
126125
}
127126

128127
func (c *handshakeConfig) writeKeyLog(label string, clientRandom, secret []byte) {

handshaker_test.go

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,7 +4,6 @@ import (
44
"bytes"
55
"context"
66
"crypto/tls"
7-
"net"
87
"sync"
98
"testing"
109
"time"
@@ -277,6 +276,6 @@ func (c *flightTestConn) handleQueuedPackets(ctx context.Context) error {
277276
return nil
278277
}
279278

280-
func (c *flightTestConn) RemoteAddr() net.Addr {
279+
func (c *flightTestConn) sessionKey() []byte {
281280
return nil
282281
}

0 commit comments

Comments
 (0)