diff --git a/common/ktls/ktls.go b/common/ktls/ktls.go index 22db2465..eb2e86cf 100644 --- a/common/ktls/ktls.go +++ b/common/ktls/ktls.go @@ -32,6 +32,7 @@ type Conn struct { readWaitOptions N.ReadWaitOptions kernelTx bool kernelRx bool + pendingRxSplice bool } func NewConn(ctx context.Context, logger logger.ContextLogger, conn aTLS.Conn, txOffload, rxOffload bool) (aTLS.Conn, error) { @@ -103,6 +104,7 @@ func (c *Conn) SyscallConnForRead() syscall.RawConn { func (c *Conn) HandleSyscallReadError(inputErr error) ([]byte, error) { if errors.Is(inputErr, unix.EINVAL) { + c.pendingRxSplice = true err := c.readRecord() if err != nil { return nil, E.Cause(err, "ktls: handle non-application-data record") diff --git a/common/ktls/ktls_linux.go b/common/ktls/ktls_linux.go index 313fe381..bc9fb8b9 100644 --- a/common/ktls/ktls_linux.go +++ b/common/ktls/ktls_linux.go @@ -258,14 +258,14 @@ func (c *Conn) readKernelRecord() (uint8, []byte, error) { var err error er := c.rawSyscallConn.Read(func(fd uintptr) bool { n, err = recvmsg(int(fd), &msg, 0) - return err != unix.EAGAIN + return err != unix.EAGAIN || c.pendingRxSplice }) if er != nil { return 0, nil, er } switch err { case nil: - case syscall.EINVAL: + case syscall.EINVAL, syscall.EAGAIN: return 0, nil, c.rawConn.In.SetErrorLocked(c.sendAlert(alertProtocolVersion)) case syscall.EMSGSIZE: return 0, nil, c.rawConn.In.SetErrorLocked(c.sendAlert(alertRecordOverflow)) @@ -276,7 +276,7 @@ func (c *Conn) readKernelRecord() (uint8, []byte, error) { } if n <= 0 { - return 0, nil, io.EOF + return 0, nil, c.rawConn.In.SetErrorLocked(io.EOF) } if cmsg.Level == unix.SOL_TLS && cmsg.Type == TLS_GET_RECORD_TYPE {