Add support for safe buffer

This commit is contained in:
世界 2022-05-27 19:41:26 +08:00
parent 6fa09df37d
commit c8403614f5
No known key found for this signature in database
GPG key ID: CD109927C34A63C4
10 changed files with 72 additions and 64 deletions

2
go.mod
View file

@ -3,7 +3,7 @@ module github.com/sagernet/sing-shadowsocks
go 1.18
require (
github.com/sagernet/sing v0.0.0-20220527064225-7abc98fdea29
github.com/sagernet/sing v0.0.0-20220528022605-7ba6439364fa
golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e
lukechampine.com/blake3 v1.1.7
)

4
go.sum
View file

@ -1,8 +1,8 @@
github.com/klauspost/cpuid/v2 v2.0.9/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
github.com/klauspost/cpuid/v2 v2.0.12 h1:p9dKCg8i4gmOxtv35DvrYoWqYzQrvEVdjQ762Y0OqZE=
github.com/klauspost/cpuid/v2 v2.0.12/go.mod h1:g2LTdtYhdyuGPqyWyv7qRAmj1WBqxuObKfj5c0PQa7c=
github.com/sagernet/sing v0.0.0-20220527064225-7abc98fdea29 h1:dOXoZvzUbNir2yxCP0Uj1+o7KY/5wtW/83ri8QAIGoQ=
github.com/sagernet/sing v0.0.0-20220527064225-7abc98fdea29/go.mod h1:w2HnJzXKHpD6F5Z/9XlSD4qbcpHY2RSZuQnFzqgELMg=
github.com/sagernet/sing v0.0.0-20220528022605-7ba6439364fa h1:h6VfxGy7dxiLn65xilHfETBYuA3UiS//iHCs0YZldnc=
github.com/sagernet/sing v0.0.0-20220528022605-7ba6439364fa/go.mod h1:w2HnJzXKHpD6F5Z/9XlSD4qbcpHY2RSZuQnFzqgELMg=
golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e h1:T8NU3HyQ8ClP4SEE+KbFlg6n0NhuTsN4MyznaarGsZM=
golang.org/x/crypto v0.0.0-20220525230936-793ad666bf5e/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a h1:dGzPydgVsqGcTRVwiLJ1jVbufYwmzD3LfVPLKsKg+0k=

10
none.go
View file

