Skip to content

Commit 272e3a3

Browse files
committed
handshake: read single message with bounded Read instead of io.ReadAll
io.ReadAll blocks until the stream is closed (EOF). For relay-based connections FIN may not propagate to the receiver, causing every inbound handshake to time out after handshakeRecvTimeout (10 s) instead of processing immediately. Since the handshake protocol is exactly one JSON message per connection, a single stream.Read(buf) is sufficient and returns as soon as the bytes land.
1 parent 0ba7677 commit 272e3a3

2 files changed

Lines changed: 15 additions & 5 deletions

File tree

plugins/handshake/handshake.go

Lines changed: 13 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,6 @@ import (
77
"encoding/base64"
88
"encoding/json"
99
"fmt"
10-
"io"
1110
"log/slog"
1211
"os"
1312
"path/filepath"
@@ -385,15 +384,26 @@ func (hm *Manager) Start() error {
385384
}
386385

387386
// handleConnection processes a single handshake stream connection.
387+
//
388+
// The handshake protocol is exactly one JSON message per connection; we do a
389+
// single bounded Read rather than io.ReadAll so we return as soon as the
390+
// message bytes land, without waiting for the sender to close the stream.
388391
func (hm *Manager) handleConnection(stream coreapi.Stream) {
392+
const maxMsgSize = 64 * 1024
393+
389394
type readResult struct {
390395
data []byte
391396
err error
392397
}
393398
ch := make(chan readResult, 1)
394399
go func() {
395-
data, err := io.ReadAll(stream)
396-
ch <- readResult{data, err}
400+
buf := make([]byte, maxMsgSize)
401+
n, err := stream.Read(buf)
402+
if err != nil {
403+
ch <- readResult{nil, err}
404+
return
405+
}
406+
ch <- readResult{buf[:n], nil}
397407
}()
398408
select {
399409
case res := <-ch:

plugins/handshake/zz_handshake_connection_parse_test.go

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -55,8 +55,8 @@ func TestHandleConnectionClosedRecvBufReturnsCleanly(t *testing.T) {
5555
hm := newTestHM(t, "")
5656
t.Cleanup(hm.Stop)
5757

58-
// An EOF stream (closed RecvBuf equivalent) causes io.ReadAllempty
59-
// data + nil error → JSON unmarshal error → handleConnection returns.
58+
// An EOF stream (closed RecvBuf equivalent) causes Read(0, io.EOF)
59+
// → handleConnection returns on the read-error path.
6060
stream := newMockStreamErr(io.EOF)
6161

6262
done := make(chan struct{})

0 commit comments

Comments
 (0)