Skip to content

Commit

Permalink
Flight3: respect curves configuration
Browse files Browse the repository at this point in the history
Reuse logic from Flight1 to ensure correct behaviour.

Signed-off-by: Vladislav Yarmak <vladislav-ex-src@vm-0.com>
  • Loading branch information
Snawoot authored and Sean-Der committed Jun 12, 2024
1 parent 61b3466 commit a5d1fac
Show file tree
Hide file tree
Showing 2 changed files with 111 additions and 1 deletion.
3 changes: 2 additions & 1 deletion flight3handler.go
Original file line number Diff line number Diff line change
Expand Up @@ -249,10 +249,11 @@ func flight3Generate(_ flightConn, state *State, _ *handshakeCache, cfg *handsha
RenegotiatedConnection: 0,
},
}

if state.namedCurve != 0 {
extensions = append(extensions, []extension.Extension{
&extension.SupportedEllipticCurves{
EllipticCurves: []elliptic.Curve{elliptic.X25519, elliptic.P256, elliptic.P384},
EllipticCurves: cfg.ellipticCurves,
},
&extension.SupportedPointFormats{
PointFormats: []elliptic.CurvePointFormat{elliptic.CurvePointFormatUncompressed},
Expand Down
109 changes: 109 additions & 0 deletions flight3handler_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,109 @@
// SPDX-FileCopyrightText: 2023 The Pion community <https://pion.ly>
// SPDX-License-Identifier: MIT

package dtls

import (
"context"
"math/rand"
"testing"
"time"

"github.com/pion/dtls/v2/pkg/crypto/elliptic"
dtlsnet "github.com/pion/dtls/v2/pkg/net"
"github.com/pion/dtls/v2/pkg/protocol/extension"
"github.com/pion/dtls/v2/pkg/protocol/handshake"
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
"github.com/pion/transport/v3/dpipe"
"github.com/pion/transport/v3/test"
)

// Assert that SupportedEllipticCurves is only sent when a ECC CipherSuite is available
func TestSupportedEllipticCurves(t *testing.T) {
// Limit runtime in case of deadlocks
lim := test.TimeOut(time.Second * 20)
defer lim.Stop()

// Check for leaking routines
report := test.CheckRoutines(t)
defer report()

ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()

expectedCurves := defaultCurves
var actualCurves []elliptic.Curve

rand.Shuffle(len(expectedCurves), func(i, j int) {
expectedCurves[i], expectedCurves[j] = expectedCurves[j], expectedCurves[i]
})

clientErr := make(chan error, 1)
ca, cb := dpipe.Pipe()
caAnalyzer := &connWithCallback{Conn: ca}
caAnalyzer.onWrite = func(in []byte) {
messages, err := recordlayer.UnpackDatagram(in)
if err != nil {
t.Fatal(err)
}

for i := range messages {
h := &handshake.Handshake{}
_ = h.Unmarshal(messages[i][recordlayer.FixedHeaderSize:])

if h.Header.Type == handshake.TypeClientHello {
clientHello := &handshake.MessageClientHello{}
msg, err := h.Message.Marshal()

if err != nil {
t.Fatal(err)
} else if err = clientHello.Unmarshal(msg); err != nil {
t.Fatal(err)
}

for _, e := range clientHello.Extensions {
if e.TypeValue() == extension.SupportedEllipticCurvesTypeValue {
if c, ok := e.(*extension.SupportedEllipticCurves); ok {
actualCurves = c.EllipticCurves
}
}
}
}
}
}

go func() {
conf := &Config{
CipherSuites: []CipherSuiteID{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
EllipticCurves: expectedCurves,
}

if client, err := testClient(ctx, dtlsnet.PacketConnFromConn(caAnalyzer), caAnalyzer.RemoteAddr(), conf, false); err != nil {
clientErr <- err
} else {
clientErr <- client.Close() //nolint
}
}()

config := &Config{
CipherSuites: []CipherSuiteID{TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256},
}

if server, err := testServer(ctx, dtlsnet.PacketConnFromConn(cb), cb.RemoteAddr(), config, true); err != nil {
t.Fatalf("Server error %v", err)
} else {
if err = server.Close(); err != nil {
t.Fatal(err)
}
}

if err := <-clientErr; err != nil {
t.Fatalf("Client error %v", err)
}

for i := range expectedCurves {
if expectedCurves[i] != actualCurves[i] {
t.Fatal("List of curves in SupportedEllipticCurves does not match config")
}
}
}

0 comments on commit a5d1fac

Please sign in to comment.