@ -5,7 +5,6 @@ import (
"io"
"net"
"net/netip"
"runtime"
"sync"
"github.com/sagernet/sing/common"
@ -126,6 +125,7 @@ func (c *nonePacketConn) ReadPacket(buffer *buf.Buffer) (M.Socksaddr, error) {
}
func (c *nonePacketConn) WritePacket(buffer *buf.Buffer, destination M.Socksaddr) error {
defer buffer.Release()
header := buf.With(buffer.ExtendHeader(M.SocksaddrSerializer.AddrPortLen(destination)))
err := M.SocksaddrSerializer.WriteAddrPort(header, destination)
if err != nil {
@ -151,9 +151,10 @@ func (c *nonePacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error) {
func (c *nonePacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) {
destination := M.SocksaddrFromNet(addr)
_buffer := buf.Make(M.SocksaddrSerializer.AddrPortLen(destination) + len(p))
defer runtime.KeepAlive(_buffer)
buffer := buf.With(common.Dup(_buffer))
_buffer := buf.StackNewSize(M.SocksaddrSerializer.AddrPortLen(destination) + len(p))
defer common.KeepAlive(_buffer)
buffer := common.Dup(_buffer)
defer buffer.Release()
err = M.SocksaddrSerializer.WriteAddrPort(buffer, destination)
if err != nil {
return
@ -210,6 +211,7 @@ func (s *nonePacketWriter) WritePacket(buffer *buf.Buffer, destination M.Socksad
header := buf.With(buffer.ExtendHeader(M.SocksaddrSerializer.AddrPortLen(destination)))
err := M.SocksaddrSerializer.WriteAddrPort(header, destination)
if err != nil {
buffer.Release()
return err
}
return s.PacketConn.WritePacket(buffer, s.sourceAddr)

View file

@ -7,7 +7,6 @@ import (
"crypto/sha1"
"io"
"net"
"runtime"
"github.com/sagernet/sing-shadowsocks"
"github.com/sagernet/sing/common"
@ -73,7 +72,7 @@ func Kdf(key, iv []byte, keyLength int) []byte {
info := []byte("ss-subkey")
subKey := buf.Make(keyLength)
kdf := hkdf.New(sha1.New, key, iv, common.Dup(info))
runtime.KeepAlive(info)
common.KeepAlive(info)
common.Must1(io.ReadFull(kdf, common.Dup(subKey)))
return subKey
}
@ -103,20 +102,20 @@ func (m *Method) KeyLength() int {
func (m *Method) ReadRequest(upstream io.Reader) (io.Reader, error) {
_salt := buf.Make(m.keySaltLength)
defer runtime.KeepAlive(_salt)
defer common.KeepAlive(_salt)
salt := common.Dup(_salt)
_, err := io.ReadFull(upstream, salt)
if err != nil {
return nil, E.Cause(err, "read salt")
}
key := Kdf(m.key, salt, m.keySaltLength)
defer runtime.KeepAlive(key)
defer common.KeepAlive(key)
return NewReader(upstream, m.constructor(common.Dup(key)), MaxPacketSize), nil
}
func (m *Method) WriteResponse(upstream io.Writer) (io.Writer, error) {
_salt := buf.Make(m.keySaltLength)
defer runtime.KeepAlive(_salt)
defer common.KeepAlive(_salt)
salt := common.Dup(_salt)
common.Must1(io.ReadFull(rand.Reader, salt))
_, err := upstream.Write(salt)
@ -151,7 +150,7 @@ func (m *Method) DialPacketConn(conn net.Conn) N.NetPacketConn {
func (m *Method) EncodePacket(buffer *buf.Buffer) error {
key := Kdf(m.key, buffer.To(m.keySaltLength), m.keySaltLength)
c := m.constructor(common.Dup(key))
runtime.KeepAlive(key)
common.KeepAlive(key)
c.Seal(buffer.Index(m.keySaltLength), rw.ZeroBytes[:c.NonceSize()], buffer.From(m.keySaltLength), nil)
buffer.Extend(Overhead)
return nil
@ -163,7 +162,7 @@ func (m *Method) DecodePacket(buffer *buf.Buffer) error {
}
key := Kdf(m.key, buffer.To(m.keySaltLength), m.keySaltLength)
c := m.constructor(common.Dup(key))
runtime.KeepAlive(key)
common.KeepAlive(key)
packet, err := c.Open(buffer.Index(m.keySaltLength), rw.ZeroBytes[:c.NonceSize()], buffer.From(m.keySaltLength), nil)
if err != nil {
return err
@ -182,18 +181,18 @@ type clientConn struct {
}
func (c *clientConn) writeRequest(payload []byte) error {
_salt := make([]byte, c.method.keySaltLength)
_salt := buf.Make(c.method.keySaltLength)
salt := common.Dup(_salt)
common.Must1(io.ReadFull(rand.Reader, salt))
key := Kdf(c.method.key, salt, c.method.keySaltLength)
runtime.KeepAlive(_salt)
common.KeepAlive(_salt)
writer := NewWriter(
c.Conn,
c.method.constructor(common.Dup(key)),
MaxPacketSize,
)
runtime.KeepAlive(key)
common.KeepAlive(key)
header := writer.Buffer()
header.Write(salt)
bufferedWriter := writer.BufferedWriter(header.Len())
@ -229,14 +228,14 @@ func (c *clientConn) readResponse() error {
return nil
}
_salt := buf.Make(c.method.keySaltLength)
defer runtime.KeepAlive(_salt)
defer common.KeepAlive(_salt)
salt := common.Dup(_salt)
_, err := io.ReadFull(c.Conn, salt)
if err != nil {
return err
}
key := Kdf(c.method.key, salt, c.method.keySaltLength)
defer runtime.KeepAlive(key)
defer common.KeepAlive(key)
c.reader = NewReader(
c.Conn,
c.method.constructor(common.Dup(key)),
@ -288,6 +287,7 @@ type clientPacketConn struct {
}
func (c *clientPacketConn) WritePacket(buffer *buf.Buffer, destination M.Socksaddr) error {
defer buffer.Release()
header := buffer.ExtendHeader(c.keySaltLength + M.SocksaddrSerializer.AddrPortLen(destination))
common.Must1(io.ReadFull(rand.Reader, header[:c.keySaltLength]))
err := M.SocksaddrSerializer.WriteAddrPort(buf.With(header[c.keySaltLength:]), destination)
@ -334,9 +334,10 @@ func (c *clientPacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error)
}
func (c *clientPacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) {
_buffer := buf.StackNew()
defer runtime.KeepAlive(_buffer)
_buffer := buf.StackNewPacket()
defer common.KeepAlive(_buffer)
buffer := common.Dup(_buffer)
defer buffer.Release()
buffer.WriteRandom(c.keySaltLength)
err = M.SocksaddrSerializer.WriteAddrPort(buffer, M.SocksaddrFromNet(addr))
if err != nil {

View file

@ -7,7 +7,6 @@ import (
"io"
"net"
"net/netip"
"runtime"
"sync"
"github.com/sagernet/sing-shadowsocks"
@ -85,7 +84,7 @@ func (s *Service) NewConnection(ctx context.Context, conn net.Conn, metadata M.M
func (s *Service) newConnection(ctx context.Context, conn net.Conn, metadata M.Metadata) error {
_header := buf.Make(s.keySaltLength + PacketLengthBufferSize + Overhead)
defer runtime.KeepAlive(_header)
defer common.KeepAlive(_header)
header := common.Dup(_header)
n, err := conn.Read(header)
@ -132,14 +131,14 @@ func (c *serverConn) writeResponse(payload []byte) (n int, err error) {
common.Must1(io.ReadFull(rand.Reader, salt))
key := Kdf(c.key, salt, c.keySaltLength)
runtime.KeepAlive(_salt)
common.KeepAlive(_salt)
writer := NewWriter(
c.Conn,
c.constructor(common.Dup(key)),
MaxPacketSize,
)
runtime.KeepAlive(key)
common.KeepAlive(key)
header := writer.Buffer()
header.Write(salt)
@ -203,7 +202,7 @@ func (s *Service) newPacket(ctx context.Context, conn N.PacketConn, buffer *buf.
}
key := Kdf(s.key, buffer.To(s.keySaltLength), s.keySaltLength)
c := s.constructor(common.Dup(key))
runtime.KeepAlive(key)
common.KeepAlive(key)
packet, err := c.Open(buffer.Index(s.keySaltLength), rw.ZeroBytes[:c.NonceSize()], buffer.From(s.keySaltLength), nil)
if err != nil {
return err
@ -235,11 +234,12 @@ func (w *serverPacketWriter) WritePacket(buffer *buf.Buffer, destination M.Socks
common.Must1(io.ReadFull(rand.Reader, header[:w.keySaltLength]))
err := M.SocksaddrSerializer.WriteAddrPort(buf.With(header[w.keySaltLength:]), destination)
if err != nil {
buffer.Release()
return err
}
key := Kdf(w.key, buffer.To(w.keySaltLength), w.keySaltLength)
c := w.constructor(common.Dup(key))
runtime.KeepAlive(key)
common.KeepAlive(key)
c.Seal(buffer.From(w.keySaltLength)[:0], rw.ZeroBytes[:c.NonceSize()], buffer.From(w.keySaltLength), nil)
buffer.Extend(Overhead)
return w.PacketConn.WritePacket(buffer, w.source)

View file

@ -13,7 +13,6 @@ import (
mRand "math/rand"
"net"
"os"
"runtime"
"strings"
"sync/atomic"
"time"
@ -231,7 +230,7 @@ func (m *Method) writeExtendedIdentityHeaders(request *buf.Buffer, salt []byte)
return err
}
b.Encrypt(header, pskHash)
runtime.KeepAlive(_identitySubkey)
common.KeepAlive(_identitySubkey)
if i == pskLen-2 {
break
}
@ -253,7 +252,7 @@ func (c *clientConn) writeRequest(payload []byte) error {
writeCipher,
MaxPacketSize,
)
runtime.KeepAlive(key)
common.KeepAlive(key)
header := writer.Buffer()
header.Write(salt)
@ -274,10 +273,10 @@ func (c *clientConn) writeRequest(payload []byte) error {
variableLengthHeaderLen := M.SocksaddrSerializer.AddrPortLen(c.destination) + 2 + paddingLen + len(payload)
common.Must(binary.Write(fixedLengthBuffer, binary.BigEndian, uint16(variableLengthHeaderLen)))
writer.WriteChunk(header, fixedLengthBuffer.Slice())
runtime.KeepAlive(_fixedLengthBuffer)
common.KeepAlive(_fixedLengthBuffer)
_variableLengthBuffer := buf.Make(variableLengthHeaderLen)
variableLengthBuffer := buf.With(common.Dup(_variableLengthBuffer))
_variableLengthBuffer := buf.StackNewSize(variableLengthHeaderLen)
variableLengthBuffer := common.Dup(_variableLengthBuffer)
common.Must(M.SocksaddrSerializer.WriteAddrPort(variableLengthBuffer, c.destination))
common.Must(binary.Write(variableLengthBuffer, binary.BigEndian, uint16(paddingLen)))
if paddingLen > 0 {
@ -286,7 +285,8 @@ func (c *clientConn) writeRequest(payload []byte) error {
common.Must1(variableLengthBuffer.Write(payload))
}
writer.WriteChunk(header, variableLengthBuffer.Slice())
runtime.KeepAlive(_variableLengthBuffer)
common.KeepAlive(_variableLengthBuffer)
variableLengthBuffer.Release()
err = writer.BufferedWriter(header.Len()).Flush()
if err != nil {
@ -315,7 +315,7 @@ func (c *clientConn) readResponse() error {
}
key := SessionKey(c.pskList[len(c.pskList)-1], salt, c.keySaltLength)
runtime.KeepAlive(_salt)
common.KeepAlive(_salt)
readCipher, err := c.constructor(common.Dup(key))
if err != nil {
return err
@ -325,7 +325,7 @@ func (c *clientConn) readResponse() error {
readCipher,
MaxPacketSize,
)
runtime.KeepAlive(key)
common.KeepAlive(key)
err = reader.ReadWithLength(uint16(1 + 8 + c.keySaltLength + 2))
if err != nil {
@ -361,7 +361,7 @@ func (c *clientConn) readResponse() error {
if bytes.Compare(requestSalt, c.requestSalt) > 0 {
return ErrBadRequestSalt
}
runtime.KeepAlive(_requestSalt)
common.KeepAlive(_requestSalt)
var length uint16
err = binary.Read(reader, binary.BigEndian, &length)
@ -423,6 +423,7 @@ type clientPacketConn struct {
}
func (c *clientPacketConn) WritePacket(buffer *buf.Buffer, destination M.Socksaddr) error {
defer buffer.Release()
var hdrLen int
if c.udpCipher != nil {
hdrLen = PacketNonceSize
@ -537,7 +538,7 @@ func (c *clientPacketConn) ReadPacket(buffer *buf.Buffer) (M.Socksaddr, error) {
if err != nil {
return M.Socksaddr{}, err
}
runtime.KeepAlive(key)
common.KeepAlive(key)
}
_, err = remoteCipher.Open(buffer.Index(0), packetHeader[4:16], buffer.Bytes(), nil)
if err != nil {
@ -646,9 +647,10 @@ func (c *clientPacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) {
overHead += 2 // padding length
overHead += M.SocksaddrSerializer.AddrPortLen(destination)
_buffer := buf.Make(overHead + len(p))
defer runtime.KeepAlive(_buffer)
buffer := buf.With(common.Dup(_buffer))
_buffer := buf.StackNewSize(overHead + len(p))
defer common.KeepAlive(_buffer)
buffer := common.Dup(_buffer)
defer buffer.Release()
var dataIndex int
if c.udpCipher != nil {
@ -749,7 +751,7 @@ func (m *Method) newUDPSession() *udpSession {
if err != nil {
return nil
}
runtime.KeepAlive(key)
common.KeepAlive(key)
}
return session
}

View file

@ -8,7 +8,6 @@ import (
"io"
"net"
"os"
"runtime"
"github.com/sagernet/sing-shadowsocks"
"github.com/sagernet/sing-shadowsocks/shadowaead"
@ -125,8 +124,9 @@ func (s *Relay[U]) NewConnection(ctx context.Context, conn net.Conn, metadata M.
func (s *Relay[U]) newConnection(ctx context.Context, conn net.Conn, metadata M.Metadata) error {
_requestHeader := buf.StackNew()
defer runtime.KeepAlive(_requestHeader)
defer common.KeepAlive(_requestHeader)
requestHeader := common.Dup(_requestHeader)
defer requestHeader.Release()
n, err := requestHeader.ReadFrom(conn)
if err != nil {
return err
@ -149,7 +149,7 @@ func (s *Relay[U]) newConnection(ctx context.Context, conn net.Conn, metadata M.
return err
}
b.Decrypt(eiHeader, eiHeader)
runtime.KeepAlive(_identitySubkey)
common.KeepAlive(_identitySubkey)
var user U
if u, loaded := s.uPSKHashR[_eiHeader]; loaded {
@ -157,7 +157,7 @@ func (s *Relay[U]) newConnection(ctx context.Context, conn net.Conn, metadata M.
} else {
return E.New("invalid request")
}
runtime.KeepAlive(_eiHeader)
common.KeepAlive(_eiHeader)
copy(requestHeader.Range(aes.BlockSize, aes.BlockSize+s.keySaltLength), requestHeader.To(s.keySaltLength))
requestHeader.Advance(aes.BlockSize)

View file

@ -11,7 +11,6 @@ import (
"math"
"net"
"os"
"runtime"
"sync"
"sync/atomic"
"time"
@ -152,7 +151,7 @@ func (s *Service) newConnection(ctx context.Context, conn net.Conn, metadata M.M
readCipher,
MaxPacketSize,
)
runtime.KeepAlive(requestKey)
common.KeepAlive(requestKey)
err = reader.ReadChunk(header[s.keySaltLength:])
if err != nil {
@ -240,7 +239,7 @@ func (c *serverConn) writeResponse(payload []byte) (n int, err error) {
salt := common.Dup(_salt[:])
common.Must1(io.ReadFull(rand.Reader, salt))
key := SessionKey(c.uPSK, salt, c.keySaltLength)
runtime.KeepAlive(_salt)
common.KeepAlive(_salt)
writeCipher, err := c.constructor(common.Dup(key))
if err != nil {
return
@ -250,7 +249,7 @@ func (c *serverConn) writeResponse(payload []byte) (n int, err error) {
writeCipher,
MaxPacketSize,
)
runtime.KeepAlive(key)
common.KeepAlive(key)
header := writer.Buffer()
header.Write(salt)
@ -262,7 +261,7 @@ func (c *serverConn) writeResponse(payload []byte) (n int, err error) {
common.Must(binary.Write(headerFixedChunk, binary.BigEndian, uint16(len(payload))))
writer.WriteChunk(header, headerFixedChunk.Slice())
runtime.KeepAlive(_headerFixedChunk)
common.KeepAlive(_headerFixedChunk)
c.requestSalt = nil
if len(payload) > 0 {
@ -348,7 +347,7 @@ func (s *Service) newPacket(ctx context.Context, conn N.PacketConn, buffer *buf.
if err != nil {
return err
}
runtime.KeepAlive(key)
common.KeepAlive(key)
}
}
goto process
@ -423,6 +422,10 @@ type serverPacketWriter struct {
session *serverUDPSession
}
func (w *serverPacketWriter) Upstream() any {
return w.PacketConn
}
func (w *serverPacketWriter) WritePacket(buffer *buf.Buffer, destination M.Socksaddr) error {
var hdrLen int
if w.udpCipher != nil {
@ -455,6 +458,7 @@ func (w *serverPacketWriter) WritePacket(buffer *buf.Buffer, destination M.Socks
err := M.SocksaddrSerializer.WriteAddrPort(header, destination)
if err != nil {
buffer.Release()
return err
}
@ -501,7 +505,7 @@ func (m *Service) newUDPSession() *serverUDPSession {
var err error
session.cipher, err = m.constructor(common.Dup(key))
common.Must(err)
runtime.KeepAlive(key)
common.KeepAlive(key)
}
return session
}

View file

@ -9,7 +9,6 @@ import (
"math"
"net"
"os"
"runtime"
"time"
"github.com/sagernet/sing-shadowsocks"
@ -142,7 +141,7 @@ func (s *MultiService[U]) newConnection(ctx context.Context, conn net.Conn, meta
return err
}
b.Decrypt(eiHeader, eiHeader)
runtime.KeepAlive(_identitySubkey)
common.KeepAlive(_identitySubkey)
var user U
var uPSK []byte
@ -152,7 +151,7 @@ func (s *MultiService[U]) newConnection(ctx context.Context, conn net.Conn, meta
} else {
return E.New("invalid request")
}
runtime.KeepAlive(_eiHeader)
common.KeepAlive(_eiHeader)
requestKey := SessionKey(uPSK, requestSalt, s.keySaltLength)
readCipher, err := s.constructor(common.Dup(requestKey))
@ -285,7 +284,7 @@ func (s *MultiService[U]) newPacket(ctx context.Context, conn N.PacketConn, buff
if err != nil {
return err
}
runtime.KeepAlive(key)
common.KeepAlive(key)
}
goto process
@ -373,6 +372,6 @@ func (s *MultiService[U]) newUDPSession(uPSK []byte) *serverUDPSession {
var err error
session.cipher, err = s.constructor(common.Dup(key))
common.Must(err)
runtime.KeepAlive(key)
common.KeepAlive(key)
return session
}

View file

@ -9,7 +9,6 @@ import (
"io"
"net"
"os"
"runtime"
"github.com/sagernet/sing-shadowsocks"
"github.com/sagernet/sing-shadowsocks/shadowaead"
@ -175,7 +174,7 @@ type clientConn struct {
func (c *clientConn) writeRequest(payload []byte) error {
_buffer := buf.Make(c.method.keyLength + M.SocksaddrSerializer.AddrPortLen(c.destination) + len(payload))
defer runtime.KeepAlive(_buffer)
defer common.KeepAlive(_buffer)
buffer := buf.With(common.Dup(_buffer))
salt := buffer.Extend(c.method.keyLength)
@ -186,7 +185,7 @@ func (c *clientConn) writeRequest(payload []byte) error {
if err != nil {
return err
}
runtime.KeepAlive(key)
common.KeepAlive(key)
err = M.SocksaddrSerializer.WriteAddrPort(buffer, c.destination)
if err != nil {
@ -211,14 +210,14 @@ func (c *clientConn) readResponse() error {
return nil
}
_salt := buf.Make(c.method.keyLength)
defer runtime.KeepAlive(_salt)
defer common.KeepAlive(_salt)
salt := common.Dup(_salt)
_, err := io.ReadFull(c.Conn, salt)
if err != nil {
return err
}
key := shadowaead.Kdf(c.method.key, salt, c.method.keyLength)
defer runtime.KeepAlive(key)
defer common.KeepAlive(key)
c.readStream, err = c.method.decryptConstructor(common.Dup(key), salt)
if err != nil {
return err
@ -261,6 +260,7 @@ type clientPacketConn struct {
}
func (c *clientPacketConn) WritePacket(buffer *buf.Buffer, destination M.Socksaddr) error {
defer buffer.Release()
header := buf.With(buffer.ExtendHeader(c.keyLength + M.SocksaddrSerializer.AddrPortLen(destination)))
common.Must1(header.ReadFullFrom(rand.Reader, c.keyLength))
err := M.SocksaddrSerializer.WriteAddrPort(header, destination)
@ -313,7 +313,7 @@ func (c *clientPacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error)
func (c *clientPacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) {
destination := M.SocksaddrFromNet(addr)
_buffer := buf.Make(c.keyLength + M.SocksaddrSerializer.AddrPortLen(destination) + len(p))
defer runtime.KeepAlive(_buffer)
defer common.KeepAlive(_buffer)
buffer := buf.With(common.Dup(_buffer))
common.Must1(buffer.ReadFullFrom(rand.Reader, c.keyLength))
err = M.SocksaddrSerializer.WriteAddrPort(buffer, M.SocksaddrFromNet(addr))