diff --git a/Makefile b/Makefile
index 57a7e20a3..660ae88af 100644
--- a/Makefile
+++ b/Makefile
@@ -234,7 +234,7 @@ setup: setup-check setup-build setup-dev tidy
setup-check: ##@setup Check if Go compiler is installed.
ifeq (, $(shell which go))
- $(error "No Go compiler found! Make sure to install 1.19.0 or newer.")
+ $(error "No Go compiler found! Make sure to install 1.20.0 or newer.")
endif
setup-dev: ##@setup Install all necessary tools for development
@@ -253,7 +253,7 @@ install-gomobile: ##@install Go Mobile Build Tools
GO111MODULE=off go get -d golang.org/x/mobile/cmd/gobind
install-lint: ##@install Install Linting Tools
- GO111MODULE=on go install github.com/golangci/golangci-lint/cmd/golangci-lint@v1.52.2
+ GO111MODULE=on go install github.com/golangci/golangci-lint/cmd/golangci-lint@v1.55.2
install-junit-report: ##@install Install Junit Report Tool for Jenkins integration
GO111MODULE=on go install github.com/jstemmer/go-junit-report/v2@latest
diff --git a/VERSION b/VERSION
index da34a74e3..1f3a6e6ed 100644
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-0.172.5
+0.172.6
diff --git a/api/backend_test.go b/api/backend_test.go
index 1f4ee4585..f344d9a45 100644
--- a/api/backend_test.go
+++ b/api/backend_test.go
@@ -765,7 +765,7 @@ func TestLoginAccount(t *testing.T) {
Password: password,
BackupDisabledDataDir: tmpdir,
NetworkID: 1,
- LogFilePath: tmpdir + "/log",
+ LogFilePath: tmpdir + "/log", // nolint: goconst
}
c := make(chan interface{}, 10)
signal.SetMobileSignalHandler(func(data []byte) {
@@ -918,7 +918,7 @@ func TestConvertAccount(t *testing.T) {
const keycardPassword = "222222" // represents password for a keycard user
const keycardUID = "1234"
const pathEIP1581Root = "m/43'/60'/1581'"
- const pathEIP1581Chat = pathEIP1581Root + "/0'/0"
+ const pathEIP1581Chat = pathEIP1581Root + "/0'/0" // nolint: goconst
const pathWalletRoot = "m/44'/60'/0'/0"
const pathDefaultWalletAccount = pathWalletRoot + "/0"
const customWalletPath1 = pathWalletRoot + "/1"
@@ -1314,7 +1314,7 @@ func TestCreateWallet(t *testing.T) {
Password: password,
BackupDisabledDataDir: tmpdir,
NetworkID: 1,
- LogFilePath: tmpdir + "/log",
+ LogFilePath: tmpdir + "/log", // nolint: goconst
}
c := make(chan interface{}, 10)
signal.SetMobileSignalHandler(func(data []byte) {
@@ -1374,7 +1374,7 @@ func TestSetFleet(t *testing.T) {
Password: password,
BackupDisabledDataDir: tmpdir,
NetworkID: 1,
- LogFilePath: tmpdir + "/log",
+ LogFilePath: tmpdir + "/log", // nolint: goconst
Emoji: "some",
}
c := make(chan interface{}, 10)
diff --git a/api/defaults.go b/api/defaults.go
index 48686d92e..6d9bfa3e8 100644
--- a/api/defaults.go
+++ b/api/defaults.go
@@ -17,7 +17,7 @@ import (
const pathWalletRoot = "m/44'/60'/0'/0"
const pathEIP1581 = "m/43'/60'/1581'"
-const pathDefaultChat = pathEIP1581 + "/0'/0"
+const pathDefaultChat = pathEIP1581 + "/0'/0" // nolint: goconst
const pathDefaultWallet = pathWalletRoot + "/0"
const defaultMnemonicLength = 12
const shardsTestClusterID = 16
diff --git a/api/geth_backend.go b/api/geth_backend.go
index 83a77f72a..302d31605 100644
--- a/api/geth_backend.go
+++ b/api/geth_backend.go
@@ -73,6 +73,8 @@ var (
ErrConfigNotAvailable = errors.New("NodeConfig is not available")
)
+const shm = "-shm"
+
var _ StatusBackend = (*GethStatusBackend)(nil)
// GethStatusBackend implements the Status.im service over go-ethereum
@@ -269,11 +271,11 @@ func (b *GethStatusBackend) DeleteMultiaccount(keyUID string, keyStoreDir string
filepath.Join(b.rootDataDir, fmt.Sprintf("%s.db-shm", keyUID)),
filepath.Join(b.rootDataDir, fmt.Sprintf("%s.db-wal", keyUID)),
appDbPath,
- appDbPath + "-shm",
- appDbPath + "-wal",
+ appDbPath + shm,
+ appDbPath + "-wal", // nolint: goconst
walletDbPath,
- walletDbPath + "-shm",
- walletDbPath + "-wal",
+ walletDbPath + shm,
+ walletDbPath + "-wal", // nolint: goconst
}
for _, path := range dbFiles {
if _, err := os.Stat(path); err == nil {
@@ -332,19 +334,19 @@ func (b *GethStatusBackend) runDBFileMigrations(account multiaccounts.Account, p
}
// rename journals as well, but ignore errors
- _ = os.Rename(unsupportedPath+"-shm", v3Path+"-shm")
+ _ = os.Rename(unsupportedPath+shm, v3Path+shm)
_ = os.Rename(unsupportedPath+"-wal", v3Path+"-wal")
}
if _, err = os.Stat(v3Path); err == nil {
if err := appdatabase.MigrateV3ToV4(v3Path, v4Path, password, account.KDFIterations, signal.SendReEncryptionStarted, signal.SendReEncryptionFinished); err != nil {
_ = os.Remove(v4Path)
- _ = os.Remove(v4Path + "-shm")
+ _ = os.Remove(v4Path + shm)
_ = os.Remove(v4Path + "-wal")
return "", errors.New("Failed to migrate v3 db to v4: " + err.Error())
}
_ = os.Remove(v3Path)
- _ = os.Remove(v3Path + "-shm")
+ _ = os.Remove(v3Path + shm)
_ = os.Remove(v3Path + "-wal")
}
@@ -1096,7 +1098,7 @@ func (b *GethStatusBackend) createTempDBFile(pattern string) (tmpDbPath string,
_ = file.Close()
_ = os.Remove(filePath)
_ = os.Remove(filePath + "-wal")
- _ = os.Remove(filePath + "-shm")
+ _ = os.Remove(filePath + shm)
_ = os.Remove(filePath + "-journal")
}
return
@@ -1110,9 +1112,9 @@ func replaceDBFile(dbPath string, newDBPath string) (cleanup func(), err error)
cleanup = func() {
_ = os.Remove(dbPath + "-wal")
- _ = os.Remove(dbPath + "-shm")
+ _ = os.Remove(dbPath + shm)
_ = os.Rename(newDBPath+"-wal", dbPath+"-wal")
- _ = os.Rename(newDBPath+"-shm", dbPath+"-shm")
+ _ = os.Rename(newDBPath+shm, dbPath+shm)
}
return
diff --git a/eth-node/bridge/geth/wakuv2.go b/eth-node/bridge/geth/wakuv2.go
index 3449b180a..31ad039ff 100644
--- a/eth-node/bridge/geth/wakuv2.go
+++ b/eth-node/bridge/geth/wakuv2.go
@@ -179,11 +179,6 @@ func (w *gethWakuV2Wrapper) SendMessagesRequest(peerID []byte, r types.MessagesR
func (w *gethWakuV2Wrapper) RequestStoreMessages(ctx context.Context, peerID []byte, r types.MessagesRequest, processEnvelopes bool) (*types.StoreRequestCursor, int, error) {
var options []store.HistoryRequestOption
- peer, err := peer.Decode(string(peerID))
- if err != nil {
- return nil, 0, err
- }
-
options = []store.HistoryRequestOption{
store.WithPaging(false, uint64(r.Limit)),
}
@@ -202,7 +197,7 @@ func (w *gethWakuV2Wrapper) RequestStoreMessages(ctx context.Context, peerID []b
contentTopics = append(contentTopics, wakucommon.BytesToTopic(topic))
}
- pbCursor, envelopesCount, err := w.waku.Query(ctx, peer, r.PubsubTopic, contentTopics, uint64(r.From), uint64(r.To), options, processEnvelopes)
+ pbCursor, envelopesCount, err := w.waku.Query(ctx, peer.ID(peerID), r.PubsubTopic, contentTopics, uint64(r.From), uint64(r.To), options, processEnvelopes)
if err != nil {
return nil, 0, err
}
diff --git a/go.mod b/go.mod
index b2478ae4a..9a89af5de 100644
--- a/go.mod
+++ b/go.mod
@@ -1,6 +1,6 @@
module github.com/status-im/status-go
-go 1.19
+go 1.20
replace github.com/ethereum/go-ethereum v1.10.26 => github.com/status-im/go-ethereum v1.10.25-status.11
@@ -33,11 +33,11 @@ require (
github.com/keighl/metabolize v0.0.0-20150915210303-97ab655d4034
github.com/kilic/bls12-381 v0.0.0-20200607163746-32e1441c8a9f
github.com/lib/pq v1.10.4
- github.com/libp2p/go-libp2p v0.29.2
- github.com/libp2p/go-libp2p-pubsub v0.9.3
+ github.com/libp2p/go-libp2p v0.32.2
+ github.com/libp2p/go-libp2p-pubsub v0.10.0
github.com/lucasb-eyer/go-colorful v1.0.3
github.com/mat/besticon v0.0.0-20210314201728-1579f269edb7
- github.com/multiformats/go-multiaddr v0.10.1
+ github.com/multiformats/go-multiaddr v0.12.0
github.com/multiformats/go-multibase v0.2.0
github.com/multiformats/go-multihash v0.2.3
github.com/multiformats/go-varint v0.0.7
@@ -51,7 +51,7 @@ require (
github.com/status-im/doubleratchet v3.0.0+incompatible
github.com/status-im/markdown v0.0.0-20231114210825-6c2d15b5dc57
github.com/status-im/migrate/v4 v4.6.2-status.3
- github.com/status-im/rendezvous v1.3.7
+ github.com/status-im/rendezvous v1.3.8-0.20240110194857-cc5be22bf83e
github.com/status-im/status-go/extkeys v1.1.2
github.com/status-im/tcp-shaker v1.1.1-status
github.com/status-im/zxcvbn-go v0.0.0-20220311183720-5e8676676857
@@ -63,8 +63,8 @@ require (
github.com/wealdtech/go-multicodec v1.4.0
github.com/xeipuuv/gojsonschema v1.2.0
github.com/zenthangplus/goccm v0.0.0-20211005163543-2f2e522aca15
- go.uber.org/zap v1.24.0
- golang.org/x/crypto v0.12.0
+ go.uber.org/zap v1.26.0
+ golang.org/x/crypto v0.14.0
golang.org/x/image v0.0.0-20210220032944-ac19c3e999fb
google.golang.org/protobuf v1.31.0
gopkg.in/go-playground/assert.v1 v1.2.1 // indirect
@@ -88,14 +88,14 @@ require (
github.com/mutecomm/go-sqlcipher/v4 v4.4.2
github.com/schollz/peerdiscovery v1.7.0
github.com/siphiuel/lc-proxy-wrapper v0.0.0-20230516150924-246507cee8c7
- github.com/waku-org/go-waku v0.8.1-0.20240104144340-585648c4eefe
+ github.com/waku-org/go-waku v0.8.1-0.20240112174027-faf046e059a5
github.com/wk8/go-ordered-map/v2 v2.1.7
github.com/yeqown/go-qrcode/v2 v2.2.1
github.com/yeqown/go-qrcode/writer/standard v1.2.1
go.uber.org/multierr v1.11.0
- golang.org/x/exp v0.0.0-20230713183714-613f0c0eb8a1
- golang.org/x/net v0.14.0
- golang.org/x/text v0.12.0
+ golang.org/x/exp v0.0.0-20231006140011-7918f672742d
+ golang.org/x/net v0.17.0
+ golang.org/x/text v0.13.0
golang.org/x/time v0.0.0-20220922220347-f3bd1da661af
)
@@ -161,21 +161,21 @@ require (
github.com/golang/snappy v0.0.4 // indirect
github.com/google/btree v1.0.1 // indirect
github.com/google/gopacket v1.1.19 // indirect
- github.com/google/pprof v0.0.0-20230705174524-200ffdc848b8 // indirect
+ github.com/google/pprof v0.0.0-20231023181126-ff6d637d2a7b // indirect
github.com/gorilla/securecookie v1.1.1 // indirect
github.com/gorilla/websocket v1.5.0 // indirect
github.com/hashicorp/errwrap v1.1.0 // indirect
github.com/hashicorp/go-bexpr v0.1.10 // indirect
github.com/hashicorp/go-multierror v1.1.1 // indirect
github.com/hashicorp/golang-lru v0.5.5-0.20210104140557-80c98217689d // indirect
- github.com/hashicorp/golang-lru/v2 v2.0.2 // indirect
+ github.com/hashicorp/golang-lru/v2 v2.0.5 // indirect
github.com/holiman/bloomfilter/v2 v2.0.3 // indirect
github.com/holiman/uint256 v1.2.0 // indirect
github.com/huandu/xstrings v1.3.2 // indirect
- github.com/huin/goupnp v1.2.0 // indirect
+ github.com/huin/goupnp v1.3.0 // indirect
github.com/jackpal/go-nat-pmp v1.0.2 // indirect
github.com/jbenet/go-temp-err-catcher v0.1.0 // indirect
- github.com/klauspost/compress v1.16.7 // indirect
+ github.com/klauspost/compress v1.17.2 // indirect
github.com/klauspost/cpuid/v2 v2.2.5 // indirect
github.com/koron/go-ssdp v0.0.4 // indirect
github.com/lann/builder v0.0.0-20180802200727-47ae307949d0 // indirect
@@ -185,19 +185,20 @@ require (
github.com/libp2p/go-cidranger v1.1.0 // indirect
github.com/libp2p/go-flow-metrics v0.1.0 // indirect
github.com/libp2p/go-libp2p-asn-util v0.3.0 // indirect
+ github.com/libp2p/go-libp2p-mplex v0.9.0 // indirect
github.com/libp2p/go-mplex v0.7.0 // indirect
github.com/libp2p/go-msgio v0.3.0 // indirect
github.com/libp2p/go-nat v0.2.0 // indirect
github.com/libp2p/go-netroute v0.2.1 // indirect
- github.com/libp2p/go-reuseport v0.3.0 // indirect
+ github.com/libp2p/go-reuseport v0.4.0 // indirect
github.com/libp2p/go-yamux/v4 v4.0.1 // indirect
github.com/mailru/easyjson v0.7.7 // indirect
github.com/marten-seemann/tcp v0.0.0-20210406111302-dfbc87cc63fd // indirect
github.com/mattn/go-colorable v0.1.8 // indirect
- github.com/mattn/go-isatty v0.0.19 // indirect
+ github.com/mattn/go-isatty v0.0.20 // indirect
github.com/mattn/go-runewidth v0.0.13 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect
- github.com/miekg/dns v1.1.55 // indirect
+ github.com/miekg/dns v1.1.56 // indirect
github.com/mikioh/tcpinfo v0.0.0-20190314235526-30a79bb1804b // indirect
github.com/mikioh/tcpopt v0.0.0-20190314235656-172688c1accc // indirect
github.com/minio/sha256-simd v1.0.1 // indirect
@@ -210,38 +211,36 @@ require (
github.com/multiformats/go-multiaddr-dns v0.3.1 // indirect
github.com/multiformats/go-multiaddr-fmt v0.1.0 // indirect
github.com/multiformats/go-multicodec v0.9.0 // indirect
- github.com/multiformats/go-multistream v0.4.1 // indirect
+ github.com/multiformats/go-multistream v0.5.0 // indirect
github.com/olekukonko/tablewriter v0.0.5 // indirect
- github.com/onsi/ginkgo/v2 v2.11.0 // indirect
- github.com/opencontainers/runtime-spec v1.0.3-0.20210326190908-1c3f411f0417 // indirect
+ github.com/onsi/ginkgo/v2 v2.13.0 // indirect
+ github.com/opencontainers/runtime-spec v1.1.0 // indirect
github.com/pbnjay/memory v0.0.0-20210728143218-7b4eea64cf58 // indirect
- github.com/pion/datachannel v1.5.2 // indirect
- github.com/pion/dtls/v2 v2.1.2 // indirect
- github.com/pion/ice/v2 v2.1.20 // indirect
- github.com/pion/interceptor v0.1.7 // indirect
+ github.com/pion/datachannel v1.5.5 // indirect
+ github.com/pion/dtls/v2 v2.2.7 // indirect
+ github.com/pion/ice/v2 v2.3.6 // indirect
+ github.com/pion/interceptor v0.1.17 // indirect
github.com/pion/logging v0.2.2 // indirect
- github.com/pion/mdns v0.0.5 // indirect
+ github.com/pion/mdns v0.0.7 // indirect
github.com/pion/randutil v0.1.0 // indirect
- github.com/pion/rtcp v1.2.9 // indirect
- github.com/pion/rtp v1.7.4 // indirect
- github.com/pion/sctp v1.8.2 // indirect
- github.com/pion/sdp/v3 v3.0.4 // indirect
- github.com/pion/srtp/v2 v2.0.5 // indirect
- github.com/pion/stun v0.3.5 // indirect
- github.com/pion/transport v0.13.0 // indirect
- github.com/pion/turn/v2 v2.0.6 // indirect
- github.com/pion/udp v0.1.1 // indirect
- github.com/pion/webrtc/v3 v3.1.24-0.20220208053747-94262c1b2b38 // indirect
+ github.com/pion/rtcp v1.2.10 // indirect
+ github.com/pion/rtp v1.7.13 // indirect
+ github.com/pion/sctp v1.8.7 // indirect
+ github.com/pion/sdp/v3 v3.0.6 // indirect
+ github.com/pion/srtp/v2 v2.0.15 // indirect
+ github.com/pion/stun v0.6.0 // indirect
+ github.com/pion/transport/v2 v2.2.1 // indirect
+ github.com/pion/turn/v2 v2.1.0 // indirect
+ github.com/pion/webrtc/v3 v3.2.9 // indirect
github.com/pmezard/go-difflib v1.0.0 // indirect
github.com/prometheus/client_model v0.4.0 // indirect
github.com/prometheus/common v0.42.0 // indirect
github.com/prometheus/procfs v0.10.1 // indirect
github.com/prometheus/tsdb v0.10.0 // indirect
github.com/quic-go/qpack v0.4.0 // indirect
- github.com/quic-go/qtls-go1-19 v0.3.3 // indirect
- github.com/quic-go/qtls-go1-20 v0.2.3 // indirect
- github.com/quic-go/quic-go v0.36.4 // indirect
- github.com/quic-go/webtransport-go v0.5.3 // indirect
+ github.com/quic-go/qtls-go1-20 v0.3.4 // indirect
+ github.com/quic-go/quic-go v0.39.4 // indirect
+ github.com/quic-go/webtransport-go v0.6.0 // indirect
github.com/raulk/go-watchdog v1.3.0 // indirect
github.com/remyoudompheng/bigfft v0.0.0-20200410134404-eec4a21b6bb0 // indirect
github.com/rivo/uniseg v0.2.0 // indirect
@@ -262,7 +261,7 @@ require (
github.com/tyler-smith/go-bip39 v1.1.0 // indirect
github.com/urfave/cli/v2 v2.24.4 // indirect
github.com/waku-org/go-discover v0.0.0-20221209174356-61c833f34d98 // indirect
- github.com/waku-org/go-libp2p-rendezvous v0.0.0-20230628220917-7b4e5ae4c0e7 // indirect
+ github.com/waku-org/go-libp2p-rendezvous v0.0.0-20240110193335-a67d1cc760a0 // indirect
github.com/waku-org/go-zerokit-rln v0.1.14-0.20240102145250-fa738c0bdf59 // indirect
github.com/waku-org/go-zerokit-rln-apple v0.0.0-20230916172309-ee0ee61dde2b // indirect
github.com/waku-org/go-zerokit-rln-arm v0.0.0-20230916171929-1dd9494ff065 // indirect
@@ -275,14 +274,14 @@ require (
github.com/yusufpapurcu/wmi v1.2.3 // indirect
go.etcd.io/bbolt v1.3.6 // indirect
go.uber.org/atomic v1.11.0 // indirect
- go.uber.org/dig v1.17.0 // indirect
- go.uber.org/fx v1.20.0 // indirect
- golang.org/x/mod v0.12.0 // indirect
- golang.org/x/sync v0.3.0 // indirect
- golang.org/x/sys v0.11.0 // indirect
- golang.org/x/term v0.11.0 // indirect
- golang.org/x/tools v0.12.1-0.20230818130535-1517d1a3ba60 // indirect
- golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f // indirect
+ go.uber.org/dig v1.17.1 // indirect
+ go.uber.org/fx v1.20.1 // indirect
+ go.uber.org/mock v0.3.0 // indirect
+ golang.org/x/mod v0.13.0 // indirect
+ golang.org/x/sync v0.4.0 // indirect
+ golang.org/x/sys v0.13.0 // indirect
+ golang.org/x/term v0.13.0 // indirect
+ golang.org/x/tools v0.14.0 // indirect
gopkg.in/natefinch/npipe.v2 v2.0.0-20160621034901-c1b8fa8bdcce // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
lukechampine.com/blake3 v1.2.1 // indirect
diff --git a/go.sum b/go.sum
index 8dfe80ef3..980c14f87 100644
--- a/go.sum
+++ b/go.sum
@@ -1025,8 +1025,8 @@ github.com/google/pprof v0.0.0-20210407192527-94a9f03dee38/go.mod h1:kpwsk12EmLe
github.com/google/pprof v0.0.0-20210601050228-01bbb1931b22/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE=
github.com/google/pprof v0.0.0-20210609004039-a478d1d731e9/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE=
github.com/google/pprof v0.0.0-20210720184732-4bb14d4b1be1/go.mod h1:kpwsk12EmLew5upagYY7GY0pfYCcupk39gWOCRROcvE=
-github.com/google/pprof v0.0.0-20230705174524-200ffdc848b8 h1:n6vlPhxsA+BW/XsS5+uqi7GyzaLa5MH7qlSLBZtRdiA=
-github.com/google/pprof v0.0.0-20230705174524-200ffdc848b8/go.mod h1:Jh3hGz2jkYak8qXPD19ryItVnUgpgeqzdkY/D0EaeuA=
+github.com/google/pprof v0.0.0-20231023181126-ff6d637d2a7b h1:RMpPgZTSApbPf7xaVel+QkoGPRLFLrwFO89uDUHEGf0=
+github.com/google/pprof v0.0.0-20231023181126-ff6d637d2a7b/go.mod h1:czg5+yv1E0ZGTi6S6vVK1mke0fV+FaUhNGcd6VRS9Ik=
github.com/google/renameio v0.1.0/go.mod h1:KWCgfxg9yswjAJkECMjeO8J8rahYeXnNhOm40UhjYkI=
github.com/google/uuid v1.0.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
github.com/google/uuid v1.1.1/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
@@ -1114,8 +1114,8 @@ github.com/hashicorp/golang-lru v0.5.1/go.mod h1:/m3WP610KZHVQ1SGc6re/UDhFvYD7pJ
github.com/hashicorp/golang-lru v0.5.4/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4=
github.com/hashicorp/golang-lru v0.5.5-0.20210104140557-80c98217689d h1:dg1dEPuWpEqDnvIw251EVy4zlP8gWbsGj4BsUKCRpYs=
github.com/hashicorp/golang-lru v0.5.5-0.20210104140557-80c98217689d/go.mod h1:iADmTwqILo4mZ8BN3D2Q6+9jd8WM5uGBxy+E8yxSoD4=
-github.com/hashicorp/golang-lru/v2 v2.0.2 h1:Dwmkdr5Nc/oBiXgJS3CDHNhJtIHkuZ3DZF5twqnfBdU=
-github.com/hashicorp/golang-lru/v2 v2.0.2/go.mod h1:QeFd9opnmA6QUJc5vARoKUSoFhyfM2/ZepoAG6RGpeM=
+github.com/hashicorp/golang-lru/v2 v2.0.5 h1:wW7h1TG88eUIJ2i69gaE3uNVtEPIagzhGvHgwfx2Vm4=
+github.com/hashicorp/golang-lru/v2 v2.0.5/go.mod h1:QeFd9opnmA6QUJc5vARoKUSoFhyfM2/ZepoAG6RGpeM=
github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ=
github.com/hashicorp/logutils v1.0.0/go.mod h1:QIAnNjmIWmVIIkWDTG1z5v++HQmx9WQRO+LraFDTW64=
github.com/hashicorp/mdns v1.0.0/go.mod h1:tL+uN++7HEJ6SQLQ2/p+z2pH24WQKWjBPkE0mNTz8vQ=
@@ -1137,8 +1137,8 @@ github.com/huandu/xstrings v1.3.2/go.mod h1:y5/lhBue+AyNmUVz9RLU9xbLR0o4KIIExikq
github.com/hudl/fargo v1.3.0/go.mod h1:y3CKSmjA+wD2gak7sUSXTAoopbhU08POFhmITJgmKTg=
github.com/huin/goupnp v1.0.1-0.20210310174557-0ca763054c88/go.mod h1:nNs7wvRfN1eKaMknBydLNQU6146XQim8t4h+q90biWo=
github.com/huin/goupnp v1.0.2/go.mod h1:0dxJBVBHqTMjIUMkESDTNgOOx/Mw5wYIfyFmdzSamkM=
-github.com/huin/goupnp v1.2.0 h1:uOKW26NG1hsSSbXIZ1IR7XP9Gjd1U8pnLaCMgntmkmY=
-github.com/huin/goupnp v1.2.0/go.mod h1:gnGPsThkYa7bFi/KWmEysQRf48l2dvR5bxr2OFckNX8=
+github.com/huin/goupnp v1.3.0 h1:UvLUlWDNpoUdYzb2TCn+MuTWtcjXKSza2n6CBdQ0xXc=
+github.com/huin/goupnp v1.3.0/go.mod h1:gnGPsThkYa7bFi/KWmEysQRf48l2dvR5bxr2OFckNX8=
github.com/huin/goutil v0.0.0-20170803182201-1ca381bf3150/go.mod h1:PpLOETDnJ0o3iZrZfqZzyLl6l7F3c6L1oWn7OICBi6o=
github.com/iancoleman/strcase v0.2.0/go.mod h1:iwCmte+B7n89clKwxIoIXy/HfoL7AsD47ZCWhYzw7ho=
github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc=
@@ -1292,8 +1292,8 @@ github.com/klauspost/compress v1.11.13/go.mod h1:aoV0uJVorq1K+umq18yTdKaF57EivdY
github.com/klauspost/compress v1.13.1/go.mod h1:8dP1Hq4DHOhN9w426knH3Rhby4rFm6D8eO+e+Dq5Gzg=
github.com/klauspost/compress v1.13.4/go.mod h1:8dP1Hq4DHOhN9w426knH3Rhby4rFm6D8eO+e+Dq5Gzg=
github.com/klauspost/compress v1.13.6/go.mod h1:/3/Vjq9QcHkK5uEr5lBEmyoZ1iFhe47etQ6QUkpK6sk=
-github.com/klauspost/compress v1.16.7 h1:2mk3MPGNzKyxErAw8YaohYh69+pa4sIQSC0fPGCFR9I=
-github.com/klauspost/compress v1.16.7/go.mod h1:ntbaceVETuRiXiv4DpjP66DpAtAGkEQskQzEyD//IeE=
+github.com/klauspost/compress v1.17.2 h1:RlWWUY/Dr4fL8qk9YG7DTZ7PDgME2V4csBXA8L/ixi4=
+github.com/klauspost/compress v1.17.2/go.mod h1:ntbaceVETuRiXiv4DpjP66DpAtAGkEQskQzEyD//IeE=
github.com/klauspost/cpuid v0.0.0-20170728055534-ae7887de9fa5/go.mod h1:Pj4uuM528wm8OyEC2QMXAi2YiTZ96dNQPGgoMS4s3ek=
github.com/klauspost/cpuid/v2 v2.0.4/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
github.com/klauspost/cpuid/v2 v2.0.6/go.mod h1:FInQzS24/EEf25PyTYn52gqo7WaD8xa0213Md/qVLRg=
@@ -1348,12 +1348,14 @@ github.com/libp2p/go-cidranger v1.1.0 h1:ewPN8EZ0dd1LSnrtuwd4709PXVcITVeuwbag38y
github.com/libp2p/go-cidranger v1.1.0/go.mod h1:KWZTfSr+r9qEo9OkI9/SIEeAtw+NNoU0dXIXt15Okic=
github.com/libp2p/go-flow-metrics v0.1.0 h1:0iPhMI8PskQwzh57jB9WxIuIOQ0r+15PChFGkx3Q3WM=
github.com/libp2p/go-flow-metrics v0.1.0/go.mod h1:4Xi8MX8wj5aWNDAZttg6UPmc0ZrnFNsMtpsYUClFtro=
-github.com/libp2p/go-libp2p v0.29.2 h1:uPw/c8hOxoLP/KhFnzlc5Ejqf+OmAL1dwIsqE31WBtY=
-github.com/libp2p/go-libp2p v0.29.2/go.mod h1:OU7nSq0aEZMsV2wY8nXn1+XNNt9q2UiR8LjW3Kmp2UE=
+github.com/libp2p/go-libp2p v0.32.2 h1:s8GYN4YJzgUoyeYNPdW7JZeZ5Ee31iNaIBfGYMAY4FQ=
+github.com/libp2p/go-libp2p v0.32.2/go.mod h1:E0LKe+diV/ZVJVnOJby8VC5xzHF0660osg71skcxJvk=
github.com/libp2p/go-libp2p-asn-util v0.3.0 h1:gMDcMyYiZKkocGXDQ5nsUQyquC9+H+iLEQHwOCZ7s8s=
github.com/libp2p/go-libp2p-asn-util v0.3.0/go.mod h1:B1mcOrKUE35Xq/ASTmQ4tN3LNzVVaMNmq2NACuqyB9w=
-github.com/libp2p/go-libp2p-pubsub v0.9.3 h1:ihcz9oIBMaCK9kcx+yHWm3mLAFBMAUsM4ux42aikDxo=
-github.com/libp2p/go-libp2p-pubsub v0.9.3/go.mod h1:RYA7aM9jIic5VV47WXu4GkcRxRhrdElWf8xtyli+Dzc=
+github.com/libp2p/go-libp2p-mplex v0.9.0 h1:R58pDRAmuBXkYugbSSXR9wrTX3+1pFM1xP2bLuodIq8=
+github.com/libp2p/go-libp2p-mplex v0.9.0/go.mod h1:ro1i4kuwiFT+uMPbIDIFkcLs1KRbNp0QwnUXM+P64Og=
+github.com/libp2p/go-libp2p-pubsub v0.10.0 h1:wS0S5FlISavMaAbxyQn3dxMOe2eegMfswM471RuHJwA=
+github.com/libp2p/go-libp2p-pubsub v0.10.0/go.mod h1:1OxbaT/pFRO5h+Dpze8hdHQ63R0ke55XTs6b6NwLLkw=
github.com/libp2p/go-libp2p-testing v0.12.0 h1:EPvBb4kKMWO29qP4mZGyhVzUyR25dvfUIK5WDu6iPUA=
github.com/libp2p/go-maddr-filter v0.1.0/go.mod h1:VzZhTXkMucEGGEOSKddrwGiOv0tUhgnKqNEmIAz/bPU=
github.com/libp2p/go-mplex v0.7.0 h1:BDhFZdlk5tbr0oyFq/xv/NPGfjbnrsDam1EvutpBDbY=
@@ -1364,8 +1366,8 @@ github.com/libp2p/go-nat v0.2.0 h1:Tyz+bUFAYqGyJ/ppPPymMGbIgNRH+WqC5QrT5fKrrGk=
github.com/libp2p/go-nat v0.2.0/go.mod h1:3MJr+GRpRkyT65EpVPBstXLvOlAPzUVlG6Pwg9ohLJk=
github.com/libp2p/go-netroute v0.2.1 h1:V8kVrpD8GK0Riv15/7VN6RbUQ3URNZVosw7H2v9tksU=
github.com/libp2p/go-netroute v0.2.1/go.mod h1:hraioZr0fhBjG0ZRXJJ6Zj2IVEVNx6tDTFQfSmcq7mQ=
-github.com/libp2p/go-reuseport v0.3.0 h1:iiZslO5byUYZEg9iCwJGf5h+sf1Agmqx2V2FDjPyvUw=
-github.com/libp2p/go-reuseport v0.3.0/go.mod h1:laea40AimhtfEqysZ71UpYj4S+R9VpH8PgqLo7L+SwI=
+github.com/libp2p/go-reuseport v0.4.0 h1:nR5KU7hD0WxXCJbmw7r2rhRYruNRl2koHw8fQscQm2s=
+github.com/libp2p/go-reuseport v0.4.0/go.mod h1:ZtI03j/wO5hZVDFo2jKywN6bYKWLOy8Se6DrI2E1cLU=
github.com/libp2p/go-yamux/v4 v4.0.1 h1:FfDR4S1wj6Bw2Pqbc8Uz7pCxeRBPbwsBbEdfwiCypkQ=
github.com/libp2p/go-yamux/v4 v4.0.1/go.mod h1:NWjl8ZTLOGlozrXSOZ/HlfG++39iKNnM5wwmtQP1YB4=
github.com/lightstep/lightstep-tracer-common/golang/gogo v0.0.0-20190605223551-bc2310a04743/go.mod h1:qklhhLq1aX+mtWk9cPHPzaBjWImj5ULL6C7HFJtXQMM=
@@ -1426,8 +1428,8 @@ github.com/mattn/go-isatty v0.0.9/go.mod h1:YNRxwqDuOph6SZLI9vUUz6OYw3QyUt7WiY2y
github.com/mattn/go-isatty v0.0.10/go.mod h1:qgIWMr58cqv1PHHyhnkY9lrL7etaEgOFcMEpPG5Rm84=
github.com/mattn/go-isatty v0.0.12/go.mod h1:cbi8OIDigv2wuxKPP5vlRcQ1OAZbq2CE4Kysco4FUpU=
github.com/mattn/go-isatty v0.0.14/go.mod h1:7GGIvUiUoEMVVmxf/4nioHXj79iQHKdU27kJ6hsGG94=
-github.com/mattn/go-isatty v0.0.19 h1:JITubQf0MOLdlGRuRq+jtsDlekdYPia9ZFsB8h/APPA=
-github.com/mattn/go-isatty v0.0.19/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
+github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
+github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
github.com/mattn/go-runewidth v0.0.2/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
github.com/mattn/go-runewidth v0.0.3/go.mod h1:LwmH8dsx7+W8Uxz3IHJYH5QSwggIsqBzpuz5H//U1FU=
github.com/mattn/go-runewidth v0.0.9/go.mod h1:H031xJmbD/WCDINGzjvQ9THkh0rPKHF+m2gUSrubnMI=
@@ -1458,8 +1460,8 @@ github.com/meirf/gopart v0.0.0-20180520194036-37e9492a85a8/go.mod h1:Uz8uoD6o+eQ
github.com/microcosm-cc/bluemonday v1.0.1/go.mod h1:hsXNsILzKxV+sX77C5b8FSuKF00vh2OMYv+xgHpAMF4=
github.com/miekg/dns v1.0.14/go.mod h1:W1PPwlIAgtquWBMBEV9nkV9Cazfe8ScdGz/Lj7v3Nrg=
github.com/miekg/dns v1.1.41/go.mod h1:p6aan82bvRIyn+zDIv9xYNUpwa73JcSh9BKwknJysuI=
-github.com/miekg/dns v1.1.55 h1:GoQ4hpsj0nFLYe+bWiCToyrBEJXkQfOOIvFGFy0lEgo=
-github.com/miekg/dns v1.1.55/go.mod h1:uInx36IzPl7FYnDcMeVWxj9byh7DutNykX4G9Sj60FY=
+github.com/miekg/dns v1.1.56 h1:5imZaSeoRNvpM9SzWNhEcP9QliKiz20/dA2QabIGVnE=
+github.com/miekg/dns v1.1.56/go.mod h1:cRm6Oo2C8TY9ZS/TqsSrseAcncm74lfK5G+ikN2SWWY=
github.com/miekg/pkcs11 v1.0.3/go.mod h1:XsNlhZGX73bx86s2hdc/FuaLm2CPZJemRLMA+WTFxgs=
github.com/mikioh/tcp v0.0.0-20190314235350-803a9b46060c h1:bzE/A84HN25pxAuk9Eej1Kz9OUelF97nAc82bDquQI8=
github.com/mikioh/tcp v0.0.0-20190314235350-803a9b46060c/go.mod h1:0SQS9kMwD2VsyFEB++InYyBJroV/FRmBgcydeSUcJms=
@@ -1526,8 +1528,8 @@ github.com/multiformats/go-multiaddr v0.1.1/go.mod h1:aMKBKNEYmzmDmxfX88/vz+J5IU
github.com/multiformats/go-multiaddr v0.2.0/go.mod h1:0nO36NvPpyV4QzvTLi/lafl2y95ncPj0vFwVF6k6wJ4=
github.com/multiformats/go-multiaddr v0.2.2/go.mod h1:NtfXiOtHvghW9KojvtySjH5y0u0xW5UouOmQQrn6a3Y=
github.com/multiformats/go-multiaddr v0.3.2/go.mod h1:lCKNGP1EQ1eZ35Za2wlqnabm9xQkib3fyB+nZXHLag0=
-github.com/multiformats/go-multiaddr v0.10.1 h1:HghtFrWyZEPrpTvgAMFJi6gFdgHfs2cb0pyfDsk+lqU=
-github.com/multiformats/go-multiaddr v0.10.1/go.mod h1:jLEZsA61rwWNZQTHHnqq2HNa+4os/Hz54eqiRnsRqYQ=
+github.com/multiformats/go-multiaddr v0.12.0 h1:1QlibTFkoXJuDjjYsMHhE73TnzJQl8FSWatk/0gxGzE=
+github.com/multiformats/go-multiaddr v0.12.0/go.mod h1:WmZXgObOQOYp9r3cslLlppkrz1FYSHmE834dfz/lWu8=
github.com/multiformats/go-multiaddr-dns v0.3.1 h1:QgQgR+LQVt3NPTjbrLLpsaT2ufAA2y0Mkk+QRVJbW3A=
github.com/multiformats/go-multiaddr-dns v0.3.1/go.mod h1:G/245BRQ6FJGmryJCrOuTdB37AMA5AMOVuO6NY3JwTk=
github.com/multiformats/go-multiaddr-fmt v0.1.0 h1:WLEFClPycPkp4fnIzoFoV9FVd49/eQsuaL3/CWe167E=
@@ -1543,8 +1545,8 @@ github.com/multiformats/go-multihash v0.0.14/go.mod h1:VdAWLKTwram9oKAatUcLxBNUj
github.com/multiformats/go-multihash v0.0.15/go.mod h1:D6aZrWNLFTV/ynMpKsNtB40mJzmCl4jb1alC0OvHiHg=
github.com/multiformats/go-multihash v0.2.3 h1:7Lyc8XfX/IY2jWb/gI7JP+o7JEq9hOa7BFvVU9RSh+U=
github.com/multiformats/go-multihash v0.2.3/go.mod h1:dXgKXCXjBzdscBLk9JkjINiEsCKRVch90MdaGiKsvSM=
-github.com/multiformats/go-multistream v0.4.1 h1:rFy0Iiyn3YT0asivDUIR05leAdwZq3de4741sbiSdfo=
-github.com/multiformats/go-multistream v0.4.1/go.mod h1:Mz5eykRVAjJWckE2U78c6xqdtyNUEhKSM0Lwar2p77Q=
+github.com/multiformats/go-multistream v0.5.0 h1:5htLSLl7lvJk3xx3qT/8Zm9J4K8vEOf/QGkvOGQAyiE=
+github.com/multiformats/go-multistream v0.5.0/go.mod h1:n6tMZiwiP2wUsR8DgfDWw1dydlEqV3l6N3/GBsX6ILA=
github.com/multiformats/go-varint v0.0.1/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE=
github.com/multiformats/go-varint v0.0.5/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE=
github.com/multiformats/go-varint v0.0.6/go.mod h1:3Ls8CIEsrijN6+B7PbrXRPxHRPuXSrVKRY101jdMZYE=
@@ -1603,8 +1605,8 @@ github.com/onsi/ginkgo v1.16.4/go.mod h1:dX+/inL/fNMqNlz0e9LfyB9TswhZpCVdJM/Z6Vv
github.com/onsi/ginkgo v1.16.5 h1:8xi0RTUf59SOSfEtZMvwTvXYMzG4gV23XVHOZiXNtnE=
github.com/onsi/ginkgo v1.16.5/go.mod h1:+E8gABHa3K6zRBolWtd+ROzc/U5bkGt0FwiG042wbpU=
github.com/onsi/ginkgo/v2 v2.1.3/go.mod h1:vw5CSIxN1JObi/U8gcbwft7ZxR2dgaR70JSE3/PpL4c=
-github.com/onsi/ginkgo/v2 v2.11.0 h1:WgqUCUt/lT6yXoQ8Wef0fsNn5cAuMK7+KT9UFRz2tcU=
-github.com/onsi/ginkgo/v2 v2.11.0/go.mod h1:ZhrRA5XmEE3x3rhlzamx/JJvujdZoJ2uvgI7kR0iZvM=
+github.com/onsi/ginkgo/v2 v2.13.0 h1:0jY9lJquiL8fcf3M4LAXN5aMlS/b2BV86HFFPCPMgE4=
+github.com/onsi/ginkgo/v2 v2.13.0/go.mod h1:TE309ZR8s5FsKKpuB1YAQYBzCaAfUgatB/xlT/ETL/o=
github.com/onsi/gomega v0.0.0-20151007035656-2152b45fa28a/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA=
github.com/onsi/gomega v0.0.0-20170829124025-dcabb60a477c/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA=
github.com/onsi/gomega v1.4.1/go.mod h1:C1qb7wdrVGGVU+Z6iS04AVkA3Q65CEZX59MT0QO5uiA=
@@ -1619,7 +1621,7 @@ github.com/onsi/gomega v1.11.0/go.mod h1:azGKhqFUon9Vuj0YmTfLSmx0FUwqXYSTl5re8lQ
github.com/onsi/gomega v1.15.0/go.mod h1:cIuvLEne0aoVhAgh/O6ac0Op8WWw9H6eYCriF+tEHG0=
github.com/onsi/gomega v1.17.0/go.mod h1:HnhC7FXeEQY45zxNK3PPoIUhzk/80Xly9PcubAlGdZY=
github.com/onsi/gomega v1.19.0/go.mod h1:LY+I3pBVzYsTBU1AnDwOSxaYi9WoWiqgwooUqq9yPro=
-github.com/onsi/gomega v1.27.8 h1:gegWiwZjBsf2DgiSbf5hpokZ98JVDMcWkUiigk6/KXc=
+github.com/onsi/gomega v1.27.10 h1:naR28SdDFlqrG6kScpT8VWpu1xWY5nJRCF3XaYyBjhI=
github.com/op/go-logging v0.0.0-20160315200505-970db520ece7/go.mod h1:HzydrMdWErDVzsI23lYNej1Htcns9BCg93Dk0bBINWk=
github.com/opencontainers/go-digest v0.0.0-20170106003457-a6d0ee40d420/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s=
github.com/opencontainers/go-digest v0.0.0-20180430190053-c9281466c8b2/go.mod h1:cMLVZDEM3+U2I4VmLI6N8jQYUd2OVphdqWwCJHrFt2s=
@@ -1644,8 +1646,9 @@ github.com/opencontainers/runtime-spec v1.0.1/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/
github.com/opencontainers/runtime-spec v1.0.2-0.20190207185410-29686dbc5559/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0=
github.com/opencontainers/runtime-spec v1.0.2/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0=
github.com/opencontainers/runtime-spec v1.0.3-0.20200929063507-e6143ca7d51d/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0=
-github.com/opencontainers/runtime-spec v1.0.3-0.20210326190908-1c3f411f0417 h1:3snG66yBm59tKhhSPQrQ/0bCrv1LQbKt40LnUPiUxdc=
github.com/opencontainers/runtime-spec v1.0.3-0.20210326190908-1c3f411f0417/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0=
+github.com/opencontainers/runtime-spec v1.1.0 h1:HHUyrt9mwHUjtasSbXSMvs4cyFxh+Bll4AjJ9odEGpg=
+github.com/opencontainers/runtime-spec v1.1.0/go.mod h1:jwyrGlmzljRJv/Fgzds9SsS/C5hL+LL3ko9hs6T5lQ0=
github.com/opencontainers/runtime-tools v0.0.0-20181011054405-1d69bd0f9c39/go.mod h1:r3f7wjNzSs2extwzU3Y+6pKfobzPh+kKFJ3ofN+3nfs=
github.com/opencontainers/selinux v1.6.0/go.mod h1:VVGKuOLlE7v4PJyT6h7mNWvq1rzqiriPsEqVhc+svHE=
github.com/opencontainers/selinux v1.8.0/go.mod h1:RScLhm78qiWa2gbVCcGkC7tCGdgk3ogry1nUQF8Evvo=
@@ -1685,34 +1688,39 @@ github.com/pierrec/lz4 v1.0.2-0.20190131084431-473cd7ce01a1/go.mod h1:3/3N9NVKO0
github.com/pierrec/lz4 v2.0.5+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY=
github.com/pierrec/lz4/v4 v4.1.8/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4=
github.com/pion/datachannel v1.4.21/go.mod h1:oiNyP4gHx2DIwRzX/MFyH0Rz/Gz05OgBlayAI2hAWjg=
-github.com/pion/datachannel v1.5.2 h1:piB93s8LGmbECrpO84DnkIVWasRMk3IimbcXkTQLE6E=
github.com/pion/datachannel v1.5.2/go.mod h1:FTGQWaHrdCwIJ1rw6xBIfZVkslikjShim5yr05XFuCQ=
+github.com/pion/datachannel v1.5.5 h1:10ef4kwdjije+M9d7Xm9im2Y3O6A6ccQb0zcqZcJew8=
+github.com/pion/datachannel v1.5.5/go.mod h1:iMz+lECmfdCMqFRhXhcA/219B0SQlbpoR2V118yimL0=
github.com/pion/dtls/v2 v2.0.1/go.mod h1:uMQkz2W0cSqY00xav7WByQ4Hb+18xeQh2oH2fRezr5U=
github.com/pion/dtls/v2 v2.0.2/go.mod h1:27PEO3MDdaCfo21heT59/vsdmZc0zMt9wQPcSlLu/1I=
github.com/pion/dtls/v2 v2.0.4/go.mod h1:qAkFscX0ZHoI1E07RfYPoRw3manThveu+mlTDdOxoGI=
github.com/pion/dtls/v2 v2.0.7/go.mod h1:QuDII+8FVvk9Dp5t5vYIMTo7hh7uBkra+8QIm7QGm10=
github.com/pion/dtls/v2 v2.0.9/go.mod h1:O0Wr7si/Zj5/EBFlDzDd6UtVxx25CE1r7XM7BQKYQho=
github.com/pion/dtls/v2 v2.1.1/go.mod h1:qG3gA7ZPZemBqpEFqRKyURYdKEwFZQCGb7gv9T3ON3Y=
-github.com/pion/dtls/v2 v2.1.2 h1:22Q1Jk9L++Yo7BIf9130MonNPfPVb+YgdYLeyQotuAA=
github.com/pion/dtls/v2 v2.1.2/go.mod h1:o6+WvyLDAlXF7YiPB/RlskRoeK+/JtuaZa5emwQcWus=
+github.com/pion/dtls/v2 v2.2.7 h1:cSUBsETxepsCSFSxC3mc/aDo14qQLMSL+O6IjG28yV8=
+github.com/pion/dtls/v2 v2.2.7/go.mod h1:8WiMkebSHFD0T+dIU+UeBaoV7kDhOW5oDCzZ7WZ/F9s=
github.com/pion/ice v0.7.18/go.mod h1:+Bvnm3nYC6Nnp7VV6glUkuOfToB/AtMRZpOU8ihuf4c=
github.com/pion/ice/v2 v2.0.15/go.mod h1:ZIiVGevpgAxF/cXiIVmuIUtCb3Xs4gCzCbXB6+nFkSI=
github.com/pion/ice/v2 v2.1.7/go.mod h1:kV4EODVD5ux2z8XncbLHIOtcXKtYXVgLVCeVqnpoeP0=
github.com/pion/ice/v2 v2.1.10/go.mod h1:kV4EODVD5ux2z8XncbLHIOtcXKtYXVgLVCeVqnpoeP0=
github.com/pion/ice/v2 v2.1.12/go.mod h1:ovgYHUmwYLlRvcCLI67PnQ5YGe+upXZbGgllBDG/ktU=
-github.com/pion/ice/v2 v2.1.20 h1:xpxXyX5b4WjCh/D905gzBeW/hbJxMEPx2ptVfrhVE6M=
github.com/pion/ice/v2 v2.1.20/go.mod h1:hEAldRzBhTtAfvlU1V/2/nLCMvveQWFKPNCop+63/Iw=
+github.com/pion/ice/v2 v2.3.6 h1:Jgqw36cAud47iD+N6rNX225uHvrgWtAlHfVyOQc3Heg=
+github.com/pion/ice/v2 v2.3.6/go.mod h1:9/TzKDRwBVAPsC+YOrKH/e3xDrubeTRACU9/sHQarsU=
github.com/pion/interceptor v0.0.9/go.mod h1:dHgEP5dtxOTf21MObuBAjJeAayPxLUAZjerGH8Xr07c=
github.com/pion/interceptor v0.0.12/go.mod h1:qzeuWuD/ZXvPqOnxNcnhWfkCZ2e1kwwslicyyPnhoK4=
github.com/pion/interceptor v0.0.13/go.mod h1:svsW2QoLHLoGLUr4pDoSopGBEWk8FZwlfxId/OKRKzo=
github.com/pion/interceptor v0.0.15/go.mod h1:pg3J253eGi5bqyKzA74+ej5Y19ez2jkWANVnF+Z9Dfk=
-github.com/pion/interceptor v0.1.7 h1:HThW0tIIKT9RRoDWGURe8rlZVOx0fJHxBHpA0ej0+bo=
github.com/pion/interceptor v0.1.7/go.mod h1:Lh3JSl/cbJ2wP8I3ccrjh1K/deRGRn3UlSPuOTiHb6U=
+github.com/pion/interceptor v0.1.17 h1:prJtgwFh/gB8zMqGZoOgJPHivOwVAp61i2aG61Du/1w=
+github.com/pion/interceptor v0.1.17/go.mod h1:SY8kpmfVBvrbUzvj2bsXz7OJt5JvmVNZ+4Kjq7FcwrI=
github.com/pion/logging v0.2.2 h1:M9+AIj/+pxNsDfAT64+MAVgJO0rsyLnoJKCqf//DoeY=
github.com/pion/logging v0.2.2/go.mod h1:k0/tDVsRCX2Mb2ZEmTqNa7CWsQPc+YYCB7Q+5pahoms=
github.com/pion/mdns v0.0.4/go.mod h1:R1sL0p50l42S5lJs91oNdUL58nm0QHrhxnSegr++qC0=
-github.com/pion/mdns v0.0.5 h1:Q2oj/JB3NqfzY9xGZ1fPzZzK7sDSD8rZPOvcIQ10BCw=
github.com/pion/mdns v0.0.5/go.mod h1:UgssrvdD3mxpi8tMxAXbsppL3vJ4Jipw1mTCW+al01g=
+github.com/pion/mdns v0.0.7 h1:P0UB4Sr6xDWEox0kTVxF0LmQihtCbSAdW0H2nEgkA3U=
+github.com/pion/mdns v0.0.7/go.mod h1:4iP2UbeFhLI/vWju/bw6ZfwjJzk0z8DNValjGxR/dD8=
github.com/pion/quic v0.1.1/go.mod h1:zEU51v7ru8Mp4AUBJvj6psrSth5eEFNnVQK5K48oV3k=
github.com/pion/quic v0.1.4/go.mod h1:dBhNvkLoQqRwfi6h3Vqj3IcPLgiW7rkZxBbRdp7Vzvk=
github.com/pion/randutil v0.0.0/go.mod h1:XcJrSMMbbMRhASFVOlj/5hQial/Y8oH/HVo7TBZq+j8=
@@ -1721,33 +1729,41 @@ github.com/pion/randutil v0.1.0/go.mod h1:XcJrSMMbbMRhASFVOlj/5hQial/Y8oH/HVo7TB
github.com/pion/rtcp v1.2.3/go.mod h1:zGhIv0RPRF0Z1Wiij22pUt5W/c9fevqSzT4jje/oK7I=
github.com/pion/rtcp v1.2.4/go.mod h1:52rMNPWFsjr39z9B9MhnkqhPLoeHTv1aN63o/42bWE0=
github.com/pion/rtcp v1.2.6/go.mod h1:52rMNPWFsjr39z9B9MhnkqhPLoeHTv1aN63o/42bWE0=
-github.com/pion/rtcp v1.2.9 h1:1ujStwg++IOLIEoOiIQ2s+qBuJ1VN81KW+9pMPsif+U=
github.com/pion/rtcp v1.2.9/go.mod h1:qVPhiCzAm4D/rxb6XzKeyZiQK69yJpbUDJSF7TgrqNo=
+github.com/pion/rtcp v1.2.10 h1:nkr3uj+8Sp97zyItdN60tE/S6vk4al5CPRR6Gejsdjc=
+github.com/pion/rtcp v1.2.10/go.mod h1:ztfEwXZNLGyF1oQDttz/ZKIBaeeg/oWbRYqzBM9TL1I=
github.com/pion/rtp v1.6.0/go.mod h1:QgfogHsMBVE/RFNno467U/KBqfUywEH+HK+0rtnwsdI=
github.com/pion/rtp v1.6.1/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
github.com/pion/rtp v1.6.2/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
github.com/pion/rtp v1.6.5/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
github.com/pion/rtp v1.7.0/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
github.com/pion/rtp v1.7.2/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
-github.com/pion/rtp v1.7.4 h1:4dMbjb1SuynU5OpA3kz1zHK+u+eOCQjW3MAeVHf1ODA=
github.com/pion/rtp v1.7.4/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
+github.com/pion/rtp v1.7.13 h1:qcHwlmtiI50t1XivvoawdCGTP4Uiypzfrsap+bijcoA=
+github.com/pion/rtp v1.7.13/go.mod h1:bDb5n+BFZxXx0Ea7E5qe+klMuqiBrP+w8XSjiWtCUko=
github.com/pion/sctp v1.7.10/go.mod h1:EhpTUQu1/lcK3xI+eriS6/96fWetHGCvBi9MSsnaBN0=
github.com/pion/sctp v1.7.11/go.mod h1:EhpTUQu1/lcK3xI+eriS6/96fWetHGCvBi9MSsnaBN0=
github.com/pion/sctp v1.7.12/go.mod h1:xFe9cLMZ5Vj6eOzpyiKjT9SwGM4KpK/8Jbw5//jc+0s=
github.com/pion/sctp v1.8.0/go.mod h1:xFe9cLMZ5Vj6eOzpyiKjT9SwGM4KpK/8Jbw5//jc+0s=
-github.com/pion/sctp v1.8.2 h1:yBBCIrUMJ4yFICL3RIvR4eh/H2BTTvlligmSTy+3kiA=
github.com/pion/sctp v1.8.2/go.mod h1:xFe9cLMZ5Vj6eOzpyiKjT9SwGM4KpK/8Jbw5//jc+0s=
+github.com/pion/sctp v1.8.5/go.mod h1:SUFFfDpViyKejTAdwD1d/HQsCu+V/40cCs2nZIvC3s0=
+github.com/pion/sctp v1.8.7 h1:JnABvFakZueGAn4KU/4PSKg+GWbF6QWbKTWZOSGJjXw=
+github.com/pion/sctp v1.8.7/go.mod h1:g1Ul+ARqZq5JEmoFy87Q/4CePtKnTJ1QCL9dBBdN6AU=
github.com/pion/sdp/v2 v2.4.0/go.mod h1:L2LxrOpSTJbAns244vfPChbciR/ReU1KWfG04OpkR7E=
-github.com/pion/sdp/v3 v3.0.4 h1:2Kf+dgrzJflNCSw3TV5v2VLeI0s/qkzy2r5jlR0wzf8=
github.com/pion/sdp/v3 v3.0.4/go.mod h1:bNiSknmJE0HYBprTHXKPQ3+JjacTv5uap92ueJZKsRk=
+github.com/pion/sdp/v3 v3.0.6 h1:WuDLhtuFUUVpTfus9ILC4HRyHsW6TdugjEX/QY9OiUw=
+github.com/pion/sdp/v3 v3.0.6/go.mod h1:iiFWFpQO8Fy3S5ldclBkpXqmWy02ns78NOKoLLL0YQw=
github.com/pion/srtp v1.5.1/go.mod h1:B+QgX5xPeQTNc1CJStJPHzOlHK66ViMDWTT0HZTCkcA=
github.com/pion/srtp v1.5.2/go.mod h1:NiBff/MSxUwMUwx/fRNyD/xGE+dVvf8BOCeXhjCXZ9U=
github.com/pion/srtp/v2 v2.0.1/go.mod h1:c8NWHhhkFf/drmHTAblkdu8++lsISEBBdAuiyxgqIsE=
github.com/pion/srtp/v2 v2.0.2/go.mod h1:VEyLv4CuxrwGY8cxM+Ng3bmVy8ckz/1t6A0q/msKOw0=
-github.com/pion/srtp/v2 v2.0.5 h1:ks3wcTvIUE/GHndO3FAvROQ9opy0uLELpwHJaQ1yqhQ=
github.com/pion/srtp/v2 v2.0.5/go.mod h1:8k6AJlal740mrZ6WYxc4Dg6qDqqhxoRG2GSjlUhDF0A=
-github.com/pion/stun v0.3.5 h1:uLUCBCkQby4S1cf6CGuR9QrVOKcvUwFeemaC865QHDg=
+github.com/pion/srtp/v2 v2.0.15 h1:+tqRtXGsGwHC0G0IUIAzRmdkHvriF79IHVfZGfHrQoA=
+github.com/pion/srtp/v2 v2.0.15/go.mod h1:b/pQOlDrbB0HEH5EUAQXzSYxikFbNcNuKmF8tM0hCtw=
github.com/pion/stun v0.3.5/go.mod h1:gDMim+47EeEtfWogA37n6qXZS88L5V6LqFcf+DZA2UA=
+github.com/pion/stun v0.4.0/go.mod h1:QPsh1/SbXASntw3zkkrIk3ZJVKz4saBY2G7S10P3wCw=
+github.com/pion/stun v0.6.0 h1:JHT/2iyGDPrFWE8NNC15wnddBN8KifsEDw8swQmrEmU=
+github.com/pion/stun v0.6.0/go.mod h1:HPqcfoeqQn9cuaet7AOmB5e5xkObu9DwBdurwLKO9oA=
github.com/pion/transport v0.6.0/go.mod h1:iWZ07doqOosSLMhZ+FXUTq+TamDoXSllxpbGcfkCmbE=
github.com/pion/transport v0.8.10/go.mod h1:tBmha/UCjpum5hqTWhfAEs3CO4/tHSg0MYRhSzR+CZ8=
github.com/pion/transport v0.10.0/go.mod h1:BnHnUipd0rZQyTVB2SBGojFHT9CBt5C5TcsJSQGkvSE=
@@ -1755,21 +1771,28 @@ github.com/pion/transport v0.10.1/go.mod h1:PBis1stIILMiis0PewDw91WJeLJkyIMcEk+D
github.com/pion/transport v0.12.1/go.mod h1:N3+vZQD9HlDP5GWkZ85LohxNsDcNgofQmyL6ojX5d8Q=
github.com/pion/transport v0.12.2/go.mod h1:N3+vZQD9HlDP5GWkZ85LohxNsDcNgofQmyL6ojX5d8Q=
github.com/pion/transport v0.12.3/go.mod h1:OViWW9SP2peE/HbwBvARicmAVnesphkNkCVZIWJ6q9A=
-github.com/pion/transport v0.13.0 h1:KWTA5ZrQogizzYwPEciGtHPLwpAjE91FgXnyu+Hv2uY=
github.com/pion/transport v0.13.0/go.mod h1:yxm9uXpK9bpBBWkITk13cLo1y5/ur5VQpG22ny6EP7g=
+github.com/pion/transport v0.14.1 h1:XSM6olwW+o8J4SCmOBb/BpwZypkHeyM0PGFCxNQBr40=
+github.com/pion/transport v0.14.1/go.mod h1:4tGmbk00NeYA3rUa9+n+dzCCoKkcy3YlYb99Jn2fNnI=
+github.com/pion/transport/v2 v2.0.0/go.mod h1:HS2MEBJTwD+1ZI2eSXSvHJx/HnzQqRy2/LXxt6eVMHc=
+github.com/pion/transport/v2 v2.1.0/go.mod h1:AdSw4YBZVDkZm8fpoz+fclXyQwANWmZAlDuQdctTThQ=
+github.com/pion/transport/v2 v2.2.0/go.mod h1:AdSw4YBZVDkZm8fpoz+fclXyQwANWmZAlDuQdctTThQ=
+github.com/pion/transport/v2 v2.2.1 h1:7qYnCBlpgSJNYMbLCKuSY9KbQdBFoETvPNETv0y4N7c=
+github.com/pion/transport/v2 v2.2.1/go.mod h1:cXXWavvCnFF6McHTft3DWS9iic2Mftcz1Aq29pGcU5g=
github.com/pion/turn/v2 v2.0.4/go.mod h1:1812p4DcGVbYVBTiraUmP50XoKye++AMkbfp+N27mog=
github.com/pion/turn/v2 v2.0.5/go.mod h1:APg43CFyt/14Uy7heYUOGWdkem/Wu4PhCO/bjyrTqMw=
-github.com/pion/turn/v2 v2.0.6 h1:AsXjSPR6Im15DMTB39NlfdTY9BQfieANPBjdg/aVNwY=
github.com/pion/turn/v2 v2.0.6/go.mod h1:+y7xl719J8bAEVpSXBXvTxStjJv3hbz9YFflvkpcGPw=
+github.com/pion/turn/v2 v2.1.0 h1:5wGHSgGhJhP/RpabkUb/T9PdsAjkGLS6toYz5HNzoSI=
+github.com/pion/turn/v2 v2.1.0/go.mod h1:yrT5XbXSGX1VFSF31A3c1kCNB5bBZgk/uu5LET162qs=
github.com/pion/udp v0.1.0/go.mod h1:BPELIjbwE9PRbd/zxI/KYBnbo7B6+oA6YuEaNE8lths=
-github.com/pion/udp v0.1.1 h1:8UAPvyqmsxK8oOjloDk4wUt63TzFe9WEJkg5lChlj7o=
github.com/pion/udp v0.1.1/go.mod h1:6AFo+CMdKQm7UiA0eUPA8/eVCTx8jBIITLZHc9DWX5M=
github.com/pion/webrtc/v2 v2.2.26/go.mod h1:XMZbZRNHyPDe1gzTIHFcQu02283YO45CbiwFgKvXnmc=
github.com/pion/webrtc/v3 v3.0.11/go.mod h1:WEvXneGTeqNmiR59v5jTsxMc4yXQyOQcRsrdAbNwSEU=
github.com/pion/webrtc/v3 v3.0.27/go.mod h1:QpLDmsU5a/a05n230gRtxZRvfHhFzn9ukGUL2x4G5ic=
github.com/pion/webrtc/v3 v3.0.32/go.mod h1:wX3V5dQQUGCifhT1mYftC2kCrDQX6ZJ3B7Yad0R9JK0=
-github.com/pion/webrtc/v3 v3.1.24-0.20220208053747-94262c1b2b38 h1:+IEql+S+YAj3S5e7Ftl/u4xPcZGG0WwLFsyFj6NRTz4=
github.com/pion/webrtc/v3 v3.1.24-0.20220208053747-94262c1b2b38/go.mod h1:L5S/oAhL0Fzt/rnftVQRrP80/j5jygY7XRZzWwFx6P4=
+github.com/pion/webrtc/v3 v3.2.9 h1:U8NSjQDlZZ+Iy/hg42Q/u6mhEVSXYvKrOIZiZwYTfLc=
+github.com/pion/webrtc/v3 v3.2.9/go.mod h1:gjQLMZeyN3jXBGdxGmUYCyKjOuYX/c99BDjGqmadq0A=
github.com/pkg/browser v0.0.0-20210706143420-7d21f8c997e2/go.mod h1:HKlIX3XHQyzLZPlr7++PzdhaXEj94dEiJgZDTsxEqUI=
github.com/pkg/browser v0.0.0-20210911075715-681adbf594b8/go.mod h1:HKlIX3XHQyzLZPlr7++PzdhaXEj94dEiJgZDTsxEqUI=
github.com/pkg/diff v0.0.0-20210226163009-20ebb0f2a09e/go.mod h1:pJLUxLENpZxwdsKMEsNbx1VGcRFpLqf3715MtcvvzbA=
@@ -1848,14 +1871,12 @@ github.com/prometheus/tsdb v0.10.0 h1:If5rVCMTp6W2SiRAQFlbpJNgVlgMEd+U2GZckwK38i
github.com/prometheus/tsdb v0.10.0/go.mod h1:oi49uRhEe9dPUTlS3JRZOwJuVi6tmh10QSgwXEyGCt4=
github.com/quic-go/qpack v0.4.0 h1:Cr9BXA1sQS2SmDUWjSofMPNKmvF6IiIfDRmgU0w1ZCo=
github.com/quic-go/qpack v0.4.0/go.mod h1:UZVnYIfi5GRk+zI9UMaCPsmZ2xKJP7XBUvVyT1Knj9A=
-github.com/quic-go/qtls-go1-19 v0.3.3 h1:wznEHvJwd+2X3PqftRha0SUKmGsnb6dfArMhy9PeJVE=
-github.com/quic-go/qtls-go1-19 v0.3.3/go.mod h1:ySOI96ew8lnoKPtSqx2BlI5wCpUVPT05RMAlajtnyOI=
-github.com/quic-go/qtls-go1-20 v0.2.3 h1:m575dovXn1y2ATOb1XrRFcrv0F+EQmlowTkoraNkDPI=
-github.com/quic-go/qtls-go1-20 v0.2.3/go.mod h1:JKtK6mjbAVcUTN/9jZpvLbGxvdWIKS8uT7EiStoU1SM=
-github.com/quic-go/quic-go v0.36.4 h1:CXn/ZLN5Vntlk53fjR+kUMC8Jt7flfQe+I5Ty5A+k0o=
-github.com/quic-go/quic-go v0.36.4/go.mod h1:qxQumdeKw5GmWs1OsTZZnOxzSI+RJWuhf1O8FN35L2o=
-github.com/quic-go/webtransport-go v0.5.3 h1:5XMlzemqB4qmOlgIus5zB45AcZ2kCgCy2EptUrfOPWU=
-github.com/quic-go/webtransport-go v0.5.3/go.mod h1:OhmmgJIzTTqXK5xvtuX0oBpLV2GkLWNDA+UeTGJXErU=
+github.com/quic-go/qtls-go1-20 v0.3.4 h1:MfFAPULvst4yoMgY9QmtpYmfij/em7O8UUi+bNVm7Cg=
+github.com/quic-go/qtls-go1-20 v0.3.4/go.mod h1:X9Nh97ZL80Z+bX/gUXMbipO6OxdiDi58b/fMC9mAL+k=
+github.com/quic-go/quic-go v0.39.4 h1:PelfiuG7wXEffUT2yceiqz5V6Pc0TA5ruOd1LcmFc1s=
+github.com/quic-go/quic-go v0.39.4/go.mod h1:T09QsDQWjLiQ74ZmacDfqZmhY/NLnw5BC40MANNNZ1Q=
+github.com/quic-go/webtransport-go v0.6.0 h1:CvNsKqc4W2HljHJnoT+rMmbRJybShZ0YPFDD3NxaZLY=
+github.com/quic-go/webtransport-go v0.6.0/go.mod h1:9KjU4AEBqEQidGHNDkZrb8CAa1abRaosM2yGOyiikEc=
github.com/raulk/go-watchdog v1.3.0 h1:oUmdlHxdkXRJlwfG0O9omj8ukerm8MEQavSiDTEtBsk=
github.com/raulk/go-watchdog v1.3.0/go.mod h1:fIvOnLbF0b0ZwkB9YU4mOW9Did//4vPZtDqv66NfsMU=
github.com/rcrowley/go-metrics v0.0.0-20181016184325-3113b8401b8a/go.mod h1:bCqnVzQkZxMG4s8nGwiZ5l3QUCyqpo9Y+/ZMZ9VjZe4=
@@ -2007,8 +2028,8 @@ github.com/status-im/migrate/v4 v4.6.2-status.3 h1:Khwjb59NzniloUr5i9s9AtkEyqBbQ
github.com/status-im/migrate/v4 v4.6.2-status.3/go.mod h1:c/kc90n47GZu/58nnz1OMLTf7uE4Da4gZP5qmU+A/v8=
github.com/status-im/notify v1.0.2-status h1:x8wev0Sh8H8KAf4bVcv+L0dVHldBESOKUlqRqRY7uL8=
github.com/status-im/notify v1.0.2-status/go.mod h1:gF3zSOrafR9DQEWSE8TjfI9NkooDxbyT4UgRGKZA0lc=
-github.com/status-im/rendezvous v1.3.7 h1:rZGWsFCjPV3MWeUkLkZSOGTAvyRf+rxx5hnEGLE4OHg=
-github.com/status-im/rendezvous v1.3.7/go.mod h1:r0vCbQJByTteMajN0f+Mcet/Vd7uAXxFPfewNpI2iXQ=
+github.com/status-im/rendezvous v1.3.8-0.20240110194857-cc5be22bf83e h1:pCOHeAYmYttXQBCn+6u01bs5d/W3XslxmplFhru4X1Y=
+github.com/status-im/rendezvous v1.3.8-0.20240110194857-cc5be22bf83e/go.mod h1:LEPENTHDBGCxXVZx6FEKNKN+tfPaIK+lmiGv1DxkJW4=
github.com/status-im/resize v0.0.0-20201215164250-7c6d9f0d3088 h1:ClCAP2FPCvl8hGMhbUx/tq/sOu2wibztAa5jAvQEe4Q=
github.com/status-im/resize v0.0.0-20201215164250-7c6d9f0d3088/go.mod h1:+92j1tN27DypDeBFxkg0uzkqfh1bNHTZe3Bv2PjvxpM=
github.com/status-im/status-go/extkeys v1.1.2 h1:FSjARgDathJ3rIapJt851LsIXP9Oyuu2M2jPJKuzloU=
@@ -2044,6 +2065,9 @@ github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/
github.com/stretchr/testify v1.7.1/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/stretchr/testify v1.7.2/go.mod h1:R6va5+xMeoiuVRoj+gSkQ7d3FALtqAAGI1FQKckRals=
github.com/stretchr/testify v1.8.0/go.mod h1:yNjHg4UonilssWZ8iaSj1OCr/vHnekPRkoO+kdMU+MU=
+github.com/stretchr/testify v1.8.1/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4=
+github.com/stretchr/testify v1.8.2/go.mod h1:w2LPCIKwWwSfY2zedu0+kehJoqGctiVI29o6fzry7u4=
+github.com/stretchr/testify v1.8.3/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
github.com/stretchr/testify v1.8.4 h1:CcVxjf3Q8PM0mHUKJCdn+eZZtm5yQwehR5yeSVQQcUk=
github.com/stretchr/testify v1.8.4/go.mod h1:sz/lmYIOXD/1dqDmKjjqLyZ2RngseejIcXlSw2iwfAo=
github.com/subosito/gotenv v1.2.0/go.mod h1:N0PQaV/YGNqwC0u51sEeR/aUtSLEXKX9iv69rRypqCw=
@@ -2104,10 +2128,10 @@ github.com/vishvananda/netns v0.0.0-20200728191858-db3c7e526aae/go.mod h1:DD4vA1
github.com/vishvananda/netns v0.0.0-20210104183010-2eb08e3e575f/go.mod h1:DD4vA1DwXk04H54A1oHXtwZmA0grkVMdPxx/VGLCah0=
github.com/waku-org/go-discover v0.0.0-20221209174356-61c833f34d98 h1:xwY0kW5XZFimdqfZb9cZwT1S3VJP9j3AE6bdNd9boXM=
github.com/waku-org/go-discover v0.0.0-20221209174356-61c833f34d98/go.mod h1:eBHgM6T4EG0RZzxpxKy+rGz/6Dw2Nd8DWxS0lm9ESDw=
-github.com/waku-org/go-libp2p-rendezvous v0.0.0-20230628220917-7b4e5ae4c0e7 h1:0e1h+p84yBp0IN7AqgbZlV7lgFBjm214lgSOE7CeJmE=
-github.com/waku-org/go-libp2p-rendezvous v0.0.0-20230628220917-7b4e5ae4c0e7/go.mod h1:pFvOZ9YTFsW0o5zJW7a0B5tr1owAijRWJctXJ2toL04=
-github.com/waku-org/go-waku v0.8.1-0.20240104144340-585648c4eefe h1:2D97fbaKlIQRjWMz/iTjnYcxi2z6ekKvspTGtcuPHgU=
-github.com/waku-org/go-waku v0.8.1-0.20240104144340-585648c4eefe/go.mod h1:+b5fPPJ4YUIAPJtPOtwB7bTrOQ9lF15I2LnQjV6NMIA=
+github.com/waku-org/go-libp2p-rendezvous v0.0.0-20240110193335-a67d1cc760a0 h1:R4YYx2QamhBRl/moIxkDCNW+OP7AHbyWLBygDc/xIMo=
+github.com/waku-org/go-libp2p-rendezvous v0.0.0-20240110193335-a67d1cc760a0/go.mod h1:EhZP9fee0DYjKH/IOQvoNSy1tSHp2iZadsHGphcAJgY=
+github.com/waku-org/go-waku v0.8.1-0.20240112174027-faf046e059a5 h1:D/IVX11ZKKUoBm9paWQFVyXyXFYAuovuqQzo9gUnqlE=
+github.com/waku-org/go-waku v0.8.1-0.20240112174027-faf046e059a5/go.mod h1:nUmz07T/miK91i9b7vCIV4QN+fWElmkClvqd+1Wd9w4=
github.com/waku-org/go-zerokit-rln v0.1.14-0.20240102145250-fa738c0bdf59 h1:jisj+OCI6QydLtFq3Pyhu49wl9ytPN7oAHjMfepHDrA=
github.com/waku-org/go-zerokit-rln v0.1.14-0.20240102145250-fa738c0bdf59/go.mod h1:1PdBdPzyTaKt3VnpAHk3zj+r9dXPFOr3IHZP9nFle6E=
github.com/waku-org/go-zerokit-rln-apple v0.0.0-20230916172309-ee0ee61dde2b h1:KgZVhsLkxsj5gb/FfndSCQu6VYwALrCOgYI3poR95yE=
@@ -2229,14 +2253,16 @@ go.uber.org/atomic v1.6.0/go.mod h1:sABNBOSYdrvTF6hTgEIbc7YasKWGhgEQZyfxyTvoXHQ=
go.uber.org/atomic v1.7.0/go.mod h1:fEN4uk6kAWBTFdckzkM89CLk9XfWZrxpCo0nPH17wJc=
go.uber.org/atomic v1.11.0 h1:ZvwS0R+56ePWxUNi+Atn9dWONBPp/AUETXlHW0DxSjE=
go.uber.org/atomic v1.11.0/go.mod h1:LUxbIzbOniOlMKjJjyPfpl4v+PKK2cNJn91OQbhoJI0=
-go.uber.org/dig v1.17.0 h1:5Chju+tUvcC+N7N6EV08BJz41UZuO3BmHcN4A287ZLI=
-go.uber.org/dig v1.17.0/go.mod h1:rTxpf7l5I0eBTlE6/9RL+lDybC7WFwY2QH55ZSjy1mU=
-go.uber.org/fx v1.20.0 h1:ZMC/pnRvhsthOZh9MZjMq5U8Or3mA9zBSPaLnzs3ihQ=
-go.uber.org/fx v1.20.0/go.mod h1:qCUj0btiR3/JnanEr1TYEePfSw6o/4qYJscgvzQ5Ub0=
+go.uber.org/dig v1.17.1 h1:Tga8Lz8PcYNsWsyHMZ1Vm0OQOUaJNDyvPImgbAu9YSc=
+go.uber.org/dig v1.17.1/go.mod h1:Us0rSJiThwCv2GteUN0Q7OKvU7n5J4dxZ9JKUXozFdE=
+go.uber.org/fx v1.20.1 h1:zVwVQGS8zYvhh9Xxcu4w1M6ESyeMzebzj2NbSayZ4Mk=
+go.uber.org/fx v1.20.1/go.mod h1:iSYNbHf2y55acNCwCXKx7LbWb5WG1Bnue5RDXz1OREg=
go.uber.org/goleak v1.1.10/go.mod h1:8a7PlsEVH3e/a/GLqe5IIrQx6GzcnRmZEufDUTk4A7A=
go.uber.org/goleak v1.1.11-0.20210813005559-691160354723/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ=
go.uber.org/goleak v1.1.12/go.mod h1:cwTWslyiVhfpKIDGSZEM2HlOvcqm+tG4zioyIeLoqMQ=
go.uber.org/goleak v1.2.1 h1:NBol2c7O1ZokfZ0LEU9K6Whx/KnwvepVetCUhtKja4A=
+go.uber.org/mock v0.3.0 h1:3mUxI1No2/60yUYax92Pt8eNOEecx2D3lcXZh2NEZJo=
+go.uber.org/mock v0.3.0/go.mod h1:a6FSlNadKUHUa9IP5Vyt1zh4fC7uAwxMutEAscFbkZc=
go.uber.org/multierr v1.1.0/go.mod h1:wR5kodmAFQ0UK8QlbwjlSNy0Z68gJhDJUG5sjR94q/0=
go.uber.org/multierr v1.3.0/go.mod h1:VgVr7evmIr6uPjLBxg28wmKNXyqE9akIJ5XnfpiKl+4=
go.uber.org/multierr v1.5.0/go.mod h1:FeouvMocqHpRaaGuG9EjoKcStLC43Zu/fmqdUMPcKYU=
@@ -2249,8 +2275,8 @@ go.uber.org/zap v1.10.0/go.mod h1:vwi/ZaCAaUcBkycHslxD9B2zi4UTXhF60s6SWpuDF0Q=
go.uber.org/zap v1.13.0/go.mod h1:zwrFLgMcdUuIBviXEYEH1YKNaOBnKXsx2IPda5bBwHM=
go.uber.org/zap v1.17.0/go.mod h1:MXVU+bhUf/A7Xi2HNOnopQOrmycQ5Ih87HtOu4q5SSo=
go.uber.org/zap v1.19.1/go.mod h1:j3DNczoxDZroyBnOT1L/Q79cfUMGZxlv/9dzN7SM1rI=
-go.uber.org/zap v1.24.0 h1:FiJd5l1UOLj0wCgbSE0rwwXHzEdAZS6hiiSnxJN/D60=
-go.uber.org/zap v1.24.0/go.mod h1:2kMP+WWQ8aoFoedH3T2sq6iJ2yDWpHbP0f6MQbS9Gkg=
+go.uber.org/zap v1.26.0 h1:sI7k6L95XOKS281NhVKOFCUNIvv9e0w4BF8N3u+tCRo=
+go.uber.org/zap v1.26.0/go.mod h1:dtElttAiwGvoJ/vj4IwHBS/gXsEu/pZ50mUIRWuG0so=
go4.org v0.0.0-20180809161055-417644f6feb5/go.mod h1:MkTOUMDaeVYJUOUsaDXIhWPZYa1yOyC1qaOBpL57BhE=
golang.org/x/build v0.0.0-20190111050920-041ab4dc3f9d/go.mod h1:OWs+y06UdEOHN4y+MfF/py+xQ/tYqIWW03b70/CG9Rw=
golang.org/x/crypto v0.0.0-20170930174604-9419663f5a44/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4=
@@ -2298,8 +2324,10 @@ golang.org/x/crypto v0.0.0-20210921155107-089bfa567519/go.mod h1:GvvjBRRGRdwPK5y
golang.org/x/crypto v0.0.0-20211215153901-e495a2d5b3d3/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
golang.org/x/crypto v0.0.0-20220131195533-30dcbda58838/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
golang.org/x/crypto v0.0.0-20220331220935-ae2d96664a29/go.mod h1:IxCIyHEi3zRg3s0A5j5BB6A9Jmi73HwBIUl50j+osU4=
-golang.org/x/crypto v0.12.0 h1:tFM/ta59kqch6LlvYnPa0yx5a83cL2nHflFhYKvv9Yk=
-golang.org/x/crypto v0.12.0/go.mod h1:NF0Gs7EO5K4qLn+Ylc+fih8BSTeIjAP05siRnAh98yw=
+golang.org/x/crypto v0.8.0/go.mod h1:mRqEX+O9/h5TFCrQhkgjo2yKi0yYA+9ecGkdQoHrywE=
+golang.org/x/crypto v0.9.0/go.mod h1:yrmDGqONDYtNj3tH8X9dzUun2m2lzPa9ngI6/RUPGR0=
+golang.org/x/crypto v0.14.0 h1:wBqGXzWJW6m1XrIKlAH0Hs1JJ7+9KBwnIO8v66Q9cHc=
+golang.org/x/crypto v0.14.0/go.mod h1:MVFd36DqK4CsrnJYDkBA3VC4m2GkXAM0PvzMCn4JQf4=
golang.org/x/exp v0.0.0-20180321215751-8460e604b9de/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
golang.org/x/exp v0.0.0-20180807140117-3d87b88a115f/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
golang.org/x/exp v0.0.0-20190121172915-509febef88a4/go.mod h1:CJ0aWSM057203Lf6IL+f9T1iT9GByDxfZKAQTCR3kQA=
@@ -2314,8 +2342,8 @@ golang.org/x/exp v0.0.0-20191227195350-da58074b4299/go.mod h1:2RIsYlXP63K8oxa1u0
golang.org/x/exp v0.0.0-20200119233911-0405dc783f0a/go.mod h1:2RIsYlXP63K8oxa1u096TMicItID8zy7Y6sNkU49FU4=
golang.org/x/exp v0.0.0-20200207192155-f17229e696bd/go.mod h1:J/WKrq2StrnmMY6+EHIKF9dgMWnmCNThgcyBT1FY9mM=
golang.org/x/exp v0.0.0-20200224162631-6cc2880d07d6/go.mod h1:3jZMyOhIsHpP37uCMkUooju7aAi5cS1Q23tOzKc+0MU=
-golang.org/x/exp v0.0.0-20230713183714-613f0c0eb8a1 h1:MGwJjxBy0HJshjDNfLsYO8xppfqWlA5ZT9OhtUUhTNw=
-golang.org/x/exp v0.0.0-20230713183714-613f0c0eb8a1/go.mod h1:FXUEEKJgO7OQYeo8N01OfiKP8RXMtf6e8aTskBGqWdc=
+golang.org/x/exp v0.0.0-20231006140011-7918f672742d h1:jtJma62tbqLibJ5sFQz8bKtEM8rJBtfilJ2qTU199MI=
+golang.org/x/exp v0.0.0-20231006140011-7918f672742d/go.mod h1:ldy0pHrwJyGW56pPQzzkH36rKxoZW1tw7ZJpeKx+hdo=
golang.org/x/image v0.0.0-20180708004352-c73c2afc3b81/go.mod h1:ux5Hcp/YLpHSI86hEcLt0YII63i6oz57MZXIpbrjZUs=
golang.org/x/image v0.0.0-20190227222117-0694c2d4d067/go.mod h1:kZ7UVZpmo3dzQBMxlp+ypCbDeSB+sBbTgSJuh5dn5js=
golang.org/x/image v0.0.0-20190802002840-cff245a6509b/go.mod h1:FeLwcggjj3mMvU+oOTbSwawSJRM1uh48EjtB4UJZlP0=
@@ -2353,8 +2381,9 @@ golang.org/x/mod v0.4.1/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
golang.org/x/mod v0.4.2/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA=
golang.org/x/mod v0.5.0/go.mod h1:5OXOZSfqPIIbmVBIIKWRFfZjPR0E5r58TLhUjH0a2Ro=
golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4=
-golang.org/x/mod v0.12.0 h1:rmsUpXtvNzj340zd98LZ4KntptpfRHwpFOHG188oHXc=
-golang.org/x/mod v0.12.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
+golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs=
+golang.org/x/mod v0.13.0 h1:I/DsJXRlw/8l/0c24sM9yb0T4z9liZTduXvdAWYiysY=
+golang.org/x/mod v0.13.0/go.mod h1:hTbmBsO62+eylJbnUtE2MGJUyE7QWk4xUqPFrRgJ+7c=
golang.org/x/net v0.0.0-20180218175443-cbe0f9307d01/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20180524181706-dfa909b99c79/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
golang.org/x/net v0.0.0-20180719180050-a680a1efc54d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4=
@@ -2444,9 +2473,15 @@ golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su
golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk=
golang.org/x/net v0.0.0-20220607020251-c690dde0001d/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c=
+golang.org/x/net v0.1.0/go.mod h1:Cx3nUiGt4eDBEyega/BKRp+/AlGL8hYe7U9odMt2Cco=
golang.org/x/net v0.4.0/go.mod h1:MBQ8lrhLObU/6UmLb4fmbmk5OcyYmqtbGd/9yIeKjEE=
-golang.org/x/net v0.14.0 h1:BONx9s002vGdD9umnlX1Po8vOZmrgH34qlHcD1MfK14=
-golang.org/x/net v0.14.0/go.mod h1:PpSgVXXLK0OxS0F31C1/tv6XNguvCrnXIDrFMspZIUI=
+golang.org/x/net v0.5.0/go.mod h1:DivGGAXEgPSlEBzxGzZI+ZLohi+xUj054jfeKui00ws=
+golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs=
+golang.org/x/net v0.8.0/go.mod h1:QVkue5JL9kW//ek3r6jTKnTFis1tRmNAW2P1shuFdJc=
+golang.org/x/net v0.9.0/go.mod h1:d48xBJpPfHeWQsugry2m+kC02ZBRGRgulfHnEXEuWns=
+golang.org/x/net v0.10.0/go.mod h1:0qNGK6F8kojg2nk9dLZ2mShWaEBan6FAoqfSigmmuDg=
+golang.org/x/net v0.17.0 h1:pVaXccu2ozPjCXewfr1S7xza/zcXTity9cCdXQYSjIM=
+golang.org/x/net v0.17.0/go.mod h1:NxSsAGuq816PNPmqtQdLE42eU2Fs7NoRIZrHJAlaCOE=
golang.org/x/oauth2 v0.0.0-20180227000427-d7d64896b5ff/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
golang.org/x/oauth2 v0.0.0-20181017192945-9dcd33a902f4/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U=
@@ -2482,8 +2517,9 @@ golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJ
golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20210220032951-036812b2e83c/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
-golang.org/x/sync v0.3.0 h1:ftCYgMx6zT/asHUrPw8BLLscYtGznsLAnjq5RH9P66E=
-golang.org/x/sync v0.3.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
+golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM=
+golang.org/x/sync v0.4.0 h1:zxkM55ReGkDlKSM+Fu41A+zmbZuaPVbGMzvvdUPznYQ=
+golang.org/x/sync v0.4.0/go.mod h1:FU7BRWz2tNW+3quACPkgCx/L+uEAv1htQ0V83Z9Rj+Y=
golang.org/x/sys v0.0.0-20180224232135-f6cff0780e54/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20180810173357-98c5dad5d1a0/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
golang.org/x/sys v0.0.0-20180823144017-11551d06cbcc/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY=
@@ -2639,19 +2675,30 @@ golang.org/x/sys v0.0.0-20220317061510-51cd9980dadf/go.mod h1:oPkhp1MJrh7nUepCBc
golang.org/x/sys v0.0.0-20220412211240-33da011f77ad/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.2.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.3.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.4.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
-golang.org/x/sys v0.11.0 h1:eG7RXZHdqOJ1i+0lgLgCpSXAp6M3LYlAo6osgSi0xOM=
-golang.org/x/sys v0.11.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.7.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.8.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
+golang.org/x/sys v0.13.0 h1:Af8nKPmuFypiUBjVoU9V20FiaFXOcuZI21p0ycVYYGE=
+golang.org/x/sys v0.13.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
golang.org/x/term v0.0.0-20201117132131-f5c789dd3221/go.mod h1:Nr5EML6q2oocZ2LXRh80K7BxOlk5/8JxuGnuhpl+muw=
golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/term v0.0.0-20210220032956-6a3ed077a48d/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo=
golang.org/x/term v0.0.0-20210615171337-6886f2dfbf5b/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
+golang.org/x/term v0.1.0/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8=
golang.org/x/term v0.3.0/go.mod h1:q750SLmJuPmVoN1blW3UFBPREJfb1KmY3vwxfr+nFDA=
-golang.org/x/term v0.11.0 h1:F9tnn/DA/Im8nCwm+fX+1/eBwi4qFjRT++MhtVC4ZX0=
-golang.org/x/term v0.11.0/go.mod h1:zC9APTIj3jG3FdV/Ons+XE1riIZXG4aZ4GTHiPZJPIU=
+golang.org/x/term v0.4.0/go.mod h1:9P2UbLfCdcvo3p/nzKvsmas4TnlujnuoV9hGgYzW1lQ=
+golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k=
+golang.org/x/term v0.6.0/go.mod h1:m6U89DPEgQRMq3DNkDClhWw02AUbt2daBVO4cn4Hv9U=
+golang.org/x/term v0.7.0/go.mod h1:P32HKFT3hSsZrRxla30E9HqToFYAQPCMs/zFMBUFqPY=
+golang.org/x/term v0.8.0/go.mod h1:xPskH00ivmX89bAKVGSKKtLOWNx2+17Eiy94tnKShWo=
+golang.org/x/term v0.13.0 h1:bb+I9cTfFazGW51MZqBVmZy7+JEJMouUHTUSKVQLBek=
+golang.org/x/term v0.13.0/go.mod h1:LTmsnFJwVN6bCy1rVCoS+qHT1HhALEFxKncY3WNNh4U=
golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ=
@@ -2661,9 +2708,14 @@ golang.org/x/text v0.3.4/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.5/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ=
golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ=
+golang.org/x/text v0.4.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
golang.org/x/text v0.5.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
-golang.org/x/text v0.12.0 h1:k+n5B8goJNdU7hSvEtMUz3d1Q6D/XW4COJSJR6fN0mc=
-golang.org/x/text v0.12.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
+golang.org/x/text v0.6.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
+golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8=
+golang.org/x/text v0.8.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
+golang.org/x/text v0.9.0/go.mod h1:e1OnstbJyHTd6l/uOt8jFFHp6TRDWZR/bV3emEE/zU8=
+golang.org/x/text v0.13.0 h1:ablQoSUd0tRdKxZewP80B+BaqeKJuVhuRxj/dkrun3k=
+golang.org/x/text v0.13.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE=
golang.org/x/time v0.0.0-20180412165947-fbb02b2291d2/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ=
@@ -2763,8 +2815,9 @@ golang.org/x/tools v0.1.3/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
golang.org/x/tools v0.1.4/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
golang.org/x/tools v0.1.5/go.mod h1:o0xws9oXOQQZyjljx8fwUC0k7L1pTE6eaCbjGeHmOkk=
golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc=
-golang.org/x/tools v0.12.1-0.20230818130535-1517d1a3ba60 h1:o4bs4seAAlSiZQAZbO6/RP5XBCZCooQS3Pgc0AUjWts=
-golang.org/x/tools v0.12.1-0.20230818130535-1517d1a3ba60/go.mod h1:Sc0INKfu04TlqNoRA1hgpFZbhYXHPr4V5DzpSBTPqQM=
+golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU=
+golang.org/x/tools v0.14.0 h1:jvNa2pY0M4r62jkRQ6RwEZZyPcymeL9XZMLBbV7U2nc=
+golang.org/x/tools v0.14.0/go.mod h1:uYBEerGOWcJyEORxN+Ek8+TT266gXkNlHdJBwexUsBg=
golang.org/x/xerrors v0.0.0-20190410155217-1f06c39b4373/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20190513163551-3ee3066db522/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
@@ -2772,8 +2825,6 @@ golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8T
golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20200804184101-5ec99f83aff1/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0=
golang.org/x/xerrors v0.0.0-20220517211312-f3a8303e98df/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8=
-golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f h1:uF6paiQQebLeSXkrTqHqz0MXhXXS1KgF41eUdBNvxK0=
-golang.org/x/xerrors v0.0.0-20220609144429-65e65417b02f/go.mod h1:K8+ghG5WaK9qNqU5K3HdILfMLy1f3aNYFI/wnl100a8=
gonum.org/v1/gonum v0.0.0-20180816165407-929014505bf4/go.mod h1:Y+Yx5eoAFn32cQvJDxZx5Dpnq+c3wtXuadVZAcxbbBo=
gonum.org/v1/gonum v0.0.0-20181121035319-3f7ecaa7e8ca/go.mod h1:Y+Yx5eoAFn32cQvJDxZx5Dpnq+c3wtXuadVZAcxbbBo=
gonum.org/v1/gonum v0.6.0/go.mod h1:9mxDZsDKxgMAuccQkewq682L+0eCu4dCN2yonUJTCLU=
diff --git a/images/decode_test.go b/images/decode_test.go
index 7df58ee1e..e6caf292d 100644
--- a/images/decode_test.go
+++ b/images/decode_test.go
@@ -120,7 +120,7 @@ func TestDecodeFromURL(t *testing.T) {
},
},
{
- s.URL + "/1.webp",
+ s.URL + "/1.webp", // nolint: goconst
false,
image.Rectangle{
Min: image.Point{X: 0, Y: 0},
@@ -128,7 +128,7 @@ func TestDecodeFromURL(t *testing.T) {
},
},
{
- s.URL + "/1.webp",
+ s.URL + "/1.webp", // nolint: goconst
true,
image.Rectangle{
Min: image.Point{X: 0, Y: 0},
diff --git a/mailserver/mailserver_test.go b/mailserver/mailserver_test.go
index 6e707e797..a0e514f0d 100644
--- a/mailserver/mailserver_test.go
+++ b/mailserver/mailserver_test.go
@@ -108,6 +108,7 @@ func (s *MailserverSuite) TestInit() {
}
for _, tc := range testCases {
+ tc := tc
s.T().Run(tc.info, func(*testing.T) {
mailServer := &WakuMailServer{}
shh := waku.New(&waku.DefaultConfig, nil)
@@ -300,6 +301,7 @@ func (s *MailserverSuite) TestMailServer() {
},
}
for _, tc := range testCases {
+ tc := tc
s.T().Run(tc.info, func(*testing.T) {
request := s.createRequest(tc.params)
src := crypto.FromECDSAPub(&tc.params.key.PublicKey)
diff --git a/multiaccounts/accounts/database_test.go b/multiaccounts/accounts/database_test.go
index 98ddd5c91..f7371bd69 100644
--- a/multiaccounts/accounts/database_test.go
+++ b/multiaccounts/accounts/database_test.go
@@ -231,9 +231,9 @@ func TestWatchOnlyAccounts(t *testing.T) {
require.Equal(t, wo4.Address, dbAcc.Address)
// updated watch onl to save the same account after it's saved
- wo4.Name = wo4.Name + "updated"
+ wo4.Name = wo4.Name + "updated" // nolint: goconst
wo4.ColorID = common.CustomizationColorCamel
- wo4.Emoji = wo4.Emoji + "updated"
+ wo4.Emoji = wo4.Emoji + "updated" // nolint: goconst
err = db.SaveOrUpdateAccounts([]*Account{wo4}, false)
require.NoError(t, err)
dbAccounts, err = db.GetActiveAccounts()
@@ -279,7 +279,7 @@ func TestUpdateKeypairName(t *testing.T) {
require.True(t, SameKeypairs(kp, dbKeypairs[0]))
// update keypair name
- kp.Name = kp.Name + "updated"
+ kp.Name = kp.Name + "updated" // nolint: goconst
kp.Accounts[0].Name = kp.Name
err = db.UpdateKeypairName(kp.KeyUID, kp.Name, kp.Clock, true)
require.NoError(t, err)
@@ -360,9 +360,9 @@ func TestKeypairs(t *testing.T) {
require.Equal(t, len(kp.Accounts), len(dbAccounts))
// update an existing account
- accToUpdate.Name = accToUpdate.Name + "updated"
+ accToUpdate.Name = accToUpdate.Name + "updated" // nolint: goconst
accToUpdate.ColorID = common.CustomizationColorBrown
- accToUpdate.Emoji = accToUpdate.Emoji + "updated"
+ accToUpdate.Emoji = accToUpdate.Emoji + "updated" // nolint: goconst
err = db.SaveOrUpdateAccounts([]*Account{accToUpdate}, false)
require.NoError(t, err)
diff --git a/multiaccounts/accounts/keycard_database.go b/multiaccounts/accounts/keycard_database.go
index 4a0ab98c0..a8a852f32 100644
--- a/multiaccounts/accounts/keycard_database.go
+++ b/multiaccounts/accounts/keycard_database.go
@@ -263,14 +263,7 @@ func (db *Database) deleteKeycardAccounts(tx *sql.Tx, kcUID string, accountAddre
}
inVector := strings.Repeat(",?", len(accountAddresses)-1)
- query := `
- DELETE
- FROM
- keycards_accounts
- WHERE
- keycard_uid = ?
- AND
- account_address IN (?` + inVector + `)`
+ query := `DELETE FROM keycards_accounts WHERE keycard_uid = ? AND account_address IN (?` + inVector + `)` // nolint: gosec
delete, err := tx.Prepare(query)
if err != nil {
diff --git a/multiaccounts/accounts/keycard_database_test.go b/multiaccounts/accounts/keycard_database_test.go
index 572983227..4d88e6752 100644
--- a/multiaccounts/accounts/keycard_database_test.go
+++ b/multiaccounts/accounts/keycard_database_test.go
@@ -20,7 +20,7 @@ func TestKeycards(t *testing.T) {
keycard2Copy := GetKeycardForSeedImportedKeypair1ForTest()
keycard2Copy.KeycardUID = keycard2Copy.KeycardUID + "C"
- keycard2Copy.KeycardName = keycard2Copy.KeycardName + "Copy"
+ keycard2Copy.KeycardName = keycard2Copy.KeycardName + "Copy" // nolint: goconst
keycard2Copy.Position = keycard2Copy.Position + 1
// Pre-condition
@@ -162,7 +162,7 @@ func TestKeycardsRemovalWhenDeletingKeypair(t *testing.T) {
keycard2Copy := GetKeycardForSeedImportedKeypair1ForTest()
keycard2Copy.KeycardUID = keycard2Copy.KeycardUID + "C"
- keycard2Copy.KeycardName = keycard2Copy.KeycardName + "Copy"
+ keycard2Copy.KeycardName = keycard2Copy.KeycardName + "Copy" // nolint: goconst
keycard2Copy.Position = keycard2Copy.Position + 1
// Pre-condition
diff --git a/protocol/activity_center_persistence.go b/protocol/activity_center_persistence.go
index 3c14a4d8a..df8efc0ec 100644
--- a/protocol/activity_center_persistence.go
+++ b/protocol/activity_center_persistence.go
@@ -813,7 +813,7 @@ func (db sqlitePersistence) MarkActivityCenterNotificationsDeleted(ids []types.H
return nil, err
}
- update := "UPDATE activity_center_notifications SET deleted = 1, updated_at = ? WHERE id IN (" + inVector + ") AND NOT deleted"
+ update := "UPDATE activity_center_notifications SET deleted = 1, updated_at = ? WHERE id IN (" + inVector + ") AND NOT deleted" // nolint: goconst, gosec
_, err = tx.Exec(update, args...)
if err != nil {
return nil, err
@@ -1072,7 +1072,7 @@ func (db sqlitePersistence) AcceptActivityCenterNotifications(ids []types.HexByt
}
inVector := strings.Repeat("?, ", len(ids)-1) + "?"
- query := "UPDATE activity_center_notifications SET read = 1, accepted = 1, updated_at = ? WHERE id IN (" + inVector + ") AND NOT deleted AND updated_at < ?" // nolint: gosec
+ query := "UPDATE activity_center_notifications SET read = 1, accepted = 1, updated_at = ? WHERE id IN (" + inVector + ") AND NOT deleted AND updated_at < ?" // nolint: gosec, goconst
_, err = tx.Exec(query, args...)
if err != nil {
return nil, err
diff --git a/protocol/communities/manager.go b/protocol/communities/manager.go
index 95665a59b..5db5be6c8 100644
--- a/protocol/communities/manager.go
+++ b/protocol/communities/manager.go
@@ -3703,8 +3703,8 @@ func (m *Manager) CreateHistoryArchiveTorrent(communityID types.HexBytes, msgs [
archiveDir := m.torrentConfig.DataDir + "/" + communityID.String()
torrentDir := m.torrentConfig.TorrentDir
- indexPath := archiveDir + "/index"
- dataPath := archiveDir + "/data"
+ indexPath := archiveDir + "/index" // nolint: goconst
+ dataPath := archiveDir + "/data" // nolint: goconst
wakuMessageArchiveIndexProto := &protobuf.WakuMessageArchiveIndex{}
wakuMessageArchiveIndex := make(map[string]*protobuf.WakuMessageArchiveIndexMetadata)
@@ -4398,11 +4398,11 @@ func (m *Manager) torrentFile(communityID string) string {
}
func (m *Manager) archiveIndexFile(communityID string) string {
- return m.torrentConfig.DataDir + "/" + communityID + "/index"
+ return m.torrentConfig.DataDir + "/" + communityID + "/index" // nolint: goconst
}
func (m *Manager) archiveDataFile(communityID string) string {
- return m.torrentConfig.DataDir + "/" + communityID + "/data"
+ return m.torrentConfig.DataDir + "/" + communityID + "/data" // nolint: goconst
}
func topicsAsByteArrays(topics []types.TopicType) [][]byte {
diff --git a/protocol/communities/persistence.go b/protocol/communities/persistence.go
index d37bfe4af..399376ec1 100644
--- a/protocol/communities/persistence.go
+++ b/protocol/communities/persistence.go
@@ -923,7 +923,7 @@ func (p *Persistence) SaveWakuMessage(message *types.Message) error {
func wakuMessageTimestampQuery(topics []types.TopicType) string {
query := " FROM waku_messages WHERE "
for i, topic := range topics {
- query += `topic = "` + topic.String() + `"`
+ query += `topic = "` + topic.String() + `"` // nolint: goconst
if i < len(topics)-1 {
query += OR
}
@@ -949,10 +949,10 @@ func (p *Persistence) GetLatestWakuMessageTimestamp(topics []types.TopicType) (u
func (p *Persistence) GetWakuMessagesByFilterTopic(topics []types.TopicType, from uint64, to uint64) ([]types.Message, error) {
- query := "SELECT sig, timestamp, topic, payload, padding, hash, third_party_id FROM waku_messages WHERE timestamp >= " + fmt.Sprint(from) + " AND timestamp < " + fmt.Sprint(to) + " AND ("
+ query := "SELECT sig, timestamp, topic, payload, padding, hash, third_party_id FROM waku_messages WHERE timestamp >= " + fmt.Sprint(from) + " AND timestamp < " + fmt.Sprint(to) + " AND (" // nolint: gosec
for i, topic := range topics {
- query += `topic = "` + topic.String() + `"`
+ query += `topic = "` + topic.String() + `"` // nolint: goconst
if i < len(topics)-1 {
query += OR
}
diff --git a/protocol/message_persistence.go b/protocol/message_persistence.go
index 83e3ac829..2c9490c1c 100644
--- a/protocol/message_persistence.go
+++ b/protocol/message_persistence.go
@@ -1483,7 +1483,7 @@ func (db sqlitePersistence) SaveMessages(messages []*common.Message) (err error)
allFields := db.tableUserMessagesAllFields()
valuesVector := strings.Repeat("?, ", db.tableUserMessagesAllFieldsCount()-1) + "?"
- query := "INSERT INTO user_messages(" + allFields + ") VALUES (" + valuesVector + ")" // nolint: gosec
+ query := "INSERT INTO user_messages(" + allFields + ") VALUES (" + valuesVector + ")" // nolint: gosec, goconst
stmt, err := tx.Prepare(query)
if err != nil {
return
diff --git a/protocol/messenger_testing_utils.go b/protocol/messenger_testing_utils.go
index 5a7476888..0cb99a00c 100644
--- a/protocol/messenger_testing_utils.go
+++ b/protocol/messenger_testing_utils.go
@@ -110,7 +110,7 @@ func WaitOnSignaledMessengerResponse(m *Messenger, condition func(*MessengerResp
return nil, errors.New(errorMessage)
case <-timeoutChan:
- return nil, errors.New("timed out: " + errorMessage)
+ return nil, errors.New("timed out: " + errorMessage) // nolint: goconst
default: // No immediate response, rest & loop back to retrieve again
time.Sleep(interval)
@@ -145,7 +145,7 @@ func WaitOnSignaledCommunityFound(m *Messenger, action func(), condition func(co
return nil
}
case <-timeoutChan:
- return errors.New("timed out: " + errorMessage)
+ return errors.New("timed out: " + errorMessage) // nolint: goconst
}
}
}
diff --git a/protocol/transport/filters_manager.go b/protocol/transport/filters_manager.go
index 8016ca5f9..c1560a832 100644
--- a/protocol/transport/filters_manager.go
+++ b/protocol/transport/filters_manager.go
@@ -151,6 +151,8 @@ func (f *FiltersManager) InitCommunityFilters(communityFiltersToInitialize []Com
defer f.mutex.Unlock()
for _, cf := range communityFiltersToInitialize {
+ cf := cf
+
if cf.PrivKey == nil {
continue
}
@@ -164,6 +166,7 @@ func (f *FiltersManager) InitCommunityFilters(communityFiltersToInitialize []Com
}
for _, pubsubTopic := range topics {
+ pubsubTopic := pubsubTopic
pk := &cf.PrivKey.PublicKey
identityStr := PublicKeyToStr(pk)
rawFilter, err := f.addAsymmetric(identityStr, pubsubTopic, cf.PrivKey, true)
diff --git a/protocol/transport/topic.go b/protocol/transport/topic.go
index e3b74d3b4..357221359 100644
--- a/protocol/transport/topic.go
+++ b/protocol/transport/topic.go
@@ -35,7 +35,7 @@ func PublicKeyToStr(publicKey *ecdsa.PublicKey) string {
}
func PersonalDiscoveryTopic(publicKey *ecdsa.PublicKey) string {
- return "contact-discovery-" + PublicKeyToStr(publicKey)
+ return "contact-discovery-" + PublicKeyToStr(publicKey) // nolint: goconst
}
// PartitionedTopic returns the associated partitioned topic string
@@ -43,7 +43,7 @@ func PersonalDiscoveryTopic(publicKey *ecdsa.PublicKey) string {
func PartitionedTopic(publicKey *ecdsa.PublicKey) string {
partition := big.NewInt(0)
partition.Mod(publicKey.X, nPartitions)
- return "contact-discovery-" + strconv.FormatInt(partition.Int64(), 10)
+ return "contact-discovery-" + strconv.FormatInt(partition.Int64(), 10) // nolint: goconst
}
func ContactCodeTopic(publicKey *ecdsa.PublicKey) string {
diff --git a/rpc/route_test.go b/rpc/route_test.go
index 2bc3835ca..091273746 100644
--- a/rpc/route_test.go
+++ b/rpc/route_test.go
@@ -13,12 +13,12 @@ func TestRouteWithUpstream(t *testing.T) {
router := newRouter(true)
for _, method := range remoteMethods {
- require.True(t, router.routeRemote(method), "method "+method+" should routed to remote")
+ require.True(t, router.routeRemote(method), "method "+method+" should routed to remote") // nolint: goconst
}
for _, method := range localTestMethods {
t.Run(method, func(t *testing.T) {
- require.False(t, router.routeRemote(method), "method "+method+" should routed to local")
+ require.False(t, router.routeRemote(method), "method "+method+" should routed to local") // nolint: goconst
})
}
}
@@ -27,11 +27,11 @@ func TestRouteWithoutUpstream(t *testing.T) {
router := newRouter(false)
for _, method := range remoteMethods {
- require.False(t, router.routeRemote(method), "method "+method+" should routed to locally without UpstreamEnabled")
+ require.False(t, router.routeRemote(method), "method "+method+" should routed to locally without UpstreamEnabled") // nolint: goconst
}
for _, method := range localTestMethods {
- require.False(t, router.routeRemote(method), "method "+method+" should routed to local")
+ require.False(t, router.routeRemote(method), "method "+method+" should routed to local") // nolint: goconst
}
}
diff --git a/server/handlers_linkpreview.go b/server/handlers_linkpreview.go
index a3af9728e..acc0337b3 100644
--- a/server/handlers_linkpreview.go
+++ b/server/handlers_linkpreview.go
@@ -67,7 +67,7 @@ func handleLinkPreviewThumbnail(db *sql.DB, logger *zap.Logger) http.HandlerFunc
return
}
- w.Header().Set("Content-Type", "image/"+mimeType)
+ w.Header().Set("Content-Type", "image/"+mimeType) // nolint: goconst
w.Header().Set("Cache-Control", "no-store")
_, err = w.Write(thumbnail)
@@ -198,7 +198,7 @@ func handleStatusLinkPreviewThumbnail(db *sql.DB, logger *zap.Logger) http.Handl
return
}
- w.Header().Set("Content-Type", "image/"+mimeType)
+ w.Header().Set("Content-Type", "image/"+mimeType) // nolint: goconst
w.Header().Set("Cache-Control", "no-store")
_, err = w.Write(thumbnail)
diff --git a/server/handlers_test.go b/server/handlers_test.go
index 72f3a533c..2325d58f8 100644
--- a/server/handlers_test.go
+++ b/server/handlers_test.go
@@ -195,7 +195,7 @@ func (s *HandlersSuite) TestHandleLinkPreviewThumbnail() {
msg.UnfurledLinks[0].ThumbnailPayload = tc.ThumbnailPayload
s.saveUserMessage(&msg)
- requestURL := "/dummy?" + tc.Parameters.Encode()
+ requestURL := "/dummy?" + tc.Parameters.Encode() // nolint: goconst
rr := s.httpGetReqRecorder(handler, requestURL)
s.Require().Equal(tc.ExpectedHTTPStatusCode, rr.Code)
if tc.CheckFunc != nil {
@@ -534,7 +534,7 @@ func (s *HandlersSuite) TestHandleStatusLinkPreviewThumbnail() {
for _, tc := range testCases {
s.Run(tc.Name, func() {
- requestURL := "/dummy?" + tc.Parameters.Encode()
+ requestURL := "/dummy?" + tc.Parameters.Encode() // nolint: goconst
rr := s.httpGetReqRecorder(handler, requestURL)
s.Require().Equal(tc.ExpectedHTTPStatusCode, rr.Code)
diff --git a/server/pairing/server_pairing_test.go b/server/pairing/server_pairing_test.go
index b8dbb87cb..9da33d83d 100644
--- a/server/pairing/server_pairing_test.go
+++ b/server/pairing/server_pairing_test.go
@@ -261,6 +261,8 @@ func (s *PairingServerSuite) TestPairingServer_handlePairingChallengeMiddleware_
s.Require().Equal("[client] status not ok when receiving account data, received '403 Forbidden'", err.Error())
}
+const helloMsg = "Hello I like to be a tls server. You said: `"
+
func testHandler(t *testing.T) func(w http.ResponseWriter, r *http.Request) {
return func(w http.ResponseWriter, r *http.Request) {
say, ok := r.URL.Query()["say"]
@@ -268,7 +270,7 @@ func testHandler(t *testing.T) func(w http.ResponseWriter, r *http.Request) {
say = append(say, "nothing")
}
- _, err := w.Write([]byte("Hello I like to be a tls server. You said: `" + say[0] + "` " + time.Now().String()))
+ _, err := w.Write([]byte("Hello I like to be a tls server. You said: `" + say[0] + "` " + time.Now().String())) // nolint: goconst
if err != nil {
require.NoError(t, err)
}
@@ -318,5 +320,5 @@ func (s *PairingServerSuite) TestGetOutboundIPWithFullServerE2e() {
content, err := ioutil.ReadAll(response.Body)
s.Require().NoError(err)
- s.Require().Equal("Hello I like to be a tls server. You said: `"+thing+"`", string(content[:109]))
+ s.Require().Equal(helloMsg+thing+"`", string(content[:109]))
}
diff --git a/server/server_test.go b/server/server_test.go
index 7a0074a5d..93ceb68c6 100644
--- a/server/server_test.go
+++ b/server/server_test.go
@@ -93,55 +93,55 @@ func (s *ServerURLSuite) TestServer_MakeBaseURL() {
}
func (s *ServerURLSuite) TestServer_MakeImageServerURL() {
- s.Require().Equal(baseURLWithCustomPort+"/messages/", s.server.MakeImageServerURL())
- s.testNoPort(baseURLWithDefaultPort+"/messages/", s.serverNoPort.MakeImageServerURL())
+ s.Require().Equal(baseURLWithCustomPort+"/messages/", s.server.MakeImageServerURL()) // nolint: goconst
+ s.testNoPort(baseURLWithDefaultPort+"/messages/", s.serverNoPort.MakeImageServerURL()) // nolint: goconst
}
func (s *ServerURLSuite) TestServer_MakeImageURL() {
s.Require().Equal(
- baseURLWithCustomPort+"/messages/images?messageId=0x10aded70ffee",
+ baseURLWithCustomPort+"/messages/images?messageId=0x10aded70ffee", // nolint: goconst
s.server.MakeImageURL("0x10aded70ffee"))
s.testNoPort(
- baseURLWithDefaultPort+"/messages/images?messageId=0x10aded70ffee",
+ baseURLWithDefaultPort+"/messages/images?messageId=0x10aded70ffee", // nolint: goconst
s.serverNoPort.MakeImageURL("0x10aded70ffee"))
}
func (s *ServerURLSuite) TestServer_MakeLinkPreviewThumbnailURL() {
s.Require().Equal(
- baseURLWithCustomPort+"/link-preview/thumbnail?message-id=99&url=https%3A%2F%2Fgithub.com",
+ baseURLWithCustomPort+"/link-preview/thumbnail?message-id=99&url=https%3A%2F%2Fgithub.com", // nolint: goconst
s.server.MakeLinkPreviewThumbnailURL("99", "https://github.com"))
s.testNoPort(
- baseURLWithDefaultPort+"/link-preview/thumbnail?message-id=99&url=https%3A%2F%2Fgithub.com",
+ baseURLWithDefaultPort+"/link-preview/thumbnail?message-id=99&url=https%3A%2F%2Fgithub.com", // nolint: goconst
s.serverNoPort.MakeLinkPreviewThumbnailURL("99", "https://github.com"))
}
func (s *ServerURLSuite) TestServer_MakeStatusLinkPreviewThumbnailURL() {
s.Require().Equal(
- baseURLWithCustomPort+"/status-link-preview/thumbnail?image-id=contact-icon&message-id=99&url=https%3A%2F%2Fstatus.app",
+ baseURLWithCustomPort+"/status-link-preview/thumbnail?image-id=contact-icon&message-id=99&url=https%3A%2F%2Fstatus.app", // nolint: goconst
s.server.MakeStatusLinkPreviewThumbnailURL("99", "https://status.app", common.MediaServerContactIcon))
s.testNoPort(
- baseURLWithDefaultPort+"/status-link-preview/thumbnail?image-id=contact-icon&message-id=99&url=https%3A%2F%2Fstatus.app",
+ baseURLWithDefaultPort+"/status-link-preview/thumbnail?image-id=contact-icon&message-id=99&url=https%3A%2F%2Fstatus.app", // nolint: goconst
s.serverNoPort.MakeStatusLinkPreviewThumbnailURL("99", "https://status.app", common.MediaServerContactIcon))
}
func (s *ServerURLSuite) TestServer_MakeAudioURL() {
s.Require().Equal(
- baseURLWithCustomPort+"/messages/audio?messageId=0xde1e7ebee71e",
+ baseURLWithCustomPort+"/messages/audio?messageId=0xde1e7ebee71e", // nolint: goconst
s.server.MakeAudioURL("0xde1e7ebee71e"))
s.testNoPort(
- baseURLWithDefaultPort+"/messages/audio?messageId=0xde1e7ebee71e",
+ baseURLWithDefaultPort+"/messages/audio?messageId=0xde1e7ebee71e", // nolint: goconst
s.serverNoPort.MakeAudioURL("0xde1e7ebee71e"))
}
func (s *ServerURLSuite) TestServer_MakeStickerURL() {
s.Require().Equal(
- baseURLWithCustomPort+"/ipfs?hash=0xdeadbeef4ac0",
+ baseURLWithCustomPort+"/ipfs?hash=0xdeadbeef4ac0", // nolint: goconst
s.server.MakeStickerURL("0xdeadbeef4ac0"))
s.testNoPort(
- baseURLWithDefaultPort+"/ipfs?hash=0xdeadbeef4ac0",
+ baseURLWithDefaultPort+"/ipfs?hash=0xdeadbeef4ac0", // nolint: goconst
s.serverNoPort.MakeStickerURL("0xdeadbeef4ac0"))
}
diff --git a/services/mailservers/database.go b/services/mailservers/database.go
index 0a9e2e6a0..853a692eb 100644
--- a/services/mailservers/database.go
+++ b/services/mailservers/database.go
@@ -37,7 +37,7 @@ func (m Mailserver) IDBytes() ([]byte, error) {
if err != nil {
return nil, err
}
- return []byte(id.Pretty()), err
+ return []byte(id), err
}
node, err := enode.ParseV4(m.Address)
diff --git a/services/wallet/balance/balance_cache.go b/services/wallet/balance/balance_cache.go
index 4d9bde8e6..2fd079041 100644
--- a/services/wallet/balance/balance_cache.go
+++ b/services/wallet/balance/balance_cache.go
@@ -56,9 +56,9 @@ type genericCache[B cacheIface[uint64, *big.Int], N cacheIface[uint64, *int64],
nonceRangeCache[NR]
// balances maps an address and chain to a cache of a block number and the balance of this particular address on the chain
- balances addressChainMap[B]
- nonces addressChainMap[N]
- rw sync.RWMutex
+ balances addressChainMap[B] // nolint: structcheck
+ nonces addressChainMap[N] // nolint: structcheck
+ rw sync.RWMutex // nolint: structcheck
}
func (b *genericCache[_, _, _]) GetBalance(account common.Address, chainID uint64, blockNumber *big.Int) *big.Int {
diff --git a/services/wallet/balance/nonce_range.go b/services/wallet/balance/nonce_range.go
index 27b369825..c3ebcd6a0 100644
--- a/services/wallet/balance/nonce_range.go
+++ b/services/wallet/balance/nonce_range.go
@@ -18,9 +18,9 @@ type nonceRange struct {
type sortedNonceRangesCacheType addressChainMap[[]nonceRange] // address->chainID->[]nonceRange
type nonceRangeCache[T cacheIface[int64, nonceRange]] struct {
- nonceRanges addressChainMap[T]
- sortedRanges sortedNonceRangesCacheType
- rw sync.RWMutex
+ nonceRanges addressChainMap[T] // nolint: structcheck
+ sortedRanges sortedNonceRangesCacheType // nolint: structcheck
+ rw sync.RWMutex // nolint: structcheck
}
func newNonceRangeCache[T cacheIface[int64, nonceRange]]() *nonceRangeCache[T] {
diff --git a/services/wallet/balance/simple_cache.go b/services/wallet/balance/simple_cache.go
index b071a1c54..78361f2d5 100644
--- a/services/wallet/balance/simple_cache.go
+++ b/services/wallet/balance/simple_cache.go
@@ -11,7 +11,7 @@ func NewSimpleCacher() Cacher {
// implements cacheIface for plain map internal storage
type mapCache[K comparable, V any] struct {
- cache map[K]V
+ cache map[K]V // nolint: structcheck
}
func (c *mapCache[K, V]) get(key K) V {
diff --git a/services/wallet/balance/ttl_cache.go b/services/wallet/balance/ttl_cache.go
index a438658bb..f0c74cd15 100644
--- a/services/wallet/balance/ttl_cache.go
+++ b/services/wallet/balance/ttl_cache.go
@@ -20,7 +20,7 @@ func NewCacherWithTTL(ttl time.Duration) Cacher {
// TTL cache implementation of cacheIface
type ttlCache[K comparable, V any] struct {
- cache *ttlcache.Cache[K, V]
+ cache *ttlcache.Cache[K, V] // nolint: structcheck
}
//nolint:golint,unused // linter does not detect using it via reflect
diff --git a/services/wallet/on_ramp_test.go b/services/wallet/on_ramp_test.go
index 5fa93f15f..602669c23 100644
--- a/services/wallet/on_ramp_test.go
+++ b/services/wallet/on_ramp_test.go
@@ -21,7 +21,7 @@ func TestCryptoOnRamps_Get(t *testing.T) {
{options: &CryptoOnRampOptions{dataSourceType: DataSourceStatic}},
{options: &CryptoOnRampOptions{
dataSourceType: DataSourceHTTP,
- dataSource: s.URL + "/ramps.json",
+ dataSource: s.URL + "/ramps.json", // nolint: goconst
}},
}
@@ -40,7 +40,7 @@ func TestCryptoOnRampManager_hasCacheExpired(t *testing.T) {
corm := NewCryptoOnRampManager(&CryptoOnRampOptions{
dataSourceType: DataSourceHTTP,
- dataSource: s.URL + "/ramps.json",
+ dataSource: s.URL + "/ramps.json", // nolint: goconst
})
nt := time.Time{}.Add(30 * time.Minute)
diff --git a/services/wallet/transfer/database.go b/services/wallet/transfer/database.go
index b734ff537..58457cea6 100644
--- a/services/wallet/transfer/database.go
+++ b/services/wallet/transfer/database.go
@@ -327,6 +327,7 @@ func insertBlocksWithTransactions(chainID uint64, creator statementCreator, head
func updateOrInsertTransfers(chainID uint64, creator statementCreator, transfers []Transfer) error {
txsDBFields := make([]transferDBFields, 0, len(transfers))
for _, t := range transfers {
+ t := t
var receiptType *uint8
var txHash, blockHash *common.Hash
var receiptStatus, cumulativeGasUsed, gasUsed *uint64
diff --git a/services/wallet/transfer/transaction_manager_multitransaction.go b/services/wallet/transfer/transaction_manager_multitransaction.go
index 729e5010a..26437665e 100644
--- a/services/wallet/transfer/transaction_manager_multitransaction.go
+++ b/services/wallet/transfer/transaction_manager_multitransaction.go
@@ -65,14 +65,14 @@ func rowsToMultiTransactions(rows *sql.Rows) ([]*MultiTransaction, error) {
if fromAmountDB.Valid {
multiTransaction.FromAmount = new(hexutil.Big)
if _, ok := (*big.Int)(multiTransaction.FromAmount).SetString(fromAmountDB.String, 0); !ok {
- return nil, errors.New("failed to convert fromAmountDB.String to big.Int: " + fromAmountDB.String)
+ return nil, errors.New("failed to convert fromAmountDB.String to big.Int: " + fromAmountDB.String) // nolint: goconst
}
}
if toAmountDB.Valid {
multiTransaction.ToAmount = new(hexutil.Big)
if _, ok := (*big.Int)(multiTransaction.ToAmount).SetString(toAmountDB.String, 0); !ok {
- return nil, errors.New("failed to convert fromAmountDB.String to big.Int: " + toAmountDB.String)
+ return nil, errors.New("failed to convert fromAmountDB.String to big.Int: " + toAmountDB.String) // nolint: goconst
}
}
diff --git a/shell.nix b/shell.nix
index 589e52177..6b16dae48 100644
--- a/shell.nix
+++ b/shell.nix
@@ -10,8 +10,8 @@
android_sdk.accept_license = true;
};
overlays = [
- (self: super: {
- androidPkgs = pkgs.androidenv.composeAndroidPackages {
+ (final: prev: {
+ androidPkgs = prev.androidenv.composeAndroidPackages {
toolsVersion = "26.1.1";
platformToolsVersion = "33.0.3";
buildToolsVersions = [ "31.0.0" ];
@@ -24,6 +24,19 @@
"extras;google;m2repository"
];
};
+ # https://github.com/golang/go/issues/58426
+ gomobile = prev.gomobile.override {
+ buildGoModule = args: prev.buildGo120Module ( args // rec {
+ version = "unstable-2023-11-27";
+ src = prev.fetchgit {
+ rev = "76ac6878050a2eef81867f2c6c21108e59919e8f";
+ name = "gomobile";
+ url = "https://go.googlesource.com/mobile";
+ sha256 = "sha256-mq7gKccvI7VCBEiQTueWxMPOCgg/MGE8y2+BlwWx5pw=";
+ };
+ vendorSha256 = "sha256-8OBLVd4zs89hoJXzC8BPRgrYjjR7DiA39+7tTaSYUFI=";
+ });
+ };
})
];
}
@@ -49,7 +62,7 @@ in pkgs.mkShell {
buildInputs = with pkgs; [
git jq which
- go_1_19 golangci-lint go-junit-report gopls go-bindata gomobileMod
+ go_1_20 golangci-lint go-junit-report gopls go-bindata gomobileMod
mockgen protobuf3_20 protoc-gen-go
] ++ lib.optional stdenv.isDarwin xcodeWrapper;
@@ -63,4 +76,4 @@ in pkgs.mkShell {
# Sandbox causes Xcode issues on MacOS. Requires sandbox=relaxed.
# https://github.com/status-im/status-mobile/pull/13912
__noChroot = stdenv.isDarwin;
-}
+}
\ No newline at end of file
diff --git a/transactions/transactor_test.go b/transactions/transactor_test.go
index e3f432c7d..b4edca5a7 100644
--- a/transactions/transactor_test.go
+++ b/transactions/transactor_test.go
@@ -267,6 +267,7 @@ func (s *TransactorSuite) TestSendTransactionWithSignature() {
}
for _, scenario := range scenarios {
+ scenario := scenario
desc := fmt.Sprintf("nonceFromNetwork: %d, tx nonce: %d, expect error: %v", scenario.nonceFromNetwork, scenario.txNonce, scenario.expectError)
s.T().Run(desc, func(t *testing.T) {
nonce := scenario.txNonce
diff --git a/vendor/github.com/golang/mock/mockgen/version.1.11.go b/vendor/github.com/golang/mock/mockgen/version.1.11.go
deleted file mode 100644
index e6b25db23..000000000
--- a/vendor/github.com/golang/mock/mockgen/version.1.11.go
+++ /dev/null
@@ -1,26 +0,0 @@
-// Copyright 2019 Google LLC
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-// +build !go1.12
-
-package main
-
-import (
- "log"
-)
-
-func printModuleVersion() {
- log.Printf("No version information is available for Mockgen compiled with " +
- "version 1.11")
-}
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/.golangci.yml b/vendor/github.com/hashicorp/golang-lru/v2/.golangci.yml
index 95700902d..7e7b8a962 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/.golangci.yml
+++ b/vendor/github.com/hashicorp/golang-lru/v2/.golangci.yml
@@ -2,12 +2,13 @@
# SPDX-License-Identifier: MPL-2.0
linters:
+ fast: false
+ disable-all: true
enable:
- - megacheck
- revive
+ - megacheck
- govet
- unconvert
- - megacheck
- gas
- gocyclo
- dupl
@@ -16,18 +17,30 @@ linters:
- unused
- typecheck
- ineffassign
- - stylecheck
+ # - stylecheck
- exportloopref
- gocritic
- nakedret
- gosimple
- prealloc
- fast: false
- disable-all: true
+
+# golangci-lint configuration file
+linters-settings:
+ revive:
+ ignore-generated-header: true
+ severity: warning
+ rules:
+ - name: package-comments
+ severity: warning
+ disabled: true
+ - name: exported
+ severity: warning
+ disabled: false
+ arguments: ["checkPrivateReceivers", "disableStutteringCheck"]
issues:
+ exclude-use-default: false
exclude-rules:
- path: _test\.go
linters:
- dupl
- exclude-use-default: false
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/2q.go b/vendor/github.com/hashicorp/golang-lru/v2/2q.go
index 1f0055b7b..5e00d9a7d 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/2q.go
+++ b/vendor/github.com/hashicorp/golang-lru/v2/2q.go
@@ -181,6 +181,16 @@ func (c *TwoQueueCache[K, V]) Keys() []K {
return append(k1, k2...)
}
+// Values returns a slice of the values in the cache.
+// The frequently used values are first in the returned slice.
+func (c *TwoQueueCache[K, V]) Values() []V {
+ c.lock.RLock()
+ defer c.lock.RUnlock()
+ v1 := c.frequent.Values()
+ v2 := c.recent.Values()
+ return append(v1, v2...)
+}
+
// Remove removes the provided key from the cache.
func (c *TwoQueueCache[K, V]) Remove(key K) {
c.lock.Lock()
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/README.md b/vendor/github.com/hashicorp/golang-lru/v2/README.md
index 4c08cc46f..a942eb539 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/README.md
+++ b/vendor/github.com/hashicorp/golang-lru/v2/README.md
@@ -9,17 +9,71 @@ Documentation
Full docs are available on [Go Packages](https://pkg.go.dev/github.com/hashicorp/golang-lru/v2)
-Example
-=======
-
-Using the LRU is very simple:
+LRU cache example
+=================
```go
-l, _ := New[int, interface{}](128)
-for i := 0; i < 256; i++ {
- l.Add(i, nil)
-}
-if l.Len() != 128 {
- panic(fmt.Sprintf("bad len: %v", l.Len()))
+package main
+
+import (
+ "fmt"
+ "github.com/hashicorp/golang-lru/v2"
+)
+
+func main() {
+ l, _ := lru.New[int, any](128)
+ for i := 0; i < 256; i++ {
+ l.Add(i, nil)
+ }
+ if l.Len() != 128 {
+ panic(fmt.Sprintf("bad len: %v", l.Len()))
+ }
+}
+```
+
+Expirable LRU cache example
+===========================
+
+```go
+package main
+
+import (
+ "fmt"
+ "time"
+
+ "github.com/hashicorp/golang-lru/v2/expirable"
+)
+
+func main() {
+ // make cache with 10ms TTL and 5 max keys
+ cache := expirable.NewLRU[string, string](5, nil, time.Millisecond*10)
+
+
+ // set value under key1.
+ cache.Add("key1", "val1")
+
+ // get value under key1
+ r, ok := cache.Get("key1")
+
+ // check for OK value
+ if ok {
+ fmt.Printf("value before expiration is found: %v, value: %q\n", ok, r)
+ }
+
+ // wait for cache to expire
+ time.Sleep(time.Millisecond * 12)
+
+ // get value under key1 after key expiration
+ r, ok = cache.Get("key1")
+ fmt.Printf("value after expiration is found: %v, value: %q\n", ok, r)
+
+ // set value under key2, would evict old entry because it is already expired.
+ cache.Add("key2", "val2")
+
+ fmt.Printf("Cache len: %d\n", cache.Len())
+ // Output:
+ // value before expiration is found: true, value: "val1"
+ // value after expiration is found: false, value: ""
+ // Cache len: 1
}
```
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/arc.go b/vendor/github.com/hashicorp/golang-lru/v2/arc.go
deleted file mode 100644
index a255aae21..000000000
--- a/vendor/github.com/hashicorp/golang-lru/v2/arc.go
+++ /dev/null
@@ -1,259 +0,0 @@
-// Copyright (c) HashiCorp, Inc.
-// SPDX-License-Identifier: MPL-2.0
-
-package lru
-
-import (
- "sync"
-
- "github.com/hashicorp/golang-lru/v2/simplelru"
-)
-
-// ARCCache is a thread-safe fixed size Adaptive Replacement Cache (ARC).
-// ARC is an enhancement over the standard LRU cache in that tracks both
-// frequency and recency of use. This avoids a burst in access to new
-// entries from evicting the frequently used older entries. It adds some
-// additional tracking overhead to a standard LRU cache, computationally
-// it is roughly 2x the cost, and the extra memory overhead is linear
-// with the size of the cache. ARC has been patented by IBM, but is
-// similar to the TwoQueueCache (2Q) which requires setting parameters.
-type ARCCache[K comparable, V any] struct {
- size int // Size is the total capacity of the cache
- p int // P is the dynamic preference towards T1 or T2
-
- t1 simplelru.LRUCache[K, V] // T1 is the LRU for recently accessed items
- b1 simplelru.LRUCache[K, struct{}] // B1 is the LRU for evictions from t1
-
- t2 simplelru.LRUCache[K, V] // T2 is the LRU for frequently accessed items
- b2 simplelru.LRUCache[K, struct{}] // B2 is the LRU for evictions from t2
-
- lock sync.RWMutex
-}
-
-// NewARC creates an ARC of the given size
-func NewARC[K comparable, V any](size int) (*ARCCache[K, V], error) {
- // Create the sub LRUs
- b1, err := simplelru.NewLRU[K, struct{}](size, nil)
- if err != nil {
- return nil, err
- }
- b2, err := simplelru.NewLRU[K, struct{}](size, nil)
- if err != nil {
- return nil, err
- }
- t1, err := simplelru.NewLRU[K, V](size, nil)
- if err != nil {
- return nil, err
- }
- t2, err := simplelru.NewLRU[K, V](size, nil)
- if err != nil {
- return nil, err
- }
-
- // Initialize the ARC
- c := &ARCCache[K, V]{
- size: size,
- p: 0,
- t1: t1,
- b1: b1,
- t2: t2,
- b2: b2,
- }
- return c, nil
-}
-
-// Get looks up a key's value from the cache.
-func (c *ARCCache[K, V]) Get(key K) (value V, ok bool) {
- c.lock.Lock()
- defer c.lock.Unlock()
-
- // If the value is contained in T1 (recent), then
- // promote it to T2 (frequent)
- if val, ok := c.t1.Peek(key); ok {
- c.t1.Remove(key)
- c.t2.Add(key, val)
- return val, ok
- }
-
- // Check if the value is contained in T2 (frequent)
- if val, ok := c.t2.Get(key); ok {
- return val, ok
- }
-
- // No hit
- return
-}
-
-// Add adds a value to the cache.
-func (c *ARCCache[K, V]) Add(key K, value V) {
- c.lock.Lock()
- defer c.lock.Unlock()
-
- // Check if the value is contained in T1 (recent), and potentially
- // promote it to frequent T2
- if c.t1.Contains(key) {
- c.t1.Remove(key)
- c.t2.Add(key, value)
- return
- }
-
- // Check if the value is already in T2 (frequent) and update it
- if c.t2.Contains(key) {
- c.t2.Add(key, value)
- return
- }
-
- // Check if this value was recently evicted as part of the
- // recently used list
- if c.b1.Contains(key) {
- // T1 set is too small, increase P appropriately
- delta := 1
- b1Len := c.b1.Len()
- b2Len := c.b2.Len()
- if b2Len > b1Len {
- delta = b2Len / b1Len
- }
- if c.p+delta >= c.size {
- c.p = c.size
- } else {
- c.p += delta
- }
-
- // Potentially need to make room in the cache
- if c.t1.Len()+c.t2.Len() >= c.size {
- c.replace(false)
- }
-
- // Remove from B1
- c.b1.Remove(key)
-
- // Add the key to the frequently used list
- c.t2.Add(key, value)
- return
- }
-
- // Check if this value was recently evicted as part of the
- // frequently used list
- if c.b2.Contains(key) {
- // T2 set is too small, decrease P appropriately
- delta := 1
- b1Len := c.b1.Len()
- b2Len := c.b2.Len()
- if b1Len > b2Len {
- delta = b1Len / b2Len
- }
- if delta >= c.p {
- c.p = 0
- } else {
- c.p -= delta
- }
-
- // Potentially need to make room in the cache
- if c.t1.Len()+c.t2.Len() >= c.size {
- c.replace(true)
- }
-
- // Remove from B2
- c.b2.Remove(key)
-
- // Add the key to the frequently used list
- c.t2.Add(key, value)
- return
- }
-
- // Potentially need to make room in the cache
- if c.t1.Len()+c.t2.Len() >= c.size {
- c.replace(false)
- }
-
- // Keep the size of the ghost buffers trim
- if c.b1.Len() > c.size-c.p {
- c.b1.RemoveOldest()
- }
- if c.b2.Len() > c.p {
- c.b2.RemoveOldest()
- }
-
- // Add to the recently seen list
- c.t1.Add(key, value)
-}
-
-// replace is used to adaptively evict from either T1 or T2
-// based on the current learned value of P
-func (c *ARCCache[K, V]) replace(b2ContainsKey bool) {
- t1Len := c.t1.Len()
- if t1Len > 0 && (t1Len > c.p || (t1Len == c.p && b2ContainsKey)) {
- k, _, ok := c.t1.RemoveOldest()
- if ok {
- c.b1.Add(k, struct{}{})
- }
- } else {
- k, _, ok := c.t2.RemoveOldest()
- if ok {
- c.b2.Add(k, struct{}{})
- }
- }
-}
-
-// Len returns the number of cached entries
-func (c *ARCCache[K, V]) Len() int {
- c.lock.RLock()
- defer c.lock.RUnlock()
- return c.t1.Len() + c.t2.Len()
-}
-
-// Keys returns all the cached keys
-func (c *ARCCache[K, V]) Keys() []K {
- c.lock.RLock()
- defer c.lock.RUnlock()
- k1 := c.t1.Keys()
- k2 := c.t2.Keys()
- return append(k1, k2...)
-}
-
-// Remove is used to purge a key from the cache
-func (c *ARCCache[K, V]) Remove(key K) {
- c.lock.Lock()
- defer c.lock.Unlock()
- if c.t1.Remove(key) {
- return
- }
- if c.t2.Remove(key) {
- return
- }
- if c.b1.Remove(key) {
- return
- }
- if c.b2.Remove(key) {
- return
- }
-}
-
-// Purge is used to clear the cache
-func (c *ARCCache[K, V]) Purge() {
- c.lock.Lock()
- defer c.lock.Unlock()
- c.t1.Purge()
- c.t2.Purge()
- c.b1.Purge()
- c.b2.Purge()
-}
-
-// Contains is used to check if the cache contains a key
-// without updating recency or frequency.
-func (c *ARCCache[K, V]) Contains(key K) bool {
- c.lock.RLock()
- defer c.lock.RUnlock()
- return c.t1.Contains(key) || c.t2.Contains(key)
-}
-
-// Peek is used to inspect the cache value of a key
-// without updating recency or frequency.
-func (c *ARCCache[K, V]) Peek(key K) (value V, ok bool) {
- c.lock.RLock()
- defer c.lock.RUnlock()
- if val, ok := c.t1.Peek(key); ok {
- return val, ok
- }
- return c.t2.Peek(key)
-}
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/doc.go b/vendor/github.com/hashicorp/golang-lru/v2/doc.go
index 2474929f7..24107ee0e 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/doc.go
+++ b/vendor/github.com/hashicorp/golang-lru/v2/doc.go
@@ -3,21 +3,21 @@
// Package lru provides three different LRU caches of varying sophistication.
//
-// Cache is a simple LRU cache. It is based on the
-// LRU implementation in groupcache:
-// https://github.com/golang/groupcache/tree/master/lru
+// Cache is a simple LRU cache. It is based on the LRU implementation in
+// groupcache: https://github.com/golang/groupcache/tree/master/lru
//
// TwoQueueCache tracks frequently used and recently used entries separately.
-// This avoids a burst of accesses from taking out frequently used entries,
-// at the cost of about 2x computational overhead and some extra bookkeeping.
+// This avoids a burst of accesses from taking out frequently used entries, at
+// the cost of about 2x computational overhead and some extra bookkeeping.
//
-// ARCCache is an adaptive replacement cache. It tracks recent evictions as
-// well as recent usage in both the frequent and recent caches. Its
-// computational overhead is comparable to TwoQueueCache, but the memory
-// overhead is linear with the size of the cache.
+// ARCCache is an adaptive replacement cache. It tracks recent evictions as well
+// as recent usage in both the frequent and recent caches. Its computational
+// overhead is comparable to TwoQueueCache, but the memory overhead is linear
+// with the size of the cache.
//
// ARC has been patented by IBM, so do not use it if that is problematic for
-// your program.
+// your program. For this reason, it is in a separate go module contained within
+// this repository.
//
// All caches in this package take locks while operating, and are therefore
// thread-safe for consumers.
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/internal/list.go b/vendor/github.com/hashicorp/golang-lru/v2/internal/list.go
new file mode 100644
index 000000000..5cd74a034
--- /dev/null
+++ b/vendor/github.com/hashicorp/golang-lru/v2/internal/list.go
@@ -0,0 +1,142 @@
+// Copyright 2009 The Go Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style
+// license that can be found in the LICENSE_list file.
+
+package internal
+
+import "time"
+
+// Entry is an LRU Entry
+type Entry[K comparable, V any] struct {
+ // Next and previous pointers in the doubly-linked list of elements.
+ // To simplify the implementation, internally a list l is implemented
+ // as a ring, such that &l.root is both the next element of the last
+ // list element (l.Back()) and the previous element of the first list
+ // element (l.Front()).
+ next, prev *Entry[K, V]
+
+ // The list to which this element belongs.
+ list *LruList[K, V]
+
+ // The LRU Key of this element.
+ Key K
+
+ // The Value stored with this element.
+ Value V
+
+ // The time this element would be cleaned up, optional
+ ExpiresAt time.Time
+
+ // The expiry bucket item was put in, optional
+ ExpireBucket uint8
+}
+
+// PrevEntry returns the previous list element or nil.
+func (e *Entry[K, V]) PrevEntry() *Entry[K, V] {
+ if p := e.prev; e.list != nil && p != &e.list.root {
+ return p
+ }
+ return nil
+}
+
+// LruList represents a doubly linked list.
+// The zero Value for LruList is an empty list ready to use.
+type LruList[K comparable, V any] struct {
+ root Entry[K, V] // sentinel list element, only &root, root.prev, and root.next are used
+ len int // current list Length excluding (this) sentinel element
+}
+
+// Init initializes or clears list l.
+func (l *LruList[K, V]) Init() *LruList[K, V] {
+ l.root.next = &l.root
+ l.root.prev = &l.root
+ l.len = 0
+ return l
+}
+
+// NewList returns an initialized list.
+func NewList[K comparable, V any]() *LruList[K, V] { return new(LruList[K, V]).Init() }
+
+// Length returns the number of elements of list l.
+// The complexity is O(1).
+func (l *LruList[K, V]) Length() int { return l.len }
+
+// Back returns the last element of list l or nil if the list is empty.
+func (l *LruList[K, V]) Back() *Entry[K, V] {
+ if l.len == 0 {
+ return nil
+ }
+ return l.root.prev
+}
+
+// lazyInit lazily initializes a zero List Value.
+func (l *LruList[K, V]) lazyInit() {
+ if l.root.next == nil {
+ l.Init()
+ }
+}
+
+// insert inserts e after at, increments l.len, and returns e.
+func (l *LruList[K, V]) insert(e, at *Entry[K, V]) *Entry[K, V] {
+ e.prev = at
+ e.next = at.next
+ e.prev.next = e
+ e.next.prev = e
+ e.list = l
+ l.len++
+ return e
+}
+
+// insertValue is a convenience wrapper for insert(&Entry{Value: v, ExpiresAt: ExpiresAt}, at).
+func (l *LruList[K, V]) insertValue(k K, v V, expiresAt time.Time, at *Entry[K, V]) *Entry[K, V] {
+ return l.insert(&Entry[K, V]{Value: v, Key: k, ExpiresAt: expiresAt}, at)
+}
+
+// Remove removes e from its list, decrements l.len
+func (l *LruList[K, V]) Remove(e *Entry[K, V]) V {
+ e.prev.next = e.next
+ e.next.prev = e.prev
+ e.next = nil // avoid memory leaks
+ e.prev = nil // avoid memory leaks
+ e.list = nil
+ l.len--
+
+ return e.Value
+}
+
+// move moves e to next to at.
+func (l *LruList[K, V]) move(e, at *Entry[K, V]) {
+ if e == at {
+ return
+ }
+ e.prev.next = e.next
+ e.next.prev = e.prev
+
+ e.prev = at
+ e.next = at.next
+ e.prev.next = e
+ e.next.prev = e
+}
+
+// PushFront inserts a new element e with value v at the front of list l and returns e.
+func (l *LruList[K, V]) PushFront(k K, v V) *Entry[K, V] {
+ l.lazyInit()
+ return l.insertValue(k, v, time.Time{}, &l.root)
+}
+
+// PushFrontExpirable inserts a new expirable element e with Value v at the front of list l and returns e.
+func (l *LruList[K, V]) PushFrontExpirable(k K, v V, expiresAt time.Time) *Entry[K, V] {
+ l.lazyInit()
+ return l.insertValue(k, v, expiresAt, &l.root)
+}
+
+// MoveToFront moves element e to the front of list l.
+// If e is not an element of l, the list is not modified.
+// The element must not be nil.
+func (l *LruList[K, V]) MoveToFront(e *Entry[K, V]) {
+ if e.list != l || l.root.next == e {
+ return
+ }
+ // see comment in List.Remove about initialization of l
+ l.move(e, &l.root)
+}
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/lru.go b/vendor/github.com/hashicorp/golang-lru/v2/lru.go
index 32d04170d..a2655f1f3 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/lru.go
+++ b/vendor/github.com/hashicorp/golang-lru/v2/lru.go
@@ -233,6 +233,14 @@ func (c *Cache[K, V]) Keys() []K {
return keys
}
+// Values returns a slice of the values in the cache, from oldest to newest.
+func (c *Cache[K, V]) Values() []V {
+ c.lock.RLock()
+ values := c.lru.Values()
+ c.lock.RUnlock()
+ return values
+}
+
// Len returns the number of items in the cache.
func (c *Cache[K, V]) Len() int {
c.lock.RLock()
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/list.go b/vendor/github.com/hashicorp/golang-lru/v2/simplelru/list.go
deleted file mode 100644
index c39da3c12..000000000
--- a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/list.go
+++ /dev/null
@@ -1,128 +0,0 @@
-// Copyright 2009 The Go Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style
-// license that can be found in the LICENSE_list file.
-
-package simplelru
-
-// entry is an LRU entry
-type entry[K comparable, V any] struct {
- // Next and previous pointers in the doubly-linked list of elements.
- // To simplify the implementation, internally a list l is implemented
- // as a ring, such that &l.root is both the next element of the last
- // list element (l.Back()) and the previous element of the first list
- // element (l.Front()).
- next, prev *entry[K, V]
-
- // The list to which this element belongs.
- list *lruList[K, V]
-
- // The LRU key of this element.
- key K
-
- // The value stored with this element.
- value V
-}
-
-// prevEntry returns the previous list element or nil.
-func (e *entry[K, V]) prevEntry() *entry[K, V] {
- if p := e.prev; e.list != nil && p != &e.list.root {
- return p
- }
- return nil
-}
-
-// lruList represents a doubly linked list.
-// The zero value for lruList is an empty list ready to use.
-type lruList[K comparable, V any] struct {
- root entry[K, V] // sentinel list element, only &root, root.prev, and root.next are used
- len int // current list length excluding (this) sentinel element
-}
-
-// init initializes or clears list l.
-func (l *lruList[K, V]) init() *lruList[K, V] {
- l.root.next = &l.root
- l.root.prev = &l.root
- l.len = 0
- return l
-}
-
-// newList returns an initialized list.
-func newList[K comparable, V any]() *lruList[K, V] { return new(lruList[K, V]).init() }
-
-// length returns the number of elements of list l.
-// The complexity is O(1).
-func (l *lruList[K, V]) length() int { return l.len }
-
-// back returns the last element of list l or nil if the list is empty.
-func (l *lruList[K, V]) back() *entry[K, V] {
- if l.len == 0 {
- return nil
- }
- return l.root.prev
-}
-
-// lazyInit lazily initializes a zero List value.
-func (l *lruList[K, V]) lazyInit() {
- if l.root.next == nil {
- l.init()
- }
-}
-
-// insert inserts e after at, increments l.len, and returns e.
-func (l *lruList[K, V]) insert(e, at *entry[K, V]) *entry[K, V] {
- e.prev = at
- e.next = at.next
- e.prev.next = e
- e.next.prev = e
- e.list = l
- l.len++
- return e
-}
-
-// insertValue is a convenience wrapper for insert(&Element{Value: v}, at).
-func (l *lruList[K, V]) insertValue(k K, v V, at *entry[K, V]) *entry[K, V] {
- return l.insert(&entry[K, V]{value: v, key: k}, at)
-}
-
-// remove removes e from its list, decrements l.len
-func (l *lruList[K, V]) remove(e *entry[K, V]) V {
- e.prev.next = e.next
- e.next.prev = e.prev
- e.next = nil // avoid memory leaks
- e.prev = nil // avoid memory leaks
- e.list = nil
- l.len--
-
- return e.value
-}
-
-// move moves e to next to at.
-func (l *lruList[K, V]) move(e, at *entry[K, V]) {
- if e == at {
- return
- }
- e.prev.next = e.next
- e.next.prev = e.prev
-
- e.prev = at
- e.next = at.next
- e.prev.next = e
- e.next.prev = e
-}
-
-// pushFront inserts a new element e with value v at the front of list l and returns e.
-func (l *lruList[K, V]) pushFront(k K, v V) *entry[K, V] {
- l.lazyInit()
- return l.insertValue(k, v, &l.root)
-}
-
-// moveToFront moves element e to the front of list l.
-// If e is not an element of l, the list is not modified.
-// The element must not be nil.
-func (l *lruList[K, V]) moveToFront(e *entry[K, V]) {
- if e.list != l || l.root.next == e {
- return
- }
- // see comment in List.Remove about initialization of l
- l.move(e, &l.root)
-}
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru.go b/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru.go
index b6731afdd..408239c45 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru.go
+++ b/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru.go
@@ -5,6 +5,8 @@ package simplelru
import (
"errors"
+
+ "github.com/hashicorp/golang-lru/v2/internal"
)
// EvictCallback is used to get a callback when a cache entry is evicted
@@ -13,8 +15,8 @@ type EvictCallback[K comparable, V any] func(key K, value V)
// LRU implements a non-thread safe fixed size LRU cache
type LRU[K comparable, V any] struct {
size int
- evictList *lruList[K, V]
- items map[K]*entry[K, V]
+ evictList *internal.LruList[K, V]
+ items map[K]*internal.Entry[K, V]
onEvict EvictCallback[K, V]
}
@@ -26,8 +28,8 @@ func NewLRU[K comparable, V any](size int, onEvict EvictCallback[K, V]) (*LRU[K,
c := &LRU[K, V]{
size: size,
- evictList: newList[K, V](),
- items: make(map[K]*entry[K, V]),
+ evictList: internal.NewList[K, V](),
+ items: make(map[K]*internal.Entry[K, V]),
onEvict: onEvict,
}
return c, nil
@@ -37,27 +39,30 @@ func NewLRU[K comparable, V any](size int, onEvict EvictCallback[K, V]) (*LRU[K,
func (c *LRU[K, V]) Purge() {
for k, v := range c.items {
if c.onEvict != nil {
- c.onEvict(k, v.value)
+ c.onEvict(k, v.Value)
}
delete(c.items, k)
}
- c.evictList.init()
+ c.evictList.Init()
}
// Add adds a value to the cache. Returns true if an eviction occurred.
func (c *LRU[K, V]) Add(key K, value V) (evicted bool) {
// Check for existing item
if ent, ok := c.items[key]; ok {
- c.evictList.moveToFront(ent)
- ent.value = value
+ c.evictList.MoveToFront(ent)
+ if c.onEvict != nil {
+ c.onEvict(key, ent.Value)
+ }
+ ent.Value = value
return false
}
// Add new item
- ent := c.evictList.pushFront(key, value)
+ ent := c.evictList.PushFront(key, value)
c.items[key] = ent
- evict := c.evictList.length() > c.size
+ evict := c.evictList.Length() > c.size
// Verify size not exceeded
if evict {
c.removeOldest()
@@ -68,8 +73,8 @@ func (c *LRU[K, V]) Add(key K, value V) (evicted bool) {
// Get looks up a key's value from the cache.
func (c *LRU[K, V]) Get(key K) (value V, ok bool) {
if ent, ok := c.items[key]; ok {
- c.evictList.moveToFront(ent)
- return ent.value, true
+ c.evictList.MoveToFront(ent)
+ return ent.Value, true
}
return
}
@@ -84,9 +89,9 @@ func (c *LRU[K, V]) Contains(key K) (ok bool) {
// Peek returns the key value (or undefined if not found) without updating
// the "recently used"-ness of the key.
func (c *LRU[K, V]) Peek(key K) (value V, ok bool) {
- var ent *entry[K, V]
+ var ent *internal.Entry[K, V]
if ent, ok = c.items[key]; ok {
- return ent.value, true
+ return ent.Value, true
}
return
}
@@ -103,35 +108,46 @@ func (c *LRU[K, V]) Remove(key K) (present bool) {
// RemoveOldest removes the oldest item from the cache.
func (c *LRU[K, V]) RemoveOldest() (key K, value V, ok bool) {
- if ent := c.evictList.back(); ent != nil {
+ if ent := c.evictList.Back(); ent != nil {
c.removeElement(ent)
- return ent.key, ent.value, true
+ return ent.Key, ent.Value, true
}
return
}
// GetOldest returns the oldest entry
func (c *LRU[K, V]) GetOldest() (key K, value V, ok bool) {
- if ent := c.evictList.back(); ent != nil {
- return ent.key, ent.value, true
+ if ent := c.evictList.Back(); ent != nil {
+ return ent.Key, ent.Value, true
}
return
}
// Keys returns a slice of the keys in the cache, from oldest to newest.
func (c *LRU[K, V]) Keys() []K {
- keys := make([]K, c.evictList.length())
+ keys := make([]K, c.evictList.Length())
i := 0
- for ent := c.evictList.back(); ent != nil; ent = ent.prevEntry() {
- keys[i] = ent.key
+ for ent := c.evictList.Back(); ent != nil; ent = ent.PrevEntry() {
+ keys[i] = ent.Key
i++
}
return keys
}
+// Values returns a slice of the values in the cache, from oldest to newest.
+func (c *LRU[K, V]) Values() []V {
+ values := make([]V, len(c.items))
+ i := 0
+ for ent := c.evictList.Back(); ent != nil; ent = ent.PrevEntry() {
+ values[i] = ent.Value
+ i++
+ }
+ return values
+}
+
// Len returns the number of items in the cache.
func (c *LRU[K, V]) Len() int {
- return c.evictList.length()
+ return c.evictList.Length()
}
// Resize changes the cache size.
@@ -149,16 +165,16 @@ func (c *LRU[K, V]) Resize(size int) (evicted int) {
// removeOldest removes the oldest item from the cache.
func (c *LRU[K, V]) removeOldest() {
- if ent := c.evictList.back(); ent != nil {
+ if ent := c.evictList.Back(); ent != nil {
c.removeElement(ent)
}
}
// removeElement is used to remove a given list element from the cache
-func (c *LRU[K, V]) removeElement(e *entry[K, V]) {
- c.evictList.remove(e)
- delete(c.items, e.key)
+func (c *LRU[K, V]) removeElement(e *internal.Entry[K, V]) {
+ c.evictList.Remove(e)
+ delete(c.items, e.Key)
if c.onEvict != nil {
- c.onEvict(e.key, e.value)
+ c.onEvict(e.Key, e.Value)
}
}
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru_interface.go b/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru_interface.go
index 3cbf02bc7..043b8bcc3 100644
--- a/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru_interface.go
+++ b/vendor/github.com/hashicorp/golang-lru/v2/simplelru/lru_interface.go
@@ -32,6 +32,9 @@ type LRUCache[K comparable, V any] interface {
// Returns a slice of the keys in the cache, from oldest to newest.
Keys() []K
+ // Values returns a slice of the values in the cache, from oldest to newest.
+ Values() []V
+
// Returns the number of items in the cache.
Len() int
diff --git a/vendor/github.com/hashicorp/golang-lru/v2/testing.go b/vendor/github.com/hashicorp/golang-lru/v2/testing.go
deleted file mode 100644
index 3277c2186..000000000
--- a/vendor/github.com/hashicorp/golang-lru/v2/testing.go
+++ /dev/null
@@ -1,19 +0,0 @@
-// Copyright (c) HashiCorp, Inc.
-// SPDX-License-Identifier: MPL-2.0
-
-package lru
-
-import (
- "crypto/rand"
- "math"
- "math/big"
- "testing"
-)
-
-func getRand(tb testing.TB) int64 {
- out, err := rand.Int(rand.Reader, big.NewInt(math.MaxInt64))
- if err != nil {
- tb.Fatal(err)
- }
- return out.Int64()
-}
diff --git a/vendor/github.com/huin/goupnp/goupnp.go b/vendor/github.com/huin/goupnp/goupnp.go
index 93c588b03..9fa89636a 100644
--- a/vendor/github.com/huin/goupnp/goupnp.go
+++ b/vendor/github.com/huin/goupnp/goupnp.go
@@ -85,7 +85,10 @@ func DiscoverDevicesCtx(ctx context.Context, searchTarget string) ([]MaybeRootDe
return nil, err
}
defer hcCleanup()
- responses, err := ssdp.SSDPRawSearchCtx(ctx, hc, string(searchTarget), 2, 3)
+
+ searchCtx, cancel := context.WithTimeout(ctx, 2*time.Second)
+ defer cancel()
+ responses, err := ssdp.RawSearch(searchCtx, hc, string(searchTarget), 3)
if err != nil {
return nil, err
}
diff --git a/vendor/github.com/huin/goupnp/httpu/httpu.go b/vendor/github.com/huin/goupnp/httpu/httpu.go
index 808d600ab..5bb8d67b6 100644
--- a/vendor/github.com/huin/goupnp/httpu/httpu.go
+++ b/vendor/github.com/huin/goupnp/httpu/httpu.go
@@ -3,6 +3,7 @@ package httpu
import (
"bufio"
"bytes"
+ "context"
"errors"
"fmt"
"log"
@@ -26,6 +27,27 @@ type ClientInterface interface {
) ([]*http.Response, error)
}
+// ClientInterfaceCtx is the equivalent of ClientInterface, except with methods
+// taking a context.Context parameter.
+type ClientInterfaceCtx interface {
+ // DoWithContext performs a request. If the input request has a
+ // deadline, then that value will be used as the timeout for how long
+ // to wait before returning the responses that were received. If the
+ // request's context is canceled, this method will return immediately.
+ //
+ // If the request's context is never canceled, and does not have a
+ // deadline, then this function WILL NEVER RETURN. You MUST set an
+ // appropriate deadline on the context, or otherwise cancel it when you
+ // want to finish an operation.
+ //
+ // An error is only returned for failing to send the request. Failures
+ // in receipt simply do not add to the resulting responses.
+ DoWithContext(
+ req *http.Request,
+ numSends int,
+ ) ([]*http.Response, error)
+}
+
// HTTPUClient is a client for dealing with HTTPU (HTTP over UDP). Its typical
// function is for HTTPMU, and particularly SSDP.
type HTTPUClient struct {
@@ -34,6 +56,7 @@ type HTTPUClient struct {
}
var _ ClientInterface = &HTTPUClient{}
+var _ ClientInterfaceCtx = &HTTPUClient{}
// NewHTTPUClient creates a new HTTPUClient, opening up a new UDP socket for the
// purpose.
@@ -75,6 +98,25 @@ func (httpu *HTTPUClient) Do(
req *http.Request,
timeout time.Duration,
numSends int,
+) ([]*http.Response, error) {
+ ctx := req.Context()
+ if timeout > 0 {
+ var cancel func()
+ ctx, cancel = context.WithTimeout(ctx, timeout)
+ defer cancel()
+ req = req.WithContext(ctx)
+ }
+
+ return httpu.DoWithContext(req, numSends)
+}
+
+// DoWithContext implements ClientInterfaceCtx.DoWithContext.
+//
+// Make sure to read the documentation on the ClientInterfaceCtx interface
+// regarding cancellation!
+func (httpu *HTTPUClient) DoWithContext(
+ req *http.Request,
+ numSends int,
) ([]*http.Response, error) {
httpu.connLock.Lock()
defer httpu.connLock.Unlock()
@@ -101,10 +143,28 @@ func (httpu *HTTPUClient) Do(
if err != nil {
return nil, err
}
- if err = httpu.conn.SetDeadline(time.Now().Add(timeout)); err != nil {
- return nil, err
+
+ // Handle context deadline/timeout
+ ctx := req.Context()
+ deadline, ok := ctx.Deadline()
+ if ok {
+ if err = httpu.conn.SetDeadline(deadline); err != nil {
+ return nil, err
+ }
}
+ // Handle context cancelation
+ done := make(chan struct{})
+ defer close(done)
+ go func() {
+ select {
+ case <-ctx.Done():
+ // if context is cancelled, stop any connections by setting time in the past.
+ httpu.conn.SetDeadline(time.Now().Add(-time.Second))
+ case <-done:
+ }
+ }()
+
// Send request.
for i := 0; i < numSends; i++ {
if n, err := httpu.conn.WriteTo(requestBuf.Bytes(), destAddr); err != nil {
diff --git a/vendor/github.com/huin/goupnp/httpu/multiclient.go b/vendor/github.com/huin/goupnp/httpu/multiclient.go
index 463ab7a69..5cc65e911 100644
--- a/vendor/github.com/huin/goupnp/httpu/multiclient.go
+++ b/vendor/github.com/huin/goupnp/httpu/multiclient.go
@@ -49,14 +49,14 @@ func (mc *MultiClient) Do(
}
func (mc *MultiClient) sendRequests(
- results chan<-[]*http.Response,
+ results chan<- []*http.Response,
req *http.Request,
timeout time.Duration,
numSends int,
) error {
tasks := &errgroup.Group{}
for _, d := range mc.delegates {
- d := d // copy for closure
+ d := d // copy for closure
tasks.Go(func() error {
responses, err := d.Do(req, timeout, numSends)
if err != nil {
@@ -68,3 +68,65 @@ func (mc *MultiClient) sendRequests(
}
return tasks.Wait()
}
+
+// MultiClientCtx dispatches requests out to all the delegated clients.
+type MultiClientCtx struct {
+ // The HTTPU clients to delegate to.
+ delegates []ClientInterfaceCtx
+}
+
+var _ ClientInterfaceCtx = &MultiClientCtx{}
+
+// NewMultiClient creates a new MultiClient that delegates to all the given
+// clients.
+func NewMultiClientCtx(delegates []ClientInterfaceCtx) *MultiClientCtx {
+ return &MultiClientCtx{
+ delegates: delegates,
+ }
+}
+
+// DoWithContext implements ClientInterfaceCtx.DoWithContext.
+func (mc *MultiClientCtx) DoWithContext(
+ req *http.Request,
+ numSends int,
+) ([]*http.Response, error) {
+ tasks, ctx := errgroup.WithContext(req.Context())
+ req = req.WithContext(ctx) // so we cancel if the errgroup errors
+ results := make(chan []*http.Response)
+
+ // For each client, send the request to it and collect results.
+ tasks.Go(func() error {
+ defer close(results)
+ return mc.sendRequestsCtx(results, req, numSends)
+ })
+
+ var responses []*http.Response
+ tasks.Go(func() error {
+ for rs := range results {
+ responses = append(responses, rs...)
+ }
+ return nil
+ })
+
+ return responses, tasks.Wait()
+}
+
+func (mc *MultiClientCtx) sendRequestsCtx(
+ results chan<- []*http.Response,
+ req *http.Request,
+ numSends int,
+) error {
+ tasks := &errgroup.Group{}
+ for _, d := range mc.delegates {
+ d := d // copy for closure
+ tasks.Go(func() error {
+ responses, err := d.DoWithContext(req, numSends)
+ if err != nil {
+ return err
+ }
+ results <- responses
+ return nil
+ })
+ }
+ return tasks.Wait()
+}
diff --git a/vendor/github.com/huin/goupnp/network.go b/vendor/github.com/huin/goupnp/network.go
index e93763a54..a2c3a45be 100644
--- a/vendor/github.com/huin/goupnp/network.go
+++ b/vendor/github.com/huin/goupnp/network.go
@@ -10,14 +10,14 @@ import (
// httpuClient creates a HTTPU client that multiplexes to all multicast-capable
// IPv4 addresses on the host. Returns a function to clean up once the client is
// no longer required.
-func httpuClient() (httpu.ClientInterface, func(), error) {
+func httpuClient() (httpu.ClientInterfaceCtx, func(), error) {
addrs, err := localIPv4MCastAddrs()
if err != nil {
return nil, nil, ctxError(err, "requesting host IPv4 addresses")
}
closers := make([]io.Closer, 0, len(addrs))
- delegates := make([]httpu.ClientInterface, 0, len(addrs))
+ delegates := make([]httpu.ClientInterfaceCtx, 0, len(addrs))
for _, addr := range addrs {
c, err := httpu.NewHTTPUClientAddr(addr)
if err != nil {
@@ -34,7 +34,7 @@ func httpuClient() (httpu.ClientInterface, func(), error) {
}
}
- return httpu.NewMultiClient(delegates), closer, nil
+ return httpu.NewMultiClientCtx(delegates), closer, nil
}
// localIPv2MCastAddrs returns the set of IPv4 addresses on multicast-able
diff --git a/vendor/github.com/huin/goupnp/ssdp/ssdp.go b/vendor/github.com/huin/goupnp/ssdp/ssdp.go
index 240dfa73d..2f318f33e 100644
--- a/vendor/github.com/huin/goupnp/ssdp/ssdp.go
+++ b/vendor/github.com/huin/goupnp/ssdp/ssdp.go
@@ -35,6 +35,15 @@ type HTTPUClient interface {
) ([]*http.Response, error)
}
+// HTTPUClientCtx is an optional interface that will be used to perform
+// HTTP-over-UDP requests if the client implements it.
+type HTTPUClientCtx interface {
+ DoWithContext(
+ req *http.Request,
+ numSends int,
+ ) ([]*http.Response, error)
+}
+
// SSDPRawSearchCtx performs a fairly raw SSDP search request, and returns the
// unique response(s) that it receives. Each response has the requested
// searchTarget, a USN, and a valid location. maxWaitSeconds states how long to
@@ -49,8 +58,64 @@ func SSDPRawSearchCtx(
maxWaitSeconds int,
numSends int,
) ([]*http.Response, error) {
+ req, err := prepareRequest(ctx, searchTarget, maxWaitSeconds)
+ if err != nil {
+ return nil, err
+ }
+
+ allResponses, err := httpu.Do(req, time.Duration(maxWaitSeconds)*time.Second+100*time.Millisecond, numSends)
+ if err != nil {
+ return nil, err
+ }
+ return processSSDPResponses(searchTarget, allResponses)
+}
+
+// RawSearch performs a fairly raw SSDP search request, and returns the
+// unique response(s) that it receives. Each response has the requested
+// searchTarget, a USN, and a valid location. If the provided context times out
+// or is canceled, the search will be aborted. numSends is the number of
+// requests to send - 3 is a reasonable value for this.
+//
+// The provided context should have a deadline, since the SSDP protocol
+// requires the max wait time be included in search requests. If the context
+// has no deadline, then a default deadline of 3 seconds will be applied.
+func RawSearch(
+ ctx context.Context,
+ httpu HTTPUClientCtx,
+ searchTarget string,
+ numSends int,
+) ([]*http.Response, error) {
+ // We need a timeout value to include in the SSDP request; get it by
+ // checking the deadline on the context.
+ var maxWaitSeconds int
+ if deadline, ok := ctx.Deadline(); ok {
+ maxWaitSeconds = int(deadline.Sub(time.Now()) / time.Second)
+ } else {
+ // Pick a default timeout of 3 seconds if none was provided.
+ maxWaitSeconds = 3
+
+ var cancel func()
+ ctx, cancel = context.WithTimeout(ctx, time.Duration(maxWaitSeconds)*time.Second)
+ defer cancel()
+ }
+
+ req, err := prepareRequest(ctx, searchTarget, maxWaitSeconds)
+ if err != nil {
+ return nil, err
+ }
+
+ allResponses, err := httpu.DoWithContext(req, numSends)
+ if err != nil {
+ return nil, err
+ }
+ return processSSDPResponses(searchTarget, allResponses)
+}
+
+// prepareRequest checks the provided parameters and constructs a SSDP search
+// request to be sent.
+func prepareRequest(ctx context.Context, searchTarget string, maxWaitSeconds int) (*http.Request, error) {
if maxWaitSeconds < 1 {
- return nil, errors.New("ssdp: maxWaitSeconds must be >= 1")
+ return nil, errors.New("ssdp: request timeout must be at least 1s")
}
req := (&http.Request{
@@ -67,11 +132,13 @@ func SSDPRawSearchCtx(
"ST": []string{searchTarget},
},
}).WithContext(ctx)
- allResponses, err := httpu.Do(req, time.Duration(maxWaitSeconds)*time.Second+100*time.Millisecond, numSends)
- if err != nil {
- return nil, err
- }
+ return req, nil
+}
+func processSSDPResponses(
+ searchTarget string,
+ allResponses []*http.Response,
+) ([]*http.Response, error) {
isExactSearch := searchTarget != SSDPAll && searchTarget != UPNPRootDevice
seenIDs := make(map[string]bool)
diff --git a/vendor/github.com/klauspost/compress/.goreleaser.yml b/vendor/github.com/klauspost/compress/.goreleaser.yml
index 7a008a4d2..4c28dff46 100644
--- a/vendor/github.com/klauspost/compress/.goreleaser.yml
+++ b/vendor/github.com/klauspost/compress/.goreleaser.yml
@@ -3,7 +3,7 @@
before:
hooks:
- ./gen.sh
- - go install mvdan.cc/garble@v0.9.3
+ - go install mvdan.cc/garble@v0.10.1
builds:
-
@@ -92,16 +92,7 @@ builds:
archives:
-
id: s2-binaries
- name_template: "s2-{{ .Os }}_{{ .Arch }}_{{ .Version }}"
- replacements:
- aix: AIX
- darwin: OSX
- linux: Linux
- windows: Windows
- 386: i386
- amd64: x86_64
- freebsd: FreeBSD
- netbsd: NetBSD
+ name_template: "s2-{{ .Os }}_{{ .Arch }}{{ if .Arm }}v{{ .Arm }}{{ end }}"
format_overrides:
- goos: windows
format: zip
@@ -125,7 +116,7 @@ changelog:
nfpms:
-
- file_name_template: "s2_package_{{ .Version }}_{{ .Os }}_{{ .Arch }}"
+ file_name_template: "s2_package__{{ .Os }}_{{ .Arch }}{{ if .Arm }}v{{ .Arm }}{{ end }}"
vendor: Klaus Post
homepage: https://github.com/klauspost/compress
maintainer: Klaus Post
@@ -134,8 +125,3 @@ nfpms:
formats:
- deb
- rpm
- replacements:
- darwin: Darwin
- linux: Linux
- freebsd: FreeBSD
- amd64: x86_64
diff --git a/vendor/github.com/klauspost/compress/README.md b/vendor/github.com/klauspost/compress/README.md
index 4002a16a6..43de48677 100644
--- a/vendor/github.com/klauspost/compress/README.md
+++ b/vendor/github.com/klauspost/compress/README.md
@@ -16,6 +16,18 @@ This package provides various compression algorithms.
# changelog
+* Sept 19th, 2023 - [v1.17.0](https://github.com/klauspost/compress/releases/tag/v1.17.0)
+ * Add experimental dictionary builder https://github.com/klauspost/compress/pull/853
+ * Add xerial snappy read/writer https://github.com/klauspost/compress/pull/838
+ * flate: Add limited window compression https://github.com/klauspost/compress/pull/843
+ * s2: Do 2 overlapping match checks https://github.com/klauspost/compress/pull/839
+ * flate: Add amd64 assembly matchlen https://github.com/klauspost/compress/pull/837
+ * gzip: Copy bufio.Reader on Reset by @thatguystone in https://github.com/klauspost/compress/pull/860
+
+* July 1st, 2023 - [v1.16.7](https://github.com/klauspost/compress/releases/tag/v1.16.7)
+ * zstd: Fix default level first dictionary encode https://github.com/klauspost/compress/pull/829
+ * s2: add GetBufferCapacity() method by @GiedriusS in https://github.com/klauspost/compress/pull/832
+
* June 13, 2023 - [v1.16.6](https://github.com/klauspost/compress/releases/tag/v1.16.6)
* zstd: correctly ignore WithEncoderPadding(1) by @ianlancetaylor in https://github.com/klauspost/compress/pull/806
* zstd: Add amd64 match length assembly https://github.com/klauspost/compress/pull/824
@@ -50,6 +62,9 @@ This package provides various compression algorithms.
* s2: Support io.ReaderAt in ReadSeeker. https://github.com/klauspost/compress/pull/747
* s2c/s2sx: Use concurrent decoding. https://github.com/klauspost/compress/pull/746
+
+ See changes to v1.15.x
+
* Jan 21st, 2023 (v1.15.15)
* deflate: Improve level 7-9 by @klauspost in https://github.com/klauspost/compress/pull/739
* zstd: Add delta encoding support by @greatroar in https://github.com/klauspost/compress/pull/728
@@ -176,6 +191,8 @@ Stream decompression is now faster on asynchronous, since the goroutine allocati
While the release has been extensively tested, it is recommended to testing when upgrading.
+
+
See changes to v1.14.x
@@ -636,6 +653,8 @@ Here are other packages of good quality and pure Go (no cgo wrappers or autoconv
* [github.com/dsnet/compress](https://github.com/dsnet/compress) - brotli decompression, bzip2 writer.
* [github.com/ronanh/intcomp](https://github.com/ronanh/intcomp) - Integer compression.
* [github.com/spenczar/fpc](https://github.com/spenczar/fpc) - Float compression.
+* [github.com/minio/zipindex](https://github.com/minio/zipindex) - External ZIP directory index.
+* [github.com/ybirader/pzip](https://github.com/ybirader/pzip) - Fast concurrent zip archiver and extractor.
# license
diff --git a/vendor/github.com/klauspost/compress/fse/bitwriter.go b/vendor/github.com/klauspost/compress/fse/bitwriter.go
index 43e463611..e82fa3bb7 100644
--- a/vendor/github.com/klauspost/compress/fse/bitwriter.go
+++ b/vendor/github.com/klauspost/compress/fse/bitwriter.go
@@ -152,12 +152,11 @@ func (b *bitWriter) flushAlign() {
// close will write the alignment bit and write the final byte(s)
// to the output.
-func (b *bitWriter) close() error {
+func (b *bitWriter) close() {
// End mark
b.addBits16Clean(1, 1)
// flush until next byte.
b.flushAlign()
- return nil
}
// reset and continue writing by appending to out.
diff --git a/vendor/github.com/klauspost/compress/fse/compress.go b/vendor/github.com/klauspost/compress/fse/compress.go
index dac97e58a..65d777357 100644
--- a/vendor/github.com/klauspost/compress/fse/compress.go
+++ b/vendor/github.com/klauspost/compress/fse/compress.go
@@ -199,7 +199,8 @@ func (s *Scratch) compress(src []byte) error {
c2.flush(s.actualTableLog)
c1.flush(s.actualTableLog)
- return s.bw.close()
+ s.bw.close()
+ return nil
}
// writeCount will write the normalized histogram count to header.
diff --git a/vendor/github.com/klauspost/compress/huff0/bitwriter.go b/vendor/github.com/klauspost/compress/huff0/bitwriter.go
index b4d7164e3..0ebc9aaac 100644
--- a/vendor/github.com/klauspost/compress/huff0/bitwriter.go
+++ b/vendor/github.com/klauspost/compress/huff0/bitwriter.go
@@ -94,10 +94,9 @@ func (b *bitWriter) flushAlign() {
// close will write the alignment bit and write the final byte(s)
// to the output.
-func (b *bitWriter) close() error {
+func (b *bitWriter) close() {
// End mark
b.addBits16Clean(1, 1)
// flush until next byte.
b.flushAlign()
- return nil
}
diff --git a/vendor/github.com/klauspost/compress/huff0/compress.go b/vendor/github.com/klauspost/compress/huff0/compress.go
index 4ee4fa18d..518436cf3 100644
--- a/vendor/github.com/klauspost/compress/huff0/compress.go
+++ b/vendor/github.com/klauspost/compress/huff0/compress.go
@@ -227,10 +227,10 @@ func EstimateSizes(in []byte, s *Scratch) (tableSz, dataSz, reuseSz int, err err
}
func (s *Scratch) compress1X(src []byte) ([]byte, error) {
- return s.compress1xDo(s.Out, src)
+ return s.compress1xDo(s.Out, src), nil
}
-func (s *Scratch) compress1xDo(dst, src []byte) ([]byte, error) {
+func (s *Scratch) compress1xDo(dst, src []byte) []byte {
var bw = bitWriter{out: dst}
// N is length divisible by 4.
@@ -260,8 +260,8 @@ func (s *Scratch) compress1xDo(dst, src []byte) ([]byte, error) {
bw.encTwoSymbols(cTable, tmp[1], tmp[0])
}
}
- err := bw.close()
- return bw.out, err
+ bw.close()
+ return bw.out
}
var sixZeros [6]byte
@@ -283,12 +283,8 @@ func (s *Scratch) compress4X(src []byte) ([]byte, error) {
}
src = src[len(toDo):]
- var err error
idx := len(s.Out)
- s.Out, err = s.compress1xDo(s.Out, toDo)
- if err != nil {
- return nil, err
- }
+ s.Out = s.compress1xDo(s.Out, toDo)
if len(s.Out)-idx > math.MaxUint16 {
// We cannot store the size in the jump table
return nil, ErrIncompressible
@@ -315,7 +311,6 @@ func (s *Scratch) compress4Xp(src []byte) ([]byte, error) {
segmentSize := (len(src) + 3) / 4
var wg sync.WaitGroup
- var errs [4]error
wg.Add(4)
for i := 0; i < 4; i++ {
toDo := src
@@ -326,15 +321,12 @@ func (s *Scratch) compress4Xp(src []byte) ([]byte, error) {
// Separate goroutine for each block.
go func(i int) {
- s.tmpOut[i], errs[i] = s.compress1xDo(s.tmpOut[i][:0], toDo)
+ s.tmpOut[i] = s.compress1xDo(s.tmpOut[i][:0], toDo)
wg.Done()
}(i)
}
wg.Wait()
for i := 0; i < 4; i++ {
- if errs[i] != nil {
- return nil, errs[i]
- }
o := s.tmpOut[i]
if len(o) > math.MaxUint16 {
// We cannot store the size in the jump table
diff --git a/vendor/github.com/klauspost/compress/zstd/bitreader.go b/vendor/github.com/klauspost/compress/zstd/bitreader.go
index 97299d499..25ca98394 100644
--- a/vendor/github.com/klauspost/compress/zstd/bitreader.go
+++ b/vendor/github.com/klauspost/compress/zstd/bitreader.go
@@ -17,7 +17,6 @@ import (
// for aligning the input.
type bitReader struct {
in []byte
- off uint // next byte to read is at in[off - 1]
value uint64 // Maybe use [16]byte, but shifting is awkward.
bitsRead uint8
}
@@ -28,7 +27,6 @@ func (b *bitReader) init(in []byte) error {
return errors.New("corrupt stream: too short")
}
b.in = in
- b.off = uint(len(in))
// The highest bit of the last byte indicates where to start
v := in[len(in)-1]
if v == 0 {
@@ -69,21 +67,19 @@ func (b *bitReader) fillFast() {
if b.bitsRead < 32 {
return
}
- // 2 bounds checks.
- v := b.in[b.off-4:]
- v = v[:4]
+ v := b.in[len(b.in)-4:]
+ b.in = b.in[:len(b.in)-4]
low := (uint32(v[0])) | (uint32(v[1]) << 8) | (uint32(v[2]) << 16) | (uint32(v[3]) << 24)
b.value = (b.value << 32) | uint64(low)
b.bitsRead -= 32
- b.off -= 4
}
// fillFastStart() assumes the bitreader is empty and there is at least 8 bytes to read.
func (b *bitReader) fillFastStart() {
- // Do single re-slice to avoid bounds checks.
- b.value = binary.LittleEndian.Uint64(b.in[b.off-8:])
+ v := b.in[len(b.in)-8:]
+ b.in = b.in[:len(b.in)-8]
+ b.value = binary.LittleEndian.Uint64(v)
b.bitsRead = 0
- b.off -= 8
}
// fill() will make sure at least 32 bits are available.
@@ -91,25 +87,25 @@ func (b *bitReader) fill() {
if b.bitsRead < 32 {
return
}
- if b.off >= 4 {
- v := b.in[b.off-4:]
- v = v[:4]
+ if len(b.in) >= 4 {
+ v := b.in[len(b.in)-4:]
+ b.in = b.in[:len(b.in)-4]
low := (uint32(v[0])) | (uint32(v[1]) << 8) | (uint32(v[2]) << 16) | (uint32(v[3]) << 24)
b.value = (b.value << 32) | uint64(low)
b.bitsRead -= 32
- b.off -= 4
return
}
- for b.off > 0 {
- b.value = (b.value << 8) | uint64(b.in[b.off-1])
- b.bitsRead -= 8
- b.off--
+
+ b.bitsRead -= uint8(8 * len(b.in))
+ for len(b.in) > 0 {
+ b.value = (b.value << 8) | uint64(b.in[len(b.in)-1])
+ b.in = b.in[:len(b.in)-1]
}
}
// finished returns true if all bits have been read from the bit stream.
func (b *bitReader) finished() bool {
- return b.off == 0 && b.bitsRead >= 64
+ return len(b.in) == 0 && b.bitsRead >= 64
}
// overread returns true if more bits have been requested than is on the stream.
@@ -119,7 +115,7 @@ func (b *bitReader) overread() bool {
// remain returns the number of bits remaining.
func (b *bitReader) remain() uint {
- return b.off*8 + 64 - uint(b.bitsRead)
+ return 8*uint(len(b.in)) + 64 - uint(b.bitsRead)
}
// close the bitstream and returns an error if out-of-buffer reads occurred.
diff --git a/vendor/github.com/klauspost/compress/zstd/bitwriter.go b/vendor/github.com/klauspost/compress/zstd/bitwriter.go
index 78b3c61be..1952f175b 100644
--- a/vendor/github.com/klauspost/compress/zstd/bitwriter.go
+++ b/vendor/github.com/klauspost/compress/zstd/bitwriter.go
@@ -97,12 +97,11 @@ func (b *bitWriter) flushAlign() {
// close will write the alignment bit and write the final byte(s)
// to the output.
-func (b *bitWriter) close() error {
+func (b *bitWriter) close() {
// End mark
b.addBits16Clean(1, 1)
// flush until next byte.
b.flushAlign()
- return nil
}
// reset and continue writing by appending to out.
diff --git a/vendor/github.com/klauspost/compress/zstd/blockenc.go b/vendor/github.com/klauspost/compress/zstd/blockenc.go
index fd4a36f73..2cfe925ad 100644
--- a/vendor/github.com/klauspost/compress/zstd/blockenc.go
+++ b/vendor/github.com/klauspost/compress/zstd/blockenc.go
@@ -361,14 +361,21 @@ func (b *blockEnc) encodeLits(lits []byte, raw bool) error {
if len(lits) >= 1024 {
// Use 4 Streams.
out, reUsed, err = huff0.Compress4X(lits, b.litEnc)
- } else if len(lits) > 32 {
+ } else if len(lits) > 16 {
// Use 1 stream
single = true
out, reUsed, err = huff0.Compress1X(lits, b.litEnc)
} else {
err = huff0.ErrIncompressible
}
-
+ if err == nil && len(out)+5 > len(lits) {
+ // If we are close, we may still be worse or equal to raw.
+ var lh literalsHeader
+ lh.setSizes(len(out), len(lits), single)
+ if len(out)+lh.size() >= len(lits) {
+ err = huff0.ErrIncompressible
+ }
+ }
switch err {
case huff0.ErrIncompressible:
if debugEncoder {
@@ -503,7 +510,7 @@ func (b *blockEnc) encode(org []byte, raw, rawAllLits bool) error {
if len(b.literals) >= 1024 && !raw {
// Use 4 Streams.
out, reUsed, err = huff0.Compress4X(b.literals, b.litEnc)
- } else if len(b.literals) > 32 && !raw {
+ } else if len(b.literals) > 16 && !raw {
// Use 1 stream
single = true
out, reUsed, err = huff0.Compress1X(b.literals, b.litEnc)
@@ -511,6 +518,17 @@ func (b *blockEnc) encode(org []byte, raw, rawAllLits bool) error {
err = huff0.ErrIncompressible
}
+ if err == nil && len(out)+5 > len(b.literals) {
+ // If we are close, we may still be worse or equal to raw.
+ var lh literalsHeader
+ lh.setSize(len(b.literals))
+ szRaw := lh.size()
+ lh.setSizes(len(out), len(b.literals), single)
+ szComp := lh.size()
+ if len(out)+szComp >= len(b.literals)+szRaw {
+ err = huff0.ErrIncompressible
+ }
+ }
switch err {
case huff0.ErrIncompressible:
lh.setType(literalsBlockRaw)
@@ -773,10 +791,7 @@ func (b *blockEnc) encode(org []byte, raw, rawAllLits bool) error {
ml.flush(mlEnc.actualTableLog)
of.flush(ofEnc.actualTableLog)
ll.flush(llEnc.actualTableLog)
- err = wr.close()
- if err != nil {
- return err
- }
+ wr.close()
b.output = wr.out
// Maybe even add a bigger margin.
diff --git a/vendor/github.com/klauspost/compress/zstd/dict.go b/vendor/github.com/klauspost/compress/zstd/dict.go
index ca0951452..8d5567fe6 100644
--- a/vendor/github.com/klauspost/compress/zstd/dict.go
+++ b/vendor/github.com/klauspost/compress/zstd/dict.go
@@ -1,10 +1,13 @@
package zstd
import (
+ "bytes"
"encoding/binary"
"errors"
"fmt"
"io"
+ "math"
+ "sort"
"github.com/klauspost/compress/huff0"
)
@@ -14,9 +17,8 @@ type dict struct {
litEnc *huff0.Scratch
llDec, ofDec, mlDec sequenceDec
- //llEnc, ofEnc, mlEnc []*fseEncoder
- offsets [3]int
- content []byte
+ offsets [3]int
+ content []byte
}
const dictMagic = "\x37\xa4\x30\xec"
@@ -159,3 +161,374 @@ func InspectDictionary(b []byte) (interface {
d, err := loadDict(b)
return d, err
}
+
+type BuildDictOptions struct {
+ // Dictionary ID.
+ ID uint32
+
+ // Content to use to create dictionary tables.
+ Contents [][]byte
+
+ // History to use for all blocks.
+ History []byte
+
+ // Offsets to use.
+ Offsets [3]int
+
+ // CompatV155 will make the dictionary compatible with Zstd v1.5.5 and earlier.
+ // See https://github.com/facebook/zstd/issues/3724
+ CompatV155 bool
+
+ // Use the specified encoder level.
+ // The dictionary will be built using the specified encoder level,
+ // which will reflect speed and make the dictionary tailored for that level.
+ // If not set SpeedBestCompression will be used.
+ Level EncoderLevel
+
+ // DebugOut will write stats and other details here if set.
+ DebugOut io.Writer
+}
+
+func BuildDict(o BuildDictOptions) ([]byte, error) {
+ initPredefined()
+ hist := o.History
+ contents := o.Contents
+ debug := o.DebugOut != nil
+ println := func(args ...interface{}) {
+ if o.DebugOut != nil {
+ fmt.Fprintln(o.DebugOut, args...)
+ }
+ }
+ printf := func(s string, args ...interface{}) {
+ if o.DebugOut != nil {
+ fmt.Fprintf(o.DebugOut, s, args...)
+ }
+ }
+ print := func(args ...interface{}) {
+ if o.DebugOut != nil {
+ fmt.Fprint(o.DebugOut, args...)
+ }
+ }
+
+ if int64(len(hist)) > dictMaxLength {
+ return nil, fmt.Errorf("dictionary of size %d > %d", len(hist), int64(dictMaxLength))
+ }
+ if len(hist) < 8 {
+ return nil, fmt.Errorf("dictionary of size %d < %d", len(hist), 8)
+ }
+ if len(contents) == 0 {
+ return nil, errors.New("no content provided")
+ }
+ d := dict{
+ id: o.ID,
+ litEnc: nil,
+ llDec: sequenceDec{},
+ ofDec: sequenceDec{},
+ mlDec: sequenceDec{},
+ offsets: o.Offsets,
+ content: hist,
+ }
+ block := blockEnc{lowMem: false}
+ block.init()
+ enc := encoder(&bestFastEncoder{fastBase: fastBase{maxMatchOff: int32(maxMatchLen), bufferReset: math.MaxInt32 - int32(maxMatchLen*2), lowMem: false}})
+ if o.Level != 0 {
+ eOpts := encoderOptions{
+ level: o.Level,
+ blockSize: maxMatchLen,
+ windowSize: maxMatchLen,
+ dict: &d,
+ lowMem: false,
+ }
+ enc = eOpts.encoder()
+ } else {
+ o.Level = SpeedBestCompression
+ }
+ var (
+ remain [256]int
+ ll [256]int
+ ml [256]int
+ of [256]int
+ )
+ addValues := func(dst *[256]int, src []byte) {
+ for _, v := range src {
+ dst[v]++
+ }
+ }
+ addHist := func(dst *[256]int, src *[256]uint32) {
+ for i, v := range src {
+ dst[i] += int(v)
+ }
+ }
+ seqs := 0
+ nUsed := 0
+ litTotal := 0
+ newOffsets := make(map[uint32]int, 1000)
+ for _, b := range contents {
+ block.reset(nil)
+ if len(b) < 8 {
+ continue
+ }
+ nUsed++
+ enc.Reset(&d, true)
+ enc.Encode(&block, b)
+ addValues(&remain, block.literals)
+ litTotal += len(block.literals)
+ seqs += len(block.sequences)
+ block.genCodes()
+ addHist(&ll, block.coders.llEnc.Histogram())
+ addHist(&ml, block.coders.mlEnc.Histogram())
+ addHist(&of, block.coders.ofEnc.Histogram())
+ for i, seq := range block.sequences {
+ if i > 3 {
+ break
+ }
+ offset := seq.offset
+ if offset == 0 {
+ continue
+ }
+ if offset > 3 {
+ newOffsets[offset-3]++
+ } else {
+ newOffsets[uint32(o.Offsets[offset-1])]++
+ }
+ }
+ }
+ // Find most used offsets.
+ var sortedOffsets []uint32
+ for k := range newOffsets {
+ sortedOffsets = append(sortedOffsets, k)
+ }
+ sort.Slice(sortedOffsets, func(i, j int) bool {
+ a, b := sortedOffsets[i], sortedOffsets[j]
+ if a == b {
+ // Prefer the longer offset
+ return sortedOffsets[i] > sortedOffsets[j]
+ }
+ return newOffsets[sortedOffsets[i]] > newOffsets[sortedOffsets[j]]
+ })
+ if len(sortedOffsets) > 3 {
+ if debug {
+ print("Offsets:")
+ for i, v := range sortedOffsets {
+ if i > 20 {
+ break
+ }
+ printf("[%d: %d],", v, newOffsets[v])
+ }
+ println("")
+ }
+
+ sortedOffsets = sortedOffsets[:3]
+ }
+ for i, v := range sortedOffsets {
+ o.Offsets[i] = int(v)
+ }
+ if debug {
+ println("New repeat offsets", o.Offsets)
+ }
+
+ if nUsed == 0 || seqs == 0 {
+ return nil, fmt.Errorf("%d blocks, %d sequences found", nUsed, seqs)
+ }
+ if debug {
+ println("Sequences:", seqs, "Blocks:", nUsed, "Literals:", litTotal)
+ }
+ if seqs/nUsed < 512 {
+ // Use 512 as minimum.
+ nUsed = seqs / 512
+ }
+ copyHist := func(dst *fseEncoder, src *[256]int) ([]byte, error) {
+ hist := dst.Histogram()
+ var maxSym uint8
+ var maxCount int
+ var fakeLength int
+ for i, v := range src {
+ if v > 0 {
+ v = v / nUsed
+ if v == 0 {
+ v = 1
+ }
+ }
+ if v > maxCount {
+ maxCount = v
+ }
+ if v != 0 {
+ maxSym = uint8(i)
+ }
+ fakeLength += v
+ hist[i] = uint32(v)
+ }
+ dst.HistogramFinished(maxSym, maxCount)
+ dst.reUsed = false
+ dst.useRLE = false
+ err := dst.normalizeCount(fakeLength)
+ if err != nil {
+ return nil, err
+ }
+ if debug {
+ println("RAW:", dst.count[:maxSym+1], "NORM:", dst.norm[:maxSym+1], "LEN:", fakeLength)
+ }
+ return dst.writeCount(nil)
+ }
+ if debug {
+ print("Literal lengths: ")
+ }
+ llTable, err := copyHist(block.coders.llEnc, &ll)
+ if err != nil {
+ return nil, err
+ }
+ if debug {
+ print("Match lengths: ")
+ }
+ mlTable, err := copyHist(block.coders.mlEnc, &ml)
+ if err != nil {
+ return nil, err
+ }
+ if debug {
+ print("Offsets: ")
+ }
+ ofTable, err := copyHist(block.coders.ofEnc, &of)
+ if err != nil {
+ return nil, err
+ }
+
+ // Literal table
+ avgSize := litTotal
+ if avgSize > huff0.BlockSizeMax/2 {
+ avgSize = huff0.BlockSizeMax / 2
+ }
+ huffBuff := make([]byte, 0, avgSize)
+ // Target size
+ div := litTotal / avgSize
+ if div < 1 {
+ div = 1
+ }
+ if debug {
+ println("Huffman weights:")
+ }
+ for i, n := range remain[:] {
+ if n > 0 {
+ n = n / div
+ // Allow all entries to be represented.
+ if n == 0 {
+ n = 1
+ }
+ huffBuff = append(huffBuff, bytes.Repeat([]byte{byte(i)}, n)...)
+ if debug {
+ printf("[%d: %d], ", i, n)
+ }
+ }
+ }
+ if o.CompatV155 && remain[255]/div == 0 {
+ huffBuff = append(huffBuff, 255)
+ }
+ scratch := &huff0.Scratch{TableLog: 11}
+ for tries := 0; tries < 255; tries++ {
+ scratch = &huff0.Scratch{TableLog: 11}
+ _, _, err = huff0.Compress1X(huffBuff, scratch)
+ if err == nil {
+ break
+ }
+ if debug {
+ printf("Try %d: Huffman error: %v\n", tries+1, err)
+ }
+ huffBuff = huffBuff[:0]
+ if tries == 250 {
+ if debug {
+ println("Huffman: Bailing out with predefined table")
+ }
+
+ // Bail out.... Just generate something
+ huffBuff = append(huffBuff, bytes.Repeat([]byte{255}, 10000)...)
+ for i := 0; i < 128; i++ {
+ huffBuff = append(huffBuff, byte(i))
+ }
+ continue
+ }
+ if errors.Is(err, huff0.ErrIncompressible) {
+ // Try truncating least common.
+ for i, n := range remain[:] {
+ if n > 0 {
+ n = n / (div * (i + 1))
+ if n > 0 {
+ huffBuff = append(huffBuff, bytes.Repeat([]byte{byte(i)}, n)...)
+ }
+ }
+ }
+ if o.CompatV155 && len(huffBuff) > 0 && huffBuff[len(huffBuff)-1] != 255 {
+ huffBuff = append(huffBuff, 255)
+ }
+ if len(huffBuff) == 0 {
+ huffBuff = append(huffBuff, 0, 255)
+ }
+ }
+ if errors.Is(err, huff0.ErrUseRLE) {
+ for i, n := range remain[:] {
+ n = n / (div * (i + 1))
+ // Allow all entries to be represented.
+ if n == 0 {
+ n = 1
+ }
+ huffBuff = append(huffBuff, bytes.Repeat([]byte{byte(i)}, n)...)
+ }
+ }
+ }
+
+ var out bytes.Buffer
+ out.Write([]byte(dictMagic))
+ out.Write(binary.LittleEndian.AppendUint32(nil, o.ID))
+ out.Write(scratch.OutTable)
+ if debug {
+ println("huff table:", len(scratch.OutTable), "bytes")
+ println("of table:", len(ofTable), "bytes")
+ println("ml table:", len(mlTable), "bytes")
+ println("ll table:", len(llTable), "bytes")
+ }
+ out.Write(ofTable)
+ out.Write(mlTable)
+ out.Write(llTable)
+ out.Write(binary.LittleEndian.AppendUint32(nil, uint32(o.Offsets[0])))
+ out.Write(binary.LittleEndian.AppendUint32(nil, uint32(o.Offsets[1])))
+ out.Write(binary.LittleEndian.AppendUint32(nil, uint32(o.Offsets[2])))
+ out.Write(hist)
+ if debug {
+ _, err := loadDict(out.Bytes())
+ if err != nil {
+ panic(err)
+ }
+ i, err := InspectDictionary(out.Bytes())
+ if err != nil {
+ panic(err)
+ }
+ println("ID:", i.ID())
+ println("Content size:", i.ContentSize())
+ println("Encoder:", i.LitEncoder() != nil)
+ println("Offsets:", i.Offsets())
+ var totalSize int
+ for _, b := range contents {
+ totalSize += len(b)
+ }
+
+ encWith := func(opts ...EOption) int {
+ enc, err := NewWriter(nil, opts...)
+ if err != nil {
+ panic(err)
+ }
+ defer enc.Close()
+ var dst []byte
+ var totalSize int
+ for _, b := range contents {
+ dst = enc.EncodeAll(b, dst[:0])
+ totalSize += len(dst)
+ }
+ return totalSize
+ }
+ plain := encWith(WithEncoderLevel(o.Level))
+ withDict := encWith(WithEncoderLevel(o.Level), WithEncoderDict(out.Bytes()))
+ println("Input size:", totalSize)
+ println("Plain Compressed:", plain)
+ println("Dict Compressed:", withDict)
+ println("Saved:", plain-withDict, (plain-withDict)/len(contents), "bytes per input (rounded down)")
+ }
+ return out.Bytes(), nil
+}
diff --git a/vendor/github.com/klauspost/compress/zstd/enc_best.go b/vendor/github.com/klauspost/compress/zstd/enc_best.go
index 9819d4145..858f8f43a 100644
--- a/vendor/github.com/klauspost/compress/zstd/enc_best.go
+++ b/vendor/github.com/klauspost/compress/zstd/enc_best.go
@@ -197,12 +197,13 @@ encodeLoop:
// Set m to a match at offset if it looks like that will improve compression.
improve := func(m *match, offset int32, s int32, first uint32, rep int32) {
- if s-offset >= e.maxMatchOff || load3232(src, offset) != first {
+ delta := s - offset
+ if delta >= e.maxMatchOff || delta <= 0 || load3232(src, offset) != first {
return
}
if debugAsserts {
- if offset <= 0 {
- panic(offset)
+ if offset >= s {
+ panic(fmt.Sprintf("offset: %d - s:%d - rep: %d - cur :%d - max: %d", offset, s, rep, e.cur, e.maxMatchOff))
}
if !bytes.Equal(src[s:s+4], src[offset:offset+4]) {
panic(fmt.Sprintf("first match mismatch: %v != %v, first: %08x", src[s:s+4], src[offset:offset+4], first))
@@ -343,8 +344,8 @@ encodeLoop:
if best.rep > 0 {
var seq seq
seq.matchLen = uint32(best.length - zstdMinMatch)
- if debugAsserts && s <= nextEmit {
- panic("s <= nextEmit")
+ if debugAsserts && s < nextEmit {
+ panic("s < nextEmit")
}
addLiterals(&seq, best.s)
diff --git a/vendor/github.com/klauspost/compress/zstd/encoder.go b/vendor/github.com/klauspost/compress/zstd/encoder.go
index 4de0aed0d..72af7ef0f 100644
--- a/vendor/github.com/klauspost/compress/zstd/encoder.go
+++ b/vendor/github.com/klauspost/compress/zstd/encoder.go
@@ -227,10 +227,7 @@ func (e *Encoder) nextBlock(final bool) error {
DictID: e.o.dict.ID(),
}
- dst, err := fh.appendTo(tmp[:0])
- if err != nil {
- return err
- }
+ dst := fh.appendTo(tmp[:0])
s.headerWritten = true
s.wWg.Wait()
var n2 int
@@ -483,7 +480,7 @@ func (e *Encoder) EncodeAll(src, dst []byte) []byte {
Checksum: false,
DictID: 0,
}
- dst, _ = fh.appendTo(dst)
+ dst = fh.appendTo(dst)
// Write raw block as last one only.
var blk blockHeader
@@ -518,10 +515,7 @@ func (e *Encoder) EncodeAll(src, dst []byte) []byte {
if len(dst) == 0 && cap(dst) == 0 && len(src) < 1<<20 && !e.o.lowMem {
dst = make([]byte, 0, len(src))
}
- dst, err := fh.appendTo(dst)
- if err != nil {
- panic(err)
- }
+ dst = fh.appendTo(dst)
// If we can do everything in one block, prefer that.
if len(src) <= e.o.blockSize {
@@ -581,6 +575,7 @@ func (e *Encoder) EncodeAll(src, dst []byte) []byte {
// Add padding with content from crypto/rand.Reader
if e.o.pad > 0 {
add := calcSkippableFrame(int64(len(dst)), int64(e.o.pad))
+ var err error
dst, err = skippableFrame(dst, add, rand.Reader)
if err != nil {
panic(err)
diff --git a/vendor/github.com/klauspost/compress/zstd/frameenc.go b/vendor/github.com/klauspost/compress/zstd/frameenc.go
index 4ef7f5a3e..2f5d5ed45 100644
--- a/vendor/github.com/klauspost/compress/zstd/frameenc.go
+++ b/vendor/github.com/klauspost/compress/zstd/frameenc.go
@@ -22,7 +22,7 @@ type frameHeader struct {
const maxHeaderSize = 14
-func (f frameHeader) appendTo(dst []byte) ([]byte, error) {
+func (f frameHeader) appendTo(dst []byte) []byte {
dst = append(dst, frameMagic...)
var fhd uint8
if f.Checksum {
@@ -88,7 +88,7 @@ func (f frameHeader) appendTo(dst []byte) ([]byte, error) {
default:
panic("invalid fcs")
}
- return dst, nil
+ return dst
}
const skippableFrameHeader = 4 + 4
diff --git a/vendor/github.com/klauspost/compress/zstd/seqdec.go b/vendor/github.com/klauspost/compress/zstd/seqdec.go
index 9405fcf10..d7fe6d82d 100644
--- a/vendor/github.com/klauspost/compress/zstd/seqdec.go
+++ b/vendor/github.com/klauspost/compress/zstd/seqdec.go
@@ -245,7 +245,7 @@ func (s *sequenceDecs) decodeSync(hist []byte) error {
return io.ErrUnexpectedEOF
}
var ll, mo, ml int
- if br.off > 4+((maxOffsetBits+16+16)>>3) {
+ if len(br.in) > 4+((maxOffsetBits+16+16)>>3) {
// inlined function:
// ll, mo, ml = s.nextFast(br, llState, mlState, ofState)
@@ -452,18 +452,13 @@ func (s *sequenceDecs) next(br *bitReader, llState, mlState, ofState decSymbol)
// extra bits are stored in reverse order.
br.fill()
- if s.maxBits <= 32 {
- mo += br.getBits(moB)
- ml += br.getBits(mlB)
- ll += br.getBits(llB)
- } else {
- mo += br.getBits(moB)
+ mo += br.getBits(moB)
+ if s.maxBits > 32 {
br.fill()
- // matchlength+literal length, max 32 bits
- ml += br.getBits(mlB)
- ll += br.getBits(llB)
-
}
+ // matchlength+literal length, max 32 bits
+ ml += br.getBits(mlB)
+ ll += br.getBits(llB)
mo = s.adjustOffset(mo, ll, moB)
return
}
diff --git a/vendor/github.com/klauspost/compress/zstd/seqdec_amd64.s b/vendor/github.com/klauspost/compress/zstd/seqdec_amd64.s
index b6f4ba6fc..974b99725 100644
--- a/vendor/github.com/klauspost/compress/zstd/seqdec_amd64.s
+++ b/vendor/github.com/klauspost/compress/zstd/seqdec_amd64.s
@@ -5,11 +5,11 @@
// func sequenceDecs_decode_amd64(s *sequenceDecs, br *bitReader, ctx *decodeAsmContext) int
// Requires: CMOV
TEXT ·sequenceDecs_decode_amd64(SB), $8-32
- MOVQ br+8(FP), AX
- MOVQ 32(AX), DX
- MOVBQZX 40(AX), BX
- MOVQ 24(AX), SI
- MOVQ (AX), AX
+ MOVQ br+8(FP), CX
+ MOVQ 24(CX), DX
+ MOVBQZX 32(CX), BX
+ MOVQ (CX), AX
+ MOVQ 8(CX), SI
ADDQ SI, AX
MOVQ AX, (SP)
MOVQ ctx+16(FP), AX
@@ -301,9 +301,9 @@ sequenceDecs_decode_amd64_match_len_ofs_ok:
MOVQ R12, 152(AX)
MOVQ R13, 160(AX)
MOVQ br+8(FP), AX
- MOVQ DX, 32(AX)
- MOVB BL, 40(AX)
- MOVQ SI, 24(AX)
+ MOVQ DX, 24(AX)
+ MOVB BL, 32(AX)
+ MOVQ SI, 8(AX)
// Return success
MOVQ $0x00000000, ret+24(FP)
@@ -336,11 +336,11 @@ error_overread:
// func sequenceDecs_decode_56_amd64(s *sequenceDecs, br *bitReader, ctx *decodeAsmContext) int
// Requires: CMOV
TEXT ·sequenceDecs_decode_56_amd64(SB), $8-32
- MOVQ br+8(FP), AX
- MOVQ 32(AX), DX
- MOVBQZX 40(AX), BX
- MOVQ 24(AX), SI
- MOVQ (AX), AX
+ MOVQ br+8(FP), CX
+ MOVQ 24(CX), DX
+ MOVBQZX 32(CX), BX
+ MOVQ (CX), AX
+ MOVQ 8(CX), SI
ADDQ SI, AX
MOVQ AX, (SP)
MOVQ ctx+16(FP), AX
@@ -603,9 +603,9 @@ sequenceDecs_decode_56_amd64_match_len_ofs_ok:
MOVQ R12, 152(AX)
MOVQ R13, 160(AX)
MOVQ br+8(FP), AX
- MOVQ DX, 32(AX)
- MOVB BL, 40(AX)
- MOVQ SI, 24(AX)
+ MOVQ DX, 24(AX)
+ MOVB BL, 32(AX)
+ MOVQ SI, 8(AX)
// Return success
MOVQ $0x00000000, ret+24(FP)
@@ -638,11 +638,11 @@ error_overread:
// func sequenceDecs_decode_bmi2(s *sequenceDecs, br *bitReader, ctx *decodeAsmContext) int
// Requires: BMI, BMI2, CMOV
TEXT ·sequenceDecs_decode_bmi2(SB), $8-32
- MOVQ br+8(FP), CX
- MOVQ 32(CX), AX
- MOVBQZX 40(CX), DX
- MOVQ 24(CX), BX
- MOVQ (CX), CX
+ MOVQ br+8(FP), BX
+ MOVQ 24(BX), AX
+ MOVBQZX 32(BX), DX
+ MOVQ (BX), CX
+ MOVQ 8(BX), BX
ADDQ BX, CX
MOVQ CX, (SP)
MOVQ ctx+16(FP), CX
@@ -892,9 +892,9 @@ sequenceDecs_decode_bmi2_match_len_ofs_ok:
MOVQ R11, 152(CX)
MOVQ R12, 160(CX)
MOVQ br+8(FP), CX
- MOVQ AX, 32(CX)
- MOVB DL, 40(CX)
- MOVQ BX, 24(CX)
+ MOVQ AX, 24(CX)
+ MOVB DL, 32(CX)
+ MOVQ BX, 8(CX)
// Return success
MOVQ $0x00000000, ret+24(FP)
@@ -927,11 +927,11 @@ error_overread:
// func sequenceDecs_decode_56_bmi2(s *sequenceDecs, br *bitReader, ctx *decodeAsmContext) int
// Requires: BMI, BMI2, CMOV
TEXT ·sequenceDecs_decode_56_bmi2(SB), $8-32
- MOVQ br+8(FP), CX
- MOVQ 32(CX), AX
- MOVBQZX 40(CX), DX
- MOVQ 24(CX), BX
- MOVQ (CX), CX
+ MOVQ br+8(FP), BX
+ MOVQ 24(BX), AX
+ MOVBQZX 32(BX), DX
+ MOVQ (BX), CX
+ MOVQ 8(BX), BX
ADDQ BX, CX
MOVQ CX, (SP)
MOVQ ctx+16(FP), CX
@@ -1152,9 +1152,9 @@ sequenceDecs_decode_56_bmi2_match_len_ofs_ok:
MOVQ R11, 152(CX)
MOVQ R12, 160(CX)
MOVQ br+8(FP), CX
- MOVQ AX, 32(CX)
- MOVB DL, 40(CX)
- MOVQ BX, 24(CX)
+ MOVQ AX, 24(CX)
+ MOVB DL, 32(CX)
+ MOVQ BX, 8(CX)
// Return success
MOVQ $0x00000000, ret+24(FP)
@@ -1797,11 +1797,11 @@ empty_seqs:
// func sequenceDecs_decodeSync_amd64(s *sequenceDecs, br *bitReader, ctx *decodeSyncAsmContext) int
// Requires: CMOV, SSE
TEXT ·sequenceDecs_decodeSync_amd64(SB), $64-32
- MOVQ br+8(FP), AX
- MOVQ 32(AX), DX
- MOVBQZX 40(AX), BX
- MOVQ 24(AX), SI
- MOVQ (AX), AX
+ MOVQ br+8(FP), CX
+ MOVQ 24(CX), DX
+ MOVBQZX 32(CX), BX
+ MOVQ (CX), AX
+ MOVQ 8(CX), SI
ADDQ SI, AX
MOVQ AX, (SP)
MOVQ ctx+16(FP), AX
@@ -2295,9 +2295,9 @@ handle_loop:
loop_finished:
MOVQ br+8(FP), AX
- MOVQ DX, 32(AX)
- MOVB BL, 40(AX)
- MOVQ SI, 24(AX)
+ MOVQ DX, 24(AX)
+ MOVB BL, 32(AX)
+ MOVQ SI, 8(AX)
// Update the context
MOVQ ctx+16(FP), AX
@@ -2362,11 +2362,11 @@ error_not_enough_space:
// func sequenceDecs_decodeSync_bmi2(s *sequenceDecs, br *bitReader, ctx *decodeSyncAsmContext) int
// Requires: BMI, BMI2, CMOV, SSE
TEXT ·sequenceDecs_decodeSync_bmi2(SB), $64-32
- MOVQ br+8(FP), CX
- MOVQ 32(CX), AX
- MOVBQZX 40(CX), DX
- MOVQ 24(CX), BX
- MOVQ (CX), CX
+ MOVQ br+8(FP), BX
+ MOVQ 24(BX), AX
+ MOVBQZX 32(BX), DX
+ MOVQ (BX), CX
+ MOVQ 8(BX), BX
ADDQ BX, CX
MOVQ CX, (SP)
MOVQ ctx+16(FP), CX
@@ -2818,9 +2818,9 @@ handle_loop:
loop_finished:
MOVQ br+8(FP), CX
- MOVQ AX, 32(CX)
- MOVB DL, 40(CX)
- MOVQ BX, 24(CX)
+ MOVQ AX, 24(CX)
+ MOVB DL, 32(CX)
+ MOVQ BX, 8(CX)
// Update the context
MOVQ ctx+16(FP), AX
@@ -2885,11 +2885,11 @@ error_not_enough_space:
// func sequenceDecs_decodeSync_safe_amd64(s *sequenceDecs, br *bitReader, ctx *decodeSyncAsmContext) int
// Requires: CMOV, SSE
TEXT ·sequenceDecs_decodeSync_safe_amd64(SB), $64-32
- MOVQ br+8(FP), AX
- MOVQ 32(AX), DX
- MOVBQZX 40(AX), BX
- MOVQ 24(AX), SI
- MOVQ (AX), AX
+ MOVQ br+8(FP), CX
+ MOVQ 24(CX), DX
+ MOVBQZX 32(CX), BX
+ MOVQ (CX), AX
+ MOVQ 8(CX), SI
ADDQ SI, AX
MOVQ AX, (SP)
MOVQ ctx+16(FP), AX
@@ -3485,9 +3485,9 @@ handle_loop:
loop_finished:
MOVQ br+8(FP), AX
- MOVQ DX, 32(AX)
- MOVB BL, 40(AX)
- MOVQ SI, 24(AX)
+ MOVQ DX, 24(AX)
+ MOVB BL, 32(AX)
+ MOVQ SI, 8(AX)
// Update the context
MOVQ ctx+16(FP), AX
@@ -3552,11 +3552,11 @@ error_not_enough_space:
// func sequenceDecs_decodeSync_safe_bmi2(s *sequenceDecs, br *bitReader, ctx *decodeSyncAsmContext) int
// Requires: BMI, BMI2, CMOV, SSE
TEXT ·sequenceDecs_decodeSync_safe_bmi2(SB), $64-32
- MOVQ br+8(FP), CX
- MOVQ 32(CX), AX
- MOVBQZX 40(CX), DX
- MOVQ 24(CX), BX
- MOVQ (CX), CX
+ MOVQ br+8(FP), BX
+ MOVQ 24(BX), AX
+ MOVBQZX 32(BX), DX
+ MOVQ (BX), CX
+ MOVQ 8(BX), BX
ADDQ BX, CX
MOVQ CX, (SP)
MOVQ ctx+16(FP), CX
@@ -4110,9 +4110,9 @@ handle_loop:
loop_finished:
MOVQ br+8(FP), CX
- MOVQ AX, 32(CX)
- MOVB DL, 40(CX)
- MOVQ BX, 24(CX)
+ MOVQ AX, 24(CX)
+ MOVB DL, 32(CX)
+ MOVQ BX, 8(CX)
// Update the context
MOVQ ctx+16(FP), AX
diff --git a/vendor/github.com/klauspost/compress/zstd/seqdec_generic.go b/vendor/github.com/klauspost/compress/zstd/seqdec_generic.go
index ac2a80d29..2fb35b788 100644
--- a/vendor/github.com/klauspost/compress/zstd/seqdec_generic.go
+++ b/vendor/github.com/klauspost/compress/zstd/seqdec_generic.go
@@ -29,7 +29,7 @@ func (s *sequenceDecs) decode(seqs []seqVals) error {
}
for i := range seqs {
var ll, mo, ml int
- if br.off > 4+((maxOffsetBits+16+16)>>3) {
+ if len(br.in) > 4+((maxOffsetBits+16+16)>>3) {
// inlined function:
// ll, mo, ml = s.nextFast(br, llState, mlState, ofState)
diff --git a/vendor/github.com/klauspost/compress/zstd/snappy.go b/vendor/github.com/klauspost/compress/zstd/snappy.go
index 9e1baad73..ec13594e8 100644
--- a/vendor/github.com/klauspost/compress/zstd/snappy.go
+++ b/vendor/github.com/klauspost/compress/zstd/snappy.go
@@ -95,10 +95,9 @@ func (r *SnappyConverter) Convert(in io.Reader, w io.Writer) (int64, error) {
var written int64
var readHeader bool
{
- var header []byte
- var n int
- header, r.err = frameHeader{WindowSize: snappyMaxBlockSize}.appendTo(r.buf[:0])
+ header := frameHeader{WindowSize: snappyMaxBlockSize}.appendTo(r.buf[:0])
+ var n int
n, r.err = w.Write(header)
if r.err != nil {
return written, r.err
diff --git a/vendor/github.com/libp2p/go-libp2p-mplex/.gitignore b/vendor/github.com/libp2p/go-libp2p-mplex/.gitignore
new file mode 100644
index 000000000..1377554eb
--- /dev/null
+++ b/vendor/github.com/libp2p/go-libp2p-mplex/.gitignore
@@ -0,0 +1 @@
+*.swp
diff --git a/vendor/github.com/pion/transport/LICENSE b/vendor/github.com/libp2p/go-libp2p-mplex/LICENSE
similarity index 86%
rename from vendor/github.com/pion/transport/LICENSE
rename to vendor/github.com/libp2p/go-libp2p-mplex/LICENSE
index ab602974d..c7386b3c9 100644
--- a/vendor/github.com/pion/transport/LICENSE
+++ b/vendor/github.com/libp2p/go-libp2p-mplex/LICENSE
@@ -1,6 +1,6 @@
-MIT License
+The MIT License (MIT)
-Copyright (c) 2018
+Copyright (c) 2014 Juan Batiz-Benet
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
@@ -9,13 +9,13 @@ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
+The above copyright notice and this permission notice shall be included in
+all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
+OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
+THE SOFTWARE.
diff --git a/vendor/github.com/libp2p/go-libp2p-mplex/README.md b/vendor/github.com/libp2p/go-libp2p-mplex/README.md
new file mode 100644
index 000000000..00782d7b9
--- /dev/null
+++ b/vendor/github.com/libp2p/go-libp2p-mplex/README.md
@@ -0,0 +1,11 @@
+# DEPRECATION NOTICE
+
+mplex has been deprecated.
+
+see https://github.com/libp2p/specs/issues/553 for details
+
+# go-libp2p-mplex - a go-stream-muxer shim for multiplex
+
+[![](https://img.shields.io/badge/made%20by-Protocol%20Labs-blue.svg?style=flat-square)](http://ipn.io) [![](https://img.shields.io/badge/freenode-%23ipfs-blue.svg?style=flat-square)](http://webchat.freenode.net/?channels=%23ipfs) ![](https://raw.githubusercontent.com/libp2p/go-stream-muxer/master/img/badge.png)
+
+This is an implementation of the [go-libp2p muxer](https://pkg.go.dev/github.com/libp2p/go-libp2p@v0.30.0/core/network#Multiplexer) interface for [multiplex](https://github.com/libp2p/go-mplex). For more information, see that repo.
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/conn.go b/vendor/github.com/libp2p/go-libp2p-mplex/conn.go
similarity index 100%
rename from vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/conn.go
rename to vendor/github.com/libp2p/go-libp2p-mplex/conn.go
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/stream.go b/vendor/github.com/libp2p/go-libp2p-mplex/stream.go
similarity index 100%
rename from vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/stream.go
rename to vendor/github.com/libp2p/go-libp2p-mplex/stream.go
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/transport.go b/vendor/github.com/libp2p/go-libp2p-mplex/transport.go
similarity index 81%
rename from vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/transport.go
rename to vendor/github.com/libp2p/go-libp2p-mplex/transport.go
index 10d54d153..bcfadfd7e 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/muxer/mplex/transport.go
+++ b/vendor/github.com/libp2p/go-libp2p-mplex/transport.go
@@ -1,3 +1,5 @@
+// DEPRECATED: mplex has been deprecated. Users should prefer Yamux over mplex. see https://github.com/libp2p/specs/issues/553
+// for details
package mplex
import (
diff --git a/vendor/github.com/libp2p/go-libp2p-mplex/version.json b/vendor/github.com/libp2p/go-libp2p-mplex/version.json
new file mode 100644
index 000000000..960b84e55
--- /dev/null
+++ b/vendor/github.com/libp2p/go-libp2p-mplex/version.json
@@ -0,0 +1,3 @@
+{
+ "version": "v0.9.0"
+}
diff --git a/vendor/github.com/libp2p/go-libp2p-pubsub/gossipsub.go b/vendor/github.com/libp2p/go-libp2p-pubsub/gossipsub.go
index 62dbd8e80..9b3023221 100644
--- a/vendor/github.com/libp2p/go-libp2p-pubsub/gossipsub.go
+++ b/vendor/github.com/libp2p/go-libp2p-pubsub/gossipsub.go
@@ -1183,7 +1183,7 @@ func (gs *GossipSubRouter) sendRPC(p peer.ID, out *RPC) {
}
func (gs *GossipSubRouter) doDropRPC(rpc *RPC, p peer.ID, reason string) {
- log.Debugf("dropping message to peer %s: %s", p.Pretty(), reason)
+ log.Debugf("dropping message to peer %s: %s", p, reason)
gs.tracer.DropRPC(rpc, p)
// push control messages that need to be retried
ctl := rpc.GetControl()
diff --git a/vendor/github.com/libp2p/go-libp2p/README.md b/vendor/github.com/libp2p/go-libp2p/README.md
index b5056de6e..7a95a1370 100644
--- a/vendor/github.com/libp2p/go-libp2p/README.md
+++ b/vendor/github.com/libp2p/go-libp2p/README.md
@@ -13,18 +13,17 @@
-# Table of Contents
-
+# Table of Contents
- [Background](#background)
- [Roadmap](#roadmap)
- [Usage](#usage)
- [Examples](#examples)
-- [Development](#development)
- - [Tests](#tests)
+ - [Dashboards](#dashboards)
- [Contribute](#contribute)
-- [Supported Go Versions](#supported-go-versions)
+ - [Supported Go Versions](#supported-go-versions)
+- [Notable Users](#notable-users)
-## Background
+# Background
[libp2p](https://github.com/libp2p/specs) is a networking stack and library modularized out of [The IPFS Project](https://github.com/ipfs/ipfs), and bundled separately for other tools to use.
>
@@ -37,12 +36,12 @@ To learn more, check out the following resources:
- [**js-libp2p implementation**](https://github.com/libp2p/js-libp2p)
- [**rust-libp2p implementation**](https://github.com/libp2p/rust-libp2p)
-## Roadmap
+# Roadmap
Our roadmap for go-libp2p can be found here: https://github.com/libp2p/go-libp2p/blob/master/ROADMAP.md
-This document represents current projects the go-libp2p team is focused on and provides an estimation of completion targets. It is a completementary roadmap to the overarching libp2p project roadmap: https://github.com/libp2p/specs/blob/master/ROADMAP.md
+This document represents current projects the go-libp2p team is focused on and provides an estimation of completion targets. It is a complementary roadmap to the overarching libp2p project roadmap: https://github.com/libp2p/specs/blob/master/ROADMAP.md
-## Usage
+# Usage
This repository (`go-libp2p`) serves as the entrypoint to the universe of packages that compose the Go implementation of the libp2p stack.
@@ -52,10 +51,17 @@ You can start using go-libp2p in your Go application simply by adding imports fr
import "github.com/libp2p/go-libp2p"
```
-### Examples
+## Examples
Examples can be found in the [examples folder](examples).
+## Dashboards
+
+We provide prebuilt Grafana dashboards so that applications can better monitor libp2p in production.
+You can find the [dashboard JSON files here](https://github.com/libp2p/go-libp2p/tree/master/dashboards).
+
+We also have live [Public Dashboards](https://github.com/libp2p/go-libp2p/tree/master/dashboards/README.md#public-dashboards) that you can check out to see real time monitoring in action.
+
# Contribute
@@ -70,7 +76,7 @@ Guidelines:
- have fun!
There's a few things you can do right now to help out:
- - Go through the modules below and **check out existing issues**. This would be especially useful for modules in active development. Some knowledge of IPFS/libp2p may be required, as well as the infrasture behind it - for instance, you may need to read up on p2p and more complex operations like muxing to be able to help technically.
+ - Go through the modules below and **check out existing issues**. This would be especially useful for modules in active development. Some knowledge of IPFS/libp2p may be required, as well as the infrastructure behind it - for instance, you may need to read up on p2p and more complex operations like muxing to be able to help technically.
- **Perform code reviews**.
- **Add tests**. There can never be enough tests.
@@ -99,4 +105,4 @@ Some notable users of go-libp2p are:
- [Kairos](https://github.com/kairos-io/kairos) - A Kubernetes-focused, Cloud Native Linux meta-distribution.
- [Oasis Core](https://github.com/oasisprotocol/oasis-core) - The consensus and runtime layers of the [Oasis protocol](https://oasisprotocol.org/).
-Please open a pull request if you want your project to be added here.
+Please open a pull request if you want your project (min. 250 GitHub stars) to be added here.
diff --git a/vendor/github.com/libp2p/go-libp2p/config/config.go b/vendor/github.com/libp2p/go-libp2p/config/config.go
index cea8ef131..8be5a4399 100644
--- a/vendor/github.com/libp2p/go-libp2p/config/config.go
+++ b/vendor/github.com/libp2p/go-libp2p/config/config.go
@@ -261,6 +261,7 @@ func (cfg *Config) addTransports(h host.Host) error {
}
fxopts = append(fxopts, fx.Provide(PrivKeyToStatelessResetKey))
+ fxopts = append(fxopts, fx.Provide(PrivKeyToTokenGeneratorKey))
if cfg.QUICReuse != nil {
fxopts = append(fxopts, cfg.QUICReuse...)
} else {
@@ -295,6 +296,15 @@ func (cfg *Config) addTransports(h host.Host) error {
//
// This function consumes the config. Do not reuse it (really!).
func (cfg *Config) NewNode() (host.Host, error) {
+ // If possible check that the resource manager conn limit is higher than the
+ // limit set in the conn manager.
+ if l, ok := cfg.ResourceManager.(connmgr.GetConnLimiter); ok {
+ err := cfg.ConnManager.CheckLimit(l)
+ if err != nil {
+ log.Warn(fmt.Sprintf("rcmgr limit conflicts with connmgr limit: %v", err))
+ }
+ }
+
eventBus := eventbus.NewBus(eventbus.WithMetricsTracer(eventbus.NewMetricsTracer(eventbus.WithRegisterer(cfg.PrometheusRegisterer))))
swrm, err := cfg.makeSwarm(eventBus, !cfg.DisableMetrics)
if err != nil {
@@ -419,6 +429,11 @@ func (cfg *Config) NewNode() (host.Host, error) {
PeerKey: autonatPrivKey,
Peerstore: ps,
DialRanker: swarm.NoDelayDialRanker,
+ SwarmOpts: []swarm.Option{
+ // It is better to disable black hole detection and just attempt a dial for autonat
+ swarm.WithUDPBlackHoleConfig(false, 0, 0),
+ swarm.WithIPv6BlackHoleConfig(false, 0, 0),
+ },
}
dialer, err := autoNatCfg.makeSwarm(eventbus.NewBus(), false)
diff --git a/vendor/github.com/libp2p/go-libp2p/config/quic_stateless_reset.go b/vendor/github.com/libp2p/go-libp2p/config/quic.go
similarity index 53%
rename from vendor/github.com/libp2p/go-libp2p/config/quic_stateless_reset.go
rename to vendor/github.com/libp2p/go-libp2p/config/quic.go
index a12be56f5..66c40da97 100644
--- a/vendor/github.com/libp2p/go-libp2p/config/quic_stateless_reset.go
+++ b/vendor/github.com/libp2p/go-libp2p/config/quic.go
@@ -11,7 +11,10 @@ import (
"github.com/quic-go/quic-go"
)
-const statelessResetKeyInfo = "libp2p quic stateless reset key"
+const (
+ statelessResetKeyInfo = "libp2p quic stateless reset key"
+ tokenGeneratorKeyInfo = "libp2p quic token generator key"
+)
func PrivKeyToStatelessResetKey(key crypto.PrivKey) (quic.StatelessResetKey, error) {
var statelessResetKey quic.StatelessResetKey
@@ -25,3 +28,16 @@ func PrivKeyToStatelessResetKey(key crypto.PrivKey) (quic.StatelessResetKey, err
}
return statelessResetKey, nil
}
+
+func PrivKeyToTokenGeneratorKey(key crypto.PrivKey) (quic.TokenGeneratorKey, error) {
+ var tokenKey quic.TokenGeneratorKey
+ keyBytes, err := key.Raw()
+ if err != nil {
+ return tokenKey, err
+ }
+ keyReader := hkdf.New(sha256.New, keyBytes, nil, []byte(tokenGeneratorKeyInfo))
+ if _, err := io.ReadFull(keyReader, tokenKey[:]); err != nil {
+ return tokenKey, err
+ }
+ return tokenKey, nil
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/core/connmgr/manager.go b/vendor/github.com/libp2p/go-libp2p/core/connmgr/manager.go
index e0d6c5201..d756e4399 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/connmgr/manager.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/connmgr/manager.go
@@ -74,6 +74,10 @@ type ConnManager interface {
// then it will return true if the peer is protected for any tag
IsProtected(id peer.ID, tag string) (protected bool)
+ // CheckLimit will return an error if the connection manager's internal
+ // connection limit exceeds the provided system limit.
+ CheckLimit(l GetConnLimiter) error
+
// Close closes the connection manager and stops background processes.
Close() error
}
@@ -89,3 +93,9 @@ type TagInfo struct {
// Conns maps connection ids (such as remote multiaddr) to their creation time.
Conns map[string]time.Time
}
+
+// GetConnLimiter provides access to a component's total connection limit.
+type GetConnLimiter interface {
+ // GetConnLimit returns the total connection limit of the implementing component.
+ GetConnLimit() int
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/core/connmgr/null.go b/vendor/github.com/libp2p/go-libp2p/core/connmgr/null.go
index 25743f4ec..735411712 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/connmgr/null.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/connmgr/null.go
@@ -21,4 +21,5 @@ func (NullConnMgr) Notifee() network.Notifiee { return network.Gl
func (NullConnMgr) Protect(peer.ID, string) {}
func (NullConnMgr) Unprotect(peer.ID, string) bool { return false }
func (NullConnMgr) IsProtected(peer.ID, string) bool { return false }
+func (NullConnMgr) CheckLimit(l GetConnLimiter) error { return nil }
func (NullConnMgr) Close() error { return nil }
diff --git a/vendor/github.com/libp2p/go-libp2p/core/crypto/ecdsa.go b/vendor/github.com/libp2p/go-libp2p/core/crypto/ecdsa.go
index c936d502a..8e392c9ed 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/crypto/ecdsa.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/crypto/ecdsa.go
@@ -12,8 +12,7 @@ import (
pb "github.com/libp2p/go-libp2p/core/crypto/pb"
"github.com/libp2p/go-libp2p/core/internal/catch"
-
- "github.com/minio/sha256-simd"
+ "github.com/libp2p/go-libp2p/internal/sha256"
)
// ECDSAPrivateKey is an implementation of an ECDSA private key
diff --git a/vendor/github.com/libp2p/go-libp2p/core/crypto/rsa_go.go b/vendor/github.com/libp2p/go-libp2p/core/crypto/rsa_go.go
index 8981ba6aa..c955cf8e0 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/crypto/rsa_go.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/crypto/rsa_go.go
@@ -10,8 +10,7 @@ import (
pb "github.com/libp2p/go-libp2p/core/crypto/pb"
"github.com/libp2p/go-libp2p/core/internal/catch"
-
- "github.com/minio/sha256-simd"
+ "github.com/libp2p/go-libp2p/internal/sha256"
)
// RsaPrivateKey is a rsa private key
diff --git a/vendor/github.com/libp2p/go-libp2p/core/crypto/secp256k1.go b/vendor/github.com/libp2p/go-libp2p/core/crypto/secp256k1.go
index 27544a59f..bcd68ac6d 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/crypto/secp256k1.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/crypto/secp256k1.go
@@ -9,7 +9,7 @@ import (
"github.com/decred/dcrd/dcrec/secp256k1/v4"
"github.com/decred/dcrd/dcrec/secp256k1/v4/ecdsa"
- "github.com/minio/sha256-simd"
+ "github.com/libp2p/go-libp2p/internal/sha256"
)
// Secp256k1PrivateKey is a Secp256k1 private key
diff --git a/vendor/github.com/libp2p/go-libp2p/core/peer/addrinfo.go b/vendor/github.com/libp2p/go-libp2p/core/peer/addrinfo.go
index fba4cfd0e..de7dd4d98 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/peer/addrinfo.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/peer/addrinfo.go
@@ -86,7 +86,7 @@ func AddrInfoFromP2pAddr(m ma.Multiaddr) (*AddrInfo, error) {
// AddrInfoToP2pAddrs converts an AddrInfo to a list of Multiaddrs.
func AddrInfoToP2pAddrs(pi *AddrInfo) ([]ma.Multiaddr, error) {
- p2ppart, err := ma.NewComponent("p2p", Encode(pi.ID))
+ p2ppart, err := ma.NewComponent("p2p", pi.ID.String())
if err != nil {
return nil, err
}
@@ -102,7 +102,7 @@ func AddrInfoToP2pAddrs(pi *AddrInfo) ([]ma.Multiaddr, error) {
func (pi *AddrInfo) Loggable() map[string]interface{} {
return map[string]interface{}{
- "peerID": pi.ID.Pretty(),
+ "peerID": pi.ID.String(),
"addrs": pi.Addrs,
}
}
diff --git a/vendor/github.com/libp2p/go-libp2p/core/peer/peer.go b/vendor/github.com/libp2p/go-libp2p/core/peer/peer.go
index f7f649f24..b77fb684e 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/peer/peer.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/peer/peer.go
@@ -41,12 +41,6 @@ const maxInlineKeyLength = 42
// hash output as a multihash. See IDFromPublicKey for details.
type ID string
-// Pretty returns a base58-encoded string representation of the ID.
-// Deprecated: use String() instead.
-func (id ID) Pretty() string {
- return id.String()
-}
-
// Loggable returns a pretty peer ID string in loggable JSON format.
func (id ID) Loggable() map[string]interface{} {
return map[string]interface{}{
@@ -145,16 +139,6 @@ func Decode(s string) (ID, error) {
return FromCid(c)
}
-// Encode encodes a peer ID as a string.
-//
-// At the moment, it base58 encodes the peer ID but, in the future, it will
-// switch to encoding it as a CID by default.
-//
-// Deprecated: use id.String instead.
-func Encode(id ID) string {
- return id.String()
-}
-
// FromCid converts a CID to a peer ID, if possible.
func FromCid(c cid.Cid) (ID, error) {
code := mc.Code(c.Type())
diff --git a/vendor/github.com/libp2p/go-libp2p/core/peer/peer_serde.go b/vendor/github.com/libp2p/go-libp2p/core/peer/peer_serde.go
index 5fd1cd50c..3e2f71793 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/peer/peer_serde.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/peer/peer_serde.go
@@ -45,7 +45,7 @@ func (id ID) Size() int {
}
func (id ID) MarshalJSON() ([]byte, error) {
- return json.Marshal(Encode(id))
+ return json.Marshal(id.String())
}
func (id *ID) UnmarshalJSON(data []byte) (err error) {
@@ -59,7 +59,7 @@ func (id *ID) UnmarshalJSON(data []byte) (err error) {
// MarshalText returns the text encoding of the ID.
func (id ID) MarshalText() ([]byte, error) {
- return []byte(Encode(id)), nil
+ return []byte(id.String()), nil
}
// UnmarshalText restores the ID from its text encoding.
diff --git a/vendor/github.com/libp2p/go-libp2p/core/sec/security.go b/vendor/github.com/libp2p/go-libp2p/core/sec/security.go
index 83059d94c..d9e918329 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/sec/security.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/sec/security.go
@@ -3,6 +3,7 @@ package sec
import (
"context"
+ "fmt"
"net"
"github.com/libp2p/go-libp2p/core/network"
@@ -29,3 +30,14 @@ type SecureTransport interface {
// ID is the protocol ID of the security protocol.
ID() protocol.ID
}
+
+type ErrPeerIDMismatch struct {
+ Expected peer.ID
+ Actual peer.ID
+}
+
+func (e ErrPeerIDMismatch) Error() string {
+ return fmt.Sprintf("peer id mismatch: expected %s, but remote key matches %s", e.Expected, e.Actual)
+}
+
+var _ error = (*ErrPeerIDMismatch)(nil)
diff --git a/vendor/github.com/libp2p/go-libp2p/core/transport/transport.go b/vendor/github.com/libp2p/go-libp2p/core/transport/transport.go
index 89a9608d4..d56a3cff0 100644
--- a/vendor/github.com/libp2p/go-libp2p/core/transport/transport.go
+++ b/vendor/github.com/libp2p/go-libp2p/core/transport/transport.go
@@ -5,6 +5,7 @@ package transport
import (
"context"
"errors"
+ "fmt"
"net"
"github.com/libp2p/go-libp2p/core/network"
@@ -124,3 +125,47 @@ type Upgrader interface {
// Upgrade upgrades the multiaddr/net connection into a full libp2p-transport connection.
Upgrade(ctx context.Context, t Transport, maconn manet.Conn, dir network.Direction, p peer.ID, scope network.ConnManagementScope) (CapableConn, error)
}
+
+// DialUpdater provides updates on in progress dials.
+type DialUpdater interface {
+ // DialWithUpdates dials a remote peer and provides updates on the passed channel.
+ DialWithUpdates(context.Context, ma.Multiaddr, peer.ID, chan<- DialUpdate) (CapableConn, error)
+}
+
+// DialUpdateKind indicates the type of DialUpdate event.
+type DialUpdateKind int
+
+const (
+ // UpdateKindDialFailed indicates dial failed.
+ UpdateKindDialFailed DialUpdateKind = iota
+ // UpdateKindDialSuccessful indicates dial succeeded.
+ UpdateKindDialSuccessful
+ // UpdateKindHandshakeProgressed indicates successful completion of the TCP 3-way
+ // handshake
+ UpdateKindHandshakeProgressed
+)
+
+func (k DialUpdateKind) String() string {
+ switch k {
+ case UpdateKindDialFailed:
+ return "DialFailed"
+ case UpdateKindDialSuccessful:
+ return "DialSuccessful"
+ case UpdateKindHandshakeProgressed:
+ return "UpdateKindHandshakeProgressed"
+ default:
+ return fmt.Sprintf("DialUpdateKind", k)
+ }
+}
+
+// DialUpdate is used by DialUpdater to provide dial updates.
+type DialUpdate struct {
+ // Kind is the kind of update event.
+ Kind DialUpdateKind
+ // Addr is the peer's address.
+ Addr ma.Multiaddr
+ // Conn is the resulting connection on success.
+ Conn CapableConn
+ // Err is the reason for dial failure.
+ Err error
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/defaults.go b/vendor/github.com/libp2p/go-libp2p/defaults.go
index c0ed6698a..d11302690 100644
--- a/vendor/github.com/libp2p/go-libp2p/defaults.go
+++ b/vendor/github.com/libp2p/go-libp2p/defaults.go
@@ -79,11 +79,9 @@ var RandomIdentity = func(cfg *Config) error {
var DefaultListenAddrs = func(cfg *Config) error {
addrs := []string{
"/ip4/0.0.0.0/tcp/0",
- "/ip4/0.0.0.0/udp/0/quic",
"/ip4/0.0.0.0/udp/0/quic-v1",
"/ip4/0.0.0.0/udp/0/quic-v1/webtransport",
"/ip6/::/tcp/0",
- "/ip6/::/udp/0/quic",
"/ip6/::/udp/0/quic-v1",
"/ip6/::/udp/0/quic-v1/webtransport",
}
diff --git a/vendor/github.com/libp2p/go-libp2p/internal/sha256/post_go1_21.go b/vendor/github.com/libp2p/go-libp2p/internal/sha256/post_go1_21.go
new file mode 100644
index 000000000..98c14b609
--- /dev/null
+++ b/vendor/github.com/libp2p/go-libp2p/internal/sha256/post_go1_21.go
@@ -0,0 +1,23 @@
+//go:build go1.21
+
+// This package use build tags to select between github.com/minio/sha256-simd
+// for go1.20 and bellow and crypto/sha256 for go1.21 and above.
+// This is used because a fast SHANI implementation of sha256 is only avaiable
+// in the std for go1.21 and above. See https://go.dev/issue/50543.
+// TODO: Once go1.22 releases remove this package and replace all uses
+// with crypto/sha256 because the two supported version of go will have the fast
+// implementation.
+package sha256
+
+import (
+ "crypto/sha256"
+ "hash"
+)
+
+func Sum256(b []byte) [sha256.Size]byte {
+ return sha256.Sum256(b)
+}
+
+func New() hash.Hash {
+ return sha256.New()
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/internal/sha256/pre_go1_21.go b/vendor/github.com/libp2p/go-libp2p/internal/sha256/pre_go1_21.go
new file mode 100644
index 000000000..db0573333
--- /dev/null
+++ b/vendor/github.com/libp2p/go-libp2p/internal/sha256/pre_go1_21.go
@@ -0,0 +1,24 @@
+//go:build !go1.21
+
+// This package use build tags to select between github.com/minio/sha256-simd
+// for go1.20 and bellow and crypto/sha256 for go1.21 and above.
+// This is used because a fast SHANI implementation of sha256 is only avaiable
+// in the std for go1.21 and above. See https://go.dev/issue/50543.
+// TODO: Once go1.22 releases remove this package and replace all uses
+// with crypto/sha256 because the two supported version of go will have the fast
+// implementation.
+package sha256
+
+import (
+ "hash"
+
+ "github.com/minio/sha256-simd"
+)
+
+func Sum256(b []byte) [sha256.Size]byte {
+ return sha256.Sum256(b)
+}
+
+func New() hash.Hash {
+ return sha256.New()
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/options.go b/vendor/github.com/libp2p/go-libp2p/options.go
index beb4930f7..1a1e9d398 100644
--- a/vendor/github.com/libp2p/go-libp2p/options.go
+++ b/vendor/github.com/libp2p/go-libp2p/options.go
@@ -579,6 +579,7 @@ func PrometheusRegisterer(reg prometheus.Registerer) Option {
// DialRanker configures libp2p to use d as the dial ranker. To enable smart
// dialing use `swarm.DefaultDialRanker`. use `swarm.NoDelayDialRanker` to
// disable smart dialing.
+//
// Deprecated: use SwarmOpts(swarm.WithDialRanker(d)) instead
func DialRanker(d network.DialRanker) Option {
return func(cfg *Config) error {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/autonat/svc.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/autonat/svc.go
index 98b421c9b..cf1dff8e7 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/autonat/svc.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/autonat/svc.go
@@ -68,7 +68,7 @@ func (as *autoNATService) handleStream(s network.Stream) {
defer s.Close()
pid := s.Conn().RemotePeer()
- log.Debugf("New stream from %s", pid.Pretty())
+ log.Debugf("New stream from %s", pid)
r := pbio.NewDelimitedReader(s, maxMsgSize)
w := pbio.NewDelimitedWriter(s)
@@ -78,14 +78,14 @@ func (as *autoNATService) handleStream(s network.Stream) {
err := r.ReadMsg(&req)
if err != nil {
- log.Debugf("Error reading message from %s: %s", pid.Pretty(), err.Error())
+ log.Debugf("Error reading message from %s: %s", pid, err.Error())
s.Reset()
return
}
t := req.GetType()
if t != pb.Message_DIAL {
- log.Debugf("Unexpected message from %s: %s (%d)", pid.Pretty(), t.String(), t)
+ log.Debugf("Unexpected message from %s: %s (%d)", pid, t.String(), t)
s.Reset()
return
}
@@ -96,7 +96,7 @@ func (as *autoNATService) handleStream(s network.Stream) {
err = w.WriteMsg(&res)
if err != nil {
- log.Debugf("Error writing response to %s: %s", pid.Pretty(), err.Error())
+ log.Debugf("Error writing response to %s: %s", pid, err.Error())
s.Reset()
return
}
@@ -234,7 +234,7 @@ func (as *autoNATService) doDial(pi peer.AddrInfo) *pb.Message_DialResponse {
conn, err := as.config.dialer.DialPeer(ctx, pi.ID)
if err != nil {
- log.Debugf("error dialing %s: %s", pi.ID.Pretty(), err.Error())
+ log.Debugf("error dialing %s: %s", pi.ID, err.Error())
// wait for the context to timeout to avoid leaking timing information
// this renders the service ineffective as a port scanner
<-ctx.Done()
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/autorelay/relay_finder.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/autorelay/relay_finder.go
index 3133b7a51..ef79950b7 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/autorelay/relay_finder.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/autorelay/relay_finder.go
@@ -736,7 +736,7 @@ func (rf *relayFinder) relayAddrs(addrs []ma.Multiaddr) []ma.Multiaddr {
for p := range rf.relays {
addrs := cleanupAddressSet(rf.host.Peerstore().Addrs(p))
relayAddrCnt += len(addrs)
- circuit := ma.StringCast(fmt.Sprintf("/p2p/%s/p2p-circuit", p.Pretty()))
+ circuit := ma.StringCast(fmt.Sprintf("/p2p/%s/p2p-circuit", p))
for _, addr := range addrs {
pub := addr.Encapsulate(circuit)
raddrs = append(raddrs, pub)
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/basic_host.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/basic_host.go
index 89f5d28db..6c3ba53e5 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/basic_host.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/basic_host.go
@@ -437,7 +437,7 @@ func (h *BasicHost) newStreamHandler(s network.Stream) {
log.Debugf("negotiated: %s (took %s)", protoID, took)
- go handle(protoID, s)
+ handle(protoID, s)
}
// SignalAddressChange signals to the host that it needs to determine whether our listen addresses have recently
@@ -629,9 +629,6 @@ func (h *BasicHost) RemoveStreamHandler(pid protocol.ID) {
// to create one. If ProtocolID is "", writes no header.
// (Thread-safe)
func (h *BasicHost) NewStream(ctx context.Context, p peer.ID, pids ...protocol.ID) (network.Stream, error) {
- // Ensure we have a connection, with peer addresses resolved by the routing system (#207)
- // It is not sufficient to let the underlying host connect, it will most likely not have
- // any addresses for the peer without any prior connections.
// If the caller wants to prevent the host from dialing, it should use the NoDial option.
if nodial, _ := network.GetNoDial(ctx); !nodial {
err := h.Connect(ctx, peer.AddrInfo{ID: p})
@@ -669,7 +666,9 @@ func (h *BasicHost) NewStream(ctx context.Context, p peer.ID, pids ...protocol.I
}
if pref != "" {
- s.SetProtocol(pref)
+ if err := s.SetProtocol(pref); err != nil {
+ return nil, err
+ }
lzcon := msmux.NewMSSelect(s, pref)
return &streamWrapper{
Stream: s,
@@ -795,10 +794,11 @@ func (h *BasicHost) Addrs() []ma.Multiaddr {
continue
}
addrWithCerthash, added := tpt.AddCertHashes(addr)
- addrs[i] = addrWithCerthash
if !added {
log.Debug("Couldn't add certhashes to webtransport multiaddr because we aren't listening on webtransport")
+ continue
}
+ addrs[i] = addrWithCerthash
}
}
return addrs
@@ -945,17 +945,17 @@ func inferWebtransportAddrsFromQuic(in []ma.Multiaddr) []ma.Multiaddr {
// Remove certhashes
addr, _ = ma.SplitLast(addr)
}
- webtransportAddrs[addr.String()] = struct{}{}
+ webtransportAddrs[string(addr.Bytes())] = struct{}{}
// Remove webtransport component, now it's a multiaddr that ends in /quic-v1
addr, _ = ma.SplitLast(addr)
}
if _, lastComponent := ma.SplitLast(addr); lastComponent.Protocol().Code == ma.P_QUIC_V1 {
- addrStr := addr.String()
- if _, ok := quicOrWebtransportAddrs[addrStr]; ok {
+ bytes := addr.Bytes()
+ if _, ok := quicOrWebtransportAddrs[string(bytes)]; ok {
foundSameListeningAddr = true
} else {
- quicOrWebtransportAddrs[addrStr] = struct{}{}
+ quicOrWebtransportAddrs[string(bytes)] = struct{}{}
}
}
}
@@ -977,7 +977,7 @@ func inferWebtransportAddrsFromQuic(in []ma.Multiaddr) []ma.Multiaddr {
if _, lastComponent := ma.SplitLast(addr); lastComponent.Protocol().Code == ma.P_QUIC_V1 {
// Convert quic to webtransport
addr = addr.Encapsulate(wtComponent)
- if _, ok := webtransportAddrs[addr.String()]; ok {
+ if _, ok := webtransportAddrs[string(addr.Bytes())]; ok {
// We already have this address
continue
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/mocks.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/mocks.go
index 3ad4d4e90..a29a0c5ef 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/mocks.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/basic/mocks.go
@@ -2,5 +2,5 @@
package basichost
-//go:generate sh -c "go run github.com/golang/mock/mockgen -build_flags=\"-tags=gomock\" -package basichost -destination mock_nat_test.go github.com/libp2p/go-libp2p/p2p/host/basic NAT"
+//go:generate sh -c "go run go.uber.org/mock/mockgen -build_flags=\"-tags=gomock\" -package basichost -destination mock_nat_test.go github.com/libp2p/go-libp2p/p2p/host/basic NAT"
type NAT nat
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/blank/blank.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/blank/blank.go
index 24304498b..0fdded30f 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/blank/blank.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/blank/blank.go
@@ -210,7 +210,7 @@ func (bh *BlankHost) newStreamHandler(s network.Stream) {
s.SetProtocol(protoID)
- go handle(protoID, s)
+ handle(protoID, s)
}
// TODO: i'm not sure this really needs to be here
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/README.md b/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/README.md
index 9371832c9..72eb192ad 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/README.md
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/README.md
@@ -541,7 +541,7 @@ works best.
## Examples
-Here we consider some concrete examples that can ellucidate the abstract
+Here we consider some concrete examples that can elucidate the abstract
design as described so far.
### Stream Lifetime
@@ -578,7 +578,7 @@ More specifically the following constraints apply:
- the peer scope, where the limits for the peer at the other end of the stream
apply.
- the service scope, where the limits of the specific service owning the stream apply.
-- the protcol scope, where the limits of the specific protocol for the stream apply.
+- the protocol scope, where the limits of the specific protocol for the stream apply.
The resource transfer that happens in the `SetProtocol` and `SetService`
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/extapi.go b/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/extapi.go
index 03edcd79e..b3214f814 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/extapi.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/host/resource-manager/extapi.go
@@ -145,3 +145,7 @@ func (r *resourceManager) Stat() (result ResourceManagerStat) {
return result
}
+
+func (r *resourceManager) GetConnLimit() int {
+ return r.limits.GetConnLimits().GetConnTotalLimit()
+}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/metricshelper/conn.go b/vendor/github.com/libp2p/go-libp2p/p2p/metricshelper/conn.go
index ef367ac9b..b07016ce8 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/metricshelper/conn.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/metricshelper/conn.go
@@ -2,7 +2,7 @@ package metricshelper
import ma "github.com/multiformats/go-multiaddr"
-var transports = [...]int{ma.P_CIRCUIT, ma.P_WEBRTC, ma.P_WEBTRANSPORT, ma.P_QUIC, ma.P_QUIC_V1, ma.P_WSS, ma.P_WS, ma.P_TCP}
+var transports = [...]int{ma.P_CIRCUIT, ma.P_WEBRTC, ma.P_WEBRTC_DIRECT, ma.P_WEBTRANSPORT, ma.P_QUIC, ma.P_QUIC_V1, ma.P_WSS, ma.P_WS, ma.P_TCP}
func GetTransport(a ma.Multiaddr) string {
for _, t := range transports {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/connmgr.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/connmgr.go
index b42a122fa..6caa3dc1a 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/connmgr.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/connmgr.go
@@ -2,6 +2,7 @@ package connmgr
import (
"context"
+ "fmt"
"sort"
"sync"
"sync/atomic"
@@ -239,6 +240,17 @@ func (cm *BasicConnMgr) IsProtected(id peer.ID, tag string) (protected bool) {
return protected
}
+func (cm *BasicConnMgr) CheckLimit(systemLimit connmgr.GetConnLimiter) error {
+ if cm.cfg.highWater > systemLimit.GetConnLimit() {
+ return fmt.Errorf(
+ "conn manager high watermark limit: %d, exceeds the system connection limit of: %d",
+ cm.cfg.highWater,
+ systemLimit.GetConnLimit(),
+ )
+ }
+ return nil
+}
+
// peerInfo stores metadata for a given peer.
type peerInfo struct {
id peer.ID
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/decay.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/decay.go
index bdac0bef7..76f1c6872 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/decay.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/connmgr/decay.go
@@ -320,7 +320,7 @@ func (t *decayingTag) Bump(p peer.ID, delta int) error {
default:
return fmt.Errorf(
"unable to bump decaying tag for peer %s, tag %s, delta %d; queue full (len=%d)",
- p.Pretty(), t.name, delta, len(t.trkr.bumpTagCh))
+ p, t.name, delta, len(t.trkr.bumpTagCh))
}
}
@@ -337,7 +337,7 @@ func (t *decayingTag) Remove(p peer.ID) error {
default:
return fmt.Errorf(
"unable to remove decaying tag for peer %s, tag %s; queue full (len=%d)",
- p.Pretty(), t.name, len(t.trkr.removeTagCh))
+ p, t.name, len(t.trkr.removeTagCh))
}
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/addrs.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/addrs.go
deleted file mode 100644
index 392900e06..000000000
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/addrs.go
+++ /dev/null
@@ -1,39 +0,0 @@
-package swarm
-
-import (
- ma "github.com/multiformats/go-multiaddr"
- manet "github.com/multiformats/go-multiaddr/net"
-)
-
-// http://www.iana.org/assignments/iana-ipv4-special-registry/iana-ipv4-special-registry.xhtml
-var lowTimeoutFilters = ma.NewFilters()
-
-func init() {
- for _, p := range []string{
- "/ip4/10.0.0.0/ipcidr/8",
- "/ip4/100.64.0.0/ipcidr/10",
- "/ip4/169.254.0.0/ipcidr/16",
- "/ip4/172.16.0.0/ipcidr/12",
- "/ip4/192.0.0.0/ipcidr/24",
- "/ip4/192.0.0.0/ipcidr/29",
- "/ip4/192.0.0.8/ipcidr/32",
- "/ip4/192.0.0.170/ipcidr/32",
- "/ip4/192.0.0.171/ipcidr/32",
- "/ip4/192.0.2.0/ipcidr/24",
- "/ip4/192.168.0.0/ipcidr/16",
- "/ip4/198.18.0.0/ipcidr/15",
- "/ip4/198.51.100.0/ipcidr/24",
- "/ip4/203.0.113.0/ipcidr/24",
- "/ip4/240.0.0.0/ipcidr/4",
- } {
- f, err := ma.NewMultiaddr(p)
- if err != nil {
- panic("error in lowTimeoutFilters init: " + err.Error())
- }
- ipnet, err := manet.MultiaddrToIPNet(f)
- if err != nil {
- panic("error in lowTimeoutFilters init: " + err.Error())
- }
- lowTimeoutFilters.AddFilter(*ipnet, ma.ActionDeny)
- }
-}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/black_hole_detector.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/black_hole_detector.go
index 078b1126c..dd7849eea 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/black_hole_detector.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/black_hole_detector.go
@@ -178,7 +178,7 @@ type blackHoleDetector struct {
}
// FilterAddrs filters the peer's addresses removing black holed addresses
-func (d *blackHoleDetector) FilterAddrs(addrs []ma.Multiaddr) []ma.Multiaddr {
+func (d *blackHoleDetector) FilterAddrs(addrs []ma.Multiaddr) (valid []ma.Multiaddr, blackHoled []ma.Multiaddr) {
hasUDP, hasIPv6 := false, false
for _, a := range addrs {
if !manet.IsPublicAddr(a) {
@@ -202,6 +202,7 @@ func (d *blackHoleDetector) FilterAddrs(addrs []ma.Multiaddr) []ma.Multiaddr {
ipv6Res = d.ipv6.HandleRequest()
}
+ blackHoled = make([]ma.Multiaddr, 0, len(addrs))
return ma.FilterAddrs(
addrs,
func(a ma.Multiaddr) bool {
@@ -218,14 +219,16 @@ func (d *blackHoleDetector) FilterAddrs(addrs []ma.Multiaddr) []ma.Multiaddr {
}
if udpRes == blackHoleResultBlocked && isProtocolAddr(a, ma.P_UDP) {
+ blackHoled = append(blackHoled, a)
return false
}
if ipv6Res == blackHoleResultBlocked && isProtocolAddr(a, ma.P_IP6) {
+ blackHoled = append(blackHoled, a)
return false
}
return true
},
- )
+ ), blackHoled
}
// RecordResult updates the state of the relevant `blackHoleFilter`s for addr
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_error.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_error.go
index 711ee0607..4de682204 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_error.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_error.go
@@ -30,10 +30,7 @@ func (e *DialError) recordErr(addr ma.Multiaddr, err error) {
e.Skipped++
return
}
- e.DialErrors = append(e.DialErrors, TransportError{
- Address: addr,
- Cause: err,
- })
+ e.DialErrors = append(e.DialErrors, TransportError{Address: addr, Cause: err})
}
func (e *DialError) Error() string {
@@ -51,9 +48,19 @@ func (e *DialError) Error() string {
return builder.String()
}
-// Unwrap implements https://godoc.org/golang.org/x/xerrors#Wrapper.
-func (e *DialError) Unwrap() error {
- return e.Cause
+func (e *DialError) Unwrap() []error {
+ if e == nil {
+ return nil
+ }
+
+ errs := make([]error, len(e.DialErrors)+1)
+ if e.Cause != nil {
+ errs = append(errs, e.Cause)
+ }
+ for i := 0; i < len(e.DialErrors); i++ {
+ errs = append(errs, &e.DialErrors[i])
+ }
+ return errs
}
var _ error = (*DialError)(nil)
@@ -68,4 +75,8 @@ func (e *TransportError) Error() string {
return fmt.Sprintf("failed to dial %s: %s", e.Address, e.Cause)
}
+func (e *TransportError) Unwrap() error {
+ return e.Cause
+}
+
var _ error = (*TransportError)(nil)
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_ranker.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_ranker.go
index 3725884e2..7e58876b9 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_ranker.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_ranker.go
@@ -58,8 +58,19 @@ func NoDelayDialRanker(addrs []ma.Multiaddr) []network.AddrDelay {
// 3. If a QUIC or WebTransport address is present, TCP addresses dials are delayed relative to the last QUIC dial:
// We prefer to end up with a QUIC connection. For public addresses, the delay introduced is 250ms (PublicTCPDelay),
// and for private addresses 30ms (PrivateTCPDelay).
+// 4. For the TCP addresses we follow a strategy similar to QUIC with an optimisation for handling the long TCP
+// handshake time described in 6. If both IPv6 TCP and IPv4 TCP addresses are present, we do a Happy Eyeballs
+// style ranking. First dial the IPv6 TCP address with the lowest port. After this, dial the IPv4 TCP address
+// with the lowest port delayed by 250ms (PublicTCPDelay) for public addresses, and 30ms (PrivateTCPDelay)
+// for local addresses. After this we dial all the rest of the addresses delayed by 250ms (PublicTCPDelay) for
+// public addresses, and 30ms (PrivateTCPDelay) for local addresses.
+// 5. If only one of TCP IPv6 or TCP IPv4 addresses are present, dial the TCP address with the lowest port
+// first. After this we dial the rest of the TCP addresses delayed by 250ms (PublicTCPDelay) for public
+// addresses, and 30ms (PrivateTCPDelay) for local addresses.
+// 6. When a TCP socket is connected and awaiting security and muxer upgrade, we stop new dials for 2*PrivateTCPDelay
+// to allow for the upgrade to complete.
//
-// We dial lowest ports first for QUIC addresses as they are more likely to be the listen port.
+// We dial lowest ports first as they are more likely to be the listen port.
func DefaultDialRanker(addrs []ma.Multiaddr) []network.AddrDelay {
relay, addrs := filterAddrs(addrs, isRelayAddr)
pvt, addrs := filterAddrs(addrs, manet.IsPrivateAddr)
@@ -88,22 +99,57 @@ func DefaultDialRanker(addrs []ma.Multiaddr) []network.AddrDelay {
// addresses relative to direct addresses.
func getAddrDelay(addrs []ma.Multiaddr, tcpDelay time.Duration, quicDelay time.Duration,
offset time.Duration) []network.AddrDelay {
+ if len(addrs) == 0 {
+ return nil
+ }
sort.Slice(addrs, func(i, j int) bool { return score(addrs[i]) < score(addrs[j]) })
- // If the first address is (QUIC, IPv6), make the second address (QUIC, IPv4).
- happyEyeballs := false
- if len(addrs) > 0 {
+ // addrs is now sorted by (Transport, IPVersion). Reorder addrs for happy eyeballs dialing.
+ // For QUIC and TCP, if we have both IPv6 and IPv4 addresses, move the
+ // highest priority IPv4 address to the second position.
+ happyEyeballsQUIC := false
+ happyEyeballsTCP := false
+ // tcpStartIdx is the index of the first TCP Address
+ var tcpStartIdx int
+ {
+ i := 0
+ // If the first QUIC address is IPv6 move the first QUIC IPv4 address to second position
if isQUICAddr(addrs[0]) && isProtocolAddr(addrs[0], ma.P_IP6) {
- for i := 1; i < len(addrs); i++ {
- if isQUICAddr(addrs[i]) && isProtocolAddr(addrs[i], ma.P_IP4) {
- // make IPv4 address the second element
- if i > 1 {
- a := addrs[i]
- copy(addrs[2:], addrs[1:i])
+ for j := 1; j < len(addrs); j++ {
+ if isQUICAddr(addrs[j]) && isProtocolAddr(addrs[j], ma.P_IP4) {
+ // The first IPv4 address is at position j
+ // Move the jth element at position 1 shifting the affected elements
+ if j > 1 {
+ a := addrs[j]
+ copy(addrs[2:], addrs[1:j])
addrs[1] = a
}
- happyEyeballs = true
+ happyEyeballsQUIC = true
+ i = j + 1
+ break
+ }
+ }
+ }
+
+ for tcpStartIdx = i; tcpStartIdx < len(addrs); tcpStartIdx++ {
+ if isProtocolAddr(addrs[tcpStartIdx], ma.P_TCP) {
+ break
+ }
+ }
+
+ // If the first TCP address is IPv6 move the first TCP IPv4 address to second position
+ if tcpStartIdx < len(addrs) && isProtocolAddr(addrs[tcpStartIdx], ma.P_IP6) {
+ for j := tcpStartIdx + 1; j < len(addrs); j++ {
+ if isProtocolAddr(addrs[j], ma.P_TCP) && isProtocolAddr(addrs[j], ma.P_IP4) {
+ // First TCP IPv4 address is at position j, move it to position tcpStartIdx+1
+ // which is the second priority TCP address
+ if j > tcpStartIdx+1 {
+ a := addrs[j]
+ copy(addrs[tcpStartIdx+2:], addrs[tcpStartIdx+1:j])
+ addrs[tcpStartIdx+1] = a
+ }
+ happyEyeballsTCP = true
break
}
}
@@ -111,25 +157,42 @@ func getAddrDelay(addrs []ma.Multiaddr, tcpDelay time.Duration, quicDelay time.D
}
res := make([]network.AddrDelay, 0, len(addrs))
-
- var totalTCPDelay time.Duration
+ var tcpFirstDialDelay time.Duration
for i, addr := range addrs {
var delay time.Duration
switch {
case isQUICAddr(addr):
- // For QUIC addresses we dial an IPv6 address, then after quicDelay an IPv4
- // address, then after quicDelay we dial rest of the addresses.
+ // We dial an IPv6 address, then after quicDelay an IPv4
+ // address, then after a further quicDelay we dial the rest of the addresses.
if i == 1 {
delay = quicDelay
}
- if i > 1 && happyEyeballs {
- delay = 2 * quicDelay
- } else if i > 1 {
- delay = quicDelay
+ if i > 1 {
+ // If we have happy eyeballs for QUIC, dials after the second position
+ // will be delayed by 2*quicDelay
+ if happyEyeballsQUIC {
+ delay = 2 * quicDelay
+ } else {
+ delay = quicDelay
+ }
}
- totalTCPDelay = delay + tcpDelay
+ tcpFirstDialDelay = delay + tcpDelay
case isProtocolAddr(addr, ma.P_TCP):
- delay = totalTCPDelay
+ // We dial an IPv6 address, then after tcpDelay an IPv4
+ // address, then after a further tcpDelay we dial the rest of the addresses.
+ if i == tcpStartIdx+1 {
+ delay = tcpDelay
+ }
+ if i > tcpStartIdx+1 {
+ // If we have happy eyeballs for TCP, dials after the second position
+ // will be delayed by 2*tcpDelay
+ if happyEyeballsTCP {
+ delay = 2 * tcpDelay
+ } else {
+ delay = tcpDelay
+ }
+ }
+ delay += tcpFirstDialDelay
}
res = append(res, network.AddrDelay{Addr: addr, Delay: offset + delay})
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_sync.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_sync.go
index 2a8ff4317..3cc854728 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_sync.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_sync.go
@@ -2,6 +2,7 @@ package swarm
import (
"context"
+ "errors"
"sync"
"github.com/libp2p/go-libp2p/core/network"
@@ -11,6 +12,9 @@ import (
// dialWorkerFunc is used by dialSync to spawn a new dial worker
type dialWorkerFunc func(peer.ID, <-chan dialRequest)
+// errConcurrentDialSuccessful is used to signal that a concurrent dial succeeded
+var errConcurrentDialSuccessful = errors.New("concurrent dial successful")
+
// newDialSync constructs a new dialSync
func newDialSync(worker dialWorkerFunc) *dialSync {
return &dialSync{
@@ -30,17 +34,12 @@ type dialSync struct {
type activeDial struct {
refCnt int
- ctx context.Context
- cancel func()
+ ctx context.Context
+ cancelCause func(error)
reqch chan dialRequest
}
-func (ad *activeDial) close() {
- ad.cancel()
- close(ad.reqch)
-}
-
func (ad *activeDial) dial(ctx context.Context) (*Conn, error) {
dialCtx := ad.ctx
@@ -74,11 +73,11 @@ func (ds *dialSync) getActiveDial(p peer.ID) (*activeDial, error) {
if !ok {
// This code intentionally uses the background context. Otherwise, if the first call
// to Dial is canceled, subsequent dial calls will also be canceled.
- ctx, cancel := context.WithCancel(context.Background())
+ ctx, cancel := context.WithCancelCause(context.Background())
actd = &activeDial{
- ctx: ctx,
- cancel: cancel,
- reqch: make(chan dialRequest),
+ ctx: ctx,
+ cancelCause: cancel,
+ reqch: make(chan dialRequest),
}
go ds.dialWorker(p, actd.reqch)
ds.dials[p] = actd
@@ -96,14 +95,21 @@ func (ds *dialSync) Dial(ctx context.Context, p peer.ID) (*Conn, error) {
return nil, err
}
- defer func() {
- ds.mutex.Lock()
- defer ds.mutex.Unlock()
- ad.refCnt--
- if ad.refCnt == 0 {
- ad.close()
- delete(ds.dials, p)
+ conn, err := ad.dial(ctx)
+
+ ds.mutex.Lock()
+ defer ds.mutex.Unlock()
+
+ ad.refCnt--
+ if ad.refCnt == 0 {
+ if err == nil {
+ ad.cancelCause(errConcurrentDialSuccessful)
+ } else {
+ ad.cancelCause(err)
}
- }()
- return ad.dial(ctx)
+ close(ad.reqch)
+ delete(ds.dials, p)
+ }
+
+ return conn, err
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_worker.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_worker.go
index 0334ac863..0cac6e4fa 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_worker.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/dial_worker.go
@@ -8,15 +8,12 @@ import (
"github.com/libp2p/go-libp2p/core/network"
"github.com/libp2p/go-libp2p/core/peer"
+ tpt "github.com/libp2p/go-libp2p/core/transport"
ma "github.com/multiformats/go-multiaddr"
+ manet "github.com/multiformats/go-multiaddr/net"
)
-// /////////////////////////////////////////////////////////////////////////////////
-// lo and behold, The Dialer
-// TODO explain how all this works
-// ////////////////////////////////////////////////////////////////////////////////
-
// dialRequest is structure used to request dials to the peer associated with a
// worker loop
type dialRequest struct {
@@ -61,15 +58,14 @@ type addrDial struct {
conn *Conn
// err is the err on dialing the address
err error
- // requests is the list of pendRequests interested in this dial
- // the value in the slice is the request number assigned to this request by the dialWorker
- requests []int
// dialed indicates whether we have triggered the dial to the address
dialed bool
// createdAt is the time this struct was created
createdAt time.Time
// dialRankingDelay is the delay in dialing this address introduced by the ranking logic
dialRankingDelay time.Duration
+ // expectedTCPUpgradeTime is the expected time by which security upgrade will complete
+ expectedTCPUpgradeTime time.Time
}
// dialWorker synchronises concurrent dials to a peer. It ensures that we make at most one dial to a
@@ -79,17 +75,13 @@ type dialWorker struct {
peer peer.ID
// reqch is used to send dial requests to the worker. close reqch to end the worker loop
reqch <-chan dialRequest
- // reqno is the request number used to track different dialRequests for a peer.
- // Each incoming request is assigned a reqno. This reqno is used in pendingRequests and in
- // addrDial objects in trackedDials to track this request
- reqno int
- // pendingRequests maps reqno to the pendRequest object for a dialRequest
- pendingRequests map[int]*pendRequest
- // trackedDials tracks dials to the peers addresses. An entry here is used to ensure that
+ // pendingRequests is the set of pendingRequests
+ pendingRequests map[*pendRequest]struct{}
+ // trackedDials tracks dials to the peer's addresses. An entry here is used to ensure that
// we dial an address at most once
trackedDials map[string]*addrDial
// resch is used to receive response for dials to the peers addresses.
- resch chan dialResult
+ resch chan tpt.DialUpdate
connected bool // true when a connection has been successfully established
@@ -106,9 +98,9 @@ func newDialWorker(s *Swarm, p peer.ID, reqch <-chan dialRequest, cl Clock) *dia
s: s,
peer: p,
reqch: reqch,
- pendingRequests: make(map[int]*pendRequest),
+ pendingRequests: make(map[*pendRequest]struct{}),
trackedDials: make(map[string]*addrDial),
- resch: make(chan dialResult),
+ resch: make(chan tpt.DialUpdate),
cl: cl,
}
}
@@ -128,6 +120,8 @@ func (w *dialWorker) loop() {
startTime := w.cl.Now()
// dialTimer is the dialTimer used to trigger dials
dialTimer := w.cl.InstantTimer(startTime.Add(math.MaxInt64))
+ defer dialTimer.Stop()
+
timerRunning := true
// scheduleNextDial updates timer for triggering the next dial
scheduleNextDial := func() {
@@ -135,12 +129,18 @@ func (w *dialWorker) loop() {
<-dialTimer.Ch()
}
timerRunning = false
- if dq.len() > 0 {
+ if dq.Len() > 0 {
if dialsInFlight == 0 && !w.connected {
// if there are no dials in flight, trigger the next dials immediately
dialTimer.Reset(startTime)
} else {
- dialTimer.Reset(startTime.Add(dq.top().Delay))
+ resetTime := startTime.Add(dq.top().Delay)
+ for _, ad := range w.trackedDials {
+ if !ad.expectedTCPUpgradeTime.IsZero() && ad.expectedTCPUpgradeTime.After(resetTime) {
+ resetTime = ad.expectedTCPUpgradeTime
+ }
+ }
+ dialTimer.Reset(resetTime)
}
timerRunning = true
}
@@ -171,15 +171,20 @@ loop:
// Enqueue the peer's addresses relevant to this request in dq and
// track dials to the addresses relevant to this request.
- c, err := w.s.bestAcceptableConnToPeer(req.ctx, w.peer)
- if c != nil || err != nil {
- req.resch <- dialResponse{conn: c, err: err}
+ c := w.s.bestAcceptableConnToPeer(req.ctx, w.peer)
+ if c != nil {
+ req.resch <- dialResponse{conn: c}
continue loop
}
- addrs, err := w.s.addrsForDial(req.ctx, w.peer)
+ addrs, addrErrs, err := w.s.addrsForDial(req.ctx, w.peer)
if err != nil {
- req.resch <- dialResponse{err: err}
+ req.resch <- dialResponse{
+ err: &DialError{
+ Peer: w.peer,
+ DialErrors: addrErrs,
+ Cause: err,
+ }}
continue loop
}
@@ -191,8 +196,8 @@ loop:
// create the pending request object
pr := &pendRequest{
req: req,
- err: &DialError{Peer: w.peer},
addrs: make(map[string]struct{}, len(addrRanking)),
+ err: &DialError{Peer: w.peer, DialErrors: addrErrs},
}
for _, adelay := range addrRanking {
pr.addrs[string(adelay.Addr.Bytes())] = struct{}{}
@@ -233,14 +238,13 @@ loop:
if len(todial) == 0 && len(tojoin) == 0 {
// all request applicable addrs have been dialed, we must have errored
+ pr.err.Cause = ErrAllDialsFailed
req.resch <- dialResponse{err: pr.err}
continue loop
}
- // The request has some pending or new dials. We assign this request a request number.
- // This value of w.reqno is used to track this request in all the structures
- w.reqno++
- w.pendingRequests[w.reqno] = pr
+ // The request has some pending or new dials
+ w.pendingRequests[pr] = struct{}{}
for _, ad := range tojoin {
if !ad.dialed {
@@ -258,7 +262,6 @@ loop:
}
}
// add the request to the addrDial
- ad.requests = append(ad.requests, w.reqno)
}
if len(todial) > 0 {
@@ -268,7 +271,6 @@ loop:
w.trackedDials[string(a.Bytes())] = &addrDial{
addr: a,
ctx: req.ctx,
- requests: []int{w.reqno},
createdAt: now,
}
dq.Add(network.AddrDelay{Addr: a, Delay: addrDelay[string(a.Bytes())]})
@@ -313,16 +315,29 @@ loop:
// Update all requests waiting on this address. On success, complete the request.
// On error, record the error
- dialsInFlight--
ad, ok := w.trackedDials[string(res.Addr.Bytes())]
if !ok {
log.Errorf("SWARM BUG: no entry for address %s in trackedDials", res.Addr)
if res.Conn != nil {
res.Conn.Close()
}
+ dialsInFlight--
continue
}
+ // TCP Connection has been established. Wait for connection upgrade on this address
+ // before making new dials.
+ if res.Kind == tpt.UpdateKindHandshakeProgressed {
+ // Only wait for public addresses to complete dialing since private dials
+ // are quick any way
+ if manet.IsPublicAddr(res.Addr) {
+ ad.expectedTCPUpgradeTime = w.cl.Now().Add(PublicTCPDelay)
+ }
+ scheduleNextDial()
+ continue
+ }
+ dialsInFlight--
+ ad.expectedTCPUpgradeTime = time.Time{}
if res.Conn != nil {
// we got a connection, add it to the swarm
conn, err := w.s.addConn(res.Conn, network.DirOutbound)
@@ -333,20 +348,14 @@ loop:
continue loop
}
- // request succeeded, respond to all pending requests
- for _, reqno := range ad.requests {
- pr, ok := w.pendingRequests[reqno]
- if !ok {
- // some other dial for this request succeeded before this one
- continue
+ for pr := range w.pendingRequests {
+ if _, ok := pr.addrs[string(ad.addr.Bytes())]; ok {
+ pr.req.resch <- dialResponse{conn: conn}
+ delete(w.pendingRequests, pr)
}
- pr.req.resch <- dialResponse{conn: conn}
- delete(w.pendingRequests, reqno)
}
ad.conn = conn
- ad.requests = nil
-
if !w.connected {
w.connected = true
if w.s.metricsTracer != nil {
@@ -380,33 +389,27 @@ loop:
// dispatches an error to a specific addr dial
func (w *dialWorker) dispatchError(ad *addrDial, err error) {
ad.err = err
- for _, reqno := range ad.requests {
- pr, ok := w.pendingRequests[reqno]
- if !ok {
- // some other dial for this request succeeded before this one
- continue
- }
-
+ for pr := range w.pendingRequests {
// accumulate the error
- pr.err.recordErr(ad.addr, err)
-
- delete(pr.addrs, string(ad.addr.Bytes()))
- if len(pr.addrs) == 0 {
- // all addrs have erred, dispatch dial error
- // but first do a last one check in case an acceptable connection has landed from
- // a simultaneous dial that started later and added new acceptable addrs
- c, _ := w.s.bestAcceptableConnToPeer(pr.req.ctx, w.peer)
- if c != nil {
- pr.req.resch <- dialResponse{conn: c}
- } else {
- pr.req.resch <- dialResponse{err: pr.err}
+ if _, ok := pr.addrs[string(ad.addr.Bytes())]; ok {
+ pr.err.recordErr(ad.addr, err)
+ delete(pr.addrs, string(ad.addr.Bytes()))
+ if len(pr.addrs) == 0 {
+ // all addrs have erred, dispatch dial error
+ // but first do a last one check in case an acceptable connection has landed from
+ // a simultaneous dial that started later and added new acceptable addrs
+ c := w.s.bestAcceptableConnToPeer(pr.req.ctx, w.peer)
+ if c != nil {
+ pr.req.resch <- dialResponse{conn: c}
+ } else {
+ pr.err.Cause = ErrAllDialsFailed
+ pr.req.resch <- dialResponse{err: pr.err}
+ }
+ delete(w.pendingRequests, pr)
}
- delete(w.pendingRequests, reqno)
}
}
- ad.requests = nil
-
// if it was a backoff, clear the address dial so that it doesn't inhibit new dial requests.
// this is necessary to support active listen scenarios, where a new dial comes in while
// another dial is in progress, and needs to do a direct connection without inhibitions from
@@ -439,7 +442,7 @@ func newDialQueue() *dialQueue {
// Add adds adelay to the queue. If another element exists in the queue with
// the same address, it replaces that element.
func (dq *dialQueue) Add(adelay network.AddrDelay) {
- for i := 0; i < dq.len(); i++ {
+ for i := 0; i < dq.Len(); i++ {
if dq.q[i].Addr.Equal(adelay.Addr) {
if dq.q[i].Delay == adelay.Delay {
// existing element is the same. nothing to do
@@ -452,7 +455,7 @@ func (dq *dialQueue) Add(adelay network.AddrDelay) {
}
}
- for i := 0; i < dq.len(); i++ {
+ for i := 0; i < dq.Len(); i++ {
if dq.q[i].Delay > adelay.Delay {
dq.q = append(dq.q, network.AddrDelay{}) // extend the slice
copy(dq.q[i+1:], dq.q[i:])
@@ -465,13 +468,13 @@ func (dq *dialQueue) Add(adelay network.AddrDelay) {
// NextBatch returns all the elements in the queue with the highest priority
func (dq *dialQueue) NextBatch() []network.AddrDelay {
- if dq.len() == 0 {
+ if dq.Len() == 0 {
return nil
}
// i is the index of the second highest priority element
var i int
- for i = 0; i < dq.len(); i++ {
+ for i = 0; i < dq.Len(); i++ {
if dq.q[i].Delay != dq.q[0].Delay {
break
}
@@ -486,7 +489,7 @@ func (dq *dialQueue) top() network.AddrDelay {
return dq.q[0]
}
-// len returns the number of elements in the queue
-func (dq *dialQueue) len() int {
+// Len returns the number of elements in the queue
+func (dq *dialQueue) Len() int {
return len(dq.q)
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/limiter.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/limiter.go
index ccfe7d237..f5638bbe7 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/limiter.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/limiter.go
@@ -13,17 +13,11 @@ import (
ma "github.com/multiformats/go-multiaddr"
)
-type dialResult struct {
- Conn transport.CapableConn
- Addr ma.Multiaddr
- Err error
-}
-
type dialJob struct {
addr ma.Multiaddr
peer peer.ID
ctx context.Context
- resp chan dialResult
+ resp chan transport.DialUpdate
timeout time.Duration
}
@@ -45,7 +39,7 @@ type dialLimiter struct {
waitingOnPeerLimit map[peer.ID][]*dialJob
}
-type dialfunc func(context.Context, peer.ID, ma.Multiaddr) (transport.CapableConn, error)
+type dialfunc func(context.Context, peer.ID, ma.Multiaddr, chan<- transport.DialUpdate) (transport.CapableConn, error)
func newDialLimiter(df dialfunc) *dialLimiter {
fd := ConcurrentFdDials
@@ -216,9 +210,13 @@ func (dl *dialLimiter) executeDial(j *dialJob) {
dctx, cancel := context.WithTimeout(j.ctx, j.timeout)
defer cancel()
- con, err := dl.dialFunc(dctx, j.peer, j.addr)
+ con, err := dl.dialFunc(dctx, j.peer, j.addr, j.resp)
+ kind := transport.UpdateKindDialSuccessful
+ if err != nil {
+ kind = transport.UpdateKindDialFailed
+ }
select {
- case j.resp <- dialResult{Conn: con, Addr: j.addr, Err: err}:
+ case j.resp <- transport.DialUpdate{Kind: kind, Conn: con, Addr: j.addr, Err: err}:
case <-j.ctx.Done():
if con != nil {
con.Close()
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm.go
index 5155cd222..a76edce6c 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm.go
@@ -17,6 +17,7 @@ import (
"github.com/libp2p/go-libp2p/core/peer"
"github.com/libp2p/go-libp2p/core/peerstore"
"github.com/libp2p/go-libp2p/core/transport"
+ "golang.org/x/exp/slices"
logging "github.com/ipfs/go-log/v2"
ma "github.com/multiformats/go-multiaddr"
@@ -136,8 +137,8 @@ func WithIPv6BlackHoleConfig(enabled bool, n, min int) Option {
// communication. The Chan sends/receives Messages, which note the
// destination or source Peer.
type Swarm struct {
- nextConnID uint64 // guarded by atomic
- nextStreamID uint64 // guarded by atomic
+ nextConnID atomic.Uint64
+ nextStreamID atomic.Uint64
// Close refcount. This allows us to fully wait for the swarm to be torn
// down before continuing.
@@ -172,6 +173,11 @@ type Swarm struct {
m map[network.Notifiee]struct{}
}
+ directConnNotifs struct {
+ sync.Mutex
+ m map[peer.ID][]chan struct{}
+ }
+
transports struct {
sync.RWMutex
m map[int]transport.Transport
@@ -231,6 +237,7 @@ func NewSwarm(local peer.ID, peers peerstore.Peerstore, eventBus event.Bus, opts
s.listeners.m = make(map[transport.Listener]struct{})
s.transports.m = make(map[int]transport.Transport)
s.notifs.m = make(map[network.Notifiee]struct{})
+ s.directConnNotifs.m = make(map[peer.ID][]chan struct{})
for _, opt := range opts {
if err := opt(s); err != nil {
@@ -343,7 +350,7 @@ func (s *Swarm) addConn(tc transport.CapableConn, dir network.Direction) (*Conn,
conn: tc,
swarm: s,
stat: stat,
- id: atomic.AddUint64(&s.nextConnID, 1),
+ id: s.nextConnID.Add(1),
}
// we ONLY check upgraded connections here so we can send them a Disconnect message.
@@ -353,7 +360,7 @@ func (s *Swarm) addConn(tc transport.CapableConn, dir network.Direction) (*Conn,
// TODO Send disconnect with reason here
err := tc.Close()
if err != nil {
- log.Warnf("failed to close connection with peer %s and addr %s; err: %s", p.Pretty(), addr, err)
+ log.Warnf("failed to close connection with peer %s and addr %s; err: %s", p, addr, err)
}
return nil, ErrGaterDisallowedConnection
}
@@ -390,6 +397,19 @@ func (s *Swarm) addConn(tc transport.CapableConn, dir network.Direction) (*Conn,
c.notifyLk.Lock()
s.conns.Unlock()
+ // Notify goroutines waiting for a direct connection
+ if !c.Stat().Transient {
+ // Go routines interested in waiting for direct connection first acquire this lock
+ // and then acquire s.conns.RLock. Do not acquire this lock before conns.Unlock to
+ // prevent deadlock.
+ s.directConnNotifs.Lock()
+ for _, ch := range s.directConnNotifs.m[p] {
+ close(ch)
+ }
+ delete(s.directConnNotifs.m, p)
+ s.directConnNotifs.Unlock()
+ }
+
// Emit event after releasing `s.conns` lock so that a consumer can still
// use swarm methods that need the `s.conns` lock.
if isFirstConnection {
@@ -429,54 +449,110 @@ func (s *Swarm) StreamHandler() network.StreamHandler {
// NewStream creates a new stream on any available connection to peer, dialing
// if necessary.
+// Use network.WithUseTransient to open a stream over a transient(relayed)
+// connection.
func (s *Swarm) NewStream(ctx context.Context, p peer.ID) (network.Stream, error) {
log.Debugf("[%s] opening stream to peer [%s]", s.local, p)
// Algorithm:
// 1. Find the best connection, otherwise, dial.
- // 2. Try opening a stream.
- // 3. If the underlying connection is, in fact, closed, close the outer
+ // 2. If the best connection is transient, wait for a direct conn via conn
+ // reversal or hole punching.
+ // 3. Try opening a stream.
+ // 4. If the underlying connection is, in fact, closed, close the outer
// connection and try again. We do this in case we have a closed
// connection but don't notice it until we actually try to open a
// stream.
//
- // Note: We only dial once.
- //
// TODO: Try all connections even if we get an error opening a stream on
// a non-closed connection.
- dials := 0
+ numDials := 0
for {
- // will prefer direct connections over relayed connections for opening streams
- c, err := s.bestAcceptableConnToPeer(ctx, p)
- if err != nil {
- return nil, err
- }
-
+ c := s.bestConnToPeer(p)
if c == nil {
- if nodial, _ := network.GetNoDial(ctx); nodial {
+ if nodial, _ := network.GetNoDial(ctx); !nodial {
+ numDials++
+ if numDials > DialAttempts {
+ return nil, errors.New("max dial attempts exceeded")
+ }
+ var err error
+ c, err = s.dialPeer(ctx, p)
+ if err != nil {
+ return nil, err
+ }
+ } else {
return nil, network.ErrNoConn
}
+ }
- if dials >= DialAttempts {
- return nil, errors.New("max dial attempts exceeded")
- }
- dials++
-
+ useTransient, _ := network.GetUseTransient(ctx)
+ if !useTransient && c.Stat().Transient {
var err error
- c, err = s.dialPeer(ctx, p)
+ c, err = s.waitForDirectConn(ctx, p)
if err != nil {
return nil, err
}
}
- s, err := c.NewStream(ctx)
+ str, err := c.NewStream(ctx)
if err != nil {
if c.conn.IsClosed() {
continue
}
return nil, err
}
- return s, nil
+ return str, nil
+ }
+}
+
+// waitForDirectConn waits for a direct connection established through hole punching or connection reversal.
+func (s *Swarm) waitForDirectConn(ctx context.Context, p peer.ID) (*Conn, error) {
+ s.directConnNotifs.Lock()
+ c := s.bestConnToPeer(p)
+ if c == nil {
+ s.directConnNotifs.Unlock()
+ return nil, network.ErrNoConn
+ } else if !c.Stat().Transient {
+ s.directConnNotifs.Unlock()
+ return c, nil
+ }
+
+ // Wait for transient connection to upgrade to a direct connection either by
+ // connection reversal or hole punching.
+ ch := make(chan struct{})
+ s.directConnNotifs.m[p] = append(s.directConnNotifs.m[p], ch)
+ s.directConnNotifs.Unlock()
+
+ // apply the DialPeer timeout
+ ctx, cancel := context.WithTimeout(ctx, network.GetDialPeerTimeout(ctx))
+ defer cancel()
+
+ // Wait for notification.
+ select {
+ case <-ctx.Done():
+ // Remove ourselves from the notification list
+ s.directConnNotifs.Lock()
+ defer s.directConnNotifs.Unlock()
+
+ s.directConnNotifs.m[p] = slices.DeleteFunc(
+ s.directConnNotifs.m[p],
+ func(c chan struct{}) bool { return c == ch },
+ )
+ if len(s.directConnNotifs.m[p]) == 0 {
+ delete(s.directConnNotifs.m, p)
+ }
+ return nil, ctx.Err()
+ case <-ch:
+ // We do not need to remove ourselves from the list here as the notifier
+ // clears the map entry
+ c := s.bestConnToPeer(p)
+ if c == nil {
+ return nil, network.ErrNoConn
+ }
+ if c.Stat().Transient {
+ return nil, network.ErrTransientConn
+ }
+ return c, nil
}
}
@@ -548,26 +624,17 @@ func (s *Swarm) bestConnToPeer(p peer.ID) *Conn {
return best
}
-// - Returns the best "acceptable" connection, if available.
-// - Returns nothing if no such connection exists, but if we should try dialing anyways.
-// - Returns an error if no such connection exists, but we should not try dialing.
-func (s *Swarm) bestAcceptableConnToPeer(ctx context.Context, p peer.ID) (*Conn, error) {
+// bestAcceptableConnToPeer returns the best acceptable connection, considering the passed in ctx.
+// If network.WithForceDirectDial is used, it only returns a direct connections, ignoring
+// any transient (relayed) connections to the peer.
+func (s *Swarm) bestAcceptableConnToPeer(ctx context.Context, p peer.ID) *Conn {
conn := s.bestConnToPeer(p)
- if conn == nil {
- return nil, nil
- }
forceDirect, _ := network.GetForceDirectDial(ctx)
if forceDirect && !isDirectConn(conn) {
- return nil, nil
+ return nil
}
-
- useTransient, _ := network.GetUseTransient(ctx)
- if useTransient || !conn.Stat().Transient {
- return conn, nil
- }
-
- return nil, network.ErrTransientConn
+ return conn
}
func isDirectConn(c *Conn) bool {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_conn.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_conn.go
index e770381a2..8c3ce7c5a 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_conn.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_conn.go
@@ -5,7 +5,6 @@ import (
"errors"
"fmt"
"sync"
- "sync/atomic"
"time"
ic "github.com/libp2p/go-libp2p/core/crypto"
@@ -49,7 +48,7 @@ func (c *Conn) IsClosed() bool {
func (c *Conn) ID() string {
// format: -
- return fmt.Sprintf("%s-%d", c.RemotePeer().Pretty()[0:10], c.id)
+ return fmt.Sprintf("%s-%d", c.RemotePeer().String()[:10], c.id)
}
// Close closes this connection.
@@ -137,6 +136,7 @@ func (c *Conn) start() {
if h := c.swarm.StreamHandler(); h != nil {
h(s)
}
+ s.completeAcceptStreamGoroutine()
}()
}
}()
@@ -147,9 +147,9 @@ func (c *Conn) String() string {
" %s (%s)>",
c.conn.Transport(),
c.conn.LocalMultiaddr(),
- c.conn.LocalPeer().Pretty(),
+ c.conn.LocalPeer(),
c.conn.RemoteMultiaddr(),
- c.conn.RemotePeer().Pretty(),
+ c.conn.RemotePeer(),
)
}
@@ -238,7 +238,8 @@ func (c *Conn) addStream(ts network.MuxedStream, dir network.Direction, scope ne
Direction: dir,
Opened: time.Now(),
},
- id: atomic.AddUint64(&c.swarm.nextStreamID, 1),
+ id: c.swarm.nextStreamID.Add(1),
+ acceptStreamGoroutineCompleted: dir != network.DirInbound,
}
c.stat.NumStreams++
c.streams.m[s] = struct{}{}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_dial.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_dial.go
index f2df93af2..3fb15383a 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_dial.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_dial.go
@@ -14,8 +14,10 @@ import (
"github.com/libp2p/go-libp2p/core/peer"
"github.com/libp2p/go-libp2p/core/peerstore"
"github.com/libp2p/go-libp2p/core/transport"
+
ma "github.com/multiformats/go-multiaddr"
madns "github.com/multiformats/go-multiaddr-dns"
+ mafmt "github.com/multiformats/go-multiaddr-fmt"
manet "github.com/multiformats/go-multiaddr/net"
)
@@ -65,6 +67,19 @@ var (
ErrGaterDisallowedConnection = errors.New("gater disallows connection to peer")
)
+// ErrQUICDraft29 wraps ErrNoTransport and provide a more meaningful error message
+var ErrQUICDraft29 errQUICDraft29
+
+type errQUICDraft29 struct{}
+
+func (errQUICDraft29) Error() string {
+ return "QUIC draft-29 has been removed, QUIC (RFC 9000) is accessible with /quic-v1"
+}
+
+func (errQUICDraft29) Unwrap() error {
+ return ErrNoTransport
+}
+
// DialAttempts governs how many times a goroutine will try to dial a given peer.
// Note: this is down to one, as we have _too many dials_ atm. To add back in,
// add loop back in Dial(.)
@@ -201,7 +216,8 @@ func (db *DialBackoff) cleanup() {
}
}
-// DialPeer connects to a peer.
+// DialPeer connects to a peer. Use network.WithForceDirectDial to force a
+// direct connection.
//
// The idea is that the client of Swarm does not need to know what network
// the connection will happen over. Swarm can use whichever it choses.
@@ -231,15 +247,14 @@ func (s *Swarm) dialPeer(ctx context.Context, p peer.ID) (*Conn, error) {
return nil, ErrDialToSelf
}
- // check if we already have an open (usable) connection first, or can't have a usable
- // connection.
- conn, err := s.bestAcceptableConnToPeer(ctx, p)
- if conn != nil || err != nil {
- return conn, err
+ // check if we already have an open (usable) connection.
+ conn := s.bestAcceptableConnToPeer(ctx, p)
+ if conn != nil {
+ return conn, nil
}
if s.gater != nil && !s.gater.InterceptPeerDial(p) {
- log.Debugf("gater disallowed outbound connection to peer %s", p.Pretty())
+ log.Debugf("gater disallowed outbound connection to peer %s", p)
return nil, &DialError{Peer: p, Cause: ErrGaterDisallowedConnection}
}
@@ -280,68 +295,47 @@ func (s *Swarm) dialWorkerLoop(p peer.ID, reqch <-chan dialRequest) {
w.loop()
}
-func (s *Swarm) addrsForDial(ctx context.Context, p peer.ID) ([]ma.Multiaddr, error) {
+func (s *Swarm) addrsForDial(ctx context.Context, p peer.ID) (goodAddrs []ma.Multiaddr, addrErrs []TransportError, err error) {
peerAddrs := s.peers.Addrs(p)
if len(peerAddrs) == 0 {
- return nil, ErrNoAddresses
- }
-
- peerAddrsAfterTransportResolved := make([]ma.Multiaddr, 0, len(peerAddrs))
- for _, a := range peerAddrs {
- tpt := s.TransportForDialing(a)
- resolver, ok := tpt.(transport.Resolver)
- if ok {
- resolvedAddrs, err := resolver.Resolve(ctx, a)
- if err != nil {
- log.Warnf("Failed to resolve multiaddr %s by transport %v: %v", a, tpt, err)
- continue
- }
- peerAddrsAfterTransportResolved = append(peerAddrsAfterTransportResolved, resolvedAddrs...)
- } else {
- peerAddrsAfterTransportResolved = append(peerAddrsAfterTransportResolved, a)
- }
+ return nil, nil, ErrNoAddresses
}
// Resolve dns or dnsaddrs
- resolved, err := s.resolveAddrs(ctx, peer.AddrInfo{
- ID: p,
- Addrs: peerAddrsAfterTransportResolved,
- })
+ resolved, err := s.resolveAddrs(ctx, peer.AddrInfo{ID: p, Addrs: peerAddrs})
if err != nil {
- return nil, err
+ return nil, nil, err
}
- goodAddrs := s.filterKnownUndialables(p, resolved)
+ goodAddrs = ma.Unique(resolved)
+ goodAddrs, addrErrs = s.filterKnownUndialables(p, goodAddrs)
if forceDirect, _ := network.GetForceDirectDial(ctx); forceDirect {
goodAddrs = ma.FilterAddrs(goodAddrs, s.nonProxyAddr)
}
- goodAddrs = ma.Unique(goodAddrs)
if len(goodAddrs) == 0 {
- return nil, ErrNoGoodAddresses
+ return nil, addrErrs, ErrNoGoodAddresses
}
s.peers.AddAddrs(p, goodAddrs, peerstore.TempAddrTTL)
- return goodAddrs, nil
+ return goodAddrs, addrErrs, nil
}
func (s *Swarm) resolveAddrs(ctx context.Context, pi peer.AddrInfo) ([]ma.Multiaddr, error) {
- proto := ma.ProtocolWithCode(ma.P_P2P).Name
- p2paddr, err := ma.NewMultiaddr("/" + proto + "/" + pi.ID.Pretty())
+ p2paddr, err := ma.NewMultiaddr("/" + ma.ProtocolWithCode(ma.P_P2P).Name + "/" + pi.ID.String())
if err != nil {
return nil, err
}
- resolveSteps := 0
-
+ var resolveSteps int
// Recursively resolve all addrs.
//
// While the toResolve list is non-empty:
// * Pop an address off.
// * If the address is fully resolved, add it to the resolved list.
// * Otherwise, resolve it and add the results to the "to resolve" list.
- toResolve := append(([]ma.Multiaddr)(nil), pi.Addrs...)
+ toResolve := append([]ma.Multiaddr{}, pi.Addrs...)
resolved := make([]ma.Multiaddr, 0, len(pi.Addrs))
for len(toResolve) > 0 {
// pop the last addr off.
@@ -368,6 +362,26 @@ func (s *Swarm) resolveAddrs(ctx context.Context, pi peer.AddrInfo) ([]ma.Multia
continue
}
+ tpt := s.TransportForDialing(addr)
+ resolver, ok := tpt.(transport.Resolver)
+ if ok {
+ resolvedAddrs, err := resolver.Resolve(ctx, addr)
+ if err != nil {
+ log.Warnf("Failed to resolve multiaddr %s by transport %v: %v", addr, tpt, err)
+ continue
+ }
+ var added bool
+ for _, a := range resolvedAddrs {
+ if !addr.Equal(a) {
+ toResolve = append(toResolve, a)
+ added = true
+ }
+ }
+ if added {
+ continue
+ }
+ }
+
// otherwise, resolve it
reqaddr := addr.Encapsulate(p2paddr)
resaddrs, err := s.maResolver.Resolve(ctx, reqaddr)
@@ -388,7 +402,7 @@ func (s *Swarm) resolveAddrs(ctx context.Context, pi peer.AddrInfo) ([]ma.Multia
return resolved, nil
}
-func (s *Swarm) dialNextAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr, resch chan dialResult) error {
+func (s *Swarm) dialNextAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr, resch chan transport.DialUpdate) error {
// check the dial backoff
if forceDirect, _ := network.GetForceDirectDial(ctx); !forceDirect {
if s.backf.Backoff(p, addr) {
@@ -402,23 +416,20 @@ func (s *Swarm) dialNextAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr,
return nil
}
-func (s *Swarm) canDial(addr ma.Multiaddr) bool {
- t := s.TransportForDialing(addr)
- return t != nil && t.CanDial(addr)
-}
-
func (s *Swarm) nonProxyAddr(addr ma.Multiaddr) bool {
t := s.TransportForDialing(addr)
return !t.Proxy()
}
+var quicDraft29DialMatcher = mafmt.And(mafmt.IP, mafmt.Base(ma.P_UDP), mafmt.Base(ma.P_QUIC))
+
// filterKnownUndialables takes a list of multiaddrs, and removes those
// that we definitely don't want to dial: addresses configured to be blocked,
// IPv6 link-local addresses, addresses without a dial-capable transport,
// addresses that we know to be our own, and addresses with a better tranport
// available. This is an optimization to avoid wasting time on dials that we
// know are going to fail or for which we have a better alternative.
-func (s *Swarm) filterKnownUndialables(p peer.ID, addrs []ma.Multiaddr) []ma.Multiaddr {
+func (s *Swarm) filterKnownUndialables(p peer.ID, addrs []ma.Multiaddr) (goodAddrs []ma.Multiaddr, addrErrs []TransportError) {
lisAddrs, _ := s.InterfaceListenAddresses()
var ourAddrs []ma.Multiaddr
for _, addr := range lisAddrs {
@@ -431,35 +442,71 @@ func (s *Swarm) filterKnownUndialables(p peer.ID, addrs []ma.Multiaddr) []ma.Mul
})
}
- // The order of these two filters is important. If we can only dial /webtransport,
- // we don't want to filter /webtransport addresses out because the peer had a /quic-v1
- // address
+ addrErrs = make([]TransportError, 0, len(addrs))
- // filter addresses we cannot dial
- addrs = ma.FilterAddrs(addrs, s.canDial)
+ // The order of checking for transport and filtering low priority addrs is important. If we
+ // can only dial /webtransport, we don't want to filter /webtransport addresses out because
+ // the peer had a /quic-v1 address
+
+ // filter addresses with no transport
+ addrs = ma.FilterAddrs(addrs, func(a ma.Multiaddr) bool {
+ if s.TransportForDialing(a) == nil {
+ e := ErrNoTransport
+ // We used to support QUIC draft-29 for a long time.
+ // Provide a more useful error when attempting to dial a QUIC draft-29 address.
+ if quicDraft29DialMatcher.Matches(a) {
+ e = ErrQUICDraft29
+ }
+ addrErrs = append(addrErrs, TransportError{Address: a, Cause: e})
+ return false
+ }
+ return true
+ })
// filter low priority addresses among the addresses we can dial
+ // We don't return an error for these addresses
addrs = filterLowPriorityAddresses(addrs)
// remove black holed addrs
- addrs = s.bhd.FilterAddrs(addrs)
+ addrs, blackHoledAddrs := s.bhd.FilterAddrs(addrs)
+ for _, a := range blackHoledAddrs {
+ addrErrs = append(addrErrs, TransportError{Address: a, Cause: ErrDialRefusedBlackHole})
+ }
return ma.FilterAddrs(addrs,
- func(addr ma.Multiaddr) bool { return !ma.Contains(ourAddrs, addr) },
+ // Linux and BSD treat an unspecified address when dialing as a localhost address.
+ // Windows doesn't support this. We filter all such addresses out because peers
+ // listening on unspecified addresses will advertise more specific addresses.
+ // https://unix.stackexchange.com/a/419881
+ // https://superuser.com/a/1755455
+ func(addr ma.Multiaddr) bool {
+ return !manet.IsIPUnspecified(addr)
+ },
+ func(addr ma.Multiaddr) bool {
+ if ma.Contains(ourAddrs, addr) {
+ addrErrs = append(addrErrs, TransportError{Address: addr, Cause: ErrDialToSelf})
+ return false
+ }
+ return true
+ },
// TODO: Consider allowing link-local addresses
func(addr ma.Multiaddr) bool { return !manet.IsIP6LinkLocal(addr) },
func(addr ma.Multiaddr) bool {
- return s.gater == nil || s.gater.InterceptAddrDial(p, addr)
+ if s.gater != nil && !s.gater.InterceptAddrDial(p, addr) {
+ addrErrs = append(addrErrs, TransportError{Address: addr, Cause: ErrGaterDisallowedConnection})
+ return false
+ }
+ return true
},
- )
+ ), addrErrs
}
// limitedDial will start a dial to the given peer when
// it is able, respecting the various different types of rate
// limiting that occur without using extra goroutines per addr
-func (s *Swarm) limitedDial(ctx context.Context, p peer.ID, a ma.Multiaddr, resp chan dialResult) {
+func (s *Swarm) limitedDial(ctx context.Context, p peer.ID, a ma.Multiaddr, resp chan transport.DialUpdate) {
timeout := s.dialTimeout
- if lowTimeoutFilters.AddrBlocked(a) && s.dialTimeoutLocal < s.dialTimeout {
+ if manet.IsPrivateAddr(a) && s.dialTimeoutLocal < s.dialTimeout {
timeout = s.dialTimeoutLocal
}
s.limiter.AddDialJob(&dialJob{
@@ -472,7 +519,7 @@ func (s *Swarm) limitedDial(ctx context.Context, p peer.ID, a ma.Multiaddr, resp
}
// dialAddr is the actual dial for an addr, indirectly invoked through the limiter
-func (s *Swarm) dialAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr) (transport.CapableConn, error) {
+func (s *Swarm) dialAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr, updCh chan<- transport.DialUpdate) (transport.CapableConn, error) {
// Just to double check. Costs nothing.
if s.local == p {
return nil, ErrDialToSelf
@@ -490,7 +537,13 @@ func (s *Swarm) dialAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr) (tra
}
start := time.Now()
- connC, err := tpt.Dial(ctx, addr, p)
+ var connC transport.CapableConn
+ var err error
+ if du, ok := tpt.(transport.DialUpdater); ok {
+ connC, err = du.DialWithUpdates(ctx, addr, p, updCh)
+ } else {
+ connC, err = tpt.Dial(ctx, addr, p)
+ }
// We're recording any error as a failure here.
// Notably, this also applies to cancelations (i.e. if another dial attempt was faster).
@@ -499,7 +552,7 @@ func (s *Swarm) dialAddr(ctx context.Context, p peer.ID, addr ma.Multiaddr) (tra
if err != nil {
if s.metricsTracer != nil {
- s.metricsTracer.FailedDialing(addr, err)
+ s.metricsTracer.FailedDialing(addr, err, context.Cause(ctx))
}
return nil, err
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_metrics.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_metrics.go
index 28564e9e5..9cc34599d 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_metrics.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_metrics.go
@@ -128,7 +128,7 @@ type MetricsTracer interface {
OpenedConnection(network.Direction, crypto.PubKey, network.ConnectionState, ma.Multiaddr)
ClosedConnection(network.Direction, time.Duration, network.ConnectionState, ma.Multiaddr)
CompletedHandshake(time.Duration, network.ConnectionState, ma.Multiaddr)
- FailedDialing(ma.Multiaddr, error)
+ FailedDialing(ma.Multiaddr, error, error)
DialCompleted(success bool, totalDials int)
DialRankingDelay(d time.Duration)
UpdatedBlackHoleFilterState(name string, state blackHoleState, nextProbeAfter int, successFraction float64)
@@ -216,18 +216,28 @@ func (m *metricsTracer) CompletedHandshake(t time.Duration, cs network.Connectio
connHandshakeLatency.WithLabelValues(*tags...).Observe(t.Seconds())
}
-func (m *metricsTracer) FailedDialing(addr ma.Multiaddr, err error) {
+func (m *metricsTracer) FailedDialing(addr ma.Multiaddr, dialErr error, cause error) {
transport := metricshelper.GetTransport(addr)
e := "other"
- if errors.Is(err, context.Canceled) {
- e = "canceled"
- } else if errors.Is(err, context.DeadlineExceeded) {
+ // dial deadline exceeded or the the parent contexts deadline exceeded
+ if errors.Is(dialErr, context.DeadlineExceeded) || errors.Is(cause, context.DeadlineExceeded) {
e = "deadline"
+ } else if errors.Is(dialErr, context.Canceled) {
+ // dial was cancelled.
+ if errors.Is(cause, context.Canceled) {
+ // parent context was canceled
+ e = "application canceled"
+ } else if errors.Is(cause, errConcurrentDialSuccessful) {
+ e = "canceled: concurrent dial successful"
+ } else {
+ // something else
+ e = "canceled: other"
+ }
} else {
- nerr, ok := err.(net.Error)
+ nerr, ok := dialErr.(net.Error)
if ok && nerr.Timeout() {
e = "timeout"
- } else if strings.Contains(err.Error(), "connect: connection refused") {
+ } else if strings.Contains(dialErr.Error(), "connect: connection refused") {
e = "connection refused"
}
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_stream.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_stream.go
index d372bcd8e..b7846adec 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_stream.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/swarm/swarm_stream.go
@@ -22,7 +22,10 @@ type Stream struct {
conn *Conn
scope network.StreamManagementScope
- closeOnce sync.Once
+ closeMx sync.Mutex
+ isClosed bool
+ // acceptStreamGoroutineCompleted indicates whether the goroutine handling the incoming stream has exited
+ acceptStreamGoroutineCompleted bool
protocol atomic.Pointer[protocol.ID]
@@ -76,7 +79,7 @@ func (s *Stream) Write(p []byte) (int, error) {
// resources.
func (s *Stream) Close() error {
err := s.stream.Close()
- s.closeOnce.Do(s.remove)
+ s.closeAndRemoveStream()
return err
}
@@ -84,10 +87,25 @@ func (s *Stream) Close() error {
// associated resources.
func (s *Stream) Reset() error {
err := s.stream.Reset()
- s.closeOnce.Do(s.remove)
+ s.closeAndRemoveStream()
return err
}
+func (s *Stream) closeAndRemoveStream() {
+ s.closeMx.Lock()
+ defer s.closeMx.Unlock()
+ if s.isClosed {
+ return
+ }
+ s.isClosed = true
+ // We don't want to keep swarm from closing till the stream handler has exited
+ s.conn.swarm.refs.Done()
+ // Cleanup the stream from connection only after the stream handler has completed
+ if s.acceptStreamGoroutineCompleted {
+ s.conn.removeStream(s)
+ }
+}
+
// CloseWrite closes the stream for writing, flushing all data and sending an EOF.
// This function does not free resources, call Close or Reset when done with the
// stream.
@@ -101,9 +119,16 @@ func (s *Stream) CloseRead() error {
return s.stream.CloseRead()
}
-func (s *Stream) remove() {
- s.conn.removeStream(s)
- s.conn.swarm.refs.Done()
+func (s *Stream) completeAcceptStreamGoroutine() {
+ s.closeMx.Lock()
+ defer s.closeMx.Unlock()
+ if s.acceptStreamGoroutineCompleted {
+ return
+ }
+ s.acceptStreamGoroutineCompleted = true
+ if s.isClosed {
+ s.conn.removeStream(s)
+ }
}
// Protocol returns the protocol negotiated on this stream (if set).
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/net/upgrader/upgrader.go b/vendor/github.com/libp2p/go-libp2p/p2p/net/upgrader/upgrader.go
index d18c16ea0..3a6f8b9f5 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/net/upgrader/upgrader.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/net/upgrader/upgrader.go
@@ -152,7 +152,8 @@ func (u *upgrader) upgrade(ctx context.Context, t transport.Transport, maconn ma
return nil, ipnet.ErrNotInPrivateNetwork
}
- sconn, security, server, err := u.setupSecurity(ctx, conn, p, dir)
+ isServer := dir == network.DirInbound
+ sconn, security, err := u.setupSecurity(ctx, conn, p, isServer)
if err != nil {
conn.Close()
return nil, fmt.Errorf("failed to negotiate security protocol: %w", err)
@@ -179,7 +180,7 @@ func (u *upgrader) upgrade(ctx context.Context, t transport.Transport, maconn ma
}
}
- muxer, smconn, err := u.setupMuxer(ctx, sconn, server, connScope.PeerScope())
+ muxer, smconn, err := u.setupMuxer(ctx, sconn, isServer, connScope.PeerScope())
if err != nil {
sconn.Close()
return nil, fmt.Errorf("failed to negotiate stream multiplexer: %w", err)
@@ -199,20 +200,17 @@ func (u *upgrader) upgrade(ctx context.Context, t transport.Transport, maconn ma
return tc, nil
}
-func (u *upgrader) setupSecurity(ctx context.Context, conn net.Conn, p peer.ID, dir network.Direction) (sec.SecureConn, protocol.ID, bool, error) {
- isServer := dir == network.DirInbound
- var st sec.SecureTransport
- var err error
- st, isServer, err = u.negotiateSecurity(ctx, conn, isServer)
+func (u *upgrader) setupSecurity(ctx context.Context, conn net.Conn, p peer.ID, isServer bool) (sec.SecureConn, protocol.ID, error) {
+ st, err := u.negotiateSecurity(ctx, conn, isServer)
if err != nil {
- return nil, "", false, err
+ return nil, "", err
}
if isServer {
sconn, err := st.SecureInbound(ctx, conn, p)
- return sconn, st.ID(), true, err
+ return sconn, st.ID(), err
}
sconn, err := st.SecureOutbound(ctx, conn, p)
- return sconn, st.ID(), false, err
+ return sconn, st.ID(), err
}
func (u *upgrader) negotiateMuxer(nc net.Conn, isServer bool) (*StreamMuxer, error) {
@@ -308,41 +306,38 @@ func (u *upgrader) getSecurityByID(id protocol.ID) sec.SecureTransport {
return nil
}
-func (u *upgrader) negotiateSecurity(ctx context.Context, insecure net.Conn, server bool) (sec.SecureTransport, bool, error) {
+func (u *upgrader) negotiateSecurity(ctx context.Context, insecure net.Conn, server bool) (sec.SecureTransport, error) {
type result struct {
- proto protocol.ID
- iamserver bool
- err error
+ proto protocol.ID
+ err error
}
done := make(chan result, 1)
go func() {
if server {
var r result
- r.iamserver = true
r.proto, _, r.err = u.securityMuxer.Negotiate(insecure)
done <- r
return
}
var r result
- r.proto, r.iamserver, r.err = mss.SelectWithSimopenOrFail(u.securityIDs, insecure)
+ r.proto, r.err = mss.SelectOneOf(u.securityIDs, insecure)
done <- r
}()
select {
case r := <-done:
if r.err != nil {
- return nil, false, r.err
+ return nil, r.err
}
if s := u.getSecurityByID(r.proto); s != nil {
- return s, r.iamserver, nil
+ return s, nil
}
- return nil, false, fmt.Errorf("selected unknown security transport: %s", r.proto)
+ return nil, fmt.Errorf("selected unknown security transport: %s", r.proto)
case <-ctx.Done():
- // We *must* do this. We have outstanding work on the connection
- // and it's no longer safe to use.
+ // We *must* do this. We have outstanding work on the connection, and it's no longer safe to use.
insecure.Close()
<-done // wait to stop using the connection.
- return nil, false, ctx.Err()
+ return nil, ctx.Err()
}
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/circuitv2/relay/constraints.go b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/circuitv2/relay/constraints.go
index 24353086f..4b9b54cd8 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/circuitv2/relay/constraints.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/circuitv2/relay/constraints.go
@@ -74,7 +74,10 @@ func (c *constraints) AddReservation(p peer.ID, a ma.Multiaddr) error {
var asnReservations []time.Time
var asn string
- if ip.To4() == nil {
+ // Only public addresses have an ASN. Skip checking ASN for private addresses as
+ // initialising the ASN store is a costly operation. Skipping this check reduces a lot of
+ // flakiness in tests
+ if ip.To4() == nil && manet.IsPublicAddr(a) {
asn, _ = asnutil.Store.AsnForIPv6(ip)
if asn != "" {
asnReservations = c.asns[asn]
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/id.go b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/id.go
index 69506e9b3..6c07dbdc8 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/id.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/id.go
@@ -556,7 +556,7 @@ func readAllIDMessages(r pbio.Reader, finalMsg proto.Message) error {
func (ids *idService) updateSnapshot() (updated bool) {
addrs := ids.Host.Addrs()
- slices.SortFunc(addrs, func(a, b ma.Multiaddr) bool { return bytes.Compare(a.Bytes(), b.Bytes()) == -1 })
+ slices.SortFunc(addrs, func(a, b ma.Multiaddr) int { return bytes.Compare(a.Bytes(), b.Bytes()) })
protos := ids.Host.Mux().Protocols()
slices.Sort(protos)
snapshot := identifySnapshot{
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/obsaddr.go b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/obsaddr.go
index 0412541f5..70a7eccd4 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/obsaddr.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/protocol/identify/obsaddr.go
@@ -212,13 +212,16 @@ func (oas *ObservedAddrManager) filter(observedAddrs []*observedAddr) []ma.Multi
for pat := range pmap {
s := pmap[pat]
- // We prefer inbound connection observations over outbound.
- // For ties, we prefer the ones with more votes.
- slices.SortFunc(s, func(first, second *observedAddr) bool {
+ slices.SortFunc(s, func(first, second *observedAddr) int {
+ // We prefer inbound connection observations over outbound.
if first.numInbound > second.numInbound {
- return true
+ return -1
}
- return len(first.seenBy) > len(second.seenBy)
+ // For ties, we prefer the ones with more votes.
+ if first.numInbound == second.numInbound && len(first.seenBy) > len(second.seenBy) {
+ return -1
+ }
+ return 1
})
for i := 0; i < maxObservedAddrsPerIPAndTransport && i < len(s); i++ {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/security/noise/handshake.go b/vendor/github.com/libp2p/go-libp2p/p2p/security/noise/handshake.go
index e1a18e9b6..a9493bf8d 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/security/noise/handshake.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/security/noise/handshake.go
@@ -12,11 +12,12 @@ import (
"github.com/libp2p/go-libp2p/core/crypto"
"github.com/libp2p/go-libp2p/core/peer"
+ "github.com/libp2p/go-libp2p/core/sec"
+ "github.com/libp2p/go-libp2p/internal/sha256"
"github.com/libp2p/go-libp2p/p2p/security/noise/pb"
"github.com/flynn/noise"
pool "github.com/libp2p/go-buffer-pool"
- "github.com/minio/sha256-simd"
"google.golang.org/protobuf/proto"
)
@@ -276,7 +277,7 @@ func (s *secureSession) handleRemoteHandshakePayload(payload []byte, remoteStati
// check the peer ID if enabled
if s.checkPeerID && s.remoteID != id {
- return nil, fmt.Errorf("peer id mismatch: expected %s, but remote key matches %s", s.remoteID.Pretty(), id.Pretty())
+ return nil, sec.ErrPeerIDMismatch{Expected: s.remoteID, Actual: id}
}
// verify payload is signed by asserted remote libp2p key.
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/security/tls/crypto.go b/vendor/github.com/libp2p/go-libp2p/p2p/security/tls/crypto.go
index b8f23f39e..385de5a16 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/security/tls/crypto.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/security/tls/crypto.go
@@ -18,6 +18,7 @@ import (
ic "github.com/libp2p/go-libp2p/core/crypto"
"github.com/libp2p/go-libp2p/core/peer"
+ "github.com/libp2p/go-libp2p/core/sec"
)
const certValidityPeriod = 100 * 365 * 24 * time.Hour // ~100 years
@@ -129,7 +130,7 @@ func (i *Identity) ConfigForPeer(remote peer.ID) (*tls.Config, <-chan ic.PubKey)
if err != nil {
peerID = peer.ID(fmt.Sprintf("(not determined: %s)", err.Error()))
}
- return fmt.Errorf("peer IDs don't match: expected %s, got %s", remote, peerID)
+ return sec.ErrPeerIDMismatch{Expected: remote, Actual: peerID}
}
keyCh <- pubKey
return nil
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/listener.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/listener.go
index 73bb5026b..d49b68649 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/listener.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/listener.go
@@ -29,9 +29,6 @@ type listener struct {
func newListener(ln quicreuse.Listener, t *transport, localPeer peer.ID, key ic.PrivKey, rcmgr network.ResourceManager) (listener, error) {
localMultiaddrs := make(map[quic.VersionNumber]ma.Multiaddr)
for _, addr := range ln.Multiaddrs() {
- if _, err := addr.ValueForProtocol(ma.P_QUIC); err == nil {
- localMultiaddrs[quic.VersionDraft29] = addr
- }
if _, err := addr.ValueForProtocol(ma.P_QUIC_V1); err == nil {
localMultiaddrs[quic.Version1] = addr
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/transport.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/transport.go
index aef3f4c9d..18d198bbe 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/transport.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quic/transport.go
@@ -268,8 +268,8 @@ loop:
}
}
-// Don't use mafmt.QUIC as we don't want to dial DNS addresses. Just /ip{4,6}/udp/quic
-var dialMatcher = mafmt.And(mafmt.IP, mafmt.Base(ma.P_UDP), mafmt.Or(mafmt.Base(ma.P_QUIC), mafmt.Base(ma.P_QUIC_V1)))
+// Don't use mafmt.QUIC as we don't want to dial DNS addresses. Just /ip{4,6}/udp/quic-v1
+var dialMatcher = mafmt.And(mafmt.IP, mafmt.Base(ma.P_UDP), mafmt.Base(ma.P_QUIC_V1))
// CanDial determines if we can dial to an address
func (t *transport) CanDial(addr ma.Multiaddr) bool {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/config.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/config.go
index 76a2c8cc4..45b1d4b8c 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/config.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/config.go
@@ -17,9 +17,7 @@ var quicConfig = &quic.Config{
return false
},
KeepAlivePeriod: 15 * time.Second,
- Versions: []quic.VersionNumber{quic.VersionDraft29, quic.Version1},
+ Versions: []quic.VersionNumber{quic.Version1},
// We don't use datagrams (yet), but this is necessary for WebTransport
EnableDatagrams: true,
- // The multiaddress encodes the QUIC version, thus there's no need to send Version Negotiation packets.
- DisableVersionNegotiationPackets: true,
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/connmgr.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/connmgr.go
index c12b86671..0add5ddfc 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/connmgr.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/connmgr.go
@@ -16,7 +16,6 @@ import (
type ConnManager struct {
reuseUDP4 *reuse
reuseUDP6 *reuse
- enableDraft29 bool
enableReuseport bool
enableMetrics bool
@@ -26,8 +25,8 @@ type ConnManager struct {
quicListenersMu sync.Mutex
quicListeners map[string]quicListenerEntry
- srk quic.StatelessResetKey
- mt *metricsTracer
+ srk quic.StatelessResetKey
+ tokenKey quic.TokenGeneratorKey
}
type quicListenerEntry struct {
@@ -35,12 +34,12 @@ type quicListenerEntry struct {
ln *quicListener
}
-func NewConnManager(statelessResetKey quic.StatelessResetKey, opts ...Option) (*ConnManager, error) {
+func NewConnManager(statelessResetKey quic.StatelessResetKey, tokenKey quic.TokenGeneratorKey, opts ...Option) (*ConnManager, error) {
cm := &ConnManager{
enableReuseport: true,
- enableDraft29: true,
quicListeners: make(map[string]quicListenerEntry),
srk: statelessResetKey,
+ tokenKey: tokenKey,
}
for _, o := range opts {
if err := o(cm); err != nil {
@@ -50,29 +49,20 @@ func NewConnManager(statelessResetKey quic.StatelessResetKey, opts ...Option) (*
quicConf := quicConfig.Clone()
- if cm.enableMetrics {
- cm.mt = newMetricsTracer()
- }
- quicConf.Tracer = func(ctx context.Context, p quiclogging.Perspective, ci quic.ConnectionID) quiclogging.ConnectionTracer {
- tracers := make([]quiclogging.ConnectionTracer, 0, 2)
+ quicConf.Tracer = func(ctx context.Context, p quiclogging.Perspective, ci quic.ConnectionID) *quiclogging.ConnectionTracer {
+ var tracer *quiclogging.ConnectionTracer
if qlogTracerDir != "" {
- tracers = append(tracers, qloggerForDir(qlogTracerDir, p, ci))
+ tracer = qloggerForDir(qlogTracerDir, p, ci)
}
- if cm.mt != nil {
- tracers = append(tracers, cm.mt.TracerForConnection(ctx, p, ci))
- }
- return quiclogging.NewMultiplexedConnectionTracer(tracers...)
+ return tracer
}
serverConfig := quicConf.Clone()
- if !cm.enableDraft29 {
- serverConfig.Versions = []quic.VersionNumber{quic.Version1}
- }
cm.clientConfig = quicConf
cm.serverConfig = serverConfig
if cm.enableReuseport {
- cm.reuseUDP4 = newReuse(&statelessResetKey, cm.mt)
- cm.reuseUDP6 = newReuse(&statelessResetKey, cm.mt)
+ cm.reuseUDP4 = newReuse(&statelessResetKey, &tokenKey)
+ cm.reuseUDP6 = newReuse(&statelessResetKey, &tokenKey)
}
return cm, nil
}
@@ -89,12 +79,6 @@ func (c *ConnManager) getReuse(network string) (*reuse, error) {
}
func (c *ConnManager) ListenQUIC(addr ma.Multiaddr, tlsConf *tls.Config, allowWindowIncrease func(conn quic.Connection, delta uint64) bool) (Listener, error) {
- if !c.enableDraft29 {
- if _, err := addr.ValueForProtocol(ma.P_QUIC); err == nil {
- return nil, errors.New("can't listen on `/quic` multiaddr (QUIC draft 29 version) when draft 29 support is disabled")
- }
- }
-
netw, host, err := manet.DialArgs(addr)
if err != nil {
return nil, err
@@ -114,7 +98,7 @@ func (c *ConnManager) ListenQUIC(addr ma.Multiaddr, tlsConf *tls.Config, allowWi
if err != nil {
return nil, err
}
- ln, err := newQuicListener(tr, c.serverConfig, c.enableDraft29)
+ ln, err := newQuicListener(tr, c.serverConfig)
if err != nil {
return nil, err
}
@@ -156,15 +140,18 @@ func (c *ConnManager) transportForListen(network string, laddr *net.UDPAddr) (re
return reuse.TransportForListen(network, laddr)
}
- conn, err := listenAndOptimize(network, laddr)
+ conn, err := net.ListenUDP(network, laddr)
if err != nil {
return nil, err
}
- tr := &singleOwnerTransport{Transport: quic.Transport{Conn: conn, StatelessResetKey: &c.srk}, packetConn: conn}
- if c.mt != nil {
- tr.Transport.Tracer = c.mt
- }
- return tr, nil
+ return &singleOwnerTransport{
+ packetConn: conn,
+ Transport: quic.Transport{
+ Conn: conn,
+ StatelessResetKey: &c.srk,
+ TokenGeneratorKey: &c.tokenKey,
+ },
+ }, nil
}
func (c *ConnManager) DialQUIC(ctx context.Context, raddr ma.Multiaddr, tlsConf *tls.Config, allowWindowIncrease func(conn quic.Connection, delta uint64) bool) (quic.Connection, error) {
@@ -183,8 +170,6 @@ func (c *ConnManager) DialQUIC(ctx context.Context, raddr ma.Multiaddr, tlsConf
if v == quic.Version1 {
// The endpoint has explicit support for QUIC v1, so we'll only use that version.
quicConf.Versions = []quic.VersionNumber{quic.Version1}
- } else if v == quic.VersionDraft29 {
- quicConf.Versions = []quic.VersionNumber{quic.VersionDraft29}
} else {
return nil, errors.New("unknown QUIC version")
}
@@ -217,22 +202,14 @@ func (c *ConnManager) TransportForDial(network string, raddr *net.UDPAddr) (refC
case "udp6":
laddr = &net.UDPAddr{IP: net.IPv6zero, Port: 0}
}
- conn, err := listenAndOptimize(network, laddr)
+ conn, err := net.ListenUDP(network, laddr)
if err != nil {
return nil, err
}
- tr := &singleOwnerTransport{Transport: quic.Transport{Conn: conn, StatelessResetKey: &c.srk}, packetConn: conn}
- if c.mt != nil {
- tr.Transport.Tracer = c.mt
- }
-
- return tr, nil
+ return &singleOwnerTransport{Transport: quic.Transport{Conn: conn, StatelessResetKey: &c.srk}, packetConn: conn}, nil
}
func (c *ConnManager) Protocols() []int {
- if c.enableDraft29 {
- return []int{ma.P_QUIC, ma.P_QUIC_V1}
- }
return []int{ma.P_QUIC_V1}
}
@@ -245,12 +222,3 @@ func (c *ConnManager) Close() error {
}
return c.reuseUDP4.Close()
}
-
-// listenAndOptimize same as net.ListenUDP, but also calls quic.OptimizeConn
-func listenAndOptimize(network string, laddr *net.UDPAddr) (net.PacketConn, error) {
- conn, err := net.ListenUDP(network, laddr)
- if err != nil {
- return nil, err
- }
- return quic.OptimizeConn(conn)
-}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/listener.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/listener.go
index 50b793451..4ee20042d 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/listener.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/listener.go
@@ -38,20 +38,13 @@ type quicListener struct {
protocols map[string]protoConf
}
-func newQuicListener(tr refCountedQuicTransport, quicConfig *quic.Config, enableDraft29 bool) (*quicListener, error) {
+func newQuicListener(tr refCountedQuicTransport, quicConfig *quic.Config) (*quicListener, error) {
localMultiaddrs := make([]ma.Multiaddr, 0, 2)
a, err := ToQuicMultiaddr(tr.LocalAddr(), quic.Version1)
if err != nil {
return nil, err
}
localMultiaddrs = append(localMultiaddrs, a)
- if enableDraft29 {
- a, err := ToQuicMultiaddr(tr.LocalAddr(), quic.VersionDraft29)
- if err != nil {
- return nil, err
- }
- localMultiaddrs = append(localMultiaddrs, a)
- }
cl := &quicListener{
protocols: map[string]protoConf{},
running: make(chan struct{}),
@@ -59,6 +52,7 @@ func newQuicListener(tr refCountedQuicTransport, quicConfig *quic.Config, enable
addrs: localMultiaddrs,
}
tlsConf := &tls.Config{
+ SessionTicketsDisabled: true, // This is set for the config for client, but we set it here as well: https://github.com/quic-go/quic-go/issues/4029
GetConfigForClient: func(info *tls.ClientHelloInfo) (*tls.Config, error) {
cl.protocolsMu.Lock()
defer cl.protocolsMu.Unlock()
@@ -89,7 +83,7 @@ func (l *quicListener) allowWindowIncrease(conn quic.Connection, delta uint64) b
l.protocolsMu.Lock()
defer l.protocolsMu.Unlock()
- conf, ok := l.protocols[conn.ConnectionState().TLS.ConnectionState.NegotiatedProtocol]
+ conf, ok := l.protocols[conn.ConnectionState().TLS.NegotiatedProtocol]
if !ok {
return false
}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/options.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/options.go
index a700a0544..c32506920 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/options.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/options.go
@@ -9,16 +9,6 @@ func DisableReuseport() Option {
}
}
-// DisableDraft29 disables support for QUIC draft-29.
-// This option should be set, unless support for this legacy QUIC version is needed for backwards compatibility.
-// Support for QUIC draft-29 is already deprecated and will be removed in the future, see https://github.com/libp2p/go-libp2p/issues/1841.
-func DisableDraft29() Option {
- return func(m *ConnManager) error {
- m.enableDraft29 = false
- return nil
- }
-}
-
// EnableMetrics enables Prometheus metrics collection.
func EnableMetrics() Option {
return func(m *ConnManager) error {
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/quic_multiaddr.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/quic_multiaddr.go
index 12eb7d8ab..3da4721b5 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/quic_multiaddr.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/quic_multiaddr.go
@@ -10,8 +10,7 @@ import (
)
var (
- quicV1MA = ma.StringCast("/quic-v1")
- quicDraft29MA = ma.StringCast("/quic")
+ quicV1MA = ma.StringCast("/quic-v1")
)
func ToQuicMultiaddr(na net.Addr, version quic.VersionNumber) (ma.Multiaddr, error) {
@@ -20,8 +19,6 @@ func ToQuicMultiaddr(na net.Addr, version quic.VersionNumber) (ma.Multiaddr, err
return nil, err
}
switch version {
- case quic.VersionDraft29:
- return udpMA.Encapsulate(quicDraft29MA), nil
case quic.Version1:
return udpMA.Encapsulate(quicV1MA), nil
default:
@@ -34,9 +31,6 @@ func FromQuicMultiaddr(addr ma.Multiaddr) (*net.UDPAddr, quic.VersionNumber, err
var partsBeforeQUIC []ma.Multiaddr
ma.ForEach(addr, func(c ma.Component) bool {
switch c.Protocol().Code {
- case ma.P_QUIC:
- version = quic.VersionDraft29
- return false
case ma.P_QUIC_V1:
version = quic.Version1
return false
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/reuse.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/reuse.go
index 1584b2925..dc2b33b85 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/reuse.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/reuse.go
@@ -51,8 +51,7 @@ func (c *singleOwnerTransport) Close() error {
}
func (c *singleOwnerTransport) WriteTo(b []byte, addr net.Addr) (int, error) {
- // Safe because we called quic.OptimizeConn ourselves.
- return c.packetConn.WriteTo(b, addr)
+ return c.Transport.WriteTo(b, addr)
}
// Constant. Defined as variables to simplify testing.
@@ -86,8 +85,7 @@ func (c *refcountedTransport) Close() error {
}
func (c *refcountedTransport) WriteTo(b []byte, addr net.Addr) (int, error) {
- // Safe because we called quic.OptimizeConn ourselves.
- return c.packetConn.WriteTo(b, addr)
+ return c.Transport.WriteTo(b, addr)
}
func (c *refcountedTransport) LocalAddr() net.Addr {
@@ -125,10 +123,10 @@ type reuse struct {
globalDialers map[int]*refcountedTransport
statelessResetKey *quic.StatelessResetKey
- metricsTracer *metricsTracer
+ tokenGeneratorKey *quic.TokenGeneratorKey
}
-func newReuse(srk *quic.StatelessResetKey, mt *metricsTracer) *reuse {
+func newReuse(srk *quic.StatelessResetKey, tokenKey *quic.TokenGeneratorKey) *reuse {
r := &reuse{
unicast: make(map[string]map[int]*refcountedTransport),
globalListeners: make(map[int]*refcountedTransport),
@@ -136,7 +134,7 @@ func newReuse(srk *quic.StatelessResetKey, mt *metricsTracer) *reuse {
closeChan: make(chan struct{}),
gcStopChan: make(chan struct{}),
statelessResetKey: srk,
- metricsTracer: mt,
+ tokenGeneratorKey: tokenKey,
}
go r.gc()
return r
@@ -265,17 +263,15 @@ func (r *reuse) transportForDialLocked(network string, source *net.IP) (*refcoun
case "udp6":
addr = &net.UDPAddr{IP: net.IPv6zero, Port: 0}
}
- conn, err := listenAndOptimize(network, addr)
+ conn, err := net.ListenUDP(network, addr)
if err != nil {
return nil, err
}
tr := &refcountedTransport{Transport: quic.Transport{
Conn: conn,
StatelessResetKey: r.statelessResetKey,
+ TokenGeneratorKey: r.tokenGeneratorKey,
}, packetConn: conn}
- if r.metricsTracer != nil {
- tr.Transport.Tracer = r.metricsTracer
- }
r.globalDialers[conn.LocalAddr().(*net.UDPAddr).Port] = tr
return tr, nil
}
@@ -314,19 +310,18 @@ func (r *reuse) TransportForListen(network string, laddr *net.UDPAddr) (*refcoun
}
}
- conn, err := listenAndOptimize(network, laddr)
+ conn, err := net.ListenUDP(network, laddr)
if err != nil {
return nil, err
}
localAddr := conn.LocalAddr().(*net.UDPAddr)
- tr := &refcountedTransport{Transport: quic.Transport{
- Conn: conn,
- StatelessResetKey: r.statelessResetKey,
- }, packetConn: conn}
- if r.metricsTracer != nil {
- tr.Transport.Tracer = r.metricsTracer
+ tr := &refcountedTransport{
+ Transport: quic.Transport{
+ Conn: conn,
+ StatelessResetKey: r.statelessResetKey,
+ },
+ packetConn: conn,
}
-
tr.IncreaseCount()
// Deal with listen on a global address
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer.go
index 1386a5c3d..16c7dce4f 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer.go
@@ -24,7 +24,7 @@ func init() {
qlogTracerDir = os.Getenv("QLOGDIR")
}
-func qloggerForDir(qlogDir string, p logging.Perspective, ci quic.ConnectionID) logging.ConnectionTracer {
+func qloggerForDir(qlogDir string, p logging.Perspective, ci quic.ConnectionID) *logging.ConnectionTracer {
// create the QLOGDIR, if it doesn't exist
if err := os.MkdirAll(qlogDir, 0777); err != nil {
log.Errorf("creating the QLOGDIR failed: %s", err)
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer_metrics.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer_metrics.go
deleted file mode 100644
index 03e73fd25..000000000
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/quicreuse/tracer_metrics.go
+++ /dev/null
@@ -1,372 +0,0 @@
-package quicreuse
-
-import (
- "context"
- "errors"
- "fmt"
- "net"
- "sync"
- "time"
-
- "github.com/prometheus/client_golang/prometheus"
- "github.com/quic-go/quic-go"
- "github.com/quic-go/quic-go/logging"
-)
-
-var (
- bytesTransferred *prometheus.CounterVec
- newConns *prometheus.CounterVec
- closedConns *prometheus.CounterVec
- sentPackets *prometheus.CounterVec
- rcvdPackets *prometheus.CounterVec
- bufferedPackets *prometheus.CounterVec
- droppedPackets *prometheus.CounterVec
- lostPackets *prometheus.CounterVec
- connErrors *prometheus.CounterVec
-)
-
-type aggregatingCollector struct {
- mutex sync.Mutex
-
- conns map[string] /* conn ID */ *metricsConnTracer
- rtts prometheus.Histogram
- connDurations prometheus.Histogram
-}
-
-func newAggregatingCollector() *aggregatingCollector {
- return &aggregatingCollector{
- conns: make(map[string]*metricsConnTracer),
- rtts: prometheus.NewHistogram(prometheus.HistogramOpts{
- Name: "quic_smoothed_rtt",
- Help: "Smoothed RTT",
- Buckets: prometheus.ExponentialBuckets(0.001, 1.25, 40), // 1ms to ~6000ms
- }),
- connDurations: prometheus.NewHistogram(prometheus.HistogramOpts{
- Name: "quic_connection_duration",
- Help: "Connection Duration",
- Buckets: prometheus.ExponentialBuckets(1, 1.5, 40), // 1s to ~12 weeks
- }),
- }
-}
-
-var _ prometheus.Collector = &aggregatingCollector{}
-
-func (c *aggregatingCollector) Describe(descs chan<- *prometheus.Desc) {
- descs <- c.rtts.Desc()
- descs <- c.connDurations.Desc()
-}
-
-func (c *aggregatingCollector) Collect(metrics chan<- prometheus.Metric) {
- now := time.Now()
- c.mutex.Lock()
- for _, conn := range c.conns {
- if rtt, valid := conn.getSmoothedRTT(); valid {
- c.rtts.Observe(rtt.Seconds())
- }
- c.connDurations.Observe(now.Sub(conn.startTime).Seconds())
- }
- c.mutex.Unlock()
- metrics <- c.rtts
- metrics <- c.connDurations
-}
-
-func (c *aggregatingCollector) AddConn(id string, t *metricsConnTracer) {
- c.mutex.Lock()
- c.conns[id] = t
- c.mutex.Unlock()
-}
-
-func (c *aggregatingCollector) RemoveConn(id string) {
- c.mutex.Lock()
- delete(c.conns, id)
- c.mutex.Unlock()
-}
-
-var collector *aggregatingCollector
-
-var initMetricsOnce sync.Once
-
-func initMetrics() {
- const (
- direction = "direction"
- encLevel = "encryption_level"
- )
-
- closedConns = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_connections_closed_total",
- Help: "closed QUIC connection",
- },
- []string{direction},
- )
- prometheus.MustRegister(closedConns)
- newConns = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_connections_new_total",
- Help: "new QUIC connection",
- },
- []string{direction, "handshake_successful"},
- )
- prometheus.MustRegister(newConns)
- bytesTransferred = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_transferred_bytes",
- Help: "QUIC bytes transferred",
- },
- []string{direction}, // TODO: this is confusing. Other times, we use direction for the perspective
- )
- prometheus.MustRegister(bytesTransferred)
- sentPackets = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_packets_sent_total",
- Help: "QUIC packets sent",
- },
- []string{encLevel},
- )
- prometheus.MustRegister(sentPackets)
- rcvdPackets = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_packets_rcvd_total",
- Help: "QUIC packets received",
- },
- []string{encLevel},
- )
- prometheus.MustRegister(rcvdPackets)
- bufferedPackets = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_packets_buffered_total",
- Help: "Buffered packets",
- },
- []string{"packet_type"},
- )
- prometheus.MustRegister(bufferedPackets)
- droppedPackets = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_packets_dropped_total",
- Help: "Dropped packets",
- },
- []string{"packet_type", "reason"},
- )
- prometheus.MustRegister(droppedPackets)
- connErrors = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_connection_errors_total",
- Help: "QUIC connection errors",
- },
- []string{"side", "error_code"},
- )
- prometheus.MustRegister(connErrors)
- lostPackets = prometheus.NewCounterVec(
- prometheus.CounterOpts{
- Name: "quic_packets_lost_total",
- Help: "QUIC lost received",
- },
- []string{encLevel, "reason"},
- )
- prometheus.MustRegister(lostPackets)
- collector = newAggregatingCollector()
- prometheus.MustRegister(collector)
-}
-
-type metricsTracer struct {
- logging.NullTracer
-}
-
-var _ logging.Tracer = &metricsTracer{}
-
-func newMetricsTracer() *metricsTracer {
- initMetricsOnce.Do(func() { initMetrics() })
- return &metricsTracer{}
-}
-
-func (m *metricsTracer) TracerForConnection(_ context.Context, p logging.Perspective, connID logging.ConnectionID) logging.ConnectionTracer {
- return &metricsConnTracer{perspective: p, connID: connID}
-}
-
-func (m *metricsTracer) SentPacket(_ net.Addr, _ *logging.Header, size logging.ByteCount, _ []logging.Frame) {
- bytesTransferred.WithLabelValues("sent").Add(float64(size))
-}
-
-type metricsConnTracer struct {
- logging.NullConnectionTracer
-
- perspective logging.Perspective
- startTime time.Time
- connID logging.ConnectionID
- handshakeComplete bool
-
- mutex sync.Mutex
- numRTTMeasurements int
- rtt time.Duration
-}
-
-var _ logging.ConnectionTracer = &metricsConnTracer{}
-
-func (m *metricsConnTracer) getDirection() string {
- if m.perspective == logging.PerspectiveClient {
- return "outgoing"
- }
- return "incoming"
-}
-
-func (m *metricsConnTracer) getEncLevel(packetType logging.PacketType) string {
- switch packetType {
- case logging.PacketType0RTT:
- return "0-RTT"
- case logging.PacketTypeInitial:
- return "Initial"
- case logging.PacketTypeHandshake:
- return "Handshake"
- case logging.PacketTypeRetry:
- return "Retry"
- case logging.PacketType1RTT:
- return "1-RTT"
- default:
- return "unknown"
- }
-}
-
-func (m *metricsConnTracer) StartedConnection(net.Addr, net.Addr, logging.ConnectionID, logging.ConnectionID) {
- m.startTime = time.Now()
- collector.AddConn(m.connID.String(), m)
-}
-
-func (m *metricsConnTracer) ClosedConnection(e error) {
- var (
- applicationErr *quic.ApplicationError
- transportErr *quic.TransportError
- statelessResetErr *quic.StatelessResetError
- vnErr *quic.VersionNegotiationError
- idleTimeoutErr *quic.IdleTimeoutError
- handshakeTimeoutErr *quic.HandshakeTimeoutError
- remote bool
- desc string
- )
-
- switch {
- case errors.As(e, &applicationErr):
- return
- case errors.As(e, &transportErr):
- remote = transportErr.Remote
- desc = transportErr.ErrorCode.String()
- case errors.As(e, &statelessResetErr):
- remote = true
- desc = "stateless_reset"
- case errors.As(e, &vnErr):
- desc = "version_negotiation"
- case errors.As(e, &idleTimeoutErr):
- desc = "idle_timeout"
- case errors.As(e, &handshakeTimeoutErr):
- desc = "handshake_timeout"
- default:
- desc = fmt.Sprintf("unknown error: %v", e)
- }
-
- side := "local"
- if remote {
- side = "remote"
- }
- connErrors.WithLabelValues(side, desc).Inc()
-}
-func (m *metricsConnTracer) SentPacket(hdr *logging.ExtendedHeader, size logging.ByteCount, _ *logging.AckFrame, _ []logging.Frame) {
- bytesTransferred.WithLabelValues("sent").Add(float64(size))
- sentPackets.WithLabelValues(m.getEncLevel(logging.PacketTypeFromHeader(&hdr.Header))).Inc()
-}
-
-func (m *metricsConnTracer) ReceivedVersionNegotiationPacket(dst, src logging.ArbitraryLenConnectionID, v []logging.VersionNumber) {
- bytesTransferred.WithLabelValues("rcvd").Add(1 /* header form byte */ + 4 /* version number */ + 2 /* src and dest conn id length fields */ + float64(dst.Len()+src.Len()) + float64(4*len(v)))
- rcvdPackets.WithLabelValues("Version Negotiation").Inc()
-}
-
-func (m *metricsConnTracer) ReceivedRetry(*logging.Header) {
- rcvdPackets.WithLabelValues("Retry").Inc()
-}
-
-func (m *metricsConnTracer) ReceivedPacket(hdr *logging.ExtendedHeader, size logging.ByteCount, _ []logging.Frame) {
- bytesTransferred.WithLabelValues("rcvd").Add(float64(size))
- rcvdPackets.WithLabelValues(m.getEncLevel(logging.PacketTypeFromHeader(&hdr.Header))).Inc()
-}
-
-func (m *metricsConnTracer) BufferedPacket(packetType logging.PacketType, _ logging.ByteCount) {
- bufferedPackets.WithLabelValues(m.getEncLevel(packetType)).Inc()
-}
-
-func (m *metricsConnTracer) DroppedPacket(packetType logging.PacketType, size logging.ByteCount, r logging.PacketDropReason) {
- bytesTransferred.WithLabelValues("rcvd").Add(float64(size))
- var reason string
- switch r {
- case logging.PacketDropKeyUnavailable:
- reason = "key_unavailable"
- case logging.PacketDropUnknownConnectionID:
- reason = "unknown_connection_id"
- case logging.PacketDropHeaderParseError:
- reason = "header_parse_error"
- case logging.PacketDropPayloadDecryptError:
- reason = "payload_decrypt_error"
- case logging.PacketDropProtocolViolation:
- reason = "protocol_violation"
- case logging.PacketDropDOSPrevention:
- reason = "dos_prevention"
- case logging.PacketDropUnsupportedVersion:
- reason = "unsupported_version"
- case logging.PacketDropUnexpectedPacket:
- reason = "unexpected_packet"
- case logging.PacketDropUnexpectedSourceConnectionID:
- reason = "unexpected_source_connection_id"
- case logging.PacketDropUnexpectedVersion:
- reason = "unexpected_version"
- case logging.PacketDropDuplicate:
- reason = "duplicate"
- default:
- reason = "unknown"
- }
- droppedPackets.WithLabelValues(m.getEncLevel(packetType), reason).Inc()
-}
-
-func (m *metricsConnTracer) UpdatedMetrics(rttStats *logging.RTTStats, cwnd, bytesInFlight logging.ByteCount, packetsInFlight int) {
- m.mutex.Lock()
- m.rtt = rttStats.SmoothedRTT()
- m.numRTTMeasurements++
- m.mutex.Unlock()
-}
-
-func (m *metricsConnTracer) LostPacket(level logging.EncryptionLevel, _ logging.PacketNumber, r logging.PacketLossReason) {
- var reason string
- switch r {
- case logging.PacketLossReorderingThreshold:
- reason = "reordering_threshold"
- case logging.PacketLossTimeThreshold:
- reason = "time_threshold"
- default:
- reason = "unknown"
- }
- lostPackets.WithLabelValues(level.String(), reason).Inc()
-}
-
-func (m *metricsConnTracer) DroppedEncryptionLevel(level logging.EncryptionLevel) {
- if level == logging.EncryptionHandshake {
- m.handleHandshakeComplete()
- }
-}
-
-func (m *metricsConnTracer) Close() {
- if m.handshakeComplete {
- closedConns.WithLabelValues(m.getDirection()).Inc()
- } else {
- newConns.WithLabelValues(m.getDirection(), "false").Inc()
- }
- collector.RemoveConn(m.connID.String())
-}
-
-func (m *metricsConnTracer) handleHandshakeComplete() {
- m.handshakeComplete = true
- newConns.WithLabelValues(m.getDirection(), "true").Inc()
-}
-
-func (m *metricsConnTracer) getSmoothedRTT() (rtt time.Duration, valid bool) {
- m.mutex.Lock()
- rtt = m.rtt
- valid = m.numRTTMeasurements > 10
- m.mutex.Unlock()
- return
-}
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics.go
index fc2add49b..8e7308f3a 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics.go
@@ -1,4 +1,4 @@
-//go:build !windows
+//go:build !windows && !riscv64
package tcp
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_general.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_general.go
index 6b6728344..e9868609f 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_general.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_general.go
@@ -1,4 +1,4 @@
-//go:build !linux && !darwin && !windows
+//go:build !linux && !darwin && !windows && !riscv64
package tcp
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_windows.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_none.go
similarity index 71%
rename from vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_windows.go
rename to vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_none.go
index 7142e7dbe..01cf3e9c5 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_windows.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/metrics_none.go
@@ -1,4 +1,6 @@
-//go:build windows
+// riscv64 see: https://github.com/marten-seemann/tcp/pull/1
+
+//go:build windows || riscv64
package tcp
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/tcp.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/tcp.go
index f277b3f8f..d52bb9601 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/tcp.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/tcp/tcp.go
@@ -131,6 +131,7 @@ type TcpTransport struct {
}
var _ transport.Transport = &TcpTransport{}
+var _ transport.DialUpdater = &TcpTransport{}
// NewTCPTransport creates a tcp transport object that tracks dialers and listeners
// created. It represents an entire TCP stack (though it might not necessarily be).
@@ -176,13 +177,17 @@ func (t *TcpTransport) maDial(ctx context.Context, raddr ma.Multiaddr) (manet.Co
// Dial dials the peer at the remote address.
func (t *TcpTransport) Dial(ctx context.Context, raddr ma.Multiaddr, p peer.ID) (transport.CapableConn, error) {
+ return t.DialWithUpdates(ctx, raddr, p, nil)
+}
+
+func (t *TcpTransport) DialWithUpdates(ctx context.Context, raddr ma.Multiaddr, p peer.ID, updateChan chan<- transport.DialUpdate) (transport.CapableConn, error) {
connScope, err := t.rcmgr.OpenConnection(network.DirOutbound, true, raddr)
if err != nil {
log.Debugw("resource manager blocked outgoing connection", "peer", p, "addr", raddr, "error", err)
return nil, err
}
- c, err := t.dialWithScope(ctx, raddr, p, connScope)
+ c, err := t.dialWithScope(ctx, raddr, p, connScope, updateChan)
if err != nil {
connScope.Done()
return nil, err
@@ -190,7 +195,7 @@ func (t *TcpTransport) Dial(ctx context.Context, raddr ma.Multiaddr, p peer.ID)
return c, nil
}
-func (t *TcpTransport) dialWithScope(ctx context.Context, raddr ma.Multiaddr, p peer.ID, connScope network.ConnManagementScope) (transport.CapableConn, error) {
+func (t *TcpTransport) dialWithScope(ctx context.Context, raddr ma.Multiaddr, p peer.ID, connScope network.ConnManagementScope, updateChan chan<- transport.DialUpdate) (transport.CapableConn, error) {
if err := connScope.SetPeer(p); err != nil {
log.Debugw("resource manager blocked outgoing connection for peer", "peer", p, "addr", raddr, "error", err)
return nil, err
@@ -212,6 +217,13 @@ func (t *TcpTransport) dialWithScope(ctx context.Context, raddr ma.Multiaddr, p
return nil, err
}
}
+ if updateChan != nil {
+ select {
+ case updateChan <- transport.DialUpdate{Kind: transport.UpdateKindHandshakeProgressed, Addr: raddr}:
+ default:
+ // It is better to skip the update than to delay upgrading the connection
+ }
+ }
direction := network.DirOutbound
if ok, isClient, _ := network.GetSimultaneousConnect(ctx); ok && !isClient {
direction = network.DirInbound
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/websocket/websocket.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/websocket/websocket.go
index e1965123d..5142ca97a 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/websocket/websocket.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/websocket/websocket.go
@@ -120,7 +120,7 @@ func (t *WebsocketTransport) Proxy() bool {
return false
}
-func (t *WebsocketTransport) Resolve(ctx context.Context, maddr ma.Multiaddr) ([]ma.Multiaddr, error) {
+func (t *WebsocketTransport) Resolve(_ context.Context, maddr ma.Multiaddr) ([]ma.Multiaddr, error) {
parsed, err := parseWebsocketMultiaddr(maddr)
if err != nil {
return nil, err
@@ -136,7 +136,7 @@ func (t *WebsocketTransport) Resolve(ctx context.Context, maddr ma.Multiaddr) ([
// We don't have an sni component, we'll use dns/dnsaddr
ma.ForEach(parsed.restMultiaddr, func(c ma.Component) bool {
switch c.Protocol().Code {
- case ma.P_DNS, ma.P_DNS4, ma.P_DNS6, ma.P_DNSADDR:
+ case ma.P_DNS, ma.P_DNS4, ma.P_DNS6:
// err shouldn't happen since this means we couldn't parse a dns hostname for an sni value.
parsed.sni, err = ma.NewComponent("sni", c.Value())
return false
diff --git a/vendor/github.com/libp2p/go-libp2p/p2p/transport/webtransport/multiaddr.go b/vendor/github.com/libp2p/go-libp2p/p2p/transport/webtransport/multiaddr.go
index d6930af36..bd90638b6 100644
--- a/vendor/github.com/libp2p/go-libp2p/p2p/transport/webtransport/multiaddr.go
+++ b/vendor/github.com/libp2p/go-libp2p/p2p/transport/webtransport/multiaddr.go
@@ -89,17 +89,23 @@ func IsWebtransportMultiaddr(multiaddr ma.Multiaddr) (bool, int) {
certhashCount := 0
ma.ForEach(multiaddr, func(c ma.Component) bool {
- if c.Protocol().Code == ma.P_QUIC_V1 && state == init {
- state = foundUDP
- }
- if c.Protocol().Code == ma.P_QUIC_V1 && state == foundUDP {
- state = foundQuicV1
- }
- if c.Protocol().Code == ma.P_WEBTRANSPORT && state == foundQuicV1 {
- state = foundWebTransport
- }
- if c.Protocol().Code == ma.P_CERTHASH && state == foundWebTransport {
- certhashCount++
+ switch c.Protocol().Code {
+ case ma.P_UDP:
+ if state == init {
+ state = foundUDP
+ }
+ case ma.P_QUIC_V1:
+ if state == foundUDP {
+ state = foundQuicV1
+ }
+ case ma.P_WEBTRANSPORT:
+ if state == foundQuicV1 {
+ state = foundWebTransport
+ }
+ case ma.P_CERTHASH:
+ if state == foundWebTransport {
+ certhashCount++
+ }
}
return true
})
diff --git a/vendor/github.com/libp2p/go-libp2p/package-list.json b/vendor/github.com/libp2p/go-libp2p/package-list.json
deleted file mode 100644
index fec3fac19..000000000
--- a/vendor/github.com/libp2p/go-libp2p/package-list.json
+++ /dev/null
@@ -1,82 +0,0 @@
-{
- "columns": [
- "Name",
- "CI/Travis",
- "Coverage",
- "Description"
- ],
- "rows": [
- "Libp2p",
- ["libp2p/go-libp2p", "go-libp2p", "go-libp2p entry point"],
- ["libp2p/go-libp2p-core", "go-libp2p-core", "core interfaces, types, and abstractions"],
- ["libp2p/go-libp2p-blankhost", "go-libp2p-blankhost", "minimal implementation of the \"host\" interface"],
-
- "Network",
- ["libp2p/go-libp2p-swarm", "go-libp2p-swarm", "reference implementation of network state machine"],
-
- "Transport",
- ["libp2p/go-ws-transport", "go-ws-transport", "WebSocket transport"],
- ["libp2p/go-tcp-transport", "go-tcp-transport", "TCP transport"],
- ["libp2p/go-libp2p-quic-transport", "go-libp2p-quic-transport", "QUIC transport"],
- ["libp2p/go-udp-transport", "go-udp-transport", "UDP transport"],
- ["libp2p/go-utp-transport", "go-utp-transport", "uTorrent transport (UTP)"],
- ["libp2p/go-libp2p-circuit", "go-libp2p-circuit", "relay transport"],
- ["libp2p/go-libp2p-transport-upgrader", "go-libp2p-transport-upgrader", "upgrades multiaddr-net connections into full libp2p transports"],
- ["libp2p/go-libp2p-reuseport-transport", "go-libp2p-reuseport-transport", "partial transport for building transports that reuse ports"],
-
- "Encrypted Channels",
- ["libp2p/go-libp2p-secio", "go-libp2p-secio", "SecIO crypto channel"],
- ["libp2p/go-libp2p-tls-transport", "go-libp2p-tls-transport", "TLS 1.3+ crypto channel"],
- ["libp2p/go-conn-security-multistream", "go-conn-security-multistream", "multistream multiplexed meta crypto channel"],
-
- "Private Network",
- ["libp2p/go-libp2p-pnet", "go-libp2p-pnet", "reference private networking implementation"],
-
- "Stream Muxers",
- ["libp2p/go-libp2p-yamux", "go-libp2p-yamux", "YAMUX stream multiplexer"],
- ["libp2p/go-libp2p-mplex", "go-libp2p-mplex", "MPLEX stream multiplexer"],
-
- "NAT Traversal",
- ["libp2p/go-libp2p-nat", "go-libp2p-nat"],
-
- "Peerstore",
- ["libp2p/go-libp2p-peerstore", "go-libp2p-peerstore", "reference implementation of peer metadata storage component"],
-
- "Connection Manager",
- ["libp2p/go-libp2p-connmgr", "go-libp2p-connmgr", "reference implementation of connection manager"],
-
- "Routing",
- ["libp2p/go-libp2p-record", "go-libp2p-record", "record type and validator logic"],
- ["libp2p/go-libp2p-kad-dht", "go-libp2p-kad-dht", "Kademlia-like router"],
- ["libp2p/go-libp2p-kbucket", "go-libp2p-kbucket", "Kademlia routing table helper types"],
- ["libp2p/go-libp2p-coral-dht", "go-libp2p-coral-dht", "Router based on Coral DHT"],
- ["libp2p/go-libp2p-pubsub-router", "go-libp2p-pubsub-router", "record-store over pubsub adapter"],
-
- "Consensus",
- ["libp2p/go-libp2p-consensus", "go-libp2p-consensus", "consensus protocols interfaces"],
- ["libp2p/go-libp2p-raft", "go-libp2p-raft", "consensus implementation over raft"],
-
- "Pubsub",
- ["libp2p/go-libp2p-pubsub", "go-libp2p-pubsub", "multiple pubsub over libp2p implementations"],
-
- "RPC",
- ["libp2p/go-libp2p-gorpc", "go-libp2p-gorpc", "a simple RPC library for libp2p"],
-
- "Utilities/miscellaneous",
- ["libp2p/go-libp2p-loggables", "go-libp2p-loggables", "logging helpers"],
- ["libp2p/go-maddr-filter", "go-maddr-filter", "multiaddr filtering helpers"],
- ["libp2p/go-libp2p-netutil", "go-libp2p-netutil", "misc utilities"],
- ["libp2p/go-msgio", "go-msgio", "length prefixed data channel"],
- ["libp2p/go-addr-util", "go-addr-util", "address utilities for libp2p swarm"],
- ["libp2p/go-buffer-pool", "go-buffer-pool", "a variable size buffer pool for go"],
- ["libp2p/go-libp2p-routing-helpers", "go-libp2p-routing-helpers", "routing helpers"],
- ["libp2p/go-reuseport", "go-reuseport", "enables reuse of addresses"],
- ["libp2p/go-sockaddr", "go-sockaddr", "utils for sockaddr conversions"],
- ["libp2p/go-flow-metrics", "go-flow-metrics", "metrics library"],
- ["libp2p/go-libp2p-gostream", "go-libp2p-gostream", "Go 'net' wrappers for libp2p"],
- ["libp2p/go-libp2p-http", "go-libp2p-http", "HTTP on top of libp2p streams"],
-
- "Testing and examples",
- ["libp2p/go-libp2p-testing", "go-libp2p-testing", "a collection of testing utilities for libp2p"]
- ]
-}
diff --git a/vendor/github.com/libp2p/go-libp2p/tools.go b/vendor/github.com/libp2p/go-libp2p/tools.go
index 46a8037df..7a650d9c1 100644
--- a/vendor/github.com/libp2p/go-libp2p/tools.go
+++ b/vendor/github.com/libp2p/go-libp2p/tools.go
@@ -3,7 +3,7 @@
package libp2p
import (
- _ "github.com/golang/mock/mockgen"
+ _ "go.uber.org/mock/mockgen"
_ "golang.org/x/tools/cmd/goimports"
_ "google.golang.org/protobuf/cmd/protoc-gen-go"
)
diff --git a/vendor/github.com/libp2p/go-libp2p/version.json b/vendor/github.com/libp2p/go-libp2p/version.json
index 462969c8e..7b5ac4c94 100644
--- a/vendor/github.com/libp2p/go-libp2p/version.json
+++ b/vendor/github.com/libp2p/go-libp2p/version.json
@@ -1,3 +1,3 @@
{
- "version": "v0.29.2"
+ "version": "v0.32.2"
}
diff --git a/vendor/github.com/libp2p/go-reuseport/control_freebsd.go b/vendor/github.com/libp2p/go-reuseport/control_freebsd.go
new file mode 100644
index 000000000..cec1b11aa
--- /dev/null
+++ b/vendor/github.com/libp2p/go-reuseport/control_freebsd.go
@@ -0,0 +1,27 @@
+//go:build freebsd
+
+package reuseport
+
+import (
+ "syscall"
+
+ "golang.org/x/sys/unix"
+)
+
+func Control(network, address string, c syscall.RawConn) (err error) {
+ controlErr := c.Control(func(fd uintptr) {
+ err = unix.SetsockoptInt(int(fd), unix.SOL_SOCKET, unix.SO_REUSEADDR, 1)
+ if err != nil {
+ return
+ }
+ err = unix.SetsockoptInt(int(fd), unix.SOL_SOCKET, unix.SO_REUSEPORT, 1)
+ if err != nil {
+ return
+ }
+ err = unix.SetsockoptInt(int(fd), unix.SOL_SOCKET, unix.SO_REUSEPORT_LB, 1)
+ })
+ if controlErr != nil {
+ err = controlErr
+ }
+ return
+}
diff --git a/vendor/github.com/libp2p/go-reuseport/control_unix.go b/vendor/github.com/libp2p/go-reuseport/control_unix.go
index 4197d1f74..e80688b5e 100644
--- a/vendor/github.com/libp2p/go-reuseport/control_unix.go
+++ b/vendor/github.com/libp2p/go-reuseport/control_unix.go
@@ -1,4 +1,4 @@
-//go:build !plan9 && !windows && !wasm
+//go:build !plan9 && !windows && !wasm && !freebsd
package reuseport
diff --git a/vendor/github.com/libp2p/go-reuseport/version.json b/vendor/github.com/libp2p/go-reuseport/version.json
index a654d65ab..372b6eab3 100644
--- a/vendor/github.com/libp2p/go-reuseport/version.json
+++ b/vendor/github.com/libp2p/go-reuseport/version.json
@@ -1,3 +1,3 @@
{
- "version": "v0.3.0"
+ "version": "v0.4.0"
}
diff --git a/vendor/github.com/mattn/go-isatty/isatty_bsd.go b/vendor/github.com/mattn/go-isatty/isatty_bsd.go
index d569c0c94..d0ea68f40 100644
--- a/vendor/github.com/mattn/go-isatty/isatty_bsd.go
+++ b/vendor/github.com/mattn/go-isatty/isatty_bsd.go
@@ -1,6 +1,7 @@
-//go:build (darwin || freebsd || openbsd || netbsd || dragonfly || hurd) && !appengine
+//go:build (darwin || freebsd || openbsd || netbsd || dragonfly || hurd) && !appengine && !tinygo
// +build darwin freebsd openbsd netbsd dragonfly hurd
// +build !appengine
+// +build !tinygo
package isatty
diff --git a/vendor/github.com/mattn/go-isatty/isatty_others.go b/vendor/github.com/mattn/go-isatty/isatty_others.go
index 31503226f..7402e0618 100644
--- a/vendor/github.com/mattn/go-isatty/isatty_others.go
+++ b/vendor/github.com/mattn/go-isatty/isatty_others.go
@@ -1,5 +1,6 @@
-//go:build appengine || js || nacl || wasm
-// +build appengine js nacl wasm
+//go:build (appengine || js || nacl || tinygo || wasm) && !windows
+// +build appengine js nacl tinygo wasm
+// +build !windows
package isatty
diff --git a/vendor/github.com/mattn/go-isatty/isatty_tcgets.go b/vendor/github.com/mattn/go-isatty/isatty_tcgets.go
index 67787657f..0337d8cf6 100644
--- a/vendor/github.com/mattn/go-isatty/isatty_tcgets.go
+++ b/vendor/github.com/mattn/go-isatty/isatty_tcgets.go
@@ -1,6 +1,7 @@
-//go:build (linux || aix || zos) && !appengine
+//go:build (linux || aix || zos) && !appengine && !tinygo
// +build linux aix zos
// +build !appengine
+// +build !tinygo
package isatty
diff --git a/vendor/github.com/miekg/dns/README.md b/vendor/github.com/miekg/dns/README.md
index 06bea9fab..95bc08d5c 100644
--- a/vendor/github.com/miekg/dns/README.md
+++ b/vendor/github.com/miekg/dns/README.md
@@ -81,6 +81,7 @@ A not-so-up-to-date-list-that-may-be-actually-current:
* https://addr.tools/
* https://dnscheck.tools/
* https://github.com/egbakou/domainverifier
+* https://github.com/semihalev/sdns
Send pull request if you want to be listed here.
diff --git a/vendor/github.com/miekg/dns/defaults.go b/vendor/github.com/miekg/dns/defaults.go
index c1558b79c..6d7e17605 100644
--- a/vendor/github.com/miekg/dns/defaults.go
+++ b/vendor/github.com/miekg/dns/defaults.go
@@ -5,6 +5,7 @@ import (
"net"
"strconv"
"strings"
+ "unicode"
)
const hexDigit = "0123456789abcdef"
@@ -330,8 +331,18 @@ func Fqdn(s string) string {
// CanonicalName returns the domain name in canonical form. A name in canonical
// form is lowercase and fully qualified. See Section 6.2 in RFC 4034.
+// According to the RFC all uppercase US-ASCII letters in the owner name of the
+// RR areeplaced by the corresponding lowercase US-ASCII letters.
func CanonicalName(s string) string {
- return strings.ToLower(Fqdn(s))
+ var result strings.Builder
+ for _, ch := range s {
+ if unicode.IsUpper(ch) && (ch >= 0x00 && ch <= 0x7F) {
+ result.WriteRune(unicode.ToLower(ch))
+ } else {
+ result.WriteRune(ch)
+ }
+ }
+ return Fqdn(result.String())
}
// Copied from the official Go code.
diff --git a/vendor/github.com/miekg/dns/msg.go b/vendor/github.com/miekg/dns/msg.go
index d5049a4f9..b05cf14e9 100644
--- a/vendor/github.com/miekg/dns/msg.go
+++ b/vendor/github.com/miekg/dns/msg.go
@@ -896,23 +896,38 @@ func (dns *Msg) String() string {
return " MsgHdr"
}
s := dns.MsgHdr.String() + " "
- s += "QUERY: " + strconv.Itoa(len(dns.Question)) + ", "
- s += "ANSWER: " + strconv.Itoa(len(dns.Answer)) + ", "
- s += "AUTHORITY: " + strconv.Itoa(len(dns.Ns)) + ", "
- s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
+ if dns.MsgHdr.Opcode == OpcodeUpdate {
+ s += "ZONE: " + strconv.Itoa(len(dns.Question)) + ", "
+ s += "PREREQ: " + strconv.Itoa(len(dns.Answer)) + ", "
+ s += "UPDATE: " + strconv.Itoa(len(dns.Ns)) + ", "
+ s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
+ } else {
+ s += "QUERY: " + strconv.Itoa(len(dns.Question)) + ", "
+ s += "ANSWER: " + strconv.Itoa(len(dns.Answer)) + ", "
+ s += "AUTHORITY: " + strconv.Itoa(len(dns.Ns)) + ", "
+ s += "ADDITIONAL: " + strconv.Itoa(len(dns.Extra)) + "\n"
+ }
opt := dns.IsEdns0()
if opt != nil {
// OPT PSEUDOSECTION
s += opt.String() + "\n"
}
if len(dns.Question) > 0 {
- s += "\n;; QUESTION SECTION:\n"
+ if dns.MsgHdr.Opcode == OpcodeUpdate {
+ s += "\n;; ZONE SECTION:\n"
+ } else {
+ s += "\n;; QUESTION SECTION:\n"
+ }
for _, r := range dns.Question {
s += r.String() + "\n"
}
}
if len(dns.Answer) > 0 {
- s += "\n;; ANSWER SECTION:\n"
+ if dns.MsgHdr.Opcode == OpcodeUpdate {
+ s += "\n;; PREREQUISITE SECTION:\n"
+ } else {
+ s += "\n;; ANSWER SECTION:\n"
+ }
for _, r := range dns.Answer {
if r != nil {
s += r.String() + "\n"
@@ -920,7 +935,11 @@ func (dns *Msg) String() string {
}
}
if len(dns.Ns) > 0 {
- s += "\n;; AUTHORITY SECTION:\n"
+ if dns.MsgHdr.Opcode == OpcodeUpdate {
+ s += "\n;; UPDATE SECTION:\n"
+ } else {
+ s += "\n;; AUTHORITY SECTION:\n"
+ }
for _, r := range dns.Ns {
if r != nil {
s += r.String() + "\n"
diff --git a/vendor/github.com/miekg/dns/types.go b/vendor/github.com/miekg/dns/types.go
index 03afeccda..c9a03dec6 100644
--- a/vendor/github.com/miekg/dns/types.go
+++ b/vendor/github.com/miekg/dns/types.go
@@ -236,6 +236,9 @@ var CertTypeToString = map[uint16]string{
CertOID: "OID",
}
+// Prefix for IPv4 encoded as IPv6 address
+const ipv4InIPv6Prefix = "::ffff:"
+
//go:generate go run types_generate.go
// Question holds a DNS question. Usually there is just one. While the
@@ -751,6 +754,11 @@ func (rr *AAAA) String() string {
if rr.AAAA == nil {
return rr.Hdr.String()
}
+
+ if rr.AAAA.To4() != nil {
+ return rr.Hdr.String() + ipv4InIPv6Prefix + rr.AAAA.String()
+ }
+
return rr.Hdr.String() + rr.AAAA.String()
}
@@ -1517,7 +1525,7 @@ func (a *APLPrefix) str() string {
case net.IPv6len:
// add prefix for IPv4-mapped IPv6
if v4 := a.Network.IP.To4(); v4 != nil {
- sb.WriteString("::ffff:")
+ sb.WriteString(ipv4InIPv6Prefix)
}
sb.WriteString(a.Network.IP.String())
}
diff --git a/vendor/github.com/miekg/dns/version.go b/vendor/github.com/miekg/dns/version.go
index 5891044a3..a09113662 100644
--- a/vendor/github.com/miekg/dns/version.go
+++ b/vendor/github.com/miekg/dns/version.go
@@ -3,7 +3,7 @@ package dns
import "fmt"
// Version is current version of this library.
-var Version = v{1, 1, 55}
+var Version = v{1, 1, 56}
// v holds the version of this library.
type v struct {
diff --git a/vendor/github.com/multiformats/go-multiaddr/multiaddr.go b/vendor/github.com/multiformats/go-multiaddr/multiaddr.go
index 7c567c9fd..af26d4486 100644
--- a/vendor/github.com/multiformats/go-multiaddr/multiaddr.go
+++ b/vendor/github.com/multiformats/go-multiaddr/multiaddr.go
@@ -220,7 +220,7 @@ func Unique(addrs []Multiaddr) []Multiaddr {
return addrs
}
// Use the new slices package here, as the sort function doesn't allocate (sort.Slice does).
- slices.SortFunc(addrs, func(a, b Multiaddr) bool { return bytes.Compare(a.Bytes(), b.Bytes()) < 0 })
+ slices.SortFunc(addrs, func(a, b Multiaddr) int { return bytes.Compare(a.Bytes(), b.Bytes()) })
idx := 1
for i := 1; i < len(addrs); i++ {
if !addrs[i-1].Equal(addrs[i]) {
diff --git a/vendor/github.com/multiformats/go-multiaddr/net/private.go b/vendor/github.com/multiformats/go-multiaddr/net/private.go
index ba57f00c3..9f966de0f 100644
--- a/vendor/github.com/multiformats/go-multiaddr/net/private.go
+++ b/vendor/github.com/multiformats/go-multiaddr/net/private.go
@@ -2,6 +2,7 @@ package manet
import (
"net"
+ "strings"
ma "github.com/multiformats/go-multiaddr"
)
@@ -46,6 +47,36 @@ var unroutableCIDR6 = []string{
"ff00::/8",
}
+// unResolvableDomains do not resolve to an IP address.
+// Ref: https://en.wikipedia.org/wiki/Special-use_domain_name#Reserved_domain_names
+var unResolvableDomains = []string{
+ // Reverse DNS Lookup
+ ".in-addr.arpa",
+ ".ip6.arpa",
+
+ // RFC 6761: Users MAY assume that queries for "invalid" names will always return NXDOMAIN
+ // responses
+ ".invalid",
+}
+
+// privateUseDomains are reserved for private use and have no central authority for consistent
+// address resolution
+// Ref: https://en.wikipedia.org/wiki/Special-use_domain_name#Reserved_domain_names
+var privateUseDomains = []string{
+ // RFC 8375: Reserved for home networks
+ ".home.arpa",
+
+ // MDNS
+ ".local",
+
+ // RFC 6761: No central authority for .test names
+ ".test",
+}
+
+// RFC 6761: Users may assume that IPv4 and IPv6 address queries for localhost names will
+// always resolve to the respective IP loopback address
+const localHostDomain = ".localhost"
+
func init() {
Private4 = parseCIDR(privateCIDR4)
Private6 = parseCIDR(privateCIDR6)
@@ -65,7 +96,8 @@ func parseCIDR(cidrs []string) []*net.IPNet {
return ipnets
}
-// IsPublicAddr retruns true if the IP part of the multiaddr is a publicly routable address
+// IsPublicAddr returns true if the IP part of the multiaddr is a publicly routable address
+// or if it's a dns address without a special use domain e.g. .local.
func IsPublicAddr(a ma.Multiaddr) bool {
isPublic := false
ma.ForEach(a, func(c ma.Component) bool {
@@ -78,12 +110,38 @@ func IsPublicAddr(a ma.Multiaddr) bool {
case ma.P_IP6:
ip := net.IP(c.RawValue())
isPublic = !inAddrRange(ip, Private6) && !inAddrRange(ip, Unroutable6)
+ case ma.P_DNS, ma.P_DNS4, ma.P_DNS6, ma.P_DNSADDR:
+ dnsAddr := c.Value()
+ isPublic = true
+ if isSubdomain(dnsAddr, localHostDomain) {
+ isPublic = false
+ return false
+ }
+ for _, ud := range unResolvableDomains {
+ if isSubdomain(dnsAddr, ud) {
+ isPublic = false
+ return false
+ }
+ }
+ for _, pd := range privateUseDomains {
+ if isSubdomain(dnsAddr, pd) {
+ isPublic = false
+ break
+ }
+ }
}
return false
})
return isPublic
}
+// isSubdomain checks if child is sub domain of parent. It also returns true if child and parent are
+// the same domain.
+// Parent must have a "." prefix.
+func isSubdomain(child, parent string) bool {
+ return strings.HasSuffix(child, parent) || child == parent[1:]
+}
+
// IsPrivateAddr returns true if the IP part of the mutiaddr is in a private network
func IsPrivateAddr(a ma.Multiaddr) bool {
isPrivate := false
@@ -95,6 +153,13 @@ func IsPrivateAddr(a ma.Multiaddr) bool {
isPrivate = inAddrRange(net.IP(c.RawValue()), Private4)
case ma.P_IP6:
isPrivate = inAddrRange(net.IP(c.RawValue()), Private6)
+ case ma.P_DNS, ma.P_DNS4, ma.P_DNS6, ma.P_DNSADDR:
+ dnsAddr := c.Value()
+ if isSubdomain(dnsAddr, localHostDomain) {
+ isPrivate = true
+ }
+ // We don't check for privateUseDomains because private use domains can
+ // resolve to public IP addresses
}
return false
})
diff --git a/vendor/github.com/multiformats/go-multiaddr/version.json b/vendor/github.com/multiformats/go-multiaddr/version.json
index b6bb0741a..21e148a94 100644
--- a/vendor/github.com/multiformats/go-multiaddr/version.json
+++ b/vendor/github.com/multiformats/go-multiaddr/version.json
@@ -1,3 +1,3 @@
{
- "version": "v0.10.1"
+ "version": "v0.12.0"
}
diff --git a/vendor/github.com/multiformats/go-multistream/client.go b/vendor/github.com/multiformats/go-multistream/client.go
index 013dd5abc..25e81e2ac 100644
--- a/vendor/github.com/multiformats/go-multistream/client.go
+++ b/vendor/github.com/multiformats/go-multistream/client.go
@@ -2,15 +2,11 @@ package multistream
import (
"bytes"
- "crypto/rand"
- "encoding/binary"
"errors"
"fmt"
"io"
"os"
"runtime/debug"
- "strconv"
- "strings"
)
// ErrNotSupported is the error returned when the muxer doesn't support
@@ -34,12 +30,6 @@ func (e ErrNotSupported[T]) Is(target error) bool {
// specified.
var ErrNoProtocols = errors.New("no protocols specified")
-const (
- tieBreakerPrefix = "select:"
- initiator = "initiator"
- responder = "responder"
-)
-
// SelectProtoOrFail performs the initial multistream handshake
// to inform the muxer of the protocol that will be used to communicate
// on this ReadWriteCloser. It returns an error if, for example,
@@ -110,84 +100,6 @@ func SelectOneOf[T StringLike](protos []T, rwc io.ReadWriteCloser) (proto T, err
return proto, err
}
-const simOpenProtocol = "/libp2p/simultaneous-connect"
-
-// SelectWithSimopenOrFail performs protocol negotiation with the simultaneous open extension.
-// The returned boolean indicator will be true if we should act as a server.
-func SelectWithSimopenOrFail[T StringLike](protos []T, rwc io.ReadWriteCloser) (proto T, isServer bool, err error) {
- defer func() {
- if rerr := recover(); rerr != nil {
- fmt.Fprintf(os.Stderr, "caught panic: %s\n%s\n", rerr, debug.Stack())
- err = fmt.Errorf("panic selecting protocol with simopen: %s", rerr)
- }
- }()
-
- if len(protos) == 0 {
- return "", false, ErrNoProtocols
- }
-
- werrCh := make(chan error, 1)
- go func() {
- var buf bytes.Buffer
- if err := delitmWriteAll(&buf, []byte(ProtocolID), []byte(simOpenProtocol), []byte(protos[0])); err != nil {
- werrCh <- err
- return
- }
-
- _, err := io.Copy(rwc, &buf)
- werrCh <- err
- }()
-
- if err := readMultistreamHeader(rwc); err != nil {
- return "", false, err
- }
-
- tok, err := ReadNextToken[T](rwc)
- if err != nil {
- return "", false, err
- }
-
- if err = <-werrCh; err != nil {
- return "", false, err
- }
-
- switch tok {
- case simOpenProtocol:
- // simultaneous open
- return simOpen(protos, rwc)
- case "na":
- // client open
- proto, err := clientOpen(protos, rwc)
- if err != nil {
- return "", false, err
- }
- return proto, false, nil
- default:
- return "", false, fmt.Errorf("unexpected response: %s", tok)
- }
-}
-
-func clientOpen[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, error) {
- // check to see if we selected the pipelined protocol
- tok, err := ReadNextToken[T](rwc)
- if err != nil {
- return "", err
- }
-
- switch tok {
- case protos[0]:
- return tok, nil
- case "na":
- proto, err := selectProtosOrFail(protos[1:], rwc)
- if _, ok := err.(ErrNotSupported[T]); ok {
- return "", ErrNotSupported[T]{protos}
- }
- return proto, err
- default:
- return "", fmt.Errorf("unexpected response: %s", tok)
- }
-}
-
func selectProtosOrFail[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, error) {
for _, p := range protos {
err := trySelect(p, rwc)
@@ -202,131 +114,6 @@ func selectProtosOrFail[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, er
return "", ErrNotSupported[T]{protos}
}
-func simOpen[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, bool, error) {
- randBytes := make([]byte, 8)
- _, err := rand.Read(randBytes)
- if err != nil {
- return "", false, err
- }
- myNonce := binary.LittleEndian.Uint64(randBytes)
-
- werrCh := make(chan error, 1)
- go func() {
- myselect := []byte(tieBreakerPrefix + strconv.FormatUint(myNonce, 10))
- err := delimWriteBuffered(rwc, myselect)
- werrCh <- err
- }()
-
- // skip exactly one protocol
- // see https://github.com/multiformats/go-multistream/pull/42#discussion_r558757135
- _, err = ReadNextToken[T](rwc)
- if err != nil {
- return "", false, err
- }
-
- // read the tie breaker nonce
- tok, err := ReadNextToken[T](rwc)
- if err != nil {
- return "", false, err
- }
- if !strings.HasPrefix(string(tok), tieBreakerPrefix) {
- return "", false, errors.New("tie breaker nonce not sent with the correct prefix")
- }
-
- if err = <-werrCh; err != nil {
- return "", false, err
- }
-
- peerNonce, err := strconv.ParseUint(string(tok[len(tieBreakerPrefix):]), 10, 64)
- if err != nil {
- return "", false, err
- }
-
- var iamserver bool
-
- if peerNonce == myNonce {
- return "", false, errors.New("failed client selection; identical nonces")
- }
- iamserver = peerNonce > myNonce
-
- var proto T
- if iamserver {
- proto, err = simOpenSelectServer(protos, rwc)
- } else {
- proto, err = simOpenSelectClient(protos, rwc)
- }
-
- return proto, iamserver, err
-}
-
-func simOpenSelectServer[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, error) {
- werrCh := make(chan error, 1)
- go func() {
- err := delimWriteBuffered(rwc, []byte(responder))
- werrCh <- err
- }()
-
- tok, err := ReadNextToken[T](rwc)
- if err != nil {
- return "", err
- }
- if tok != initiator {
- return "", fmt.Errorf("unexpected response: %s", tok)
- }
- if err = <-werrCh; err != nil {
- return "", err
- }
- for {
- tok, err = ReadNextToken[T](rwc)
-
- if err == io.EOF {
- return "", ErrNotSupported[T]{protos}
- }
-
- if err != nil {
- return "", err
- }
-
- for _, p := range protos {
- if tok == p {
- err = delimWriteBuffered(rwc, []byte(p))
- if err != nil {
- return "", err
- }
-
- return p, nil
- }
- }
-
- err = delimWriteBuffered(rwc, []byte("na"))
- if err != nil {
- return "", err
- }
- }
-
-}
-
-func simOpenSelectClient[T StringLike](protos []T, rwc io.ReadWriteCloser) (T, error) {
- werrCh := make(chan error, 1)
- go func() {
- err := delimWriteBuffered(rwc, []byte(initiator))
- werrCh <- err
- }()
-
- tok, err := ReadNextToken[T](rwc)
- if err != nil {
- return "", err
- }
- if tok != responder {
- return "", fmt.Errorf("unexpected response: %s", tok)
- }
- if err = <-werrCh; err != nil {
- return "", err
- }
-
- return selectProtosOrFail(protos, rwc)
-}
-
func readMultistreamHeader(r io.Reader) error {
tok, err := ReadNextToken[string](r)
if err != nil {
diff --git a/vendor/github.com/onsi/ginkgo/v2/ginkgo/outline/ginkgo.go b/vendor/github.com/onsi/ginkgo/v2/ginkgo/outline/ginkgo.go
index 0b9b19fe7..958daccbf 100644
--- a/vendor/github.com/onsi/ginkgo/v2/ginkgo/outline/ginkgo.go
+++ b/vendor/github.com/onsi/ginkgo/v2/ginkgo/outline/ginkgo.go
@@ -244,9 +244,7 @@ func labelFromCallExpr(ce *ast.CallExpr) []string {
}
if id.Name == "Label" {
ls := extractLabels(expr)
- for _, label := range ls {
- labels = append(labels, label)
- }
+ labels = append(labels, ls...)
}
}
}
diff --git a/vendor/github.com/onsi/ginkgo/v2/types/config.go b/vendor/github.com/onsi/ginkgo/v2/types/config.go
index 1014c7b49..c88fc85a7 100644
--- a/vendor/github.com/onsi/ginkgo/v2/types/config.go
+++ b/vendor/github.com/onsi/ginkgo/v2/types/config.go
@@ -27,6 +27,7 @@ type SuiteConfig struct {
FailOnPending bool
FailFast bool
FlakeAttempts int
+ MustPassRepeatedly int
DryRun bool
PollProgressAfter time.Duration
PollProgressInterval time.Duration
diff --git a/vendor/github.com/onsi/ginkgo/v2/types/errors.go b/vendor/github.com/onsi/ginkgo/v2/types/errors.go
index 1e0dbfd9d..4fbdc3e9b 100644
--- a/vendor/github.com/onsi/ginkgo/v2/types/errors.go
+++ b/vendor/github.com/onsi/ginkgo/v2/types/errors.go
@@ -453,8 +453,8 @@ func (g ginkgoErrors) InvalidEntryDescription(cl CodeLocation) error {
func (g ginkgoErrors) MissingParametersForTableFunction(cl CodeLocation) error {
return GinkgoError{
- Heading: fmt.Sprintf("No parameters have been passed to the Table Function"),
- Message: fmt.Sprintf("The Table Function expected at least 1 parameter"),
+ Heading: "No parameters have been passed to the Table Function",
+ Message: "The Table Function expected at least 1 parameter",
CodeLocation: cl,
DocLink: "table-specs",
}
diff --git a/vendor/github.com/onsi/ginkgo/v2/types/types.go b/vendor/github.com/onsi/ginkgo/v2/types/types.go
index d048a8ada..aae69b04c 100644
--- a/vendor/github.com/onsi/ginkgo/v2/types/types.go
+++ b/vendor/github.com/onsi/ginkgo/v2/types/types.go
@@ -97,9 +97,7 @@ func (report Report) Add(other Report) Report {
report.RunTime = report.EndTime.Sub(report.StartTime)
reports := make(SpecReports, len(report.SpecReports)+len(other.SpecReports))
- for i := range report.SpecReports {
- reports[i] = report.SpecReports[i]
- }
+ copy(reports, report.SpecReports)
offset := len(report.SpecReports)
for i := range other.SpecReports {
reports[i+offset] = other.SpecReports[i]
diff --git a/vendor/github.com/onsi/ginkgo/v2/types/version.go b/vendor/github.com/onsi/ginkgo/v2/types/version.go
index f895739b8..a37f30828 100644
--- a/vendor/github.com/onsi/ginkgo/v2/types/version.go
+++ b/vendor/github.com/onsi/ginkgo/v2/types/version.go
@@ -1,3 +1,3 @@
package types
-const VERSION = "2.11.0"
+const VERSION = "2.13.0"
diff --git a/vendor/github.com/opencontainers/runtime-spec/specs-go/config.go b/vendor/github.com/opencontainers/runtime-spec/specs-go/config.go
index 6a7a91e55..4e7717d53 100644
--- a/vendor/github.com/opencontainers/runtime-spec/specs-go/config.go
+++ b/vendor/github.com/opencontainers/runtime-spec/specs-go/config.go
@@ -12,10 +12,12 @@ type Spec struct {
Root *Root `json:"root,omitempty"`
// Hostname configures the container's hostname.
Hostname string `json:"hostname,omitempty"`
+ // Domainname configures the container's domainname.
+ Domainname string `json:"domainname,omitempty"`
// Mounts configures additional mounts (on top of Root).
Mounts []Mount `json:"mounts,omitempty"`
// Hooks configures callbacks for container lifecycle events.
- Hooks *Hooks `json:"hooks,omitempty" platform:"linux,solaris"`
+ Hooks *Hooks `json:"hooks,omitempty" platform:"linux,solaris,zos"`
// Annotations contains arbitrary metadata for the container.
Annotations map[string]string `json:"annotations,omitempty"`
@@ -27,6 +29,36 @@ type Spec struct {
Windows *Windows `json:"windows,omitempty" platform:"windows"`
// VM specifies configuration for virtual-machine-based containers.
VM *VM `json:"vm,omitempty" platform:"vm"`
+ // ZOS is platform-specific configuration for z/OS based containers.
+ ZOS *ZOS `json:"zos,omitempty" platform:"zos"`
+}
+
+// Scheduler represents the scheduling attributes for a process. It is based on
+// the Linux sched_setattr(2) syscall.
+type Scheduler struct {
+ // Policy represents the scheduling policy (e.g., SCHED_FIFO, SCHED_RR, SCHED_OTHER).
+ Policy LinuxSchedulerPolicy `json:"policy"`
+
+ // Nice is the nice value for the process, which affects its priority.
+ Nice int32 `json:"nice,omitempty"`
+
+ // Priority represents the static priority of the process.
+ Priority int32 `json:"priority,omitempty"`
+
+ // Flags is an array of scheduling flags.
+ Flags []LinuxSchedulerFlag `json:"flags,omitempty"`
+
+ // The following ones are used by the DEADLINE scheduler.
+
+ // Runtime is the amount of time in nanoseconds during which the process
+ // is allowed to run in a given period.
+ Runtime uint64 `json:"runtime,omitempty"`
+
+ // Deadline is the absolute deadline for the process to complete its execution.
+ Deadline uint64 `json:"deadline,omitempty"`
+
+ // Period is the length of the period in nanoseconds used for determining the process runtime.
+ Period uint64 `json:"period,omitempty"`
}
// Process contains information to start a specific application inside the container.
@@ -49,15 +81,19 @@ type Process struct {
// Capabilities are Linux capabilities that are kept for the process.
Capabilities *LinuxCapabilities `json:"capabilities,omitempty" platform:"linux"`
// Rlimits specifies rlimit options to apply to the process.
- Rlimits []POSIXRlimit `json:"rlimits,omitempty" platform:"linux,solaris"`
+ Rlimits []POSIXRlimit `json:"rlimits,omitempty" platform:"linux,solaris,zos"`
// NoNewPrivileges controls whether additional privileges could be gained by processes in the container.
NoNewPrivileges bool `json:"noNewPrivileges,omitempty" platform:"linux"`
// ApparmorProfile specifies the apparmor profile for the container.
ApparmorProfile string `json:"apparmorProfile,omitempty" platform:"linux"`
// Specify an oom_score_adj for the container.
OOMScoreAdj *int `json:"oomScoreAdj,omitempty" platform:"linux"`
+ // Scheduler specifies the scheduling attributes for a process
+ Scheduler *Scheduler `json:"scheduler,omitempty" platform:"linux"`
// SelinuxLabel specifies the selinux context that the container process is run as.
SelinuxLabel string `json:"selinuxLabel,omitempty" platform:"linux"`
+ // IOPriority contains the I/O priority settings for the cgroup.
+ IOPriority *LinuxIOPriority `json:"ioPriority,omitempty" platform:"linux"`
}
// LinuxCapabilities specifies the list of allowed capabilities that are kept for a process.
@@ -75,6 +111,22 @@ type LinuxCapabilities struct {
Ambient []string `json:"ambient,omitempty" platform:"linux"`
}
+// IOPriority represents I/O priority settings for the container's processes within the process group.
+type LinuxIOPriority struct {
+ Class IOPriorityClass `json:"class"`
+ Priority int `json:"priority"`
+}
+
+// IOPriorityClass represents an I/O scheduling class.
+type IOPriorityClass string
+
+// Possible values for IOPriorityClass.
+const (
+ IOPRIO_CLASS_RT IOPriorityClass = "IOPRIO_CLASS_RT"
+ IOPRIO_CLASS_BE IOPriorityClass = "IOPRIO_CLASS_BE"
+ IOPRIO_CLASS_IDLE IOPriorityClass = "IOPRIO_CLASS_IDLE"
+)
+
// Box specifies dimensions of a rectangle. Used for specifying the size of a console.
type Box struct {
// Height is the vertical dimension of a box.
@@ -86,11 +138,11 @@ type Box struct {
// User specifies specific user (and group) information for the container process.
type User struct {
// UID is the user id.
- UID uint32 `json:"uid" platform:"linux,solaris"`
+ UID uint32 `json:"uid" platform:"linux,solaris,zos"`
// GID is the group id.
- GID uint32 `json:"gid" platform:"linux,solaris"`
+ GID uint32 `json:"gid" platform:"linux,solaris,zos"`
// Umask is the umask for the init process.
- Umask *uint32 `json:"umask,omitempty" platform:"linux,solaris"`
+ Umask *uint32 `json:"umask,omitempty" platform:"linux,solaris,zos"`
// AdditionalGids are additional group ids set for the container's process.
AdditionalGids []uint32 `json:"additionalGids,omitempty" platform:"linux,solaris"`
// Username is the user name.
@@ -110,11 +162,16 @@ type Mount struct {
// Destination is the absolute path where the mount will be placed in the container.
Destination string `json:"destination"`
// Type specifies the mount kind.
- Type string `json:"type,omitempty" platform:"linux,solaris"`
+ Type string `json:"type,omitempty" platform:"linux,solaris,zos"`
// Source specifies the source path of the mount.
Source string `json:"source,omitempty"`
// Options are fstab style mount options.
Options []string `json:"options,omitempty"`
+
+ // UID/GID mappings used for changing file owners w/o calling chown, fs should support it.
+ // Every mount point could have its own mapping.
+ UIDMappings []LinuxIDMapping `json:"uidMappings,omitempty" platform:"linux"`
+ GIDMappings []LinuxIDMapping `json:"gidMappings,omitempty" platform:"linux"`
}
// Hook specifies a command that is run at a particular event in the lifecycle of a container
@@ -178,10 +235,12 @@ type Linux struct {
// MountLabel specifies the selinux context for the mounts in the container.
MountLabel string `json:"mountLabel,omitempty"`
// IntelRdt contains Intel Resource Director Technology (RDT) information for
- // handling resource constraints (e.g., L3 cache, memory bandwidth) for the container
+ // handling resource constraints and monitoring metrics (e.g., L3 cache, memory bandwidth) for the container
IntelRdt *LinuxIntelRdt `json:"intelRdt,omitempty"`
// Personality contains configuration for the Linux personality syscall
Personality *LinuxPersonality `json:"personality,omitempty"`
+ // TimeOffsets specifies the offset for supporting time namespaces.
+ TimeOffsets map[string]LinuxTimeOffset `json:"timeOffsets,omitempty"`
}
// LinuxNamespace is the configuration for a Linux namespace
@@ -211,6 +270,8 @@ const (
UserNamespace LinuxNamespaceType = "user"
// CgroupNamespace for isolating cgroup hierarchies
CgroupNamespace LinuxNamespaceType = "cgroup"
+ // TimeNamespace for isolating the clocks
+ TimeNamespace LinuxNamespaceType = "time"
)
// LinuxIDMapping specifies UID/GID mappings
@@ -223,6 +284,14 @@ type LinuxIDMapping struct {
Size uint32 `json:"size"`
}
+// LinuxTimeOffset specifies the offset for Time Namespace
+type LinuxTimeOffset struct {
+ // Secs is the offset of clock (in secs) in the container
+ Secs int64 `json:"secs,omitempty"`
+ // Nanosecs is the additional offset for Secs (in nanosecs)
+ Nanosecs uint32 `json:"nanosecs,omitempty"`
+}
+
// POSIXRlimit type and restrictions
type POSIXRlimit struct {
// Type of the rlimit to set
@@ -233,12 +302,13 @@ type POSIXRlimit struct {
Soft uint64 `json:"soft"`
}
-// LinuxHugepageLimit structure corresponds to limiting kernel hugepages
+// LinuxHugepageLimit structure corresponds to limiting kernel hugepages.
+// Default to reservation limits if supported. Otherwise fallback to page fault limits.
type LinuxHugepageLimit struct {
- // Pagesize is the hugepage size
- // Format: "B' (e.g. 64KB, 2MB, 1GB, etc.)
+ // Pagesize is the hugepage size.
+ // Format: "B' (e.g. 64KB, 2MB, 1GB, etc.).
Pagesize string `json:"pageSize"`
- // Limit is the limit of "hugepagesize" hugetlb usage
+ // Limit is the limit of "hugepagesize" hugetlb reservations (if supported) or usage.
Limit uint64 `json:"limit"`
}
@@ -250,8 +320,8 @@ type LinuxInterfacePriority struct {
Priority uint32 `json:"priority"`
}
-// linuxBlockIODevice holds major:minor format supported in blkio cgroup
-type linuxBlockIODevice struct {
+// LinuxBlockIODevice holds major:minor format supported in blkio cgroup
+type LinuxBlockIODevice struct {
// Major is the device's major number.
Major int64 `json:"major"`
// Minor is the device's minor number.
@@ -260,7 +330,7 @@ type linuxBlockIODevice struct {
// LinuxWeightDevice struct holds a `major:minor weight` pair for weightDevice
type LinuxWeightDevice struct {
- linuxBlockIODevice
+ LinuxBlockIODevice
// Weight is the bandwidth rate for the device.
Weight *uint16 `json:"weight,omitempty"`
// LeafWeight is the bandwidth rate for the device while competing with the cgroup's child cgroups, CFQ scheduler only
@@ -269,7 +339,7 @@ type LinuxWeightDevice struct {
// LinuxThrottleDevice struct holds a `major:minor rate_per_second` pair
type LinuxThrottleDevice struct {
- linuxBlockIODevice
+ LinuxBlockIODevice
// Rate is the IO rate limit per cgroup per device
Rate uint64 `json:"rate"`
}
@@ -310,6 +380,10 @@ type LinuxMemory struct {
DisableOOMKiller *bool `json:"disableOOMKiller,omitempty"`
// Enables hierarchical memory accounting
UseHierarchy *bool `json:"useHierarchy,omitempty"`
+ // CheckBeforeUpdate enables checking if a new memory limit is lower
+ // than the current usage during update, and if so, rejecting the new
+ // limit.
+ CheckBeforeUpdate *bool `json:"checkBeforeUpdate,omitempty"`
}
// LinuxCPU for Linux cgroup 'cpu' resource management
@@ -318,6 +392,9 @@ type LinuxCPU struct {
Shares *uint64 `json:"shares,omitempty"`
// CPU hardcap limit (in usecs). Allowed cpu time in a given period.
Quota *int64 `json:"quota,omitempty"`
+ // CPU hardcap burst limit (in usecs). Allowed accumulated cpu time additionally for burst in a
+ // given period.
+ Burst *uint64 `json:"burst,omitempty"`
// CPU period to be used for hardcapping (in usecs).
Period *uint64 `json:"period,omitempty"`
// How much time realtime scheduling may use (in usecs).
@@ -328,6 +405,8 @@ type LinuxCPU struct {
Cpus string `json:"cpus,omitempty"`
// List of memory nodes in the cpuset. Default is to use any available memory node.
Mems string `json:"mems,omitempty"`
+ // cgroups are configured with minimum weight, 0: default behavior, 1: SCHED_IDLE.
+ Idle *int64 `json:"idle,omitempty"`
}
// LinuxPids for Linux cgroup 'pids' resource management (Linux 4.3)
@@ -364,7 +443,7 @@ type LinuxResources struct {
Pids *LinuxPids `json:"pids,omitempty"`
// BlockIO restriction configuration
BlockIO *LinuxBlockIO `json:"blockIO,omitempty"`
- // Hugetlb limit (in bytes)
+ // Hugetlb limits (in bytes). Default to reservation limits if supported.
HugepageLimits []LinuxHugepageLimit `json:"hugepageLimits,omitempty"`
// Network restriction configuration
Network *LinuxNetwork `json:"network,omitempty"`
@@ -522,11 +601,21 @@ type WindowsMemoryResources struct {
// WindowsCPUResources contains CPU resource management settings.
type WindowsCPUResources struct {
- // Number of CPUs available to the container.
+ // Count is the number of CPUs available to the container. It represents the
+ // fraction of the configured processor `count` in a container in relation
+ // to the processors available in the host. The fraction ultimately
+ // determines the portion of processor cycles that the threads in a
+ // container can use during each scheduling interval, as the number of
+ // cycles per 10,000 cycles.
Count *uint64 `json:"count,omitempty"`
- // CPU shares (relative weight to other containers with cpu shares).
+ // Shares limits the share of processor time given to the container relative
+ // to other workloads on the processor. The processor `shares` (`weight` at
+ // the platform level) is a value between 0 and 10000.
Shares *uint16 `json:"shares,omitempty"`
- // Specifies the portion of processor cycles that this container can use as a percentage times 100.
+ // Maximum determines the portion of processor cycles that the threads in a
+ // container can use during each scheduling interval, as the number of
+ // cycles per 10,000 cycles. Set processor `maximum` to a percentage times
+ // 100.
Maximum *uint16 `json:"maximum,omitempty"`
}
@@ -613,6 +702,23 @@ type Arch string
// LinuxSeccompFlag is a flag to pass to seccomp(2).
type LinuxSeccompFlag string
+const (
+ // LinuxSeccompFlagLog is a seccomp flag to request all returned
+ // actions except SECCOMP_RET_ALLOW to be logged. An administrator may
+ // override this filter flag by preventing specific actions from being
+ // logged via the /proc/sys/kernel/seccomp/actions_logged file. (since
+ // Linux 4.14)
+ LinuxSeccompFlagLog LinuxSeccompFlag = "SECCOMP_FILTER_FLAG_LOG"
+
+ // LinuxSeccompFlagSpecAllow can be used to disable Speculative Store
+ // Bypass mitigation. (since Linux 4.17)
+ LinuxSeccompFlagSpecAllow LinuxSeccompFlag = "SECCOMP_FILTER_FLAG_SPEC_ALLOW"
+
+ // LinuxSeccompFlagWaitKillableRecv can be used to switch to the wait
+ // killable semantics. (since Linux 5.19)
+ LinuxSeccompFlagWaitKillableRecv LinuxSeccompFlag = "SECCOMP_FILTER_FLAG_WAIT_KILLABLE_RECV"
+)
+
// Additional architectures permitted to be used for system calls
// By default only the native architecture of the kernel is permitted
const (
@@ -683,8 +789,9 @@ type LinuxSyscall struct {
Args []LinuxSeccompArg `json:"args,omitempty"`
}
-// LinuxIntelRdt has container runtime resource constraints for Intel RDT
-// CAT and MBA features which introduced in Linux 4.10 and 4.12 kernel
+// LinuxIntelRdt has container runtime resource constraints for Intel RDT CAT and MBA
+// features and flags enabling Intel RDT CMT and MBM features.
+// Intel RDT features are available in Linux 4.14 and newer kernel versions.
type LinuxIntelRdt struct {
// The identity for RDT Class of Service
ClosID string `json:"closID,omitempty"`
@@ -697,4 +804,76 @@ type LinuxIntelRdt struct {
// The unit of memory bandwidth is specified in "percentages" by
// default, and in "MBps" if MBA Software Controller is enabled.
MemBwSchema string `json:"memBwSchema,omitempty"`
+
+ // EnableCMT is the flag to indicate if the Intel RDT CMT is enabled. CMT (Cache Monitoring Technology) supports monitoring of
+ // the last-level cache (LLC) occupancy for the container.
+ EnableCMT bool `json:"enableCMT,omitempty"`
+
+ // EnableMBM is the flag to indicate if the Intel RDT MBM is enabled. MBM (Memory Bandwidth Monitoring) supports monitoring of
+ // total and local memory bandwidth for the container.
+ EnableMBM bool `json:"enableMBM,omitempty"`
}
+
+// ZOS contains platform-specific configuration for z/OS based containers.
+type ZOS struct {
+ // Devices are a list of device nodes that are created for the container
+ Devices []ZOSDevice `json:"devices,omitempty"`
+}
+
+// ZOSDevice represents the mknod information for a z/OS special device file
+type ZOSDevice struct {
+ // Path to the device.
+ Path string `json:"path"`
+ // Device type, block, char, etc.
+ Type string `json:"type"`
+ // Major is the device's major number.
+ Major int64 `json:"major"`
+ // Minor is the device's minor number.
+ Minor int64 `json:"minor"`
+ // FileMode permission bits for the device.
+ FileMode *os.FileMode `json:"fileMode,omitempty"`
+ // UID of the device.
+ UID *uint32 `json:"uid,omitempty"`
+ // Gid of the device.
+ GID *uint32 `json:"gid,omitempty"`
+}
+
+// LinuxSchedulerPolicy represents different scheduling policies used with the Linux Scheduler
+type LinuxSchedulerPolicy string
+
+const (
+ // SchedOther is the default scheduling policy
+ SchedOther LinuxSchedulerPolicy = "SCHED_OTHER"
+ // SchedFIFO is the First-In-First-Out scheduling policy
+ SchedFIFO LinuxSchedulerPolicy = "SCHED_FIFO"
+ // SchedRR is the Round-Robin scheduling policy
+ SchedRR LinuxSchedulerPolicy = "SCHED_RR"
+ // SchedBatch is the Batch scheduling policy
+ SchedBatch LinuxSchedulerPolicy = "SCHED_BATCH"
+ // SchedISO is the Isolation scheduling policy
+ SchedISO LinuxSchedulerPolicy = "SCHED_ISO"
+ // SchedIdle is the Idle scheduling policy
+ SchedIdle LinuxSchedulerPolicy = "SCHED_IDLE"
+ // SchedDeadline is the Deadline scheduling policy
+ SchedDeadline LinuxSchedulerPolicy = "SCHED_DEADLINE"
+)
+
+// LinuxSchedulerFlag represents the flags used by the Linux Scheduler.
+type LinuxSchedulerFlag string
+
+const (
+ // SchedFlagResetOnFork represents the reset on fork scheduling flag
+ SchedFlagResetOnFork LinuxSchedulerFlag = "SCHED_FLAG_RESET_ON_FORK"
+ // SchedFlagReclaim represents the reclaim scheduling flag
+ SchedFlagReclaim LinuxSchedulerFlag = "SCHED_FLAG_RECLAIM"
+ // SchedFlagDLOverrun represents the deadline overrun scheduling flag
+ SchedFlagDLOverrun LinuxSchedulerFlag = "SCHED_FLAG_DL_OVERRUN"
+ // SchedFlagKeepPolicy represents the keep policy scheduling flag
+ SchedFlagKeepPolicy LinuxSchedulerFlag = "SCHED_FLAG_KEEP_POLICY"
+ // SchedFlagKeepParams represents the keep parameters scheduling flag
+ SchedFlagKeepParams LinuxSchedulerFlag = "SCHED_FLAG_KEEP_PARAMS"
+ // SchedFlagUtilClampMin represents the utilization clamp minimum scheduling flag
+ SchedFlagUtilClampMin LinuxSchedulerFlag = "SCHED_FLAG_UTIL_CLAMP_MIN"
+ // SchedFlagUtilClampMin represents the utilization clamp maximum scheduling flag
+ SchedFlagUtilClampMax LinuxSchedulerFlag = "SCHED_FLAG_UTIL_CLAMP_MAX"
+)
diff --git a/vendor/github.com/opencontainers/runtime-spec/specs-go/version.go b/vendor/github.com/opencontainers/runtime-spec/specs-go/version.go
index 596af0c2f..b3fca349c 100644
--- a/vendor/github.com/opencontainers/runtime-spec/specs-go/version.go
+++ b/vendor/github.com/opencontainers/runtime-spec/specs-go/version.go
@@ -6,12 +6,12 @@ const (
// VersionMajor is for an API incompatible changes
VersionMajor = 1
// VersionMinor is for functionality in a backwards-compatible manner
- VersionMinor = 0
+ VersionMinor = 1
// VersionPatch is for backwards-compatible bug fixes
- VersionPatch = 2
+ VersionPatch = 0
// VersionDev indicates development branch. Releases will be empty string.
- VersionDev = "-dev"
+ VersionDev = ""
)
// Version is the specification version that the package types support.
diff --git a/vendor/github.com/pion/datachannel/.gitignore b/vendor/github.com/pion/datachannel/.gitignore
index 83db74ba5..f977e7485 100644
--- a/vendor/github.com/pion/datachannel/.gitignore
+++ b/vendor/github.com/pion/datachannel/.gitignore
@@ -22,3 +22,4 @@ cover.out
*.wasm
examples/sfu-ws/cert.pem
examples/sfu-ws/key.pem
+wasm_exec.js
diff --git a/vendor/github.com/pion/datachannel/.golangci.yml b/vendor/github.com/pion/datachannel/.golangci.yml
index d6162c970..d7a88eca3 100644
--- a/vendor/github.com/pion/datachannel/.golangci.yml
+++ b/vendor/github.com/pion/datachannel/.golangci.yml
@@ -15,14 +15,22 @@ linters-settings:
linters:
enable:
- asciicheck # Simple linter to check that your code does not contain non-ASCII identifiers
+ - bidichk # Checks for dangerous unicode character sequences
- bodyclose # checks whether HTTP response body is closed successfully
+ - contextcheck # check the function whether use a non-inherited context
- deadcode # Finds unused code
+ - decorder # check declaration order and count of types, constants, variables and functions
- depguard # Go linter that checks if package imports are in a list of acceptable packages
- dogsled # Checks assignments with too many blank identifiers (e.g. x, _, _, _, := f())
- dupl # Tool for code clone detection
+ - durationcheck # check for two durations multiplied together
- errcheck # Errcheck is a program for checking for unchecked errors in go programs. These unchecked errors can be critical bugs in some cases
+ - errchkjson # Checks types passed to the json encoding functions. Reports unsupported types and optionally reports occations, where the check for the returned error can be omitted.
+ - errname # Checks that sentinel errors are prefixed with the `Err` and error types are suffixed with the `Error`.
+ - errorlint # errorlint is a linter for that can be used to find code that will cause problems with the error wrapping scheme introduced in Go 1.13.
- exhaustive # check exhaustiveness of enum switch statements
- exportloopref # checks for pointers to enclosing loop variables
+ - forcetypeassert # finds forced type assertions
- gci # Gci control golang package import order and make it always deterministic.
- gochecknoglobals # Checks that no globals are present in Go code
- gochecknoinits # Checks that no init functions are present in Go code
@@ -35,40 +43,62 @@ linters:
- gofumpt # Gofumpt checks whether code was gofumpt-ed.
- goheader # Checks is file header matches to pattern
- goimports # Goimports does everything that gofmt does. Additionally it checks unused imports
- - golint # Golint differs from gofmt. Gofmt reformats Go source code, whereas golint prints out style mistakes
+ - gomoddirectives # Manage the use of 'replace', 'retract', and 'excludes' directives in go.mod.
- gomodguard # Allow and block list linter for direct Go module dependencies. This is different from depguard where there are different block types for example version constraints and module recommendations.
- goprintffuncname # Checks that printf-like functions are named with `f` at the end
- gosec # Inspects source code for security problems
- gosimple # Linter for Go source code that specializes in simplifying a code
- govet # Vet examines Go source code and reports suspicious constructs, such as Printf calls whose arguments do not align with the format string
+ - grouper # An analyzer to analyze expression groups.
+ - importas # Enforces consistent import aliases
- ineffassign # Detects when assignments to existing variables are not used
- misspell # Finds commonly misspelled English words in comments
- nakedret # Finds naked returns in functions greater than a specified function length
+ - nilerr # Finds the code that returns nil even if it checks that the error is not nil.
+ - nilnil # Checks that there is no simultaneous return of `nil` error and an invalid value.
- noctx # noctx finds sending http request without context.Context
- - scopelint # Scopelint checks for unpinned variables in go programs
+ - predeclared # find code that shadows one of Go's predeclared identifiers
+ - revive # golint replacement, finds style mistakes
- staticcheck # Staticcheck is a go vet on steroids, applying a ton of static analysis checks
- structcheck # Finds unused struct fields
- stylecheck # Stylecheck is a replacement for golint
+ - tagliatelle # Checks the struct tags.
+ - tenv # tenv is analyzer that detects using os.Setenv instead of t.Setenv since Go1.17
+ - tparallel # tparallel detects inappropriate usage of t.Parallel() method in your Go test codes
- typecheck # Like the front-end of a Go compiler, parses and type-checks Go code
- unconvert # Remove unnecessary type conversions
- unparam # Reports unused function parameters
- unused # Checks Go code for unused constants, variables, functions and types
- varcheck # Finds unused global variables and constants
+ - wastedassign # wastedassign finds wasted assignment statements
- whitespace # Tool for detection of leading and trailing whitespace
disable:
+ - containedctx # containedctx is a linter that detects struct contained context.Context field
+ - cyclop # checks function and package cyclomatic complexity
+ - exhaustivestruct # Checks if all struct's fields are initialized
+ - forbidigo # Forbids identifiers
- funlen # Tool for detection of long functions
- gocyclo # Computes and checks the cyclomatic complexity of functions
- godot # Check if comments end in a period
- gomnd # An analyzer to detect magic numbers.
+ - ifshort # Checks that your code uses short syntax for if-statements whenever possible
+ - ireturn # Accept Interfaces, Return Concrete Types
- lll # Reports long lines
+ - maintidx # maintidx measures the maintainability index of each function.
+ - makezero # Finds slice declarations with non-zero initial length
- maligned # Tool to detect Go structs that would take less memory if their fields were sorted
- nestif # Reports deeply nested if statements
- nlreturn # nlreturn checks for a new line before return and branch statements to increase code clarity
- nolintlint # Reports ill-formed or insufficient nolint directives
+ - paralleltest # paralleltest detects missing usage of t.Parallel() method in your Go test
- prealloc # Finds slice declarations that could potentially be preallocated
+ - promlinter # Check Prometheus metrics naming via promlint
- rowserrcheck # checks whether Err of rows is checked successfully
- sqlclosecheck # Checks that sql.Rows and sql.Stmt are closed.
- testpackage # linter that makes you use a separate _test package
+ - thelper # thelper detects golang test helpers without t.Helper() call and checks the consistency of test helpers
+ - varnamelen # checks that the length of a variable's name matches its scope
+ - wrapcheck # Checks that errors returned from external packages are wrapped
- wsl # Whitespace Linter - Forces you to use empty lines!
issues:
diff --git a/vendor/github.com/pion/datachannel/AUTHORS.txt b/vendor/github.com/pion/datachannel/AUTHORS.txt
index 92073e2c1..c5d9d8d34 100644
--- a/vendor/github.com/pion/datachannel/AUTHORS.txt
+++ b/vendor/github.com/pion/datachannel/AUTHORS.txt
@@ -6,6 +6,7 @@
Atsushi Watanabe
backkem
Benny Daon
+Chinmay Kousik
Eric Daniels
Hugo Arregui
Hugo Arregui
diff --git a/vendor/github.com/pion/datachannel/datachannel.go b/vendor/github.com/pion/datachannel/datachannel.go
index 11f30cc78..0b125d662 100644
--- a/vendor/github.com/pion/datachannel/datachannel.go
+++ b/vendor/github.com/pion/datachannel/datachannel.go
@@ -2,10 +2,12 @@
package datachannel
import (
+ "errors"
"fmt"
"io"
"sync"
"sync/atomic"
+ "time"
"github.com/pion/logging"
"github.com/pion/sctp"
@@ -19,6 +21,11 @@ type Reader interface {
ReadDataChannel([]byte) (int, bool, error)
}
+// ReadDeadliner extends an io.Reader to expose setting a read deadline.
+type ReadDeadliner interface {
+ SetReadDeadline(time.Time) error
+}
+
// Writer is an extended io.Writer
// that also allows indicating if a message is text.
type Writer interface {
@@ -184,7 +191,7 @@ func (c *DataChannel) Read(p []byte) (int, error) {
func (c *DataChannel) ReadDataChannel(p []byte) (int, bool, error) {
for {
n, ppi, err := c.stream.ReadSCTP(p)
- if err == io.EOF {
+ if errors.Is(err, io.EOF) {
// When the peer sees that an incoming stream was
// reset, it also resets its corresponding outgoing stream.
if closeErr := c.stream.Close(); closeErr != nil {
@@ -212,6 +219,11 @@ func (c *DataChannel) ReadDataChannel(p []byte) (int, bool, error) {
}
}
+// SetReadDeadline sets a deadline for reads to return
+func (c *DataChannel) SetReadDeadline(t time.Time) error {
+ return c.stream.SetReadDeadline(t)
+}
+
// MessagesSent returns the number of messages sent
func (c *DataChannel) MessagesSent() uint32 {
return atomic.LoadUint32(&c.messagesSent)
diff --git a/vendor/github.com/pion/datachannel/message_channel_open.go b/vendor/github.com/pion/datachannel/message_channel_open.go
index c257bea8d..5eb58633c 100644
--- a/vendor/github.com/pion/datachannel/message_channel_open.go
+++ b/vendor/github.com/pion/datachannel/message_channel_open.go
@@ -8,8 +8,9 @@ import (
/*
channelOpen represents a DATA_CHANNEL_OPEN Message
- 0 1 2 3
- 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+ 0 1 2 3
+ 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1
+
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
| Message Type | Channel Type | Priority |
+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+
diff --git a/vendor/github.com/pion/datachannel/renovate.json b/vendor/github.com/pion/datachannel/renovate.json
index 08c1e39d6..f1614058a 100644
--- a/vendor/github.com/pion/datachannel/renovate.json
+++ b/vendor/github.com/pion/datachannel/renovate.json
@@ -1,6 +1,7 @@
{
"extends": [
- "config:base"
+ "config:base",
+ ":disableDependencyDashboard"
],
"postUpdateOptions": [
"gomodTidy"
diff --git a/vendor/github.com/pion/dtls/v2/.editorconfig b/vendor/github.com/pion/dtls/v2/.editorconfig
index d2b32061a..1dca00f8a 100644
--- a/vendor/github.com/pion/dtls/v2/.editorconfig
+++ b/vendor/github.com/pion/dtls/v2/.editorconfig
@@ -1,4 +1,6 @@
# http://editorconfig.org/
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
root = true
diff --git a/vendor/github.com/pion/dtls/v2/.gitignore b/vendor/github.com/pion/dtls/v2/.gitignore
index 83db74ba5..6e2f206a9 100644
--- a/vendor/github.com/pion/dtls/v2/.gitignore
+++ b/vendor/github.com/pion/dtls/v2/.gitignore
@@ -1,3 +1,6 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
### JetBrains IDE ###
#####################
.idea/
@@ -22,3 +25,4 @@ cover.out
*.wasm
examples/sfu-ws/cert.pem
examples/sfu-ws/key.pem
+wasm_exec.js
diff --git a/vendor/github.com/pion/dtls/v2/.golangci.yml b/vendor/github.com/pion/dtls/v2/.golangci.yml
index d6162c970..4e3eddf42 100644
--- a/vendor/github.com/pion/dtls/v2/.golangci.yml
+++ b/vendor/github.com/pion/dtls/v2/.golangci.yml
@@ -1,3 +1,6 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
linters-settings:
govet:
check-shadowing: true
@@ -10,19 +13,34 @@ linters-settings:
modules:
- github.com/pkg/errors:
recommendations:
- - errors
+ - errors
+ forbidigo:
+ forbid:
+ - ^fmt.Print(f|ln)?$
+ - ^log.(Panic|Fatal|Print)(f|ln)?$
+ - ^os.Exit$
+ - ^panic$
+ - ^print(ln)?$
linters:
enable:
- asciicheck # Simple linter to check that your code does not contain non-ASCII identifiers
+ - bidichk # Checks for dangerous unicode character sequences
- bodyclose # checks whether HTTP response body is closed successfully
- - deadcode # Finds unused code
+ - contextcheck # check the function whether use a non-inherited context
+ - decorder # check declaration order and count of types, constants, variables and functions
- depguard # Go linter that checks if package imports are in a list of acceptable packages
- dogsled # Checks assignments with too many blank identifiers (e.g. x, _, _, _, := f())
- dupl # Tool for code clone detection
+ - durationcheck # check for two durations multiplied together
- errcheck # Errcheck is a program for checking for unchecked errors in go programs. These unchecked errors can be critical bugs in some cases
+ - errchkjson # Checks types passed to the json encoding functions. Reports unsupported types and optionally reports occations, where the check for the returned error can be omitted.
+ - errname # Checks that sentinel errors are prefixed with the `Err` and error types are suffixed with the `Error`.
+ - errorlint # errorlint is a linter for that can be used to find code that will cause problems with the error wrapping scheme introduced in Go 1.13.
- exhaustive # check exhaustiveness of enum switch statements
- exportloopref # checks for pointers to enclosing loop variables
+ - forbidigo # Forbids identifiers
+ - forcetypeassert # finds forced type assertions
- gci # Gci control golang package import order and make it always deterministic.
- gochecknoglobals # Checks that no globals are present in Go code
- gochecknoinits # Checks that no init functions are present in Go code
@@ -35,40 +53,59 @@ linters:
- gofumpt # Gofumpt checks whether code was gofumpt-ed.
- goheader # Checks is file header matches to pattern
- goimports # Goimports does everything that gofmt does. Additionally it checks unused imports
- - golint # Golint differs from gofmt. Gofmt reformats Go source code, whereas golint prints out style mistakes
+ - gomoddirectives # Manage the use of 'replace', 'retract', and 'excludes' directives in go.mod.
- gomodguard # Allow and block list linter for direct Go module dependencies. This is different from depguard where there are different block types for example version constraints and module recommendations.
- goprintffuncname # Checks that printf-like functions are named with `f` at the end
- gosec # Inspects source code for security problems
- gosimple # Linter for Go source code that specializes in simplifying a code
- govet # Vet examines Go source code and reports suspicious constructs, such as Printf calls whose arguments do not align with the format string
+ - grouper # An analyzer to analyze expression groups.
+ - importas # Enforces consistent import aliases
- ineffassign # Detects when assignments to existing variables are not used
- misspell # Finds commonly misspelled English words in comments
- nakedret # Finds naked returns in functions greater than a specified function length
+ - nilerr # Finds the code that returns nil even if it checks that the error is not nil.
+ - nilnil # Checks that there is no simultaneous return of `nil` error and an invalid value.
- noctx # noctx finds sending http request without context.Context
- - scopelint # Scopelint checks for unpinned variables in go programs
+ - predeclared # find code that shadows one of Go's predeclared identifiers
+ - revive # golint replacement, finds style mistakes
- staticcheck # Staticcheck is a go vet on steroids, applying a ton of static analysis checks
- - structcheck # Finds unused struct fields
- stylecheck # Stylecheck is a replacement for golint
+ - tagliatelle # Checks the struct tags.
+ - tenv # tenv is analyzer that detects using os.Setenv instead of t.Setenv since Go1.17
+ - tparallel # tparallel detects inappropriate usage of t.Parallel() method in your Go test codes
- typecheck # Like the front-end of a Go compiler, parses and type-checks Go code
- unconvert # Remove unnecessary type conversions
- unparam # Reports unused function parameters
- unused # Checks Go code for unused constants, variables, functions and types
- - varcheck # Finds unused global variables and constants
+ - wastedassign # wastedassign finds wasted assignment statements
- whitespace # Tool for detection of leading and trailing whitespace
disable:
+ - containedctx # containedctx is a linter that detects struct contained context.Context field
+ - cyclop # checks function and package cyclomatic complexity
+ - exhaustivestruct # Checks if all struct's fields are initialized
- funlen # Tool for detection of long functions
- gocyclo # Computes and checks the cyclomatic complexity of functions
- godot # Check if comments end in a period
- gomnd # An analyzer to detect magic numbers.
+ - ifshort # Checks that your code uses short syntax for if-statements whenever possible
+ - ireturn # Accept Interfaces, Return Concrete Types
- lll # Reports long lines
+ - maintidx # maintidx measures the maintainability index of each function.
+ - makezero # Finds slice declarations with non-zero initial length
- maligned # Tool to detect Go structs that would take less memory if their fields were sorted
- nestif # Reports deeply nested if statements
- nlreturn # nlreturn checks for a new line before return and branch statements to increase code clarity
- nolintlint # Reports ill-formed or insufficient nolint directives
+ - paralleltest # paralleltest detects missing usage of t.Parallel() method in your Go test
- prealloc # Finds slice declarations that could potentially be preallocated
+ - promlinter # Check Prometheus metrics naming via promlint
- rowserrcheck # checks whether Err of rows is checked successfully
- sqlclosecheck # Checks that sql.Rows and sql.Stmt are closed.
- testpackage # linter that makes you use a separate _test package
+ - thelper # thelper detects golang test helpers without t.Helper() call and checks the consistency of test helpers
+ - varnamelen # checks that the length of a variable's name matches its scope
+ - wrapcheck # Checks that errors returned from external packages are wrapped
- wsl # Whitespace Linter - Forces you to use empty lines!
issues:
@@ -78,12 +115,23 @@ issues:
- path: _test\.go
linters:
- gocognit
+ - forbidigo
# Allow complex main function in examples
- path: examples
text: "of func `main` is high"
linters:
- gocognit
+
+ # Allow forbidden identifiers in examples
+ - path: examples
+ linters:
+ - forbidigo
+
+ # Allow forbidden identifiers in CLI commands
+ - path: cmd
+ linters:
+ - forbidigo
run:
skip-dirs-use-default: false
diff --git a/vendor/github.com/pion/dtls/v2/.goreleaser.yml b/vendor/github.com/pion/dtls/v2/.goreleaser.yml
new file mode 100644
index 000000000..30093e9d6
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/.goreleaser.yml
@@ -0,0 +1,5 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
+builds:
+- skip: true
diff --git a/vendor/github.com/pion/dtls/v2/AUTHORS.txt b/vendor/github.com/pion/dtls/v2/AUTHORS.txt
index a8e6fb46f..e14fae4c0 100644
--- a/vendor/github.com/pion/dtls/v2/AUTHORS.txt
+++ b/vendor/github.com/pion/dtls/v2/AUTHORS.txt
@@ -2,7 +2,7 @@
# we would love to have you https://github.com/pion/webrtc/wiki/Contributing
#
# This file is auto generated, using git to list all individuals contributors.
-# see `.github/generate-authors.sh` for the scripting
+# see https://github.com/pion/.goassets/blob/master/scripts/generate-authors.sh for the scripting
Aleksandr Razumov
alvarowolfx
Arlo Breault
@@ -14,6 +14,7 @@ Bragadeesh
Carson Hoffman
Cecylia Bocovich
Chris Hiszpanski
+cnderrauber
Daniele Sluijters
folbrich
Hayden James
@@ -27,19 +28,30 @@ Jim Wert
jinleileiking
Jozef Kralik
Julien Salleyron
+Juliusz Chroboczek
Kegan Dougal
+Kevin Wang
Lander Noterman
Len
Lukas Lihotzki
+ManuelBk <26275612+ManuelBk@users.noreply.github.com>
Michael Zabka
Michiel De Backker
+Rachel Chen
Robert Eperjesi
Ryan Gordon
+Sam Lancia
+Sean DuBois
Sean DuBois
Sean DuBois
+Shelikhoo
Stefan Tatschner
+Steffen Vogel
Vadim
Vadim Filimonov
wmiao
ZHENK
吕海涛
+
+# List of contributors not appearing in Git history
+
diff --git a/vendor/github.com/pion/dtls/v2/LICENSE b/vendor/github.com/pion/dtls/v2/LICENSE
index ab602974d..491caf6b0 100644
--- a/vendor/github.com/pion/dtls/v2/LICENSE
+++ b/vendor/github.com/pion/dtls/v2/LICENSE
@@ -1,21 +1,9 @@
MIT License
-Copyright (c) 2018
+Copyright (c) 2023 The Pion community
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
diff --git a/vendor/github.com/pion/dtls/v2/Makefile b/vendor/github.com/pion/dtls/v2/Makefile
deleted file mode 100644
index 1df38b223..000000000
--- a/vendor/github.com/pion/dtls/v2/Makefile
+++ /dev/null
@@ -1,6 +0,0 @@
-fuzz-build-record-layer: fuzz-prepare
- go-fuzz-build -tags gofuzz -func FuzzRecordLayer
-fuzz-run-record-layer:
- go-fuzz -bin dtls-fuzz.zip -workdir fuzz
-fuzz-prepare:
- @GO111MODULE=on go mod vendor
diff --git a/vendor/github.com/pion/dtls/v2/README.md b/vendor/github.com/pion/dtls/v2/README.md
index d6da5b33a..0c0659593 100644
--- a/vendor/github.com/pion/dtls/v2/README.md
+++ b/vendor/github.com/pion/dtls/v2/README.md
@@ -9,11 +9,10 @@
-
-
+
+
-
-
+
@@ -22,7 +21,22 @@ Native [DTLS 1.2][rfc6347] implementation in the Go programming language.
A long term goal is a professional security review, and maybe an inclusion in stdlib.
+### RFCs
+#### Implemented
+- **RFC 6347**: [Datagram Transport Layer Security Version 1.2][rfc6347]
+- **RFC 5705**: [Keying Material Exporters for Transport Layer Security (TLS)][rfc5705]
+- **RFC 7627**: [Transport Layer Security (TLS) - Session Hash and Extended Master Secret Extension][rfc7627]
+- **RFC 7301**: [Transport Layer Security (TLS) - Application-Layer Protocol Negotiation Extension][rfc7301]
+
+[rfc5289]: https://tools.ietf.org/html/rfc5289
+[rfc5487]: https://tools.ietf.org/html/rfc5487
+[rfc5489]: https://tools.ietf.org/html/rfc5489
+[rfc5705]: https://tools.ietf.org/html/rfc5705
[rfc6347]: https://tools.ietf.org/html/rfc6347
+[rfc6655]: https://tools.ietf.org/html/rfc6655
+[rfc7301]: https://tools.ietf.org/html/rfc7301
+[rfc7627]: https://tools.ietf.org/html/rfc7627
+[rfc8422]: https://tools.ietf.org/html/rfc8422
### Goals/Progress
This will only be targeting DTLS 1.2, and the most modern/common cipher suites.
@@ -37,13 +51,10 @@ We would love contributions that fall under the 'Planned Features' and any bug f
* Extended Master Secret extension ([RFC 7627][rfc7627])
* ALPN extension ([RFC 7301][rfc7301])
-[rfc5705]: https://tools.ietf.org/html/rfc5705
-[rfc7627]: https://tools.ietf.org/html/rfc7627
-[rfc7301]: https://tools.ietf.org/html/rfc7301
-
#### Supported ciphers
##### ECDHE
+
* TLS_ECDHE_ECDSA_WITH_AES_128_CCM ([RFC 6655][rfc6655])
* TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 ([RFC 6655][rfc6655])
* TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 ([RFC 5289][rfc5289])
@@ -54,15 +65,16 @@ We would love contributions that fall under the 'Planned Features' and any bug f
* TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA ([RFC 8422][rfc8422])
##### PSK
+
* TLS_PSK_WITH_AES_128_CCM ([RFC 6655][rfc6655])
* TLS_PSK_WITH_AES_128_CCM_8 ([RFC 6655][rfc6655])
+* TLS_PSK_WITH_AES_256_CCM_8 ([RFC 6655][rfc6655])
* TLS_PSK_WITH_AES_128_GCM_SHA256 ([RFC 5487][rfc5487])
* TLS_PSK_WITH_AES_128_CBC_SHA256 ([RFC 5487][rfc5487])
-[rfc5289]: https://tools.ietf.org/html/rfc5289
-[rfc8422]: https://tools.ietf.org/html/rfc8422
-[rfc6655]: https://tools.ietf.org/html/rfc6655
-[rfc5487]: https://tools.ietf.org/html/rfc5487
+##### ECDHE & PSK
+
+* TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 ([RFC 5489][rfc5489])
#### Planned Features
* Chacha20Poly1305
@@ -106,7 +118,6 @@ Pion DTLS can connect to itself and OpenSSL.
### Using with PSK
Pion DTLS also comes with examples that do key exchange via PSK
-
#### Pion DTLS
```sh
go run examples/listen/psk/main.go
@@ -125,8 +136,16 @@ go run examples/dial/psk/main.go
openssl s_client -dtls1_2 -connect 127.0.0.1:4444 -psk abc123 -cipher PSK-AES128-CCM8
```
+### Community
+Pion has an active community on the [Slack](https://pion.ly/slack).
+
+Follow the [Pion Twitter](https://twitter.com/_pion) for project updates and important WebRTC news.
+
+We are always looking to support **your projects**. Please reach out if you have something to build!
+If you need commercial support or don't want to use public methods you can contact us at [team@pion.ly](mailto:team@pion.ly)
+
### Contributing
-Check out the **[contributing wiki](https://github.com/pion/webrtc/wiki/Contributing)** to join the group of amazing people making this project possible:
+Check out the [contributing wiki](https://github.com/pion/webrtc/wiki/Contributing) to join the group of amazing people making this project possible: [AUTHORS.txt](./AUTHORS.txt)
### License
MIT License - see [LICENSE](LICENSE) for full text
diff --git a/vendor/github.com/pion/dtls/v2/certificate.go b/vendor/github.com/pion/dtls/v2/certificate.go
index c99e1c93d..519fc875f 100644
--- a/vendor/github.com/pion/dtls/v2/certificate.go
+++ b/vendor/github.com/pion/dtls/v2/certificate.go
@@ -1,35 +1,105 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
+ "bytes"
"crypto/tls"
"crypto/x509"
+ "fmt"
"strings"
)
-func (c *handshakeConfig) getCertificate(serverName string) (*tls.Certificate, error) {
+// ClientHelloInfo contains information from a ClientHello message in order to
+// guide application logic in the GetCertificate.
+type ClientHelloInfo struct {
+ // ServerName indicates the name of the server requested by the client
+ // in order to support virtual hosting. ServerName is only set if the
+ // client is using SNI (see RFC 4366, Section 3.1).
+ ServerName string
+
+ // CipherSuites lists the CipherSuites supported by the client (e.g.
+ // TLS_AES_128_GCM_SHA256, TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256).
+ CipherSuites []CipherSuiteID
+}
+
+// CertificateRequestInfo contains information from a server's
+// CertificateRequest message, which is used to demand a certificate and proof
+// of control from a client.
+type CertificateRequestInfo struct {
+ // AcceptableCAs contains zero or more, DER-encoded, X.501
+ // Distinguished Names. These are the names of root or intermediate CAs
+ // that the server wishes the returned certificate to be signed by. An
+ // empty slice indicates that the server has no preference.
+ AcceptableCAs [][]byte
+}
+
+// SupportsCertificate returns nil if the provided certificate is supported by
+// the server that sent the CertificateRequest. Otherwise, it returns an error
+// describing the reason for the incompatibility.
+// NOTE: original src: https://github.com/golang/go/blob/29b9a328d268d53833d2cc063d1d8b4bf6852675/src/crypto/tls/common.go#L1273
+func (cri *CertificateRequestInfo) SupportsCertificate(c *tls.Certificate) error {
+ if len(cri.AcceptableCAs) == 0 {
+ return nil
+ }
+
+ for j, cert := range c.Certificate {
+ x509Cert := c.Leaf
+ // Parse the certificate if this isn't the leaf node, or if
+ // chain.Leaf was nil.
+ if j != 0 || x509Cert == nil {
+ var err error
+ if x509Cert, err = x509.ParseCertificate(cert); err != nil {
+ return fmt.Errorf("failed to parse certificate #%d in the chain: %w", j, err)
+ }
+ }
+
+ for _, ca := range cri.AcceptableCAs {
+ if bytes.Equal(x509Cert.RawIssuer, ca) {
+ return nil
+ }
+ }
+ }
+ return errNotAcceptableCertificateChain
+}
+
+func (c *handshakeConfig) setNameToCertificateLocked() {
+ nameToCertificate := make(map[string]*tls.Certificate)
+ for i := range c.localCertificates {
+ cert := &c.localCertificates[i]
+ x509Cert := cert.Leaf
+ if x509Cert == nil {
+ var parseErr error
+ x509Cert, parseErr = x509.ParseCertificate(cert.Certificate[0])
+ if parseErr != nil {
+ continue
+ }
+ }
+ if len(x509Cert.Subject.CommonName) > 0 {
+ nameToCertificate[strings.ToLower(x509Cert.Subject.CommonName)] = cert
+ }
+ for _, san := range x509Cert.DNSNames {
+ nameToCertificate[strings.ToLower(san)] = cert
+ }
+ }
+ c.nameToCertificate = nameToCertificate
+}
+
+func (c *handshakeConfig) getCertificate(clientHelloInfo *ClientHelloInfo) (*tls.Certificate, error) {
c.mu.Lock()
defer c.mu.Unlock()
- if c.nameToCertificate == nil {
- nameToCertificate := make(map[string]*tls.Certificate)
- for i := range c.localCertificates {
- cert := &c.localCertificates[i]
- x509Cert := cert.Leaf
- if x509Cert == nil {
- var parseErr error
- x509Cert, parseErr = x509.ParseCertificate(cert.Certificate[0])
- if parseErr != nil {
- continue
- }
- }
- if len(x509Cert.Subject.CommonName) > 0 {
- nameToCertificate[strings.ToLower(x509Cert.Subject.CommonName)] = cert
- }
- for _, san := range x509Cert.DNSNames {
- nameToCertificate[strings.ToLower(san)] = cert
- }
+ if c.localGetCertificate != nil &&
+ (len(c.localCertificates) == 0 || len(clientHelloInfo.ServerName) > 0) {
+ cert, err := c.localGetCertificate(clientHelloInfo)
+ if cert != nil || err != nil {
+ return cert, err
}
- c.nameToCertificate = nameToCertificate
+ }
+
+ if c.nameToCertificate == nil {
+ c.setNameToCertificateLocked()
}
if len(c.localCertificates) == 0 {
@@ -41,11 +111,11 @@ func (c *handshakeConfig) getCertificate(serverName string) (*tls.Certificate, e
return &c.localCertificates[0], nil
}
- if len(serverName) == 0 {
+ if len(clientHelloInfo.ServerName) == 0 {
return &c.localCertificates[0], nil
}
- name := strings.TrimRight(strings.ToLower(serverName), ".")
+ name := strings.TrimRight(strings.ToLower(clientHelloInfo.ServerName), ".")
if cert, ok := c.nameToCertificate[name]; ok {
return cert, nil
@@ -65,3 +135,23 @@ func (c *handshakeConfig) getCertificate(serverName string) (*tls.Certificate, e
// If nothing matches, return the first certificate.
return &c.localCertificates[0], nil
}
+
+// NOTE: original src: https://github.com/golang/go/blob/29b9a328d268d53833d2cc063d1d8b4bf6852675/src/crypto/tls/handshake_client.go#L974
+func (c *handshakeConfig) getClientCertificate(cri *CertificateRequestInfo) (*tls.Certificate, error) {
+ c.mu.Lock()
+ defer c.mu.Unlock()
+ if c.localGetClientCertificate != nil {
+ return c.localGetClientCertificate(cri)
+ }
+
+ for i := range c.localCertificates {
+ chain := c.localCertificates[i]
+ if err := cri.SupportsCertificate(&chain); err != nil {
+ continue
+ }
+ return &chain, nil
+ }
+
+ // No acceptable certificate found. Don't send a certificate.
+ return new(tls.Certificate), nil
+}
diff --git a/vendor/github.com/pion/dtls/v2/cipher_suite.go b/vendor/github.com/pion/dtls/v2/cipher_suite.go
index 5f35a8504..7a5bb4a58 100644
--- a/vendor/github.com/pion/dtls/v2/cipher_suite.go
+++ b/vendor/github.com/pion/dtls/v2/cipher_suite.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -19,24 +22,27 @@ type CipherSuiteID = ciphersuite.ID
// Supported Cipher Suites
const (
// AES-128-CCM
- TLS_ECDHE_ECDSA_WITH_AES_128_CCM CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM //nolint:golint,stylecheck
- TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_CCM CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM //nolint:revive,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 //nolint:revive,stylecheck
// AES-128-GCM-SHA256
- TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 //nolint:revive,stylecheck
- TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 //nolint:revive,stylecheck
// AES-256-CBC-SHA
- TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA CipherSuiteID = ciphersuite.TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA CipherSuiteID = ciphersuite.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA //nolint:revive,stylecheck
- TLS_PSK_WITH_AES_128_CCM CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CCM //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_CCM_8 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CCM_8 //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_GCM_SHA256 //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_CBC_SHA256 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CBC_SHA256 //nolint:golint,stylecheck
+ TLS_PSK_WITH_AES_128_CCM CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CCM //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_CCM_8 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CCM_8 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_256_CCM_8 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_256_CCM_8 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_GCM_SHA256 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_GCM_SHA256 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_CBC_SHA256 CipherSuiteID = ciphersuite.TLS_PSK_WITH_AES_128_CBC_SHA256 //nolint:revive,stylecheck
+
+ TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 CipherSuiteID = ciphersuite.TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 //nolint:revive,stylecheck
)
// CipherSuiteAuthenticationType controls what authentication method is using during the handshake for a CipherSuite
@@ -49,6 +55,16 @@ const (
CipherSuiteAuthenticationTypeAnonymous CipherSuiteAuthenticationType = ciphersuite.AuthenticationTypeAnonymous
)
+// CipherSuiteKeyExchangeAlgorithm controls what exchange algorithm is using during the handshake for a CipherSuite
+type CipherSuiteKeyExchangeAlgorithm = ciphersuite.KeyExchangeAlgorithm
+
+// CipherSuiteKeyExchangeAlgorithm Bitmask
+const (
+ CipherSuiteKeyExchangeAlgorithmNone CipherSuiteKeyExchangeAlgorithm = ciphersuite.KeyExchangeAlgorithmNone
+ CipherSuiteKeyExchangeAlgorithmPsk CipherSuiteKeyExchangeAlgorithm = ciphersuite.KeyExchangeAlgorithmPsk
+ CipherSuiteKeyExchangeAlgorithmEcdhe CipherSuiteKeyExchangeAlgorithm = ciphersuite.KeyExchangeAlgorithmEcdhe
+)
+
var _ = allCipherSuites() // Necessary until this function isn't only used by Go 1.14
// CipherSuite is an interface that all DTLS CipherSuites must satisfy
@@ -68,6 +84,13 @@ type CipherSuite interface {
// AuthenticationType controls what authentication method is using during the handshake
AuthenticationType() CipherSuiteAuthenticationType
+ // KeyExchangeAlgorithm controls what exchange algorithm is using during the handshake
+ KeyExchangeAlgorithm() CipherSuiteKeyExchangeAlgorithm
+
+ // ECC (Elliptic Curve Cryptography) determines whether ECC extesions will be send during handshake.
+ // https://datatracker.ietf.org/doc/html/rfc4492#page-10
+ ECC() bool
+
// Called when keying material has been generated, should initialize the internal cipher
Init(masterSecret, clientRandom, serverRandom []byte, isClient bool) error
IsInitialized() bool
@@ -109,6 +132,8 @@ func cipherSuiteForID(id CipherSuiteID, customCiphers func() []CipherSuite) Ciph
return ciphersuite.NewTLSPskWithAes128Ccm()
case TLS_PSK_WITH_AES_128_CCM_8:
return ciphersuite.NewTLSPskWithAes128Ccm8()
+ case TLS_PSK_WITH_AES_256_CCM_8:
+ return ciphersuite.NewTLSPskWithAes256Ccm8()
case TLS_PSK_WITH_AES_128_GCM_SHA256:
return &ciphersuite.TLSPskWithAes128GcmSha256{}
case TLS_PSK_WITH_AES_128_CBC_SHA256:
@@ -117,6 +142,8 @@ func cipherSuiteForID(id CipherSuiteID, customCiphers func() []CipherSuite) Ciph
return &ciphersuite.TLSEcdheEcdsaWithAes256GcmSha384{}
case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384:
return &ciphersuite.TLSEcdheRsaWithAes256GcmSha384{}
+ case TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256:
+ return ciphersuite.NewTLSEcdhePskWithAes128CbcSha256()
}
if customCiphers != nil {
@@ -152,6 +179,7 @@ func allCipherSuites() []CipherSuite {
&ciphersuite.TLSEcdheRsaWithAes256CbcSha{},
ciphersuite.NewTLSPskWithAes128Ccm(),
ciphersuite.NewTLSPskWithAes128Ccm8(),
+ ciphersuite.NewTLSPskWithAes256Ccm8(),
&ciphersuite.TLSPskWithAes128GcmSha256{},
&ciphersuite.TLSEcdheEcdsaWithAes256GcmSha384{},
&ciphersuite.TLSEcdheRsaWithAes256GcmSha384{},
@@ -172,7 +200,7 @@ func parseCipherSuites(userSelectedSuites []CipherSuiteID, customCipherSuites fu
for _, id := range ids {
c := cipherSuiteForID(id, nil)
if c == nil {
- return nil, &invalidCipherSuite{id}
+ return nil, &invalidCipherSuiteError{id}
}
cipherSuites = append(cipherSuites, c)
}
diff --git a/vendor/github.com/pion/dtls/v2/cipher_suite_go114.go b/vendor/github.com/pion/dtls/v2/cipher_suite_go114.go
index 5c63c0913..fd46d7bd9 100644
--- a/vendor/github.com/pion/dtls/v2/cipher_suite_go114.go
+++ b/vendor/github.com/pion/dtls/v2/cipher_suite_go114.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
//go:build go1.14
// +build go1.14
diff --git a/vendor/github.com/pion/dtls/v2/codecov.yml b/vendor/github.com/pion/dtls/v2/codecov.yml
index 085200a48..263e4d45c 100644
--- a/vendor/github.com/pion/dtls/v2/codecov.yml
+++ b/vendor/github.com/pion/dtls/v2/codecov.yml
@@ -3,6 +3,8 @@
#
# It is automatically copied from https://github.com/pion/.goassets repository.
#
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
coverage:
status:
diff --git a/vendor/github.com/pion/dtls/v2/compression_method.go b/vendor/github.com/pion/dtls/v2/compression_method.go
index 693eb7a52..7e44de009 100644
--- a/vendor/github.com/pion/dtls/v2/compression_method.go
+++ b/vendor/github.com/pion/dtls/v2/compression_method.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import "github.com/pion/dtls/v2/pkg/protocol"
diff --git a/vendor/github.com/pion/dtls/v2/config.go b/vendor/github.com/pion/dtls/v2/config.go
index 7f68c03b1..fbc3ee247 100644
--- a/vendor/github.com/pion/dtls/v2/config.go
+++ b/vendor/github.com/pion/dtls/v2/config.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -10,6 +13,7 @@ import (
"io"
"time"
+ "github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/logging"
)
@@ -82,6 +86,16 @@ type Config struct {
// be considered but the verifiedChains will always be nil.
VerifyPeerCertificate func(rawCerts [][]byte, verifiedChains [][]*x509.Certificate) error
+ // VerifyConnection, if not nil, is called after normal certificate
+ // verification/PSK and after VerifyPeerCertificate by either a TLS client
+ // or server. If it returns a non-nil error, the handshake is aborted
+ // and that error results.
+ //
+ // If normal verification fails then the handshake will abort before
+ // considering this callback. This callback will run for all connections
+ // regardless of InsecureSkipVerify or ClientAuth settings.
+ VerifyConnection func(*State) error
+
// RootCAs defines the set of root certificate authorities
// that one peer uses when verifying the other peer's certificates.
// If RootCAs is nil, TLS uses the host's root CA set.
@@ -130,6 +144,38 @@ type Config struct {
// List of application protocols the peer supports, for ALPN
SupportedProtocols []string
+
+ // List of Elliptic Curves to use
+ //
+ // If an ECC ciphersuite is configured and EllipticCurves is empty
+ // it will default to X25519, P-256, P-384 in this specific order.
+ EllipticCurves []elliptic.Curve
+
+ // GetCertificate returns a Certificate based on the given
+ // ClientHelloInfo. It will only be called if the client supplies SNI
+ // information or if Certificates is empty.
+ //
+ // If GetCertificate is nil or returns nil, then the certificate is
+ // retrieved from NameToCertificate. If NameToCertificate is nil, the
+ // best element of Certificates will be used.
+ GetCertificate func(*ClientHelloInfo) (*tls.Certificate, error)
+
+ // GetClientCertificate, if not nil, is called when a server requests a
+ // certificate from a client. If set, the contents of Certificates will
+ // be ignored.
+ //
+ // If GetClientCertificate returns an error, the handshake will be
+ // aborted and that error will be returned. Otherwise
+ // GetClientCertificate must return a non-nil Certificate. If
+ // Certificate.Certificate is empty then no certificate will be sent to
+ // the server. If this is unacceptable to the server then it may abort
+ // the handshake.
+ GetClientCertificate func(*CertificateRequestInfo) (*tls.Certificate, error)
+
+ // InsecureSkipVerifyHello, if true and when acting as server, allow client to
+ // skip hello verify phase and receive ServerHello after initial ClientHello.
+ // This have implication on DoS attack resistance.
+ InsecureSkipVerifyHello bool
}
func defaultConnectContextMaker() (context.Context, func()) {
@@ -143,8 +189,14 @@ func (c *Config) connectContextMaker() (context.Context, func()) {
return c.ConnectContextMaker()
}
+func (c *Config) includeCertificateSuites() bool {
+ return c.PSK == nil || len(c.Certificates) > 0 || c.GetCertificate != nil || c.GetClientCertificate != nil
+}
+
const defaultMTU = 1200 // bytes
+var defaultCurves = []elliptic.Curve{elliptic.X25519, elliptic.P256, elliptic.P384} //nolint:gochecknoglobals
+
// PSKCallback is called once we have the remote's PSKIdentityHint.
// If the remote provided none it will be nil
type PSKCallback func([]byte) ([]byte, error)
@@ -196,6 +248,6 @@ func validateConfig(config *Config) error {
}
}
- _, err := parseCipherSuites(config.CipherSuites, config.CustomCipherSuites, config.PSK == nil || len(config.Certificates) > 0, config.PSK != nil)
+ _, err := parseCipherSuites(config.CipherSuites, config.CustomCipherSuites, config.includeCertificateSuites(), config.PSK != nil)
return err
}
diff --git a/vendor/github.com/pion/dtls/v2/conn.go b/vendor/github.com/pion/dtls/v2/conn.go
index fd8cf734d..2b7585108 100644
--- a/vendor/github.com/pion/dtls/v2/conn.go
+++ b/vendor/github.com/pion/dtls/v2/conn.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -18,9 +21,9 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/handshake"
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
"github.com/pion/logging"
- "github.com/pion/transport/connctx"
- "github.com/pion/transport/deadline"
- "github.com/pion/transport/replaydetector"
+ "github.com/pion/transport/v2/connctx"
+ "github.com/pion/transport/v2/deadline"
+ "github.com/pion/transport/v2/replaydetector"
)
const (
@@ -88,7 +91,7 @@ func createConn(ctx context.Context, nextConn net.Conn, config *Config, isClient
return nil, errNilNextConn
}
- cipherSuites, err := parseCipherSuites(config.CipherSuites, config.CustomCipherSuites, config.PSK == nil || len(config.Certificates) > 0, config.PSK != nil)
+ cipherSuites, err := parseCipherSuites(config.CipherSuites, config.CustomCipherSuites, config.includeCertificateSuites(), config.PSK != nil)
if err != nil {
return nil, err
}
@@ -154,6 +157,11 @@ func createConn(ctx context.Context, nextConn net.Conn, config *Config, isClient
serverName = ""
}
+ curves := config.EllipticCurves
+ if len(curves) == 0 {
+ curves = defaultCurves
+ }
+
hsCfg := &handshakeConfig{
localPSKCallback: config.PSK,
localPSKIdentityHint: config.PSKIdentityHint,
@@ -167,6 +175,7 @@ func createConn(ctx context.Context, nextConn net.Conn, config *Config, isClient
localCertificates: config.Certificates,
insecureSkipVerify: config.InsecureSkipVerify,
verifyPeerCertificate: config.VerifyPeerCertificate,
+ verifyConnection: config.VerifyConnection,
rootCAs: config.RootCAs,
clientCAs: config.ClientCAs,
customCipherSuites: config.CustomCipherSuites,
@@ -175,13 +184,22 @@ func createConn(ctx context.Context, nextConn net.Conn, config *Config, isClient
initialEpoch: 0,
keyLogWriter: config.KeyLogWriter,
sessionStore: config.SessionStore,
+ ellipticCurves: curves,
+ localGetCertificate: config.GetCertificate,
+ localGetClientCertificate: config.GetClientCertificate,
+ insecureSkipHelloVerify: config.InsecureSkipVerifyHello,
}
- cert, err := hsCfg.getCertificate(serverName)
- if err != nil && !errors.Is(err, errNoCertificates) {
- return nil, err
+ // rfc5246#section-7.4.3
+ // In addition, the hash and signature algorithms MUST be compatible
+ // with the key in the server's end-entity certificate.
+ if !isClient {
+ cert, err := hsCfg.getCertificate(&ClientHelloInfo{})
+ if err != nil && !errors.Is(err, errNoCertificates) {
+ return nil, err
+ }
+ hsCfg.localCipherSuites = filterCipherSuitesForCertificate(cert, cipherSuites)
}
- hsCfg.localCipherSuites = filterCipherSuitesForCertificate(cert, cipherSuites)
var initialFlight flightVal
var initialFSMState handshakeState
@@ -327,7 +345,7 @@ func (c *Conn) Write(p []byte) (int, error) {
{
record: &recordlayer.RecordLayer{
Header: recordlayer.Header{
- Epoch: c.getLocalEpoch(),
+ Epoch: c.state.getLocalEpoch(),
Version: protocol.Version1_2,
},
Content: &protocol.ApplicationData{
@@ -341,7 +359,7 @@ func (c *Conn) Write(p []byte) (int, error) {
// Close closes the connection.
func (c *Conn) Close() error {
- err := c.close(true)
+ err := c.close(true) //nolint:contextcheck
c.handshakeLoopsFinished.Wait()
return err
}
@@ -412,6 +430,11 @@ func (c *Conn) writePackets(ctx context.Context, pkts []*packet) error {
}
func (c *Conn) compactRawPackets(rawPackets [][]byte) [][]byte {
+ // avoid a useless copy in the common case
+ if len(rawPackets) == 1 {
+ return rawPackets
+ }
+
combinedRawPackets := make([][]byte, 0)
currentCombinedRawPacket := make([]byte, 0)
@@ -484,14 +507,14 @@ func (c *Conn) processHandshakePacket(p *packet, h *handshake.Handshake) ([][]by
SequenceNumber: seq,
}
- recordlayerHeaderBytes, err := recordlayerHeader.Marshal()
+ rawPacket, err := recordlayerHeader.Marshal()
if err != nil {
return nil, err
}
p.record.Header = *recordlayerHeader
- rawPacket := append(recordlayerHeaderBytes, handshakeFragment...)
+ rawPacket = append(rawPacket, handshakeFragment...)
if p.shouldEncrypt {
var err error
rawPacket, err = c.state.cipherSuite.Encrypt(p.record, rawPacket)
@@ -535,12 +558,12 @@ func (c *Conn) fragmentHandshake(h *handshake.Handshake) ([][]byte, error) {
offset += contentFragmentLen
- headerFragmentRaw, err := headerFragment.Marshal()
+ fragmentedHandshake, err := headerFragment.Marshal()
if err != nil {
return nil, err
}
- fragmentedHandshake := append(headerFragmentRaw, contentFragment...)
+ fragmentedHandshake = append(fragmentedHandshake, contentFragment...)
fragmentedHandshakes = append(fragmentedHandshakes, fragmentedHandshake)
}
@@ -555,7 +578,10 @@ var poolReadBuffer = sync.Pool{ //nolint:gochecknoglobals
}
func (c *Conn) readAndBuffer(ctx context.Context) error {
- bufptr := poolReadBuffer.Get().(*[]byte)
+ bufptr, ok := poolReadBuffer.Get().(*[]byte)
+ if !ok {
+ return errFailedToAccessPoolReadBuffer
+ }
defer poolReadBuffer.Put(bufptr)
b := *bufptr
@@ -582,13 +608,13 @@ func (c *Conn) readAndBuffer(ctx context.Context) error {
if hs {
hasHandshake = true
}
- switch e := err.(type) {
- case nil:
- case *errAlert:
+
+ var e *alertError
+ if errors.As(err, &e) {
if e.IsFatalOrCloseNotify() {
return e
}
- default:
+ } else if err != nil {
return e
}
}
@@ -618,13 +644,12 @@ func (c *Conn) handleQueuedPackets(ctx context.Context) error {
}
}
}
- switch e := err.(type) {
- case nil:
- case *errAlert:
+ var e *alertError
+ if errors.As(err, &e) {
if e.IsFatalOrCloseNotify() {
return e
}
- default:
+ } else if err != nil {
return e
}
}
@@ -641,7 +666,7 @@ func (c *Conn) handleIncomingPacket(ctx context.Context, buf []byte, enqueue boo
}
// Validate epoch
- remoteEpoch := c.getRemoteEpoch()
+ remoteEpoch := c.state.getRemoteEpoch()
if h.Epoch > remoteEpoch {
if h.Epoch > remoteEpoch+1 {
c.log.Debugf("discarded future packet (epoch: %d, seq: %d)",
@@ -697,13 +722,12 @@ func (c *Conn) handleIncomingPacket(ctx context.Context, buf []byte, enqueue boo
} else if isHandshake {
markPacketAsValid()
for out, epoch := c.fragmentBuffer.pop(); out != nil; out, epoch = c.fragmentBuffer.pop() {
- rawHandshake := &handshake.Handshake{}
- if err := rawHandshake.Unmarshal(out); err != nil {
+ header := &handshake.Header{}
+ if err := header.Unmarshal(out); err != nil {
c.log.Debugf("%s: handshake parse failed: %s", srvCliStr(c.state.isClient), err)
continue
}
-
- _ = c.handshakeCache.push(out, epoch, rawHandshake.Header.MessageSequence, rawHandshake.Header.Type, !c.state.isClient)
+ c.handshakeCache.push(out, epoch, header.MessageSequence, header.Type, !c.state.isClient)
}
return true, nil, nil
@@ -723,7 +747,7 @@ func (c *Conn) handleIncomingPacket(ctx context.Context, buf []byte, enqueue boo
a = &alert.Alert{Level: alert.Warning, Description: alert.CloseNotify}
}
markPacketAsValid()
- return false, a, &errAlert{content}
+ return false, a, &alertError{content}
case *protocol.ChangeCipherSpec:
if c.state.cipherSuite == nil || !c.state.cipherSuite.IsInitialized() {
if enqueue {
@@ -736,7 +760,7 @@ func (c *Conn) handleIncomingPacket(ctx context.Context, buf []byte, enqueue boo
newRemoteEpoch := h.Epoch + 1
c.log.Tracef("%s: <- ChangeCipherSpec (epoch: %d)", srvCliStr(c.state.isClient), newRemoteEpoch)
- if c.getRemoteEpoch()+1 == newRemoteEpoch {
+ if c.state.getRemoteEpoch()+1 == newRemoteEpoch {
c.setRemoteEpoch(newRemoteEpoch)
markPacketAsValid()
}
@@ -778,7 +802,7 @@ func (c *Conn) notify(ctx context.Context, level alert.Level, desc alert.Descrip
{
record: &recordlayer.RecordLayer{
Header: recordlayer.Header{
- Epoch: c.getLocalEpoch(),
+ Epoch: c.state.getLocalEpoch(),
Version: protocol.Version1_2,
},
Content: &alert.Alert{
@@ -844,8 +868,8 @@ func (c *Conn) handshake(ctx context.Context, cfg *handshakeConfig, initialFligh
defer c.handshakeLoopsFinished.Done()
for {
if err := c.readAndBuffer(ctxRead); err != nil {
- switch e := err.(type) {
- case *errAlert:
+ var e *alertError
+ if errors.As(err, &e) {
if !e.IsFatalOrCloseNotify() {
if c.isHandshakeCompletedSuccessfully() {
// Pass the error to Read()
@@ -857,9 +881,9 @@ func (c *Conn) handshake(ctx context.Context, cfg *handshakeConfig, initialFligh
}
continue // non-fatal alert must not stop read loop
}
- case error:
- switch err {
- case context.DeadlineExceeded, context.Canceled, io.EOF:
+ } else {
+ switch {
+ case errors.Is(err, context.DeadlineExceeded), errors.Is(err, context.Canceled), errors.Is(err, io.EOF):
default:
if c.isHandshakeCompletedSuccessfully() {
// Keep read loop and pass the read error to Read()
@@ -872,16 +896,21 @@ func (c *Conn) handshake(ctx context.Context, cfg *handshakeConfig, initialFligh
}
}
}
+
select {
case firstErr <- err:
default:
}
- if e, ok := err.(*errAlert); ok {
+ if e != nil {
if e.IsFatalOrCloseNotify() {
- _ = c.close(false)
+ _ = c.close(false) //nolint:contextcheck
}
}
+ if !c.isConnectionClosed() && errors.Is(err, context.Canceled) {
+ c.log.Trace("handshake timeouts - closing underline connection")
+ _ = c.close(false) //nolint:contextcheck
+ }
return
}
}
@@ -891,10 +920,12 @@ func (c *Conn) handshake(ctx context.Context, cfg *handshakeConfig, initialFligh
case err := <-firstErr:
cancelRead()
cancel()
+ c.handshakeLoopsFinished.Wait()
return c.translateHandshakeCtxError(err)
case <-ctx.Done():
cancelRead()
cancel()
+ c.handshakeLoopsFinished.Wait()
return c.translateHandshakeCtxError(ctx.Err())
case <-done:
return nil
@@ -927,6 +958,7 @@ func (c *Conn) close(byUser bool) error {
if byUser {
c.connectionClosedByUser = true
}
+ isClosed := c.isConnectionClosed()
c.closed.Close()
c.closeLock.Unlock()
@@ -934,6 +966,10 @@ func (c *Conn) close(byUser bool) error {
return ErrConnClosed
}
+ if isClosed {
+ return nil
+ }
+
return c.nextConn.Close()
}
@@ -950,18 +986,10 @@ func (c *Conn) setLocalEpoch(epoch uint16) {
c.state.localEpoch.Store(epoch)
}
-func (c *Conn) getLocalEpoch() uint16 {
- return c.state.localEpoch.Load().(uint16)
-}
-
func (c *Conn) setRemoteEpoch(epoch uint16) {
c.state.remoteEpoch.Store(epoch)
}
-func (c *Conn) getRemoteEpoch() uint16 {
- return c.state.remoteEpoch.Load().(uint16)
-}
-
// LocalAddr implements net.Conn.LocalAddr
func (c *Conn) LocalAddr() net.Addr {
return c.nextConn.LocalAddr()
diff --git a/vendor/github.com/pion/dtls/v2/crypto.go b/vendor/github.com/pion/dtls/v2/crypto.go
index 768ee470e..968910c7e 100644
--- a/vendor/github.com/pion/dtls/v2/crypto.go
+++ b/vendor/github.com/pion/dtls/v2/crypto.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -108,6 +111,13 @@ func verifyKeySignature(message, remoteKeySignature []byte, hashAlgorithm hash.A
// the private key in the certificate.
// https://tools.ietf.org/html/rfc5246#section-7.3
func generateCertificateVerify(handshakeBodies []byte, privateKey crypto.PrivateKey, hashAlgorithm hash.Algorithm) ([]byte, error) {
+ if p, ok := privateKey.(ed25519.PrivateKey); ok {
+ // https://pkg.go.dev/crypto/ed25519#PrivateKey.Sign
+ // Sign signs the given message with priv. Ed25519 performs two passes over
+ // messages to be signed and therefore cannot handle pre-hashed messages.
+ return p.Sign(rand.Reader, handshakeBodies, crypto.Hash(0))
+ }
+
h := sha256.New()
if _, err := h.Write(handshakeBodies); err != nil {
return nil, err
@@ -115,9 +125,6 @@ func generateCertificateVerify(handshakeBodies []byte, privateKey crypto.Private
hashed := h.Sum(nil)
switch p := privateKey.(type) {
- case ed25519.PrivateKey:
- // https://crypto.stackexchange.com/a/55483
- return p.Sign(rand.Reader, hashed, crypto.Hash(0))
case *ecdsa.PrivateKey:
return p.Sign(rand.Reader, hashed, hashAlgorithm.CryptoHash())
case *rsa.PrivateKey:
diff --git a/vendor/github.com/pion/dtls/v2/dtls.go b/vendor/github.com/pion/dtls/v2/dtls.go
index 125b904e5..b799770d8 100644
--- a/vendor/github.com/pion/dtls/v2/dtls.go
+++ b/vendor/github.com/pion/dtls/v2/dtls.go
@@ -1,2 +1,5 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package dtls implements Datagram Transport Layer Security (DTLS) 1.2
package dtls
diff --git a/vendor/github.com/pion/dtls/v2/errors.go b/vendor/github.com/pion/dtls/v2/errors.go
index 2e1638828..025d8645e 100644
--- a/vendor/github.com/pion/dtls/v2/errors.go
+++ b/vendor/github.com/pion/dtls/v2/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -10,14 +13,13 @@ import (
"github.com/pion/dtls/v2/pkg/protocol"
"github.com/pion/dtls/v2/pkg/protocol/alert"
- "golang.org/x/xerrors"
)
// Typed errors
var (
ErrConnClosed = &FatalError{Err: errors.New("conn is closed")} //nolint:goerr113
- errDeadlineExceeded = &TimeoutError{Err: xerrors.Errorf("read/write timeout: %w", context.DeadlineExceeded)}
+ errDeadlineExceeded = &TimeoutError{Err: fmt.Errorf("read/write timeout: %w", context.DeadlineExceeded)}
errInvalidContentType = &TemporaryError{Err: errors.New("invalid content type")} //nolint:goerr113
errBufferTooSmall = &TemporaryError{Err: errors.New("buffer is too small")} //nolint:goerr113
@@ -55,6 +57,7 @@ var (
errServerNoMatchingSRTPProfile = &FatalError{Err: errors.New("client requested SRTP but we have no matching profiles")} //nolint:goerr113
errServerRequiredButNoClientEMS = &FatalError{Err: errors.New("server requires the Extended Master Secret extension, but the client does not support it")} //nolint:goerr113
errVerifyDataMismatch = &FatalError{Err: errors.New("expected and actual verify data does not match")} //nolint:goerr113
+ errNotAcceptableCertificateChain = &FatalError{Err: errors.New("certificate chain is not signed by an acceptable CA")} //nolint:goerr113
errInvalidFlight = &InternalError{Err: errors.New("invalid flight number")} //nolint:goerr113
errKeySignatureGenerateUnimplemented = &InternalError{Err: errors.New("unable to generate key signature, unimplemented")} //nolint:goerr113
@@ -62,6 +65,8 @@ var (
errLengthMismatch = &InternalError{Err: errors.New("data length and declared length do not match")} //nolint:goerr113
errSequenceNumberOverflow = &InternalError{Err: errors.New("sequence number overflow")} //nolint:goerr113
errInvalidFSMTransition = &InternalError{Err: errors.New("invalid state machine transition")} //nolint:goerr113
+ errFailedToAccessPoolReadBuffer = &InternalError{Err: errors.New("failed to access pool read buffer")} //nolint:goerr113
+ errFragmentBufferOverflow = &InternalError{Err: errors.New("fragment buffer overflow")} //nolint:goerr113
)
// FatalError indicates that the DTLS connection is no longer available.
@@ -81,37 +86,39 @@ type TimeoutError = protocol.TimeoutError
// HandshakeError indicates that the handshake failed.
type HandshakeError = protocol.HandshakeError
-// invalidCipherSuite indicates an attempt at using an unsupported cipher suite.
-type invalidCipherSuite struct {
+// errInvalidCipherSuite indicates an attempt at using an unsupported cipher suite.
+type invalidCipherSuiteError struct {
id CipherSuiteID
}
-func (e *invalidCipherSuite) Error() string {
+func (e *invalidCipherSuiteError) Error() string {
return fmt.Sprintf("CipherSuite with id(%d) is not valid", e.id)
}
-func (e *invalidCipherSuite) Is(err error) bool {
- if other, ok := err.(*invalidCipherSuite); ok {
+func (e *invalidCipherSuiteError) Is(err error) bool {
+ var other *invalidCipherSuiteError
+ if errors.As(err, &other) {
return e.id == other.id
}
return false
}
// errAlert wraps DTLS alert notification as an error
-type errAlert struct {
+type alertError struct {
*alert.Alert
}
-func (e *errAlert) Error() string {
+func (e *alertError) Error() string {
return fmt.Sprintf("alert: %s", e.Alert.String())
}
-func (e *errAlert) IsFatalOrCloseNotify() bool {
+func (e *alertError) IsFatalOrCloseNotify() bool {
return e.Level == alert.Fatal || e.Description == alert.CloseNotify
}
-func (e *errAlert) Is(err error) bool {
- if other, ok := err.(*errAlert); ok {
+func (e *alertError) Is(err error) bool {
+ var other *alertError
+ if errors.As(err, &other) {
return e.Level == other.Level && e.Description == other.Description
}
return false
@@ -119,14 +126,20 @@ func (e *errAlert) Is(err error) bool {
// netError translates an error from underlying Conn to corresponding net.Error.
func netError(err error) error {
- switch err {
- case io.EOF, context.Canceled, context.DeadlineExceeded:
+ switch {
+ case errors.Is(err, io.EOF), errors.Is(err, context.Canceled), errors.Is(err, context.DeadlineExceeded):
// Return io.EOF and context errors as is.
return err
}
- switch e := err.(type) {
- case (*net.OpError):
- if se, ok := e.Err.(*os.SyscallError); ok {
+
+ var (
+ ne net.Error
+ opError *net.OpError
+ se *os.SyscallError
+ )
+
+ if errors.As(err, &opError) {
+ if errors.As(opError, &se) {
if se.Timeout() {
return &TimeoutError{Err: err}
}
@@ -134,8 +147,11 @@ func netError(err error) error {
return &TemporaryError{Err: err}
}
}
- case (net.Error):
+ }
+
+ if errors.As(err, &ne) {
return err
}
+
return &FatalError{Err: err}
}
diff --git a/vendor/github.com/pion/dtls/v2/errors_errno.go b/vendor/github.com/pion/dtls/v2/errors_errno.go
index c03779a45..f8e424eb3 100644
--- a/vendor/github.com/pion/dtls/v2/errors_errno.go
+++ b/vendor/github.com/pion/dtls/v2/errors_errno.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
//go:build aix || darwin || dragonfly || freebsd || linux || nacl || nacljs || netbsd || openbsd || solaris || windows
// +build aix darwin dragonfly freebsd linux nacl nacljs netbsd openbsd solaris windows
@@ -9,18 +12,11 @@
package dtls
import (
+ "errors"
"os"
"syscall"
)
func isOpErrorTemporary(err *os.SyscallError) bool {
- if ne, ok := err.Err.(syscall.Errno); ok {
- switch ne {
- case syscall.ECONNREFUSED:
- return true
- default:
- return false
- }
- }
- return false
+ return errors.Is(err.Err, syscall.ECONNREFUSED)
}
diff --git a/vendor/github.com/pion/dtls/v2/errors_noerrno.go b/vendor/github.com/pion/dtls/v2/errors_noerrno.go
index ad1bf8523..844ff1e75 100644
--- a/vendor/github.com/pion/dtls/v2/errors_noerrno.go
+++ b/vendor/github.com/pion/dtls/v2/errors_noerrno.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
//go:build !aix && !darwin && !dragonfly && !freebsd && !linux && !nacl && !nacljs && !netbsd && !openbsd && !solaris && !windows
// +build !aix,!darwin,!dragonfly,!freebsd,!linux,!nacl,!nacljs,!netbsd,!openbsd,!solaris,!windows
diff --git a/vendor/github.com/pion/dtls/v2/flight.go b/vendor/github.com/pion/dtls/v2/flight.go
index bed3f8c9a..cfa58c574 100644
--- a/vendor/github.com/pion/dtls/v2/flight.go
+++ b/vendor/github.com/pion/dtls/v2/flight.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
/*
diff --git a/vendor/github.com/pion/dtls/v2/flight0handler.go b/vendor/github.com/pion/dtls/v2/flight0handler.go
index 23dddeda6..ec766ddff 100644
--- a/vendor/github.com/pion/dtls/v2/flight0handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight0handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -11,8 +14,8 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/handshake"
)
-func flight0Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- seq, msgs, ok := cache.fullPullMap(0,
+func flight0Parse(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
+ seq, msgs, ok := cache.fullPullMap(0, state.cipherSuite,
handshakeCachePullRule{handshake.TypeClientHello, cfg.initialEpoch, true, false},
)
if !ok {
@@ -81,7 +84,13 @@ func flight0Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
}
- return handleHelloResume(clientHello.SessionID, state, cfg, flight2)
+ nextFlight := flight2
+
+ if cfg.insecureSkipHelloVerify {
+ nextFlight = flight4
+ }
+
+ return handleHelloResume(clientHello.SessionID, state, cfg, nextFlight)
}
func handleHelloResume(sessionID []byte, state *State, cfg *handshakeConfig, next flightVal) (flightVal, *alert.Alert, error) {
@@ -107,11 +116,13 @@ func handleHelloResume(sessionID []byte, state *State, cfg *handshakeConfig, nex
return next, nil, nil
}
-func flight0Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight0Generate(_ flightConn, state *State, _ *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
// Initialize
- state.cookie = make([]byte, cookieLength)
- if _, err := rand.Read(state.cookie); err != nil {
- return nil, nil, err
+ if !cfg.insecureSkipHelloVerify {
+ state.cookie = make([]byte, cookieLength)
+ if _, err := rand.Read(state.cookie); err != nil {
+ return nil, nil, err
+ }
}
var zeroEpoch uint16
diff --git a/vendor/github.com/pion/dtls/v2/flight1handler.go b/vendor/github.com/pion/dtls/v2/flight1handler.go
index 48c82013c..94fdc222d 100644
--- a/vendor/github.com/pion/dtls/v2/flight1handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight1handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -14,7 +17,7 @@ import (
func flight1Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
// HelloVerifyRequest can be skipped by the server,
// so allow ServerHello during flight1 also
- seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+ seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeHelloVerifyRequest, cfg.initialEpoch, false, true},
handshakeCachePullRule{handshake.TypeServerHello, cfg.initialEpoch, false, true},
)
@@ -43,7 +46,7 @@ func flight1Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, nil
}
-func flight1Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight1Generate(c flightConn, state *State, _ *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
var zeroEpoch uint16
state.localEpoch.Store(zeroEpoch)
state.remoteEpoch.Store(zeroEpoch)
@@ -62,10 +65,19 @@ func flight1Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
RenegotiatedConnection: 0,
},
}
- if cfg.localPSKCallback == nil {
+
+ var setEllipticCurveCryptographyClientHelloExtensions bool
+ for _, c := range cfg.localCipherSuites {
+ if c.ECC() {
+ setEllipticCurveCryptographyClientHelloExtensions = true
+ break
+ }
+ }
+
+ if setEllipticCurveCryptographyClientHelloExtensions {
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},
diff --git a/vendor/github.com/pion/dtls/v2/flight2handler.go b/vendor/github.com/pion/dtls/v2/flight2handler.go
index bb8e91db0..26e57d2f2 100644
--- a/vendor/github.com/pion/dtls/v2/flight2handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight2handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -11,7 +14,7 @@ import (
)
func flight2Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+ seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeClientHello, cfg.initialEpoch, true, false},
)
if !ok {
@@ -41,7 +44,7 @@ func flight2Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return flight4, nil, nil
}
-func flight2Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight2Generate(_ flightConn, state *State, _ *handshakeCache, _ *handshakeConfig) ([]*packet, *alert.Alert, error) {
state.handshakeSendSequence = 0
return []*packet{
{
diff --git a/vendor/github.com/pion/dtls/v2/flight3handler.go b/vendor/github.com/pion/dtls/v2/flight3handler.go
index 697b304c4..5a763dc08 100644
--- a/vendor/github.com/pion/dtls/v2/flight3handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight3handler.go
@@ -1,9 +1,13 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
"bytes"
"context"
+ "github.com/pion/dtls/v2/internal/ciphersuite/types"
"github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/dtls/v2/pkg/crypto/prf"
"github.com/pion/dtls/v2/pkg/protocol"
@@ -17,7 +21,7 @@ func flight3Parse(ctx context.Context, c flightConn, state *State, cache *handsh
// Clients may receive multiple HelloVerifyRequest messages with different cookies.
// Clients SHOULD handle this by sending a new ClientHello with a cookie in response
// to the new HelloVerifyRequest. RFC 6347 Section 4.2.1
- seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+ seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeHelloVerifyRequest, cfg.initialEpoch, false, true},
)
if ok {
@@ -33,7 +37,7 @@ func flight3Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
}
- _, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence,
+ _, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeServerHello, cfg.initialEpoch, false, false},
)
if !ok {
@@ -106,12 +110,12 @@ func flight3Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
if cfg.localPSKCallback != nil {
- seq, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence+1,
+ seq, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence+1, state.cipherSuite,
handshakeCachePullRule{handshake.TypeServerKeyExchange, cfg.initialEpoch, false, true},
handshakeCachePullRule{handshake.TypeServerHelloDone, cfg.initialEpoch, false, false},
)
} else {
- seq, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence+1,
+ seq, msgs, ok = cache.fullPullMap(state.handshakeRecvSequence+1, state.cipherSuite,
handshakeCachePullRule{handshake.TypeCertificate, cfg.initialEpoch, false, true},
handshakeCachePullRule{handshake.TypeServerKeyExchange, cfg.initialEpoch, false, false},
handshakeCachePullRule{handshake.TypeCertificateRequest, cfg.initialEpoch, false, true},
@@ -154,7 +158,7 @@ func handleResumption(ctx context.Context, c flightConn, state *State, cache *ha
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
}
- _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence+1,
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence+1, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, false, false},
)
if !ok {
@@ -187,13 +191,29 @@ func handleResumption(ctx context.Context, c flightConn, state *State, cache *ha
func handleServerKeyExchange(_ flightConn, state *State, cfg *handshakeConfig, h *handshake.MessageServerKeyExchange) (*alert.Alert, error) {
var err error
+ if state.cipherSuite == nil {
+ return &alert.Alert{Level: alert.Fatal, Description: alert.InsufficientSecurity}, errInvalidCipherSuite
+ }
if cfg.localPSKCallback != nil {
var psk []byte
if psk, err = cfg.localPSKCallback(h.IdentityHint); err != nil {
return &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
}
state.IdentityHint = h.IdentityHint
- state.preMasterSecret = prf.PSKPreMasterSecret(psk)
+ switch state.cipherSuite.KeyExchangeAlgorithm() {
+ case types.KeyExchangeAlgorithmPsk:
+ state.preMasterSecret = prf.PSKPreMasterSecret(psk)
+ case (types.KeyExchangeAlgorithmEcdhe | types.KeyExchangeAlgorithmPsk):
+ if state.localKeypair, err = elliptic.GenerateKeypair(h.NamedCurve); err != nil {
+ return &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
+ }
+ state.preMasterSecret, err = prf.EcdhePSKPreMasterSecret(psk, h.PublicKey, state.localKeypair.PrivateKey, state.localKeypair.Curve)
+ if err != nil {
+ return &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
+ }
+ default:
+ return &alert.Alert{Level: alert.Fatal, Description: alert.InsufficientSecurity}, errInvalidCipherSuite
+ }
} else {
if state.localKeypair, err = elliptic.GenerateKeypair(h.NamedCurve); err != nil {
return &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
@@ -204,10 +224,10 @@ func handleServerKeyExchange(_ flightConn, state *State, cfg *handshakeConfig, h
}
}
- return nil, nil
+ return nil, nil //nolint:nilnil
}
-func flight3Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight3Generate(_ flightConn, state *State, _ *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
extensions := []extension.Extension{
&extension.SupportedSignatureAlgorithms{
SignatureHashAlgorithms: cfg.localSignatureSchemes,
@@ -216,7 +236,7 @@ func flight3Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
RenegotiatedConnection: 0,
},
}
- if cfg.localPSKCallback == nil {
+ if state.namedCurve != 0 {
extensions = append(extensions, []extension.Extension{
&extension.SupportedEllipticCurves{
EllipticCurves: []elliptic.Curve{elliptic.X25519, elliptic.P256, elliptic.P384},
diff --git a/vendor/github.com/pion/dtls/v2/flight4bhandler.go b/vendor/github.com/pion/dtls/v2/flight4bhandler.go
index 36cd0b45f..6bbbc5972 100644
--- a/vendor/github.com/pion/dtls/v2/flight4bhandler.go
+++ b/vendor/github.com/pion/dtls/v2/flight4bhandler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -12,8 +15,8 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
-func flight4bParse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+func flight4bParse(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, true, false},
)
if !ok {
@@ -44,7 +47,7 @@ func flight4bParse(ctx context.Context, c flightConn, state *State, cache *hands
return flight4b, nil, nil
}
-func flight4bGenerate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight4bGenerate(_ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
var pkts []*packet
extensions := []extension.Extension{&extension.RenegotiationInfo{
diff --git a/vendor/github.com/pion/dtls/v2/flight4handler.go b/vendor/github.com/pion/dtls/v2/flight4handler.go
index a6ba36c2c..67a486461 100644
--- a/vendor/github.com/pion/dtls/v2/flight4handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight4handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -5,6 +8,7 @@ import (
"crypto/rand"
"crypto/x509"
+ "github.com/pion/dtls/v2/internal/ciphersuite"
"github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
"github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/dtls/v2/pkg/crypto/prf"
@@ -17,7 +21,7 @@ import (
)
func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) { //nolint:gocognit
- seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+ seq, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeCertificate, cfg.initialEpoch, true, true},
handshakeCachePullRule{handshake.TypeClientKeyExchange, cfg.initialEpoch, true, false},
handshakeCachePullRule{handshake.TypeCertificateVerify, cfg.initialEpoch, true, true},
@@ -89,6 +93,10 @@ func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
}
state.peerCertificatesVerified = verified
+ } else if state.PeerCertificates != nil {
+ // A certificate was received, but we haven't seen a CertificateVerify
+ // keep reading until we receive one
+ return 0, nil, nil
}
if !state.cipherSuite.IsInitialized() {
@@ -103,7 +111,16 @@ func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
}
state.IdentityHint = clientKeyExchange.IdentityHint
- preMasterSecret = prf.PSKPreMasterSecret(psk)
+ switch state.cipherSuite.KeyExchangeAlgorithm() {
+ case CipherSuiteKeyExchangeAlgorithmPsk:
+ preMasterSecret = prf.PSKPreMasterSecret(psk)
+ case (CipherSuiteKeyExchangeAlgorithmPsk | CipherSuiteKeyExchangeAlgorithmEcdhe):
+ if preMasterSecret, err = prf.EcdhePSKPreMasterSecret(psk, clientKeyExchange.PublicKey, state.localKeypair.PrivateKey, state.localKeypair.Curve); err != nil {
+ return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
+ }
+ default:
+ return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, errInvalidCipherSuite
+ }
} else {
preMasterSecret, err = prf.PreMasterSecret(clientKeyExchange.PublicKey, state.localKeypair.PrivateKey, state.localKeypair.Curve)
if err != nil {
@@ -151,7 +168,7 @@ func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
}
- seq, msgs, ok = cache.fullPullMap(seq,
+ seq, msgs, ok = cache.fullPullMap(seq, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, true, false},
)
if !ok {
@@ -165,6 +182,11 @@ func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
if state.cipherSuite.AuthenticationType() == CipherSuiteAuthenticationTypeAnonymous {
+ if cfg.verifyConnection != nil {
+ if err := cfg.verifyConnection(state.clone()); err != nil {
+ return 0, &alert.Alert{Level: alert.Fatal, Description: alert.BadCertificate}, err
+ }
+ }
return flight6, nil, nil
}
@@ -185,13 +207,18 @@ func flight4Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return 0, &alert.Alert{Level: alert.Fatal, Description: alert.BadCertificate}, errClientCertificateNotVerified
}
case NoClientCert, RequestClientCert:
- return flight6, nil, nil
+ // go to flight6
+ }
+ if cfg.verifyConnection != nil {
+ if err := cfg.verifyConnection(state.clone()); err != nil {
+ return 0, &alert.Alert{Level: alert.Fatal, Description: alert.BadCertificate}, err
+ }
}
return flight6, nil, nil
}
-func flight4Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight4Generate(_ flightConn, state *State, _ *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
extensions := []extension.Extension{&extension.RenegotiationInfo{
RenegotiatedConnection: 0,
}}
@@ -253,7 +280,10 @@ func flight4Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
switch {
case state.cipherSuite.AuthenticationType() == CipherSuiteAuthenticationTypeCertificate:
- certificate, err := cfg.getCertificate(state.serverName)
+ certificate, err := cfg.getCertificate(&ClientHelloInfo{
+ ServerName: state.serverName,
+ CipherSuites: []ciphersuite.ID{state.cipherSuite.ID()},
+ })
if err != nil {
return nil, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, err
}
@@ -305,6 +335,16 @@ func flight4Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
})
if cfg.clientAuth > NoClientCert {
+ // An empty list of certificateAuthorities signals to
+ // the client that it may send any certificate in response
+ // to our request. When we know the CAs we trust, then
+ // we can send them down, so that the client can choose
+ // an appropriate certificate to give to us.
+ var certificateAuthorities [][]byte
+ if cfg.clientCAs != nil {
+ // nolint:staticcheck // ignoring tlsCert.RootCAs.Subjects is deprecated ERR because cert does not come from SystemCertPool and it's ok if certificate authorities is empty.
+ certificateAuthorities = cfg.clientCAs.Subjects()
+ }
pkts = append(pkts, &packet{
record: &recordlayer.RecordLayer{
Header: recordlayer.Header{
@@ -312,43 +352,36 @@ func flight4Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
},
Content: &handshake.Handshake{
Message: &handshake.MessageCertificateRequest{
- CertificateTypes: []clientcertificate.Type{clientcertificate.RSASign, clientcertificate.ECDSASign},
- SignatureHashAlgorithms: cfg.localSignatureSchemes,
+ CertificateTypes: []clientcertificate.Type{clientcertificate.RSASign, clientcertificate.ECDSASign},
+ SignatureHashAlgorithms: cfg.localSignatureSchemes,
+ CertificateAuthoritiesNames: certificateAuthorities,
},
},
},
})
}
- case cfg.localPSKIdentityHint != nil:
+ case cfg.localPSKIdentityHint != nil || state.cipherSuite.KeyExchangeAlgorithm().Has(CipherSuiteKeyExchangeAlgorithmEcdhe):
// To help the client in selecting which identity to use, the server
// can provide a "PSK identity hint" in the ServerKeyExchange message.
- // If no hint is provided, the ServerKeyExchange message is omitted.
+ // If no hint is provided and cipher suite doesn't use elliptic curve,
+ // the ServerKeyExchange message is omitted.
//
// https://tools.ietf.org/html/rfc4279#section-2
+ srvExchange := &handshake.MessageServerKeyExchange{
+ IdentityHint: cfg.localPSKIdentityHint,
+ }
+ if state.cipherSuite.KeyExchangeAlgorithm().Has(CipherSuiteKeyExchangeAlgorithmEcdhe) {
+ srvExchange.EllipticCurveType = elliptic.CurveTypeNamedCurve
+ srvExchange.NamedCurve = state.namedCurve
+ srvExchange.PublicKey = state.localKeypair.PublicKey
+ }
pkts = append(pkts, &packet{
record: &recordlayer.RecordLayer{
Header: recordlayer.Header{
Version: protocol.Version1_2,
},
Content: &handshake.Handshake{
- Message: &handshake.MessageServerKeyExchange{
- IdentityHint: cfg.localPSKIdentityHint,
- },
- },
- },
- })
- case state.cipherSuite.AuthenticationType() == CipherSuiteAuthenticationTypeAnonymous:
- pkts = append(pkts, &packet{
- record: &recordlayer.RecordLayer{
- Header: recordlayer.Header{
- Version: protocol.Version1_2,
- },
- Content: &handshake.Handshake{
- Message: &handshake.MessageServerKeyExchange{
- EllipticCurveType: elliptic.CurveTypeNamedCurve,
- NamedCurve: state.namedCurve,
- PublicKey: state.localKeypair.PublicKey,
- },
+ Message: srvExchange,
},
},
})
diff --git a/vendor/github.com/pion/dtls/v2/flight5bhandler.go b/vendor/github.com/pion/dtls/v2/flight5bhandler.go
index 577342e5b..ddd37324c 100644
--- a/vendor/github.com/pion/dtls/v2/flight5bhandler.go
+++ b/vendor/github.com/pion/dtls/v2/flight5bhandler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -10,8 +13,8 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
-func flight5bParse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-1,
+func flight5bParse(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-1, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, false, false},
)
if !ok {
@@ -27,7 +30,7 @@ func flight5bParse(ctx context.Context, c flightConn, state *State, cache *hands
return flight5b, nil, nil
}
-func flight5bGenerate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) { //nolint:gocognit
+func flight5bGenerate(_ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) { //nolint:gocognit
var pkts []*packet
pkts = append(pkts,
diff --git a/vendor/github.com/pion/dtls/v2/flight5handler.go b/vendor/github.com/pion/dtls/v2/flight5handler.go
index 510fa4512..e8adf4f36 100644
--- a/vendor/github.com/pion/dtls/v2/flight5handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight5handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -14,8 +17,8 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
-func flight5Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence,
+func flight5Parse(_ context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, false, false},
)
if !ok {
@@ -63,20 +66,30 @@ func flight5Parse(ctx context.Context, c flightConn, state *State, cache *handsh
}
func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) { //nolint:gocognit
- var certBytes [][]byte
var privateKey crypto.PrivateKey
- if len(cfg.localCertificates) > 0 {
- certificate, err := cfg.getCertificate(cfg.serverName)
+ var pkts []*packet
+ if state.remoteRequestedCertificate {
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-2, state.cipherSuite,
+ handshakeCachePullRule{handshake.TypeCertificateRequest, cfg.initialEpoch, false, false})
+ if !ok {
+ return nil, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, errClientCertificateRequired
+ }
+ reqInfo := CertificateRequestInfo{}
+ if r, ok := msgs[handshake.TypeCertificateRequest].(*handshake.MessageCertificateRequest); ok {
+ reqInfo.AcceptableCAs = r.CertificateAuthoritiesNames
+ } else {
+ return nil, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, errClientCertificateRequired
+ }
+ certificate, err := cfg.getClientCertificate(&reqInfo)
if err != nil {
return nil, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, err
}
- certBytes = certificate.Certificate
- privateKey = certificate.PrivateKey
- }
-
- var pkts []*packet
-
- if state.remoteRequestedCertificate {
+ if certificate == nil {
+ return nil, &alert.Alert{Level: alert.Fatal, Description: alert.HandshakeFailure}, errNotAcceptableCertificateChain
+ }
+ if certificate.Certificate != nil {
+ privateKey = certificate.PrivateKey
+ }
pkts = append(pkts,
&packet{
record: &recordlayer.RecordLayer{
@@ -85,7 +98,7 @@ func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
},
Content: &handshake.Handshake{
Message: &handshake.MessageCertificate{
- Certificate: certBytes,
+ Certificate: certificate.Certificate,
},
},
},
@@ -98,6 +111,9 @@ func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
} else {
clientKeyExchange.IdentityHint = cfg.localPSKIdentityHint
}
+ if state != nil && state.localKeypair != nil && len(state.localKeypair.PublicKey) > 0 {
+ clientKeyExchange.PublicKey = state.localKeypair.PublicKey
+ }
pkts = append(pkts,
&packet{
@@ -124,7 +140,9 @@ func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
return nil, alertPtr, err
}
} else {
- rawHandshake := &handshake.Handshake{}
+ rawHandshake := &handshake.Handshake{
+ KeyExchangeAlgorithm: state.cipherSuite.KeyExchangeAlgorithm(),
+ }
err := rawHandshake.Unmarshal(serverKeyExchangeData)
if err != nil {
return nil, &alert.Alert{Level: alert.Fatal, Description: alert.UnexpectedMessage}, err
@@ -162,7 +180,7 @@ func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
// If the client has sent a certificate with signing ability, a digitally-signed
// CertificateVerify message is sent to explicitly verify possession of the
// private key in the certificate.
- if state.remoteRequestedCertificate && len(cfg.localCertificates) > 0 {
+ if state.remoteRequestedCertificate && privateKey != nil {
plainText := append(cache.pullAndMerge(
handshakeCachePullRule{handshake.TypeClientHello, cfg.initialEpoch, true, false},
handshakeCachePullRule{handshake.TypeServerHello, cfg.initialEpoch, false, false},
@@ -268,7 +286,7 @@ func flight5Generate(c flightConn, state *State, cache *handshakeCache, cfg *han
func initalizeCipherSuite(state *State, cache *handshakeCache, cfg *handshakeConfig, h *handshake.MessageServerKeyExchange, sendingPlainText []byte) (*alert.Alert, error) { //nolint:gocognit
if state.cipherSuite.IsInitialized() {
- return nil, nil
+ return nil, nil //nolint
}
clientRandom := state.localRandom.MarshalFixed()
@@ -323,6 +341,11 @@ func initalizeCipherSuite(state *State, cache *handshakeCache, cfg *handshakeCon
}
}
}
+ if cfg.verifyConnection != nil {
+ if err = cfg.verifyConnection(state.clone()); err != nil {
+ return &alert.Alert{Level: alert.Fatal, Description: alert.BadCertificate}, err
+ }
+ }
if err = state.cipherSuite.Init(state.masterSecret, clientRandom[:], serverRandom[:], true); err != nil {
return &alert.Alert{Level: alert.Fatal, Description: alert.InternalError}, err
@@ -330,5 +353,5 @@ func initalizeCipherSuite(state *State, cache *handshakeCache, cfg *handshakeCon
cfg.writeKeyLog(keyLogLabelTLS12, clientRandom[:], state.masterSecret)
- return nil, nil
+ return nil, nil //nolint
}
diff --git a/vendor/github.com/pion/dtls/v2/flight6handler.go b/vendor/github.com/pion/dtls/v2/flight6handler.go
index fddaa0e6b..57ac14360 100644
--- a/vendor/github.com/pion/dtls/v2/flight6handler.go
+++ b/vendor/github.com/pion/dtls/v2/flight6handler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -10,8 +13,8 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
-func flight6Parse(ctx context.Context, c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
- _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-1,
+func flight6Parse(_ context.Context, _ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) (flightVal, *alert.Alert, error) {
+ _, msgs, ok := cache.fullPullMap(state.handshakeRecvSequence-1, state.cipherSuite,
handshakeCachePullRule{handshake.TypeFinished, cfg.initialEpoch + 1, true, false},
)
if !ok {
@@ -27,7 +30,7 @@ func flight6Parse(ctx context.Context, c flightConn, state *State, cache *handsh
return flight6, nil, nil
}
-func flight6Generate(c flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
+func flight6Generate(_ flightConn, state *State, cache *handshakeCache, cfg *handshakeConfig) ([]*packet, *alert.Alert, error) {
var pkts []*packet
pkts = append(pkts,
diff --git a/vendor/github.com/pion/dtls/v2/flighthandler.go b/vendor/github.com/pion/dtls/v2/flighthandler.go
index f899ffa5b..ceb4a992b 100644
--- a/vendor/github.com/pion/dtls/v2/flighthandler.go
+++ b/vendor/github.com/pion/dtls/v2/flighthandler.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
diff --git a/vendor/github.com/pion/dtls/v2/fragment_buffer.go b/vendor/github.com/pion/dtls/v2/fragment_buffer.go
index 02749939f..f20033758 100644
--- a/vendor/github.com/pion/dtls/v2/fragment_buffer.go
+++ b/vendor/github.com/pion/dtls/v2/fragment_buffer.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -6,6 +9,9 @@ import (
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
+// 2 megabytes
+const fragmentBufferMaxSize = 2000000
+
type fragment struct {
recordLayerHeader recordlayer.Header
handshakeHeader handshake.Header
@@ -23,10 +29,25 @@ func newFragmentBuffer() *fragmentBuffer {
return &fragmentBuffer{cache: map[uint16][]*fragment{}}
}
+// current total size of buffer
+func (f *fragmentBuffer) size() int {
+ size := 0
+ for i := range f.cache {
+ for j := range f.cache[i] {
+ size += len(f.cache[i][j].data)
+ }
+ }
+ return size
+}
+
// Attempts to push a DTLS packet to the fragmentBuffer
// when it returns true it means the fragmentBuffer has inserted and the buffer shouldn't be handled
// when an error returns it is fatal, and the DTLS connection should be stopped
func (f *fragmentBuffer) push(buf []byte) (bool, error) {
+ if f.size()+len(buf) >= fragmentBufferMaxSize {
+ return false, errFragmentBufferOverflow
+ }
+
frag := new(fragment)
if err := frag.recordLayerHeader.Unmarshal(buf); err != nil {
return false, err
@@ -76,7 +97,7 @@ func (f *fragmentBuffer) pop() (content []byte, epoch uint16) {
for _, f := range frags {
if f.handshakeHeader.FragmentOffset == targetOffset {
fragmentEnd := (f.handshakeHeader.FragmentOffset + f.handshakeHeader.FragmentLength)
- if fragmentEnd != f.handshakeHeader.Length {
+ if fragmentEnd != f.handshakeHeader.Length && f.handshakeHeader.FragmentLength != 0 {
if !appendMessage(fragmentEnd) {
return false
}
diff --git a/vendor/github.com/pion/dtls/v2/fuzz.go b/vendor/github.com/pion/dtls/v2/fuzz.go
deleted file mode 100644
index d6863241e..000000000
--- a/vendor/github.com/pion/dtls/v2/fuzz.go
+++ /dev/null
@@ -1,39 +0,0 @@
-//go:build gofuzz
-// +build gofuzz
-
-package dtls
-
-import "fmt"
-
-func partialHeaderMismatch(a, b recordlayer.Header) bool {
- // Ignoring content length for now.
- a.contentLen = b.contentLen
- return a != b
-}
-
-func FuzzRecordLayer(data []byte) int {
- var r recordLayer
- if err := r.Unmarshal(data); err != nil {
- return 0
- }
- buf, err := r.Marshal()
- if err != nil {
- return 1
- }
- if len(buf) == 0 {
- panic("zero buff") // nolint
- }
- var nr recordLayer
- if err = nr.Unmarshal(data); err != nil {
- panic(err) // nolint
- }
- if partialHeaderMismatch(nr.recordlayer.Header, r.recordlayer.Header) {
- panic( // nolint
- fmt.Sprintf("header mismatch: %+v != %+v",
- nr.recordlayer.Header, r.recordlayer.Header,
- ),
- )
- }
-
- return 1
-}
diff --git a/vendor/github.com/pion/dtls/v2/handshake_cache.go b/vendor/github.com/pion/dtls/v2/handshake_cache.go
index 063a85807..8d5960568 100644
--- a/vendor/github.com/pion/dtls/v2/handshake_cache.go
+++ b/vendor/github.com/pion/dtls/v2/handshake_cache.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -31,17 +34,10 @@ func newHandshakeCache() *handshakeCache {
return &handshakeCache{}
}
-func (h *handshakeCache) push(data []byte, epoch, messageSequence uint16, typ handshake.Type, isClient bool) bool { //nolint
+func (h *handshakeCache) push(data []byte, epoch, messageSequence uint16, typ handshake.Type, isClient bool) {
h.mu.Lock()
defer h.mu.Unlock()
- for _, i := range h.cache {
- if i.messageSequence == messageSequence &&
- i.isClient == isClient {
- return false
- }
- }
-
h.cache = append(h.cache, &handshakeCacheItem{
data: append([]byte{}, data...),
epoch: epoch,
@@ -49,7 +45,6 @@ func (h *handshakeCache) push(data []byte, epoch, messageSequence uint16, typ ha
typ: typ,
isClient: isClient,
})
- return true
}
// returns a list handshakes that match the requested rules
@@ -77,7 +72,7 @@ func (h *handshakeCache) pull(rules ...handshakeCachePullRule) []*handshakeCache
}
// fullPullMap pulls all handshakes between rules[0] to rules[len(rules)-1] as map.
-func (h *handshakeCache) fullPullMap(startSeq int, rules ...handshakeCachePullRule) (int, map[handshake.Type]handshake.Message, bool) {
+func (h *handshakeCache) fullPullMap(startSeq int, cipherSuite CipherSuite, rules ...handshakeCachePullRule) (int, map[handshake.Type]handshake.Message, bool) {
h.mu.Lock()
defer h.mu.Unlock()
@@ -108,7 +103,13 @@ func (h *handshakeCache) fullPullMap(startSeq int, rules ...handshakeCachePullRu
if i == nil {
continue
}
- rawHandshake := &handshake.Handshake{}
+ var keyExchangeAlgorithm CipherSuiteKeyExchangeAlgorithm
+ if cipherSuite != nil {
+ keyExchangeAlgorithm = cipherSuite.KeyExchangeAlgorithm()
+ }
+ rawHandshake := &handshake.Handshake{
+ KeyExchangeAlgorithm: keyExchangeAlgorithm,
+ }
if err := rawHandshake.Unmarshal(i.data); err != nil {
return startSeq, nil, false
}
diff --git a/vendor/github.com/pion/dtls/v2/handshaker.go b/vendor/github.com/pion/dtls/v2/handshaker.go
index 1c7b9ffa2..1c6d58fe9 100644
--- a/vendor/github.com/pion/dtls/v2/handshaker.go
+++ b/vendor/github.com/pion/dtls/v2/handshaker.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -9,6 +12,7 @@ import (
"sync"
"time"
+ "github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/dtls/v2/pkg/crypto/signaturehash"
"github.com/pion/dtls/v2/pkg/protocol/alert"
"github.com/pion/dtls/v2/pkg/protocol/handshake"
@@ -101,16 +105,22 @@ type handshakeConfig struct {
nameToCertificate map[string]*tls.Certificate
insecureSkipVerify bool
verifyPeerCertificate func(rawCerts [][]byte, verifiedChains [][]*x509.Certificate) error
+ verifyConnection func(*State) error
sessionStore SessionStore
rootCAs *x509.CertPool
clientCAs *x509.CertPool
retransmitInterval time.Duration
customCipherSuites func() []CipherSuite
+ ellipticCurves []elliptic.Curve
+ insecureSkipHelloVerify bool
onFlightState func(flightVal, handshakeState)
log logging.LeveledLogger
keyLogWriter io.Writer
+ localGetCertificate func(*ClientHelloInfo) (*tls.Certificate, error)
+ localGetClientCertificate func(*CertificateRequestInfo) (*tls.Certificate, error)
+
initialEpoch uint16
mu sync.Mutex
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_128_ccm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_128_ccm.go
index dcc537991..f78b6dc2c 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_128_ccm.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_128_ccm.go
@@ -1,108 +1,33 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
- "crypto/sha256"
- "fmt"
- "hash"
- "sync/atomic"
-
"github.com/pion/dtls/v2/pkg/crypto/ciphersuite"
"github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
- "github.com/pion/dtls/v2/pkg/crypto/prf"
- "github.com/pion/dtls/v2/pkg/protocol/recordlayer"
)
// Aes128Ccm is a base class used by multiple AES-CCM Ciphers
type Aes128Ccm struct {
- ccm atomic.Value // *cryptoCCM
- clientCertificateType clientcertificate.Type
- id ID
- psk bool
- cryptoCCMTagLen ciphersuite.CCMTagLen
+ AesCcm
}
-func newAes128Ccm(clientCertificateType clientcertificate.Type, id ID, psk bool, cryptoCCMTagLen ciphersuite.CCMTagLen) *Aes128Ccm {
+func newAes128Ccm(clientCertificateType clientcertificate.Type, id ID, psk bool, cryptoCCMTagLen ciphersuite.CCMTagLen, keyExchangeAlgorithm KeyExchangeAlgorithm, ecc bool) *Aes128Ccm {
return &Aes128Ccm{
- clientCertificateType: clientCertificateType,
- id: id,
- psk: psk,
- cryptoCCMTagLen: cryptoCCMTagLen,
+ AesCcm: AesCcm{
+ clientCertificateType: clientCertificateType,
+ id: id,
+ psk: psk,
+ cryptoCCMTagLen: cryptoCCMTagLen,
+ keyExchangeAlgorithm: keyExchangeAlgorithm,
+ ecc: ecc,
+ },
}
}
-// CertificateType returns what type of certificate this CipherSuite exchanges
-func (c *Aes128Ccm) CertificateType() clientcertificate.Type {
- return c.clientCertificateType
-}
-
-// ID returns the ID of the CipherSuite
-func (c *Aes128Ccm) ID() ID {
- return c.id
-}
-
-func (c *Aes128Ccm) String() string {
- return c.id.String()
-}
-
-// HashFunc returns the hashing func for this CipherSuite
-func (c *Aes128Ccm) HashFunc() func() hash.Hash {
- return sha256.New
-}
-
-// AuthenticationType controls what authentication method is using during the handshake
-func (c *Aes128Ccm) AuthenticationType() AuthenticationType {
- if c.psk {
- return AuthenticationTypePreSharedKey
- }
- return AuthenticationTypeCertificate
-}
-
-// IsInitialized returns if the CipherSuite has keying material and can
-// encrypt/decrypt packets
-func (c *Aes128Ccm) IsInitialized() bool {
- return c.ccm.Load() != nil
-}
-
// Init initializes the internal Cipher with keying material
func (c *Aes128Ccm) Init(masterSecret, clientRandom, serverRandom []byte, isClient bool) error {
- const (
- prfMacLen = 0
- prfKeyLen = 16
- prfIvLen = 4
- )
-
- keys, err := prf.GenerateEncryptionKeys(masterSecret, clientRandom, serverRandom, prfMacLen, prfKeyLen, prfIvLen, c.HashFunc())
- if err != nil {
- return err
- }
-
- var ccm *ciphersuite.CCM
- if isClient {
- ccm, err = ciphersuite.NewCCM(c.cryptoCCMTagLen, keys.ClientWriteKey, keys.ClientWriteIV, keys.ServerWriteKey, keys.ServerWriteIV)
- } else {
- ccm, err = ciphersuite.NewCCM(c.cryptoCCMTagLen, keys.ServerWriteKey, keys.ServerWriteIV, keys.ClientWriteKey, keys.ClientWriteIV)
- }
- c.ccm.Store(ccm)
-
- return err
-}
-
-// Encrypt encrypts a single TLS RecordLayer
-func (c *Aes128Ccm) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
- ccm := c.ccm.Load()
- if ccm == nil {
- return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
- }
-
- return ccm.(*ciphersuite.CCM).Encrypt(pkt, raw)
-}
-
-// Decrypt decrypts a single TLS RecordLayer
-func (c *Aes128Ccm) Decrypt(raw []byte) ([]byte, error) {
- ccm := c.ccm.Load()
- if ccm == nil {
- return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
- }
-
- return ccm.(*ciphersuite.CCM).Decrypt(raw)
+ const prfKeyLen = 16
+ return c.AesCcm.Init(masterSecret, clientRandom, serverRandom, isClient, prfKeyLen)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_256_ccm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_256_ccm.go
new file mode 100644
index 000000000..bb8128627
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_256_ccm.go
@@ -0,0 +1,33 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ciphersuite
+
+import (
+ "github.com/pion/dtls/v2/pkg/crypto/ciphersuite"
+ "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
+)
+
+// Aes256Ccm is a base class used by multiple AES-CCM Ciphers
+type Aes256Ccm struct {
+ AesCcm
+}
+
+func newAes256Ccm(clientCertificateType clientcertificate.Type, id ID, psk bool, cryptoCCMTagLen ciphersuite.CCMTagLen, keyExchangeAlgorithm KeyExchangeAlgorithm, ecc bool) *Aes256Ccm {
+ return &Aes256Ccm{
+ AesCcm: AesCcm{
+ clientCertificateType: clientCertificateType,
+ id: id,
+ psk: psk,
+ cryptoCCMTagLen: cryptoCCMTagLen,
+ keyExchangeAlgorithm: keyExchangeAlgorithm,
+ ecc: ecc,
+ },
+ }
+}
+
+// Init initializes the internal Cipher with keying material
+func (c *Aes256Ccm) Init(masterSecret, clientRandom, serverRandom []byte, isClient bool) error {
+ const prfKeyLen = 32
+ return c.AesCcm.Init(masterSecret, clientRandom, serverRandom, isClient, prfKeyLen)
+}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_ccm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_ccm.go
new file mode 100644
index 000000000..dc5119823
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/aes_ccm.go
@@ -0,0 +1,113 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ciphersuite
+
+import (
+ "crypto/sha256"
+ "fmt"
+ "hash"
+ "sync/atomic"
+
+ "github.com/pion/dtls/v2/pkg/crypto/ciphersuite"
+ "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
+ "github.com/pion/dtls/v2/pkg/crypto/prf"
+ "github.com/pion/dtls/v2/pkg/protocol/recordlayer"
+)
+
+// AesCcm is a base class used by multiple AES-CCM Ciphers
+type AesCcm struct {
+ ccm atomic.Value // *cryptoCCM
+ clientCertificateType clientcertificate.Type
+ id ID
+ psk bool
+ keyExchangeAlgorithm KeyExchangeAlgorithm
+ cryptoCCMTagLen ciphersuite.CCMTagLen
+ ecc bool
+}
+
+// CertificateType returns what type of certificate this CipherSuite exchanges
+func (c *AesCcm) CertificateType() clientcertificate.Type {
+ return c.clientCertificateType
+}
+
+// ID returns the ID of the CipherSuite
+func (c *AesCcm) ID() ID {
+ return c.id
+}
+
+func (c *AesCcm) String() string {
+ return c.id.String()
+}
+
+// ECC uses Elliptic Curve Cryptography
+func (c *AesCcm) ECC() bool {
+ return c.ecc
+}
+
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *AesCcm) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return c.keyExchangeAlgorithm
+}
+
+// HashFunc returns the hashing func for this CipherSuite
+func (c *AesCcm) HashFunc() func() hash.Hash {
+ return sha256.New
+}
+
+// AuthenticationType controls what authentication method is using during the handshake
+func (c *AesCcm) AuthenticationType() AuthenticationType {
+ if c.psk {
+ return AuthenticationTypePreSharedKey
+ }
+ return AuthenticationTypeCertificate
+}
+
+// IsInitialized returns if the CipherSuite has keying material and can
+// encrypt/decrypt packets
+func (c *AesCcm) IsInitialized() bool {
+ return c.ccm.Load() != nil
+}
+
+// Init initializes the internal Cipher with keying material
+func (c *AesCcm) Init(masterSecret, clientRandom, serverRandom []byte, isClient bool, prfKeyLen int) error {
+ const (
+ prfMacLen = 0
+ prfIvLen = 4
+ )
+
+ keys, err := prf.GenerateEncryptionKeys(masterSecret, clientRandom, serverRandom, prfMacLen, prfKeyLen, prfIvLen, c.HashFunc())
+ if err != nil {
+ return err
+ }
+
+ var ccm *ciphersuite.CCM
+ if isClient {
+ ccm, err = ciphersuite.NewCCM(c.cryptoCCMTagLen, keys.ClientWriteKey, keys.ClientWriteIV, keys.ServerWriteKey, keys.ServerWriteIV)
+ } else {
+ ccm, err = ciphersuite.NewCCM(c.cryptoCCMTagLen, keys.ServerWriteKey, keys.ServerWriteIV, keys.ClientWriteKey, keys.ClientWriteIV)
+ }
+ c.ccm.Store(ccm)
+
+ return err
+}
+
+// Encrypt encrypts a single TLS RecordLayer
+func (c *AesCcm) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
+ cipherSuite, ok := c.ccm.Load().(*ciphersuite.CCM)
+ if !ok {
+ return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
+ }
+
+ return cipherSuite.Encrypt(pkt, raw)
+}
+
+// Decrypt decrypts a single TLS RecordLayer
+func (c *AesCcm) Decrypt(raw []byte) ([]byte, error) {
+ cipherSuite, ok := c.ccm.Load().(*ciphersuite.CCM)
+ if !ok {
+ return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
+ }
+
+ return cipherSuite.Decrypt(raw)
+}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/ciphersuite.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/ciphersuite.go
index 7405792c2..f44f29fd3 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/ciphersuite.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/ciphersuite.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package ciphersuite provides TLS Ciphers as registered with the IANA https://www.iana.org/assignments/tls-parameters/tls-parameters.xhtml#tls-parameters-4
package ciphersuite
@@ -5,6 +8,7 @@ import (
"errors"
"fmt"
+ "github.com/pion/dtls/v2/internal/ciphersuite/types"
"github.com/pion/dtls/v2/pkg/protocol"
)
@@ -31,6 +35,8 @@ func (i ID) String() string {
return "TLS_PSK_WITH_AES_128_CCM"
case TLS_PSK_WITH_AES_128_CCM_8:
return "TLS_PSK_WITH_AES_128_CCM_8"
+ case TLS_PSK_WITH_AES_256_CCM_8:
+ return "TLS_PSK_WITH_AES_256_CCM_8"
case TLS_PSK_WITH_AES_128_GCM_SHA256:
return "TLS_PSK_WITH_AES_128_GCM_SHA256"
case TLS_PSK_WITH_AES_128_CBC_SHA256:
@@ -39,6 +45,8 @@ func (i ID) String() string {
return "TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384"
case TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384:
return "TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384"
+ case TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256:
+ return "TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256"
default:
return fmt.Sprintf("unknown(%v)", uint16(i))
}
@@ -47,31 +55,44 @@ func (i ID) String() string {
// Supported Cipher Suites
const (
// AES-128-CCM
- TLS_ECDHE_ECDSA_WITH_AES_128_CCM ID = 0xc0ac //nolint:golint,stylecheck
- TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 ID = 0xc0ae //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_CCM ID = 0xc0ac //nolint:revive,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 ID = 0xc0ae //nolint:revive,stylecheck
// AES-128-GCM-SHA256
- TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 ID = 0xc02b //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 ID = 0xc02f //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256 ID = 0xc02b //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 ID = 0xc02f //nolint:revive,stylecheck
- TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 ID = 0xc02c //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 ID = 0xc030 //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384 ID = 0xc02c //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 ID = 0xc030 //nolint:revive,stylecheck
// AES-256-CBC-SHA
- TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA ID = 0xc00a //nolint:golint,stylecheck
- TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA ID = 0xc014 //nolint:golint,stylecheck
+ TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA ID = 0xc00a //nolint:revive,stylecheck
+ TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA ID = 0xc014 //nolint:revive,stylecheck
- TLS_PSK_WITH_AES_128_CCM ID = 0xc0a4 //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_CCM_8 ID = 0xc0a8 //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_GCM_SHA256 ID = 0x00a8 //nolint:golint,stylecheck
- TLS_PSK_WITH_AES_128_CBC_SHA256 ID = 0x00ae //nolint:golint,stylecheck
+ TLS_PSK_WITH_AES_128_CCM ID = 0xc0a4 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_CCM_8 ID = 0xc0a8 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_256_CCM_8 ID = 0xc0a9 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_GCM_SHA256 ID = 0x00a8 //nolint:revive,stylecheck
+ TLS_PSK_WITH_AES_128_CBC_SHA256 ID = 0x00ae //nolint:revive,stylecheck
+
+ TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 ID = 0xC037 //nolint:revive,stylecheck
)
// AuthenticationType controls what authentication method is using during the handshake
-type AuthenticationType int
+type AuthenticationType = types.AuthenticationType
// AuthenticationType Enums
const (
- AuthenticationTypeCertificate AuthenticationType = iota + 1
- AuthenticationTypePreSharedKey
- AuthenticationTypeAnonymous
+ AuthenticationTypeCertificate AuthenticationType = types.AuthenticationTypeCertificate
+ AuthenticationTypePreSharedKey AuthenticationType = types.AuthenticationTypePreSharedKey
+ AuthenticationTypeAnonymous AuthenticationType = types.AuthenticationTypeAnonymous
+)
+
+// KeyExchangeAlgorithm controls what exchange algorithm was chosen.
+type KeyExchangeAlgorithm = types.KeyExchangeAlgorithm
+
+// KeyExchangeAlgorithm Bitmask
+const (
+ KeyExchangeAlgorithmNone KeyExchangeAlgorithm = types.KeyExchangeAlgorithmNone
+ KeyExchangeAlgorithmPsk KeyExchangeAlgorithm = types.KeyExchangeAlgorithmPsk
+ KeyExchangeAlgorithmEcdhe KeyExchangeAlgorithm = types.KeyExchangeAlgorithmEcdhe
)
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm.go
index ac73556fb..8367b2c6d 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -7,5 +10,5 @@ import (
// NewTLSEcdheEcdsaWithAes128Ccm constructs a TLS_ECDHE_ECDSA_WITH_AES_128_CCM Cipher
func NewTLSEcdheEcdsaWithAes128Ccm() *Aes128Ccm {
- return newAes128Ccm(clientcertificate.ECDSASign, TLS_ECDHE_ECDSA_WITH_AES_128_CCM, false, ciphersuite.CCMTagLength)
+ return newAes128Ccm(clientcertificate.ECDSASign, TLS_ECDHE_ECDSA_WITH_AES_128_CCM, false, ciphersuite.CCMTagLength, KeyExchangeAlgorithmEcdhe, true)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm8.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm8.go
index 49b1a8304..11b687327 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm8.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_ccm8.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -7,5 +10,5 @@ import (
// NewTLSEcdheEcdsaWithAes128Ccm8 creates a new TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8 CipherSuite
func NewTLSEcdheEcdsaWithAes128Ccm8() *Aes128Ccm {
- return newAes128Ccm(clientcertificate.ECDSASign, TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8, false, ciphersuite.CCMTagLength8)
+ return newAes128Ccm(clientcertificate.ECDSASign, TLS_ECDHE_ECDSA_WITH_AES_128_CCM_8, false, ciphersuite.CCMTagLength8, KeyExchangeAlgorithmEcdhe, true)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_gcm_sha256.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_gcm_sha256.go
index ede12bbe5..0c919fe47 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_gcm_sha256.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_128_gcm_sha256.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -22,6 +25,16 @@ func (c *TLSEcdheEcdsaWithAes128GcmSha256) CertificateType() clientcertificate.T
return clientcertificate.ECDSASign
}
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *TLSEcdheEcdsaWithAes128GcmSha256) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return KeyExchangeAlgorithmEcdhe
+}
+
+// ECC uses Elliptic Curve Cryptography
+func (c *TLSEcdheEcdsaWithAes128GcmSha256) ECC() bool {
+ return true
+}
+
// ID returns the ID of the CipherSuite
func (c *TLSEcdheEcdsaWithAes128GcmSha256) ID() ID {
return TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256
@@ -76,20 +89,20 @@ func (c *TLSEcdheEcdsaWithAes128GcmSha256) Init(masterSecret, clientRandom, serv
// Encrypt encrypts a single TLS RecordLayer
func (c *TLSEcdheEcdsaWithAes128GcmSha256) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
- gcm := c.gcm.Load()
- if gcm == nil {
+ cipherSuite, ok := c.gcm.Load().(*ciphersuite.GCM)
+ if !ok {
return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
}
- return gcm.(*ciphersuite.GCM).Encrypt(pkt, raw)
+ return cipherSuite.Encrypt(pkt, raw)
}
// Decrypt decrypts a single TLS RecordLayer
func (c *TLSEcdheEcdsaWithAes128GcmSha256) Decrypt(raw []byte) ([]byte, error) {
- gcm := c.gcm.Load()
- if gcm == nil {
+ cipherSuite, ok := c.gcm.Load().(*ciphersuite.GCM)
+ if !ok {
return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
}
- return gcm.(*ciphersuite.GCM).Decrypt(raw)
+ return cipherSuite.Decrypt(raw)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_cbc_sha.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_cbc_sha.go
index f7a33ad8d..577192c89 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_cbc_sha.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_cbc_sha.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -23,6 +26,16 @@ func (c *TLSEcdheEcdsaWithAes256CbcSha) CertificateType() clientcertificate.Type
return clientcertificate.ECDSASign
}
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *TLSEcdheEcdsaWithAes256CbcSha) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return KeyExchangeAlgorithmEcdhe
+}
+
+// ECC uses Elliptic Curve Cryptography
+func (c *TLSEcdheEcdsaWithAes256CbcSha) ECC() bool {
+ return true
+}
+
// ID returns the ID of the CipherSuite
func (c *TLSEcdheEcdsaWithAes256CbcSha) ID() ID {
return TLS_ECDHE_ECDSA_WITH_AES_256_CBC_SHA
@@ -82,20 +95,20 @@ func (c *TLSEcdheEcdsaWithAes256CbcSha) Init(masterSecret, clientRandom, serverR
// Encrypt encrypts a single TLS RecordLayer
func (c *TLSEcdheEcdsaWithAes256CbcSha) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
- cbc := c.cbc.Load()
- if cbc == nil { // !c.isInitialized()
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok {
return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
}
- return cbc.(*ciphersuite.CBC).Encrypt(pkt, raw)
+ return cipherSuite.Encrypt(pkt, raw)
}
// Decrypt decrypts a single TLS RecordLayer
func (c *TLSEcdheEcdsaWithAes256CbcSha) Decrypt(raw []byte) ([]byte, error) {
- cbc := c.cbc.Load()
- if cbc == nil { // !c.isInitialized()
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok {
return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
}
- return cbc.(*ciphersuite.CBC).Decrypt(raw)
+ return cipherSuite.Decrypt(raw)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_gcm_sha384.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_gcm_sha384.go
index a2fe30244..2a3cfa4f5 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_gcm_sha384.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_ecdsa_with_aes_256_gcm_sha384.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_psk_with_aes_128_cbc_sha256.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_psk_with_aes_128_cbc_sha256.go
new file mode 100644
index 000000000..75a25633a
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_psk_with_aes_128_cbc_sha256.go
@@ -0,0 +1,118 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ciphersuite
+
+import (
+ "crypto/sha256"
+ "fmt"
+ "hash"
+ "sync/atomic"
+
+ "github.com/pion/dtls/v2/pkg/crypto/ciphersuite"
+ "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
+ "github.com/pion/dtls/v2/pkg/crypto/prf"
+ "github.com/pion/dtls/v2/pkg/protocol/recordlayer"
+)
+
+// TLSEcdhePskWithAes128CbcSha256 implements the TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 CipherSuite
+type TLSEcdhePskWithAes128CbcSha256 struct {
+ cbc atomic.Value // *cryptoCBC
+}
+
+// NewTLSEcdhePskWithAes128CbcSha256 creates TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256 cipher.
+func NewTLSEcdhePskWithAes128CbcSha256() *TLSEcdhePskWithAes128CbcSha256 {
+ return &TLSEcdhePskWithAes128CbcSha256{}
+}
+
+// CertificateType returns what type of certificate this CipherSuite exchanges
+func (c *TLSEcdhePskWithAes128CbcSha256) CertificateType() clientcertificate.Type {
+ return clientcertificate.Type(0)
+}
+
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *TLSEcdhePskWithAes128CbcSha256) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return (KeyExchangeAlgorithmPsk | KeyExchangeAlgorithmEcdhe)
+}
+
+// ECC uses Elliptic Curve Cryptography
+func (c *TLSEcdhePskWithAes128CbcSha256) ECC() bool {
+ return true
+}
+
+// ID returns the ID of the CipherSuite
+func (c *TLSEcdhePskWithAes128CbcSha256) ID() ID {
+ return TLS_ECDHE_PSK_WITH_AES_128_CBC_SHA256
+}
+
+func (c *TLSEcdhePskWithAes128CbcSha256) String() string {
+ return "TLS-ECDHE-PSK-WITH-AES-128-CBC-SHA256"
+}
+
+// HashFunc returns the hashing func for this CipherSuite
+func (c *TLSEcdhePskWithAes128CbcSha256) HashFunc() func() hash.Hash {
+ return sha256.New
+}
+
+// AuthenticationType controls what authentication method is using during the handshake
+func (c *TLSEcdhePskWithAes128CbcSha256) AuthenticationType() AuthenticationType {
+ return AuthenticationTypePreSharedKey
+}
+
+// IsInitialized returns if the CipherSuite has keying material and can
+// encrypt/decrypt packets
+func (c *TLSEcdhePskWithAes128CbcSha256) IsInitialized() bool {
+ return c.cbc.Load() != nil
+}
+
+// Init initializes the internal Cipher with keying material
+func (c *TLSEcdhePskWithAes128CbcSha256) Init(masterSecret, clientRandom, serverRandom []byte, isClient bool) error {
+ const (
+ prfMacLen = 32
+ prfKeyLen = 16
+ prfIvLen = 16
+ )
+
+ keys, err := prf.GenerateEncryptionKeys(masterSecret, clientRandom, serverRandom, prfMacLen, prfKeyLen, prfIvLen, c.HashFunc())
+ if err != nil {
+ return err
+ }
+
+ var cbc *ciphersuite.CBC
+ if isClient {
+ cbc, err = ciphersuite.NewCBC(
+ keys.ClientWriteKey, keys.ClientWriteIV, keys.ClientMACKey,
+ keys.ServerWriteKey, keys.ServerWriteIV, keys.ServerMACKey,
+ c.HashFunc(),
+ )
+ } else {
+ cbc, err = ciphersuite.NewCBC(
+ keys.ServerWriteKey, keys.ServerWriteIV, keys.ServerMACKey,
+ keys.ClientWriteKey, keys.ClientWriteIV, keys.ClientMACKey,
+ c.HashFunc(),
+ )
+ }
+ c.cbc.Store(cbc)
+
+ return err
+}
+
+// Encrypt encrypts a single TLS RecordLayer
+func (c *TLSEcdhePskWithAes128CbcSha256) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok { // !c.isInitialized()
+ return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
+ }
+
+ return cipherSuite.Encrypt(pkt, raw)
+}
+
+// Decrypt decrypts a single TLS RecordLayer
+func (c *TLSEcdhePskWithAes128CbcSha256) Decrypt(raw []byte) ([]byte, error) {
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok { // !c.isInitialized()
+ return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
+ }
+
+ return cipherSuite.Decrypt(raw)
+}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_128_gcm_sha256.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_128_gcm_sha256.go
index 70400c37d..478a2e0dc 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_128_gcm_sha256.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_128_gcm_sha256.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_cbc_sha.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_cbc_sha.go
index 0d82dc3ad..8e88ee639 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_cbc_sha.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_cbc_sha.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_gcm_sha384.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_gcm_sha384.go
index 3473527e7..752fb529c 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_gcm_sha384.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_ecdhe_rsa_with_aes_256_gcm_sha384.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_cbc_sha256.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_cbc_sha256.go
index 43e5e3800..7336ad946 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_cbc_sha256.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_cbc_sha256.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -22,6 +25,16 @@ func (c *TLSPskWithAes128CbcSha256) CertificateType() clientcertificate.Type {
return clientcertificate.Type(0)
}
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *TLSPskWithAes128CbcSha256) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return KeyExchangeAlgorithmPsk
+}
+
+// ECC uses Elliptic Curve Cryptography
+func (c *TLSPskWithAes128CbcSha256) ECC() bool {
+ return false
+}
+
// ID returns the ID of the CipherSuite
func (c *TLSPskWithAes128CbcSha256) ID() ID {
return TLS_PSK_WITH_AES_128_CBC_SHA256
@@ -81,20 +94,20 @@ func (c *TLSPskWithAes128CbcSha256) Init(masterSecret, clientRandom, serverRando
// Encrypt encrypts a single TLS RecordLayer
func (c *TLSPskWithAes128CbcSha256) Encrypt(pkt *recordlayer.RecordLayer, raw []byte) ([]byte, error) {
- cbc := c.cbc.Load()
- if cbc == nil { // !c.isInitialized()
- return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok {
+ return nil, fmt.Errorf("%w, unable to encrypt", errCipherSuiteNotInit)
}
- return cbc.(*ciphersuite.CBC).Encrypt(pkt, raw)
+ return cipherSuite.Encrypt(pkt, raw)
}
// Decrypt decrypts a single TLS RecordLayer
func (c *TLSPskWithAes128CbcSha256) Decrypt(raw []byte) ([]byte, error) {
- cbc := c.cbc.Load()
- if cbc == nil { // !c.isInitialized()
+ cipherSuite, ok := c.cbc.Load().(*ciphersuite.CBC)
+ if !ok {
return nil, fmt.Errorf("%w, unable to decrypt", errCipherSuiteNotInit)
}
- return cbc.(*ciphersuite.CBC).Decrypt(raw)
+ return cipherSuite.Decrypt(raw)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm.go
index 8c13bb1b3..1ded09b88 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -7,5 +10,5 @@ import (
// NewTLSPskWithAes128Ccm returns the TLS_PSK_WITH_AES_128_CCM CipherSuite
func NewTLSPskWithAes128Ccm() *Aes128Ccm {
- return newAes128Ccm(clientcertificate.Type(0), TLS_PSK_WITH_AES_128_CCM, true, ciphersuite.CCMTagLength)
+ return newAes128Ccm(clientcertificate.Type(0), TLS_PSK_WITH_AES_128_CCM, true, ciphersuite.CCMTagLength, KeyExchangeAlgorithmPsk, false)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm8.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm8.go
index d04abb4d2..478197074 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm8.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_ccm8.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -7,5 +10,5 @@ import (
// NewTLSPskWithAes128Ccm8 returns the TLS_PSK_WITH_AES_128_CCM_8 CipherSuite
func NewTLSPskWithAes128Ccm8() *Aes128Ccm {
- return newAes128Ccm(clientcertificate.Type(0), TLS_PSK_WITH_AES_128_CCM_8, true, ciphersuite.CCMTagLength8)
+ return newAes128Ccm(clientcertificate.Type(0), TLS_PSK_WITH_AES_128_CCM_8, true, ciphersuite.CCMTagLength8, KeyExchangeAlgorithmPsk, false)
}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_gcm_sha256.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_gcm_sha256.go
index 5f1033559..8ab5b89a8 100644
--- a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_gcm_sha256.go
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_128_gcm_sha256.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
@@ -12,6 +15,11 @@ func (c *TLSPskWithAes128GcmSha256) CertificateType() clientcertificate.Type {
return clientcertificate.Type(0)
}
+// KeyExchangeAlgorithm controls what key exchange algorithm is using during the handshake
+func (c *TLSPskWithAes128GcmSha256) KeyExchangeAlgorithm() KeyExchangeAlgorithm {
+ return KeyExchangeAlgorithmPsk
+}
+
// ID returns the ID of the CipherSuite
func (c *TLSPskWithAes128GcmSha256) ID() ID {
return TLS_PSK_WITH_AES_128_GCM_SHA256
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_256_ccm8.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_256_ccm8.go
new file mode 100644
index 000000000..32d503018
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/tls_psk_with_aes_256_ccm8.go
@@ -0,0 +1,14 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ciphersuite
+
+import (
+ "github.com/pion/dtls/v2/pkg/crypto/ciphersuite"
+ "github.com/pion/dtls/v2/pkg/crypto/clientcertificate"
+)
+
+// NewTLSPskWithAes256Ccm8 returns the TLS_PSK_WITH_AES_256_CCM_8 CipherSuite
+func NewTLSPskWithAes256Ccm8() *Aes256Ccm {
+ return newAes256Ccm(clientcertificate.Type(0), TLS_PSK_WITH_AES_256_CCM_8, true, ciphersuite.CCMTagLength8, KeyExchangeAlgorithmPsk, false)
+}
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/authentication_type.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/authentication_type.go
new file mode 100644
index 000000000..2da21e642
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/authentication_type.go
@@ -0,0 +1,14 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package types
+
+// AuthenticationType controls what authentication method is using during the handshake
+type AuthenticationType int
+
+// AuthenticationType Enums
+const (
+ AuthenticationTypeCertificate AuthenticationType = iota + 1
+ AuthenticationTypePreSharedKey
+ AuthenticationTypeAnonymous
+)
diff --git a/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/key_exchange_algorithm.go b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/key_exchange_algorithm.go
new file mode 100644
index 000000000..c2c39113a
--- /dev/null
+++ b/vendor/github.com/pion/dtls/v2/internal/ciphersuite/types/key_exchange_algorithm.go
@@ -0,0 +1,20 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+// Package types provides types for TLS Ciphers
+package types
+
+// KeyExchangeAlgorithm controls what exchange algorithm was chosen.
+type KeyExchangeAlgorithm int
+
+// KeyExchangeAlgorithm Bitmask
+const (
+ KeyExchangeAlgorithmNone KeyExchangeAlgorithm = 0
+ KeyExchangeAlgorithmPsk KeyExchangeAlgorithm = iota << 1
+ KeyExchangeAlgorithmEcdhe
+)
+
+// Has check if keyExchangeAlgorithm is supported.
+func (a KeyExchangeAlgorithm) Has(v KeyExchangeAlgorithm) bool {
+ return (a & v) == v
+}
diff --git a/vendor/github.com/pion/dtls/v2/internal/closer/closer.go b/vendor/github.com/pion/dtls/v2/internal/closer/closer.go
index b99e13e44..bfa171cda 100644
--- a/vendor/github.com/pion/dtls/v2/internal/closer/closer.go
+++ b/vendor/github.com/pion/dtls/v2/internal/closer/closer.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package closer provides signaling channel for shutdown
package closer
diff --git a/vendor/github.com/pion/dtls/v2/internal/util/util.go b/vendor/github.com/pion/dtls/v2/internal/util/util.go
index 746a670f4..685910fc2 100644
--- a/vendor/github.com/pion/dtls/v2/internal/util/util.go
+++ b/vendor/github.com/pion/dtls/v2/internal/util/util.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package util contains small helpers used across the repo
package util
diff --git a/vendor/github.com/pion/dtls/v2/listener.go b/vendor/github.com/pion/dtls/v2/listener.go
index bf80345b1..190d236c7 100644
--- a/vendor/github.com/pion/dtls/v2/listener.go
+++ b/vendor/github.com/pion/dtls/v2/listener.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -5,7 +8,7 @@ import (
"github.com/pion/dtls/v2/pkg/protocol"
"github.com/pion/dtls/v2/pkg/protocol/recordlayer"
- "github.com/pion/udp"
+ "github.com/pion/transport/v2/udp"
)
// Listen creates a DTLS listener
diff --git a/vendor/github.com/pion/dtls/v2/packet.go b/vendor/github.com/pion/dtls/v2/packet.go
index 8366a3c3d..55d6272ee 100644
--- a/vendor/github.com/pion/dtls/v2/packet.go
+++ b/vendor/github.com/pion/dtls/v2/packet.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import "github.com/pion/dtls/v2/pkg/protocol/recordlayer"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/ccm/ccm.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/ccm/ccm.go
index 20e3436e2..d6e6fc479 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/ccm/ccm.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/ccm/ccm.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package ccm implements a CCM, Counter with CBC-MAC
// as per RFC 3610.
//
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/cbc.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/cbc.go
index 8ff163486..460fb1437 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/cbc.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/cbc.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import ( //nolint:gci
@@ -39,11 +42,21 @@ func NewCBC(localKey, localWriteIV, localMac, remoteKey, remoteWriteIV, remoteMa
return nil, err
}
+ writeCBC, ok := cipher.NewCBCEncrypter(writeBlock, localWriteIV).(cbcMode)
+ if !ok {
+ return nil, errFailedToCast
+ }
+
+ readCBC, ok := cipher.NewCBCDecrypter(readBlock, remoteWriteIV).(cbcMode)
+ if !ok {
+ return nil, errFailedToCast
+ }
+
return &CBC{
- writeCBC: cipher.NewCBCEncrypter(writeBlock, localWriteIV).(cbcMode),
+ writeCBC: writeCBC,
writeMac: localMac,
- readCBC: cipher.NewCBCDecrypter(readBlock, remoteWriteIV).(cbcMode),
+ readCBC: readCBC,
readMac: remoteMac,
h: h,
}, nil
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ccm.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ccm.go
index 354b1cc50..24050dc92 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ccm.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ccm.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -98,7 +101,7 @@ func (c *CCM) Decrypt(in []byte) ([]byte, error) {
additionalData := generateAEADAdditionalData(&h, len(out)-int(c.tagLen))
out, err = c.remoteCCM.Open(out[:0], nonce, out, additionalData)
if err != nil {
- return nil, fmt.Errorf("%w: %v", errDecryptPacket, err)
+ return nil, fmt.Errorf("%w: %v", errDecryptPacket, err) //nolint:errorlint
}
return append(in[:recordlayer.HeaderSize], out...), nil
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ciphersuite.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ciphersuite.go
index 72beffd09..9d9fb7418 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ciphersuite.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/ciphersuite.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package ciphersuite provides the crypto operations needed for a DTLS CipherSuite
package ciphersuite
@@ -13,6 +16,7 @@ var (
errNotEnoughRoomForNonce = &protocol.InternalError{Err: errors.New("buffer not long enough to contain nonce")} //nolint:goerr113
errDecryptPacket = &protocol.TemporaryError{Err: errors.New("failed to decrypt packet")} //nolint:goerr113
errInvalidMAC = &protocol.TemporaryError{Err: errors.New("invalid mac")} //nolint:goerr113
+ errFailedToCast = &protocol.FatalError{Err: errors.New("failed to cast")} //nolint:goerr113
)
func generateAEADAdditionalData(h *recordlayer.Header, payloadLen int) []byte {
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/gcm.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/gcm.go
index af986d46e..c0fd1f76f 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/gcm.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/ciphersuite/gcm.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ciphersuite
import (
@@ -94,7 +97,7 @@ func (g *GCM) Decrypt(in []byte) ([]byte, error) {
additionalData := generateAEADAdditionalData(&h, len(out)-gcmTagLength)
out, err = g.remoteGCM.Open(out[:0], nonce, out, additionalData)
if err != nil {
- return nil, fmt.Errorf("%w: %v", errDecryptPacket, err)
+ return nil, fmt.Errorf("%w: %v", errDecryptPacket, err) //nolint:errorlint
}
return append(in[:recordlayer.HeaderSize], out...), nil
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/clientcertificate/client_certificate.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/clientcertificate/client_certificate.go
index c222c01c7..ddfa39ebe 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/clientcertificate/client_certificate.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/clientcertificate/client_certificate.go
@@ -1,10 +1,13 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package clientcertificate provides all the support Client Certificate types
package clientcertificate
// Type is used to communicate what
// type of certificate is being transported
//
-//https://www.iana.org/assignments/tls-parameters/tls-parameters.xhtml#tls-parameters-2
+// https://www.iana.org/assignments/tls-parameters/tls-parameters.xhtml#tls-parameters-2
type Type byte
// ClientCertificateType enums
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/elliptic/elliptic.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/elliptic/elliptic.go
index 5b0e4fa14..126523872 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/elliptic/elliptic.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/elliptic/elliptic.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package elliptic provides elliptic curve cryptography for DTLS
package elliptic
@@ -5,6 +8,7 @@ import (
"crypto/elliptic"
"crypto/rand"
"errors"
+ "fmt"
"golang.org/x/crypto/curve25519"
)
@@ -57,6 +61,18 @@ const (
X25519 Curve = 0x001d
)
+func (c Curve) String() string {
+ switch c {
+ case P256:
+ return "P-256"
+ case P384:
+ return "P-384"
+ case X25519:
+ return "X25519"
+ }
+ return fmt.Sprintf("%#x", uint16(c))
+}
+
// Curves returns all curves we implement
func Curves() map[Curve]bool {
return map[Curve]bool{
@@ -68,7 +84,7 @@ func Curves() map[Curve]bool {
// GenerateKeypair generates a keypair for the given Curve
func GenerateKeypair(c Curve) (*Keypair, error) {
- switch c { //nolint:golint
+ switch c { //nolint:revive
case X25519:
tmp := make([]byte, 32)
if _, err := rand.Read(tmp); err != nil {
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/fingerprint.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/fingerprint.go
index 215b44ec7..7c66265c7 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/fingerprint.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/fingerprint.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package fingerprint provides a helper to create fingerprint string from certificate
package fingerprint
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/hash.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/hash.go
index 09107db92..3f988ffb7 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/hash.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/fingerprint/hash.go
@@ -1,8 +1,12 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package fingerprint
import (
"crypto"
"errors"
+ "strings"
)
var errInvalidHashAlgorithm = errors.New("fingerprint: invalid hash algorithm")
@@ -20,7 +24,7 @@ func nameToHash() map[string]crypto.Hash {
// HashFromString allows looking up a hash algorithm by it's string representation
func HashFromString(s string) (crypto.Hash, error) {
- if h, ok := nameToHash()[s]; ok {
+ if h, ok := nameToHash()[strings.ToLower(s)]; ok {
return h, nil
}
return 0, errInvalidHashAlgorithm
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/hash/hash.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/hash/hash.go
index 660326f78..9966626e3 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/hash/hash.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/hash/hash.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package hash provides TLS HashAlgorithm as defined in TLS 1.2
package hash
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/prf/prf.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/prf/prf.go
index d33df19cb..6e7b3ecba 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/prf/prf.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/prf/prf.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package prf implements TLS 1.2 Pseudorandom functions
package prf
@@ -74,6 +77,34 @@ func PSKPreMasterSecret(psk []byte) []byte {
return out
}
+// EcdhePSKPreMasterSecret implements TLS 1.2 Premaster Secret generation given a psk, a keypair and a curve
+//
+// https://datatracker.ietf.org/doc/html/rfc5489#section-2
+func EcdhePSKPreMasterSecret(psk, publicKey, privateKey []byte, curve elliptic.Curve) ([]byte, error) {
+ preMasterSecret, err := PreMasterSecret(publicKey, privateKey, curve)
+ if err != nil {
+ return nil, err
+ }
+ out := make([]byte, 2+len(preMasterSecret)+2+len(psk))
+
+ // write preMasterSecret length
+ offset := 0
+ binary.BigEndian.PutUint16(out[offset:], uint16(len(preMasterSecret)))
+ offset += 2
+
+ // write preMasterSecret
+ copy(out[offset:], preMasterSecret)
+ offset += len(preMasterSecret)
+
+ // write psk length
+ binary.BigEndian.PutUint16(out[offset:], uint16(len(psk)))
+ offset += 2
+
+ // write psk
+ copy(out[offset:], psk)
+ return out, nil
+}
+
// PreMasterSecret implements TLS 1.2 Premaster Secret generation given a keypair and a curve
func PreMasterSecret(publicKey, privateKey []byte, curve elliptic.Curve) ([]byte, error) {
switch curve {
@@ -107,14 +138,14 @@ func ellipticCurvePreMasterSecret(publicKey, privateKey []byte, c1, c2 ellipticS
// specify a PRF and, in general, SHOULD use the TLS PRF with SHA-256 or a
// stronger standard hash function.
//
-// P_hash(secret, seed) = HMAC_hash(secret, A(1) + seed) +
-// HMAC_hash(secret, A(2) + seed) +
-// HMAC_hash(secret, A(3) + seed) + ...
+// P_hash(secret, seed) = HMAC_hash(secret, A(1) + seed) +
+// HMAC_hash(secret, A(2) + seed) +
+// HMAC_hash(secret, A(3) + seed) + ...
//
// A() is defined as:
//
-// A(0) = seed
-// A(i) = HMAC_hash(secret, A(i-1))
+// A(0) = seed
+// A(i) = HMAC_hash(secret, A(i-1))
//
// P_hash can be iterated as many times as necessary to produce the
// required quantity of data. For example, if P_SHA256 is being used to
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/signature/signature.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/signature/signature.go
index d9150eb8c..fec7fba3b 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/signature/signature.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/signature/signature.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package signature provides our implemented Signature Algorithms
package signature
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/errors.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/errors.go
index 9d9d3b309..4aeb3e40a 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/errors.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package signaturehash
import "errors"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/signaturehash.go b/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/signaturehash.go
index f2017bc28..2561accd1 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/signaturehash.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/crypto/signaturehash/signaturehash.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package signaturehash provides the SignatureHashAlgorithm as defined in TLS 1.2
package signaturehash
@@ -7,10 +10,10 @@ import (
"crypto/ed25519"
"crypto/rsa"
"crypto/tls"
+ "fmt"
"github.com/pion/dtls/v2/pkg/crypto/hash"
"github.com/pion/dtls/v2/pkg/crypto/signature"
- "golang.org/x/xerrors"
)
// Algorithm is a signature/hash algorithm pairs which may be used in
@@ -70,11 +73,11 @@ func ParseSignatureSchemes(sigs []tls.SignatureScheme, insecureHashes bool) ([]A
sig := signature.Algorithm(ss & 0xFF)
if _, ok := signature.Algorithms()[sig]; !ok {
return nil,
- xerrors.Errorf("SignatureScheme %04x: %w", ss, errInvalidSignatureAlgorithm)
+ fmt.Errorf("SignatureScheme %04x: %w", ss, errInvalidSignatureAlgorithm)
}
h := hash.Algorithm(ss >> 8)
if _, ok := hash.Algorithms()[h]; !ok || (ok && h == hash.None) {
- return nil, xerrors.Errorf("SignatureScheme %04x: %w", ss, errInvalidHashAlgorithm)
+ return nil, fmt.Errorf("SignatureScheme %04x: %w", ss, errInvalidHashAlgorithm)
}
if h.Insecure() && !insecureHashes {
continue
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/alert/alert.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/alert/alert.go
index 663c6b379..91e9f4d60 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/alert/alert.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/alert/alert.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package alert implements TLS alert protocol https://tools.ietf.org/html/rfc5246#section-7.2
package alert
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/application_data.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/application_data.go
index e5fd6f549..f42211511 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/application_data.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/application_data.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package protocol
// ApplicationData messages are carried by the record layer and are
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/change_cipher_spec.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/change_cipher_spec.go
index b42647a05..87f28bc37 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/change_cipher_spec.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/change_cipher_spec.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package protocol
// ChangeCipherSpec protocol exists to signal transitions in
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/compression_method.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/compression_method.go
index 678e816cb..3478ee38c 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/compression_method.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/compression_method.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package protocol
// CompressionMethodID is the ID for a CompressionMethod
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/content.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/content.go
index 47e5c96bb..92c9db2bf 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/content.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/content.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package protocol
// ContentType represents the IANA Registered ContentTypes
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/errors.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/errors.go
index e52014a1e..d87aff7fb 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/errors.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package protocol
import (
@@ -84,7 +87,8 @@ func (e *TimeoutError) Error() string { return fmt.Sprintf("dtls timeout: %v", e
// Timeout implements net.Error.Timeout()
func (e *HandshakeError) Timeout() bool {
- if netErr, ok := e.Err.(net.Error); ok {
+ var netErr net.Error
+ if errors.As(e.Err, &netErr) {
return netErr.Timeout()
}
return false
@@ -92,8 +96,9 @@ func (e *HandshakeError) Timeout() bool {
// Temporary implements net.Error.Temporary()
func (e *HandshakeError) Temporary() bool {
- if netErr, ok := e.Err.(net.Error); ok {
- return netErr.Temporary()
+ var netErr net.Error
+ if errors.As(e.Err, &netErr) {
+ return netErr.Temporary() //nolint
}
return false
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/alpn.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/alpn.go
index 8d7e1123e..e780dc9e1 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/alpn.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/alpn.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/errors.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/errors.go
index 82d8b3408..c5e954ce5 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/errors.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/extension.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/extension.go
index ec4c1ff5c..5173a5863 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/extension.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/extension.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package extension implements the extension values in the ClientHello/ServerHello
package extension
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/renegotiation_info.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/renegotiation_info.go
index 8378c3d94..c5092a7db 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/renegotiation_info.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/renegotiation_info.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import "encoding/binary"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/server_name.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/server_name.go
index 9a1cc2926..183e08e6e 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/server_name.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/server_name.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/srtp_protection_profile.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/srtp_protection_profile.go
index 2c4d1d4a6..2966966dd 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/srtp_protection_profile.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/srtp_protection_profile.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
// SRTPProtectionProfile defines the parameters and options that are in effect for the SRTP processing
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_elliptic_curves.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_elliptic_curves.go
index 8f077fcc7..dd9b54f0d 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_elliptic_curves.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_elliptic_curves.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_point_formats.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_point_formats.go
index 873d07827..9c2543e6e 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_point_formats.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_point_formats.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_signature_algorithms.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_signature_algorithms.go
index ee284f6e1..2ff4b90b6 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_signature_algorithms.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/supported_signature_algorithms.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_master_secret.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_master_secret.go
index 04ddc956a..d0b70cafb 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_master_secret.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_master_secret.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import "encoding/binary"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_srtp.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_srtp.go
index 729fa3a98..ea9f10872 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_srtp.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/extension/use_srtp.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package extension
import "encoding/binary"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/cipher_suite.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/cipher_suite.go
index e8fbdeae7..b29629717 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/cipher_suite.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/cipher_suite.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import "encoding/binary"
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/errors.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/errors.go
index ac77c0434..1354300c4 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/errors.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/handshake.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/handshake.go
index f25458178..b1f682bf5 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/handshake.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/handshake.go
@@ -1,7 +1,11 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package handshake provides the DTLS wire protocol for handshakes
package handshake
import (
+ "github.com/pion/dtls/v2/internal/ciphersuite/types"
"github.com/pion/dtls/v2/internal/util"
"github.com/pion/dtls/v2/pkg/protocol"
)
@@ -70,6 +74,8 @@ type Message interface {
type Handshake struct {
Header Header
Message Message
+
+ KeyExchangeAlgorithm types.KeyExchangeAlgorithm
}
// ContentType returns what kind of content this message is carying
@@ -126,13 +132,13 @@ func (h *Handshake) Unmarshal(data []byte) error {
case TypeCertificate:
h.Message = &MessageCertificate{}
case TypeServerKeyExchange:
- h.Message = &MessageServerKeyExchange{}
+ h.Message = &MessageServerKeyExchange{KeyExchangeAlgorithm: h.KeyExchangeAlgorithm}
case TypeCertificateRequest:
h.Message = &MessageCertificateRequest{}
case TypeServerHelloDone:
h.Message = &MessageServerHelloDone{}
case TypeClientKeyExchange:
- h.Message = &MessageClientKeyExchange{}
+ h.Message = &MessageClientKeyExchange{KeyExchangeAlgorithm: h.KeyExchangeAlgorithm}
case TypeFinished:
h.Message = &MessageFinished{}
case TypeCertificateVerify:
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/header.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/header.go
index cb6a22489..4f9a96287 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/header.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/header.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate.go
index 05fb74656..d5c861d90 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_request.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_request.go
index e711f392b..11a44d440 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_request.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_request.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
@@ -19,8 +22,9 @@ server's Certificate message).
https://tools.ietf.org/html/rfc5246#section-7.4.4
*/
type MessageCertificateRequest struct {
- CertificateTypes []clientcertificate.Type
- SignatureHashAlgorithms []signaturehash.Algorithm
+ CertificateTypes []clientcertificate.Type
+ SignatureHashAlgorithms []signaturehash.Algorithm
+ CertificateAuthoritiesNames [][]byte
}
const (
@@ -46,7 +50,20 @@ func (m *MessageCertificateRequest) Marshal() ([]byte, error) {
out = append(out, byte(v.Signature))
}
- out = append(out, []byte{0x00, 0x00}...) // Distinguished Names Length
+ // Distinguished Names
+ casLength := 0
+ for _, ca := range m.CertificateAuthoritiesNames {
+ casLength += len(ca) + 2
+ }
+ out = append(out, []byte{0x00, 0x00}...)
+ binary.BigEndian.PutUint16(out[len(out)-2:], uint16(casLength))
+ if casLength > 0 {
+ for _, ca := range m.CertificateAuthoritiesNames {
+ out = append(out, []byte{0x00, 0x00}...)
+ binary.BigEndian.PutUint16(out[len(out)-2:], uint16(len(ca)))
+ out = append(out, ca...)
+ }
+ }
return out, nil
}
@@ -96,5 +113,32 @@ func (m *MessageCertificateRequest) Unmarshal(data []byte) error {
m.SignatureHashAlgorithms = append(m.SignatureHashAlgorithms, signaturehash.Algorithm{Signature: s, Hash: h})
}
+ offset += signatureHashAlgorithmsLength
+ if len(data) < offset+2 {
+ return errBufferTooSmall
+ }
+ casLength := int(binary.BigEndian.Uint16(data[offset:]))
+ offset += 2
+ if (offset + casLength) > len(data) {
+ return errBufferTooSmall
+ }
+ cas := make([]byte, casLength)
+ copy(cas, data[offset:offset+casLength])
+ m.CertificateAuthoritiesNames = nil
+ for len(cas) > 0 {
+ if len(cas) < 2 {
+ return errBufferTooSmall
+ }
+ caLen := binary.BigEndian.Uint16(cas)
+ cas = cas[2:]
+
+ if len(cas) < int(caLen) {
+ return errBufferTooSmall
+ }
+
+ m.CertificateAuthoritiesNames = append(m.CertificateAuthoritiesNames, cas[:caLen])
+ cas = cas[caLen:]
+ }
+
return nil
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_verify.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_verify.go
index fb5e4639d..9e02a9c11 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_verify.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_certificate_verify.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_hello.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_hello.go
index 1deca38aa..bea6dd969 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_hello.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_hello.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_key_exchange.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_key_exchange.go
index f8fc36985..2abcd5bf7 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_key_exchange.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_client_key_exchange.go
@@ -1,7 +1,12 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
"encoding/binary"
+
+ "github.com/pion/dtls/v2/internal/ciphersuite/types"
)
// MessageClientKeyExchange is a DTLS Handshake Message
@@ -14,6 +19,9 @@ import (
type MessageClientKeyExchange struct {
IdentityHint []byte
PublicKey []byte
+
+ // for unmarshaling
+ KeyExchangeAlgorithm types.KeyExchangeAlgorithm
}
// Type returns the Handshake Type
@@ -22,35 +30,52 @@ func (m MessageClientKeyExchange) Type() Type {
}
// Marshal encodes the Handshake
-func (m *MessageClientKeyExchange) Marshal() ([]byte, error) {
- switch {
- case (m.IdentityHint != nil && m.PublicKey != nil) || (m.IdentityHint == nil && m.PublicKey == nil):
+func (m *MessageClientKeyExchange) Marshal() (out []byte, err error) {
+ if m.IdentityHint == nil && m.PublicKey == nil {
return nil, errInvalidClientKeyExchange
- case m.PublicKey != nil:
- return append([]byte{byte(len(m.PublicKey))}, m.PublicKey...), nil
- default:
- out := append([]byte{0x00, 0x00}, m.IdentityHint...)
- binary.BigEndian.PutUint16(out, uint16(len(out)-2))
- return out, nil
}
+
+ if m.IdentityHint != nil {
+ out = append([]byte{0x00, 0x00}, m.IdentityHint...)
+ binary.BigEndian.PutUint16(out, uint16(len(out)-2))
+ }
+
+ if m.PublicKey != nil {
+ out = append(out, byte(len(m.PublicKey)))
+ out = append(out, m.PublicKey...)
+ }
+
+ return out, nil
}
// Unmarshal populates the message from encoded data
func (m *MessageClientKeyExchange) Unmarshal(data []byte) error {
- if len(data) < 2 {
+ switch {
+ case len(data) < 2:
return errBufferTooSmall
+ case m.KeyExchangeAlgorithm == types.KeyExchangeAlgorithmNone:
+ return errCipherSuiteUnset
}
- // If parsed as PSK return early and only populate PSK Identity Hint
- if pskLength := binary.BigEndian.Uint16(data); len(data) == int(pskLength+2) {
- m.IdentityHint = append([]byte{}, data[2:]...)
- return nil
+ offset := 0
+ if m.KeyExchangeAlgorithm.Has(types.KeyExchangeAlgorithmPsk) {
+ pskLength := int(binary.BigEndian.Uint16(data))
+ if pskLength > len(data)-2 {
+ return errBufferTooSmall
+ }
+
+ m.IdentityHint = append([]byte{}, data[2:pskLength+2]...)
+ offset += pskLength + 2
}
- if publicKeyLength := int(data[0]); len(data) != publicKeyLength+1 {
- return errBufferTooSmall
+ if m.KeyExchangeAlgorithm.Has(types.KeyExchangeAlgorithmEcdhe) {
+ publicKeyLength := int(data[offset])
+ if publicKeyLength > len(data)-1-offset {
+ return errBufferTooSmall
+ }
+
+ m.PublicKey = append([]byte{}, data[offset+1:]...)
}
- m.PublicKey = append([]byte{}, data[1:]...)
return nil
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_finished.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_finished.go
index c65d42abb..255aedd7e 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_finished.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_finished.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
// MessageFinished is a DTLS Handshake Message
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_hello_verify_request.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_hello_verify_request.go
index ef834dc85..398e59cc3 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_hello_verify_request.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_hello_verify_request.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
@@ -6,19 +9,19 @@ import (
// MessageHelloVerifyRequest is as follows:
//
-// struct {
-// ProtocolVersion server_version;
-// opaque cookie<0..2^8-1>;
-// } HelloVerifyRequest;
+// struct {
+// ProtocolVersion server_version;
+// opaque cookie<0..2^8-1>;
+// } HelloVerifyRequest;
//
-// The HelloVerifyRequest message type is hello_verify_request(3).
+// The HelloVerifyRequest message type is hello_verify_request(3).
//
-// When the client sends its ClientHello message to the server, the server
-// MAY respond with a HelloVerifyRequest message. This message contains
-// a stateless cookie generated using the technique of [PHOTURIS]. The
-// client MUST retransmit the ClientHello with the cookie added.
+// When the client sends its ClientHello message to the server, the server
+// MAY respond with a HelloVerifyRequest message. This message contains
+// a stateless cookie generated using the technique of [PHOTURIS]. The
+// client MUST retransmit the ClientHello with the cookie added.
//
-// https://tools.ietf.org/html/rfc6347#section-4.2.1
+// https://tools.ietf.org/html/rfc6347#section-4.2.1
type MessageHelloVerifyRequest struct {
Version protocol.Version
Cookie []byte
@@ -51,8 +54,8 @@ func (m *MessageHelloVerifyRequest) Unmarshal(data []byte) error {
}
m.Version.Major = data[0]
m.Version.Minor = data[1]
- cookieLength := data[2]
- if len(data) < (int(cookieLength) + 3) {
+ cookieLength := int(data[2])
+ if len(data) < cookieLength+3 {
return errBufferTooSmall
}
m.Cookie = make([]byte, cookieLength)
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello.go
index 9c1cc2218..caf186da8 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
@@ -88,11 +91,14 @@ func (m *MessageServerHello) Unmarshal(data []byte) error {
m.SessionID = append([]byte{}, data[currOffset:currOffset+n]...)
currOffset += len(m.SessionID)
+ if len(data) < currOffset+2 {
+ return errBufferTooSmall
+ }
m.CipherSuiteID = new(uint16)
*m.CipherSuiteID = binary.BigEndian.Uint16(data[currOffset:])
currOffset += 2
- if len(data) < currOffset {
+ if len(data) <= currOffset {
return errBufferTooSmall
}
if compressionMethod, ok := protocol.CompressionMethods()[protocol.CompressionMethodID(data[currOffset])]; ok {
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello_done.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello_done.go
index 0f65b198e..b187dd417 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello_done.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_hello_done.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
// MessageServerHelloDone is final non-encrypted message from server
@@ -16,6 +19,6 @@ func (m *MessageServerHelloDone) Marshal() ([]byte, error) {
}
// Unmarshal populates the message from encoded data
-func (m *MessageServerHelloDone) Unmarshal(data []byte) error {
+func (m *MessageServerHelloDone) Unmarshal([]byte) error {
return nil
}
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_key_exchange.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_key_exchange.go
index 4148fe05b..82abbe0d4 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_key_exchange.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/message_server_key_exchange.go
@@ -1,8 +1,12 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
"encoding/binary"
+ "github.com/pion/dtls/v2/internal/ciphersuite/types"
"github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/dtls/v2/pkg/crypto/hash"
"github.com/pion/dtls/v2/pkg/crypto/signature"
@@ -18,6 +22,9 @@ type MessageServerKeyExchange struct {
HashAlgorithm hash.Algorithm
SignatureAlgorithm signature.Algorithm
Signature []byte
+
+ // for unmarshaling
+ KeyExchangeAlgorithm types.KeyExchangeAlgorithm
}
// Type returns the Handshake Type
@@ -27,19 +34,28 @@ func (m MessageServerKeyExchange) Type() Type {
// Marshal encodes the Handshake
func (m *MessageServerKeyExchange) Marshal() ([]byte, error) {
+ var out []byte
if m.IdentityHint != nil {
- out := append([]byte{0x00, 0x00}, m.IdentityHint...)
+ out = append([]byte{0x00, 0x00}, m.IdentityHint...)
binary.BigEndian.PutUint16(out, uint16(len(out)-2))
- return out, nil
}
- out := []byte{byte(m.EllipticCurveType), 0x00, 0x00}
- binary.BigEndian.PutUint16(out[1:], uint16(m.NamedCurve))
+ if m.EllipticCurveType == 0 || len(m.PublicKey) == 0 {
+ return out, nil
+ }
+ out = append(out, byte(m.EllipticCurveType), 0x00, 0x00)
+ binary.BigEndian.PutUint16(out[len(out)-2:], uint16(m.NamedCurve))
out = append(out, byte(len(m.PublicKey)))
out = append(out, m.PublicKey...)
-
- if m.HashAlgorithm == hash.None && m.SignatureAlgorithm == signature.Anonymous && len(m.Signature) == 0 {
+ switch {
+ case m.HashAlgorithm != hash.None && len(m.Signature) == 0:
+ return nil, errInvalidHashAlgorithm
+ case m.HashAlgorithm == hash.None && len(m.Signature) > 0:
+ return nil, errInvalidHashAlgorithm
+ case m.SignatureAlgorithm == signature.Anonymous && (m.HashAlgorithm != hash.None || len(m.Signature) > 0):
+ return nil, errInvalidSignatureAlgorithm
+ case m.SignatureAlgorithm == signature.Anonymous:
return out, nil
}
@@ -52,14 +68,27 @@ func (m *MessageServerKeyExchange) Marshal() ([]byte, error) {
// Unmarshal populates the message from encoded data
func (m *MessageServerKeyExchange) Unmarshal(data []byte) error {
- if len(data) < 2 {
+ switch {
+ case len(data) < 2:
return errBufferTooSmall
+ case m.KeyExchangeAlgorithm == types.KeyExchangeAlgorithmNone:
+ return errCipherSuiteUnset
}
- // If parsed as PSK return early and only populate PSK Identity Hint
- if pskLength := binary.BigEndian.Uint16(data); len(data) == int(pskLength+2) {
- m.IdentityHint = append([]byte{}, data[2:]...)
- return nil
+ hintLength := binary.BigEndian.Uint16(data)
+ if int(hintLength) <= len(data)-2 && m.KeyExchangeAlgorithm.Has(types.KeyExchangeAlgorithmPsk) {
+ m.IdentityHint = append([]byte{}, data[2:2+hintLength]...)
+ data = data[2+hintLength:]
+ }
+ if m.KeyExchangeAlgorithm == types.KeyExchangeAlgorithmPsk {
+ if len(data) == 0 {
+ return nil
+ }
+ return errLengthMismatch
+ }
+
+ if !m.KeyExchangeAlgorithm.Has(types.KeyExchangeAlgorithmEcdhe) {
+ return errLengthMismatch
}
if _, ok := elliptic.CurveTypes()[elliptic.CurveType(data[0])]; ok {
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/random.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/random.go
index 0ade936eb..56f37569b 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/random.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/handshake/random.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package handshake
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/errors.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/errors.go
index 7033d4058..cd4cb60a5 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/errors.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package recordlayer implements the TLS Record Layer https://tools.ietf.org/html/rfc5246#section-6
package recordlayer
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/header.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/header.go
index 65047d767..92252502b 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/header.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/header.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package recordlayer
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/recordlayer.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/recordlayer.go
index 67e5a727b..02325fd2d 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/recordlayer.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/recordlayer/recordlayer.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package recordlayer
import (
diff --git a/vendor/github.com/pion/dtls/v2/pkg/protocol/version.go b/vendor/github.com/pion/dtls/v2/pkg/protocol/version.go
index d5ddb1d00..c4d94ac3a 100644
--- a/vendor/github.com/pion/dtls/v2/pkg/protocol/version.go
+++ b/vendor/github.com/pion/dtls/v2/pkg/protocol/version.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package protocol provides the DTLS wire format
package protocol
diff --git a/vendor/github.com/pion/dtls/v2/renovate.json b/vendor/github.com/pion/dtls/v2/renovate.json
index f1614058a..f1bb98c6a 100644
--- a/vendor/github.com/pion/dtls/v2/renovate.json
+++ b/vendor/github.com/pion/dtls/v2/renovate.json
@@ -1,27 +1,6 @@
{
+ "$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": [
- "config:base",
- ":disableDependencyDashboard"
- ],
- "postUpdateOptions": [
- "gomodTidy"
- ],
- "commitBody": "Generated by renovateBot",
- "packageRules": [
- {
- "matchUpdateTypes": ["minor", "patch", "pin", "digest"],
- "automerge": true
- },
- {
- "packagePatterns": ["^golang.org/x/"],
- "schedule": ["on the first day of the month"]
- }
- ],
- "ignorePaths": [
- ".github/workflows/generate-authors.yml",
- ".github/workflows/lint.yaml",
- ".github/workflows/renovate-go-mod-fix.yaml",
- ".github/workflows/test.yaml",
- ".github/workflows/tidy-check.yaml"
+ "github>pion/renovate-config"
]
}
diff --git a/vendor/github.com/pion/dtls/v2/resume.go b/vendor/github.com/pion/dtls/v2/resume.go
index 40e55e449..c470d856b 100644
--- a/vendor/github.com/pion/dtls/v2/resume.go
+++ b/vendor/github.com/pion/dtls/v2/resume.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
diff --git a/vendor/github.com/pion/dtls/v2/session.go b/vendor/github.com/pion/dtls/v2/session.go
index f52120cd8..99bf5a499 100644
--- a/vendor/github.com/pion/dtls/v2/session.go
+++ b/vendor/github.com/pion/dtls/v2/session.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
// Session store data needed in resumption
diff --git a/vendor/github.com/pion/dtls/v2/srtp_protection_profile.go b/vendor/github.com/pion/dtls/v2/srtp_protection_profile.go
index 1c3ae55dc..e306e9e6a 100644
--- a/vendor/github.com/pion/dtls/v2/srtp_protection_profile.go
+++ b/vendor/github.com/pion/dtls/v2/srtp_protection_profile.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import "github.com/pion/dtls/v2/pkg/protocol/extension"
@@ -7,8 +10,8 @@ import "github.com/pion/dtls/v2/pkg/protocol/extension"
type SRTPProtectionProfile = extension.SRTPProtectionProfile
const (
- SRTP_AES128_CM_HMAC_SHA1_80 SRTPProtectionProfile = extension.SRTP_AES128_CM_HMAC_SHA1_80 // nolint
- SRTP_AES128_CM_HMAC_SHA1_32 SRTPProtectionProfile = extension.SRTP_AES128_CM_HMAC_SHA1_32 // nolint
- SRTP_AEAD_AES_128_GCM SRTPProtectionProfile = extension.SRTP_AEAD_AES_128_GCM // nolint
- SRTP_AEAD_AES_256_GCM SRTPProtectionProfile = extension.SRTP_AEAD_AES_256_GCM // nolint
+ SRTP_AES128_CM_HMAC_SHA1_80 SRTPProtectionProfile = extension.SRTP_AES128_CM_HMAC_SHA1_80 // nolint:revive,stylecheck
+ SRTP_AES128_CM_HMAC_SHA1_32 SRTPProtectionProfile = extension.SRTP_AES128_CM_HMAC_SHA1_32 // nolint:revive,stylecheck
+ SRTP_AEAD_AES_128_GCM SRTPProtectionProfile = extension.SRTP_AEAD_AES_128_GCM // nolint:revive,stylecheck
+ SRTP_AEAD_AES_256_GCM SRTPProtectionProfile = extension.SRTP_AEAD_AES_256_GCM // nolint:revive,stylecheck
)
diff --git a/vendor/github.com/pion/dtls/v2/state.go b/vendor/github.com/pion/dtls/v2/state.go
index 96fc71b12..e9f86a80b 100644
--- a/vendor/github.com/pion/dtls/v2/state.go
+++ b/vendor/github.com/pion/dtls/v2/state.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
import (
@@ -8,7 +11,7 @@ import (
"github.com/pion/dtls/v2/pkg/crypto/elliptic"
"github.com/pion/dtls/v2/pkg/crypto/prf"
"github.com/pion/dtls/v2/pkg/protocol/handshake"
- "github.com/pion/transport/replaydetector"
+ "github.com/pion/transport/v2/replaydetector"
)
// State holds the dtls connection state and implements both encoding.BinaryMarshaler and encoding.BinaryUnmarshaler
@@ -75,10 +78,10 @@ func (s *State) serialize() *serializedState {
localRnd := s.localRandom.MarshalFixed()
remoteRnd := s.remoteRandom.MarshalFixed()
- epoch := s.localEpoch.Load().(uint16)
+ epoch := s.getLocalEpoch()
return &serializedState{
- LocalEpoch: epoch,
- RemoteEpoch: s.remoteEpoch.Load().(uint16),
+ LocalEpoch: s.getLocalEpoch(),
+ RemoteEpoch: s.getRemoteEpoch(),
CipherSuiteID: uint16(s.cipherSuite.ID()),
MasterSecret: s.masterSecret,
SequenceNumber: atomic.LoadUint64(&s.localSequenceNumber[epoch]),
@@ -169,10 +172,8 @@ func (s *State) UnmarshalBinary(data []byte) error {
}
s.deserialize(serialized)
- if err := s.initCipherSuite(); err != nil {
- return err
- }
- return nil
+
+ return s.initCipherSuite()
}
// ExportKeyingMaterial returns length bytes of exported key material in a new
@@ -180,7 +181,7 @@ func (s *State) UnmarshalBinary(data []byte) error {
// This allows protocols to use DTLS for key establishment, but
// then use some of the keying material for their own purposes
func (s *State) ExportKeyingMaterial(label string, context []byte, length int) ([]byte, error) {
- if s.localEpoch.Load().(uint16) == 0 {
+ if s.getLocalEpoch() == 0 {
return nil, errHandshakeInProgress
} else if len(context) != 0 {
return nil, errContextUnsupported
@@ -199,3 +200,17 @@ func (s *State) ExportKeyingMaterial(label string, context []byte, length int) (
}
return prf.PHash(s.masterSecret, seed, length, s.cipherSuite.HashFunc())
}
+
+func (s *State) getRemoteEpoch() uint16 {
+ if remoteEpoch, ok := s.remoteEpoch.Load().(uint16); ok {
+ return remoteEpoch
+ }
+ return 0
+}
+
+func (s *State) getLocalEpoch() uint16 {
+ if localEpoch, ok := s.localEpoch.Load().(uint16); ok {
+ return localEpoch
+ }
+ return 0
+}
diff --git a/vendor/github.com/pion/dtls/v2/util.go b/vendor/github.com/pion/dtls/v2/util.go
index 745182dcd..663c4437c 100644
--- a/vendor/github.com/pion/dtls/v2/util.go
+++ b/vendor/github.com/pion/dtls/v2/util.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package dtls
func findMatchingSRTPProfile(a, b []SRTPProtectionProfile) (SRTPProtectionProfile, bool) {
@@ -11,7 +14,7 @@ func findMatchingSRTPProfile(a, b []SRTPProtectionProfile) (SRTPProtectionProfil
return 0, false
}
-func findMatchingCipherSuite(a, b []CipherSuite) (CipherSuite, bool) { //nolint
+func findMatchingCipherSuite(a, b []CipherSuite) (CipherSuite, bool) {
for _, aSuite := range a {
for _, bSuite := range b {
if aSuite.ID() == bSuite.ID() {
diff --git a/vendor/github.com/pion/ice/v2/.gitignore b/vendor/github.com/pion/ice/v2/.gitignore
index 83db74ba5..6e2f206a9 100644
--- a/vendor/github.com/pion/ice/v2/.gitignore
+++ b/vendor/github.com/pion/ice/v2/.gitignore
@@ -1,3 +1,6 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
### JetBrains IDE ###
#####################
.idea/
@@ -22,3 +25,4 @@ cover.out
*.wasm
examples/sfu-ws/cert.pem
examples/sfu-ws/key.pem
+wasm_exec.js
diff --git a/vendor/github.com/pion/ice/v2/.golangci.yml b/vendor/github.com/pion/ice/v2/.golangci.yml
index d6162c970..4e3eddf42 100644
--- a/vendor/github.com/pion/ice/v2/.golangci.yml
+++ b/vendor/github.com/pion/ice/v2/.golangci.yml
@@ -1,3 +1,6 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
linters-settings:
govet:
check-shadowing: true
@@ -10,19 +13,34 @@ linters-settings:
modules:
- github.com/pkg/errors:
recommendations:
- - errors
+ - errors
+ forbidigo:
+ forbid:
+ - ^fmt.Print(f|ln)?$
+ - ^log.(Panic|Fatal|Print)(f|ln)?$
+ - ^os.Exit$
+ - ^panic$
+ - ^print(ln)?$
linters:
enable:
- asciicheck # Simple linter to check that your code does not contain non-ASCII identifiers
+ - bidichk # Checks for dangerous unicode character sequences
- bodyclose # checks whether HTTP response body is closed successfully
- - deadcode # Finds unused code
+ - contextcheck # check the function whether use a non-inherited context
+ - decorder # check declaration order and count of types, constants, variables and functions
- depguard # Go linter that checks if package imports are in a list of acceptable packages
- dogsled # Checks assignments with too many blank identifiers (e.g. x, _, _, _, := f())
- dupl # Tool for code clone detection
+ - durationcheck # check for two durations multiplied together
- errcheck # Errcheck is a program for checking for unchecked errors in go programs. These unchecked errors can be critical bugs in some cases
+ - errchkjson # Checks types passed to the json encoding functions. Reports unsupported types and optionally reports occations, where the check for the returned error can be omitted.
+ - errname # Checks that sentinel errors are prefixed with the `Err` and error types are suffixed with the `Error`.
+ - errorlint # errorlint is a linter for that can be used to find code that will cause problems with the error wrapping scheme introduced in Go 1.13.
- exhaustive # check exhaustiveness of enum switch statements
- exportloopref # checks for pointers to enclosing loop variables
+ - forbidigo # Forbids identifiers
+ - forcetypeassert # finds forced type assertions
- gci # Gci control golang package import order and make it always deterministic.
- gochecknoglobals # Checks that no globals are present in Go code
- gochecknoinits # Checks that no init functions are present in Go code
@@ -35,40 +53,59 @@ linters:
- gofumpt # Gofumpt checks whether code was gofumpt-ed.
- goheader # Checks is file header matches to pattern
- goimports # Goimports does everything that gofmt does. Additionally it checks unused imports
- - golint # Golint differs from gofmt. Gofmt reformats Go source code, whereas golint prints out style mistakes
+ - gomoddirectives # Manage the use of 'replace', 'retract', and 'excludes' directives in go.mod.
- gomodguard # Allow and block list linter for direct Go module dependencies. This is different from depguard where there are different block types for example version constraints and module recommendations.
- goprintffuncname # Checks that printf-like functions are named with `f` at the end
- gosec # Inspects source code for security problems
- gosimple # Linter for Go source code that specializes in simplifying a code
- govet # Vet examines Go source code and reports suspicious constructs, such as Printf calls whose arguments do not align with the format string
+ - grouper # An analyzer to analyze expression groups.
+ - importas # Enforces consistent import aliases
- ineffassign # Detects when assignments to existing variables are not used
- misspell # Finds commonly misspelled English words in comments
- nakedret # Finds naked returns in functions greater than a specified function length
+ - nilerr # Finds the code that returns nil even if it checks that the error is not nil.
+ - nilnil # Checks that there is no simultaneous return of `nil` error and an invalid value.
- noctx # noctx finds sending http request without context.Context
- - scopelint # Scopelint checks for unpinned variables in go programs
+ - predeclared # find code that shadows one of Go's predeclared identifiers
+ - revive # golint replacement, finds style mistakes
- staticcheck # Staticcheck is a go vet on steroids, applying a ton of static analysis checks
- - structcheck # Finds unused struct fields
- stylecheck # Stylecheck is a replacement for golint
+ - tagliatelle # Checks the struct tags.
+ - tenv # tenv is analyzer that detects using os.Setenv instead of t.Setenv since Go1.17
+ - tparallel # tparallel detects inappropriate usage of t.Parallel() method in your Go test codes
- typecheck # Like the front-end of a Go compiler, parses and type-checks Go code
- unconvert # Remove unnecessary type conversions
- unparam # Reports unused function parameters
- unused # Checks Go code for unused constants, variables, functions and types
- - varcheck # Finds unused global variables and constants
+ - wastedassign # wastedassign finds wasted assignment statements
- whitespace # Tool for detection of leading and trailing whitespace
disable:
+ - containedctx # containedctx is a linter that detects struct contained context.Context field
+ - cyclop # checks function and package cyclomatic complexity
+ - exhaustivestruct # Checks if all struct's fields are initialized
- funlen # Tool for detection of long functions
- gocyclo # Computes and checks the cyclomatic complexity of functions
- godot # Check if comments end in a period
- gomnd # An analyzer to detect magic numbers.
+ - ifshort # Checks that your code uses short syntax for if-statements whenever possible
+ - ireturn # Accept Interfaces, Return Concrete Types
- lll # Reports long lines
+ - maintidx # maintidx measures the maintainability index of each function.
+ - makezero # Finds slice declarations with non-zero initial length
- maligned # Tool to detect Go structs that would take less memory if their fields were sorted
- nestif # Reports deeply nested if statements
- nlreturn # nlreturn checks for a new line before return and branch statements to increase code clarity
- nolintlint # Reports ill-formed or insufficient nolint directives
+ - paralleltest # paralleltest detects missing usage of t.Parallel() method in your Go test
- prealloc # Finds slice declarations that could potentially be preallocated
+ - promlinter # Check Prometheus metrics naming via promlint
- rowserrcheck # checks whether Err of rows is checked successfully
- sqlclosecheck # Checks that sql.Rows and sql.Stmt are closed.
- testpackage # linter that makes you use a separate _test package
+ - thelper # thelper detects golang test helpers without t.Helper() call and checks the consistency of test helpers
+ - varnamelen # checks that the length of a variable's name matches its scope
+ - wrapcheck # Checks that errors returned from external packages are wrapped
- wsl # Whitespace Linter - Forces you to use empty lines!
issues:
@@ -78,12 +115,23 @@ issues:
- path: _test\.go
linters:
- gocognit
+ - forbidigo
# Allow complex main function in examples
- path: examples
text: "of func `main` is high"
linters:
- gocognit
+
+ # Allow forbidden identifiers in examples
+ - path: examples
+ linters:
+ - forbidigo
+
+ # Allow forbidden identifiers in CLI commands
+ - path: cmd
+ linters:
+ - forbidigo
run:
skip-dirs-use-default: false
diff --git a/vendor/github.com/pion/ice/v2/.goreleaser.yml b/vendor/github.com/pion/ice/v2/.goreleaser.yml
new file mode 100644
index 000000000..30093e9d6
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/.goreleaser.yml
@@ -0,0 +1,5 @@
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
+
+builds:
+- skip: true
diff --git a/vendor/github.com/pion/ice/v2/AUTHORS.txt b/vendor/github.com/pion/ice/v2/AUTHORS.txt
index 8c8b66b05..57eb69378 100644
--- a/vendor/github.com/pion/ice/v2/AUTHORS.txt
+++ b/vendor/github.com/pion/ice/v2/AUTHORS.txt
@@ -2,20 +2,26 @@
# we would love to have you https://github.com/pion/webrtc/wiki/Contributing
#
# This file is auto generated, using git to list all individuals contributors.
-# see `.github/generate-authors.sh` for the scripting
+# see https://github.com/pion/.goassets/blob/master/scripts/generate-authors.sh for the scripting
Aaron France
Adam Kiss
adwpc
Aleksandr Razumov
+aler9 <46489434+aler9@users.noreply.github.com>
Antoine Baché
+Artur Shellunts
Assad Obaid
Atsushi Watanabe
backkem
buptczq
cgojin
Chao Yuan
+cnderrauber
David Hamilton
David Zhao
+David Zhao
+Eric Daniels
+Genteure
Henry
hexiang
hn8 <10730886+hn8@users.noreply.github.com>
@@ -25,6 +31,8 @@ Jason Maldonis
Jerko Steiner
JooYoung
Juliusz Chroboczek
+Kacper Bąk <56700396+53jk1@users.noreply.github.com>
+Kevin Caffrey
Konstantin Itskov
korymiller1489
Kyle Carberry
@@ -33,17 +41,25 @@ Luke Curley
Meelap Shah
Michael MacDonald
Michael MacDonald
+Mikhail Bragin
+Miroslav Šedivý
Nevio Vesic
Ori Bernstein
+Rasmus Hanning
Robert Eperjesi
Sam Lancia
Sam Lancia
+San9H0
Sean DuBois
Sean DuBois
Sebastian Waisbrot
Sidney San Martín
+Steffen Vogel
Will Forcey
Woodrow Douglass
Yutaka Takeda
ZHENK
Zizheng Tai
+
+# List of contributors not appearing in Git history
+
diff --git a/vendor/github.com/pion/ice/v2/LICENSE b/vendor/github.com/pion/ice/v2/LICENSE
index ab602974d..491caf6b0 100644
--- a/vendor/github.com/pion/ice/v2/LICENSE
+++ b/vendor/github.com/pion/ice/v2/LICENSE
@@ -1,21 +1,9 @@
MIT License
-Copyright (c) 2018
+Copyright (c) 2023 The Pion community
-Permission is hereby granted, free of charge, to any person obtaining a copy
-of this software and associated documentation files (the "Software"), to deal
-in the Software without restriction, including without limitation the rights
-to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
-copies of the Software, and to permit persons to whom the Software is
-furnished to do so, subject to the following conditions:
+Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions:
-The above copyright notice and this permission notice shall be included in all
-copies or substantial portions of the Software.
+The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software.
-THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
-IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
-FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
-AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
-LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
-OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
-SOFTWARE.
+THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
diff --git a/vendor/github.com/pion/ice/v2/README.md b/vendor/github.com/pion/ice/v2/README.md
index 8191fc479..111ca7057 100644
--- a/vendor/github.com/pion/ice/v2/README.md
+++ b/vendor/github.com/pion/ice/v2/README.md
@@ -5,11 +5,11 @@
A Go implementation of ICE
-
+
-
-
+
+
@@ -20,14 +20,15 @@
The library is used as a part of our WebRTC implementation. Please refer to that [roadmap](https://github.com/pion/webrtc/issues/9) to track our major milestones.
### Community
-Pion has an active community on the [Golang Slack](https://invite.slack.golangbridge.org/). Sign up and join the **#pion** channel for discussions and support. You can also use [Pion mailing list](https://groups.google.com/forum/#!forum/pion).
+Pion has an active community on the [Slack](https://pion.ly/slack).
+
+Follow the [Pion Twitter](https://twitter.com/_pion) for project updates and important WebRTC news.
We are always looking to support **your projects**. Please reach out if you have something to build!
-
If you need commercial support or don't want to use public methods you can contact us at [team@pion.ly](mailto:team@pion.ly)
### Contributing
-Check out the **[contributing wiki](https://github.com/pion/webrtc/wiki/Contributing)** to join the group of amazing people making this project possible:
+Check out the [contributing wiki](https://github.com/pion/webrtc/wiki/Contributing) to join the group of amazing people making this project possible: [AUTHORS.txt](./AUTHORS.txt)
### License
MIT License - see [LICENSE](LICENSE) for full text
diff --git a/vendor/github.com/pion/ice/v2/addr.go b/vendor/github.com/pion/ice/v2/addr.go
new file mode 100644
index 000000000..1d70025be
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/addr.go
@@ -0,0 +1,71 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ice
+
+import (
+ "net"
+)
+
+func parseMulticastAnswerAddr(in net.Addr) (net.IP, bool) {
+ switch addr := in.(type) {
+ case *net.IPAddr:
+ return addr.IP, true
+ case *net.UDPAddr:
+ return addr.IP, true
+ case *net.TCPAddr:
+ return addr.IP, true
+ }
+ return nil, false
+}
+
+func parseAddr(in net.Addr) (net.IP, int, NetworkType, bool) {
+ switch addr := in.(type) {
+ case *net.UDPAddr:
+ return addr.IP, addr.Port, NetworkTypeUDP4, true
+ case *net.TCPAddr:
+ return addr.IP, addr.Port, NetworkTypeTCP4, true
+ }
+ return nil, 0, 0, false
+}
+
+func createAddr(network NetworkType, ip net.IP, port int) net.Addr {
+ switch {
+ case network.IsTCP():
+ return &net.TCPAddr{IP: ip, Port: port}
+ default:
+ return &net.UDPAddr{IP: ip, Port: port}
+ }
+}
+
+func addrEqual(a, b net.Addr) bool {
+ aIP, aPort, aType, aOk := parseAddr(a)
+ if !aOk {
+ return false
+ }
+
+ bIP, bPort, bType, bOk := parseAddr(b)
+ if !bOk {
+ return false
+ }
+
+ return aType == bType && aIP.Equal(bIP) && aPort == bPort
+}
+
+// AddrPort is an IP and a port number.
+type AddrPort [18]byte
+
+func toAddrPort(addr net.Addr) AddrPort {
+ var ap AddrPort
+ switch addr := addr.(type) {
+ case *net.UDPAddr:
+ copy(ap[:16], addr.IP.To16())
+ ap[16] = uint8(addr.Port >> 8)
+ ap[17] = uint8(addr.Port)
+ case *net.TCPAddr:
+ copy(ap[:16], addr.IP.To16())
+ ap[16] = uint8(addr.Port >> 8)
+ ap[17] = uint8(addr.Port)
+ }
+ return ap
+}
diff --git a/vendor/github.com/pion/ice/v2/agent.go b/vendor/github.com/pion/ice/v2/agent.go
index b4aba19f5..5350330f6 100644
--- a/vendor/github.com/pion/ice/v2/agent.go
+++ b/vendor/github.com/pion/ice/v2/agent.go
@@ -1,20 +1,28 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package ice implements the Interactive Connectivity Establishment (ICE)
// protocol defined in rfc5245.
package ice
import (
"context"
+ "fmt"
"net"
"strings"
"sync"
"sync/atomic"
"time"
+ atomicx "github.com/pion/ice/v2/internal/atomic"
+ stunx "github.com/pion/ice/v2/internal/stun"
"github.com/pion/logging"
"github.com/pion/mdns"
"github.com/pion/stun"
- "github.com/pion/transport/packetio"
- "github.com/pion/transport/vnet"
+ "github.com/pion/transport/v2"
+ "github.com/pion/transport/v2/packetio"
+ "github.com/pion/transport/v2/stdnet"
+ "github.com/pion/transport/v2/vnet"
"golang.org/x/net/proxy"
)
@@ -39,7 +47,7 @@ type Agent struct {
onConnected chan struct{}
onConnectedOnce sync.Once
- // force candidate to be contacted immediately (instead of waiting for task ticker)
+ // Force candidate to be contacted immediately (instead of waiting for task ticker)
forceCandidateContact chan bool
tieBreaker uint64
@@ -64,8 +72,8 @@ type Agent struct {
prflxAcceptanceMinWait time.Duration
relayAcceptanceMinWait time.Duration
- portmin uint16
- portmax uint16
+ portMin uint16
+ portMax uint16
candidateTypes []CandidateType
@@ -97,10 +105,10 @@ type Agent struct {
selectedPair atomic.Value // *CandidatePair
- urls []*URL
+ urls []*stun.URI
networkTypes []NetworkType
- buffer *packetio.Buffer
+ buf *packetio.Buffer
// LRU of outbound Binding request Transaction IDs
pendingBindingRequests []bindingRequest
@@ -111,9 +119,10 @@ type Agent struct {
// State for closing
done chan struct{}
taskLoopDone chan struct{}
- err atomicError
+ err atomicx.Error
gatherCandidateCancel func()
+ gatherCandidateDone chan struct{}
chanCandidate chan Candidate
chanCandidatePair chan *CandidatePair
@@ -122,11 +131,14 @@ type Agent struct {
loggerFactory logging.LoggerFactory
log logging.LeveledLogger
- net *vnet.Net
- tcpMux TCPMux
- udpMux UDPMux
+ net transport.Net
+ tcpMux TCPMux
+ udpMux UDPMux
+ udpMuxSrflx UniversalUDPMux
interfaceFilter func(string) bool
+ ipFilter func(net.IP) bool
+ includeLoopback bool
insecureSkipVerify bool
@@ -202,8 +214,8 @@ func (a *Agent) taskLoop() {
a.deleteAllCandidates()
a.startedFn()
- if err := a.buffer.Close(); err != nil {
- a.log.Warnf("failed to close buffer: %v", err)
+ if err := a.buf.Close(); err != nil {
+ a.log.Warnf("Failed to close buffer: %v", err)
}
a.closeMulticastConn()
@@ -258,21 +270,6 @@ func NewAgent(config *AgentConfig) (*Agent, error) { //nolint:gocognit
}
log := loggerFactory.NewLogger("ice")
- var mDNSConn *mdns.Conn
- mDNSConn, mDNSMode, err = createMulticastDNS(mDNSMode, mDNSName, log)
- // Opportunistic mDNS: If we can't open the connection, that's ok: we
- // can continue without it.
- if err != nil {
- log.Warnf("Failed to initialize mDNS %s: %v", mDNSName, err)
- }
- closeMDNSConn := func() {
- if mDNSConn != nil {
- if mdnsCloseErr := mDNSConn.Close(); mdnsCloseErr != nil {
- log.Warnf("Failed to close mDNS: %v", mdnsCloseErr)
- }
- }
- }
-
startedCtx, startedFn := context.WithCancel(context.Background())
a := &Agent{
@@ -289,21 +286,23 @@ func NewAgent(config *AgentConfig) (*Agent, error) { //nolint:gocognit
urls: config.Urls,
networkTypes: config.NetworkTypes,
onConnected: make(chan struct{}),
- buffer: packetio.NewBuffer(),
+ buf: packetio.NewBuffer(),
done: make(chan struct{}),
taskLoopDone: make(chan struct{}),
startedCh: startedCtx.Done(),
startedFn: startedFn,
- portmin: config.PortMin,
- portmax: config.PortMax,
+ portMin: config.PortMin,
+ portMax: config.PortMax,
loggerFactory: loggerFactory,
log: log,
net: config.Net,
proxyDialer: config.ProxyDialer,
+ tcpMux: config.TCPMux,
+ udpMux: config.UDPMux,
+ udpMuxSrflx: config.UDPMuxSrflx,
mDNSMode: mDNSMode,
mDNSName: mDNSName,
- mDNSConn: mDNSConn,
gatherCandidateCancel: func() {},
@@ -311,22 +310,29 @@ func NewAgent(config *AgentConfig) (*Agent, error) { //nolint:gocognit
interfaceFilter: config.InterfaceFilter,
- insecureSkipVerify: config.InsecureSkipVerify,
- }
+ ipFilter: config.IPFilter,
- a.tcpMux = config.TCPMux
- if a.tcpMux == nil {
- a.tcpMux = newInvalidTCPMux()
+ insecureSkipVerify: config.InsecureSkipVerify,
+
+ includeLoopback: config.IncludeLoopback,
}
- a.udpMux = config.UDPMux
if a.net == nil {
- a.net = vnet.NewNet(nil)
- } else if a.net.IsVirtual() {
- a.log.Warn("vnet is enabled")
- if a.mDNSMode != MulticastDNSModeDisabled {
- a.log.Warn("vnet does not support mDNS yet")
+ a.net, err = stdnet.NewNet()
+ if err != nil {
+ return nil, fmt.Errorf("failed to create network: %w", err)
}
+ } else if _, isVirtual := a.net.(*vnet.Net); isVirtual {
+ a.log.Warn("Virtual network is enabled")
+ if a.mDNSMode != MulticastDNSModeDisabled {
+ a.log.Warn("Virtual network does not support mDNS yet")
+ }
+ }
+
+ // Opportunistic mDNS: If we can't open the connection, that's ok: we
+ // can continue without it.
+ if a.mDNSConn, a.mDNSMode, err = createMulticastDNS(a.net, mDNSMode, mDNSName, log); err != nil {
+ log.Warnf("Failed to initialize mDNS %s: %v", mDNSName, err)
}
config.initWithDefaults(a)
@@ -334,29 +340,35 @@ func NewAgent(config *AgentConfig) (*Agent, error) { //nolint:gocognit
// Make sure the buffer doesn't grow indefinitely.
// NOTE: We actually won't get anywhere close to this limit.
// SRTP will constantly read from the endpoint and drop packets if it's full.
- a.buffer.SetLimitSize(maxBufferSize)
+ a.buf.SetLimitSize(maxBufferSize)
if a.lite && (len(a.candidateTypes) != 1 || a.candidateTypes[0] != CandidateTypeHost) {
- closeMDNSConn()
+ a.closeMulticastConn()
return nil, ErrLiteUsingNonHostCandidates
}
if config.Urls != nil && len(config.Urls) > 0 && !containsCandidateType(CandidateTypeServerReflexive, a.candidateTypes) && !containsCandidateType(CandidateTypeRelay, a.candidateTypes) {
- closeMDNSConn()
+ a.closeMulticastConn()
return nil, ErrUselessUrlsProvided
}
if err = config.initExtIPMapping(a); err != nil {
- closeMDNSConn()
+ a.closeMulticastConn()
return nil, err
}
go a.taskLoop()
- a.startOnConnectionStateChangeRoutine()
+
+ // CandidatePair and ConnectionState are usually changed at once.
+ // Blocking one by the other one causes deadlock.
+ // Hence, we call handlers from independent Goroutines.
+ go a.candidatePairRoutine()
+ go a.connectionStateRoutine()
+ go a.candidateRoutine()
// Restart is also used to initialize the agent for the first time
if err := a.Restart(config.LocalUfrag, config.LocalPwd); err != nil {
- closeMDNSConn()
+ a.closeMulticastConn()
_ = a.Close()
return nil, err
}
@@ -364,81 +376,6 @@ func NewAgent(config *AgentConfig) (*Agent, error) { //nolint:gocognit
return a, nil
}
-// OnConnectionStateChange sets a handler that is fired when the connection state changes
-func (a *Agent) OnConnectionStateChange(f func(ConnectionState)) error {
- a.onConnectionStateChangeHdlr.Store(f)
- return nil
-}
-
-// OnSelectedCandidatePairChange sets a handler that is fired when the final candidate
-// pair is selected
-func (a *Agent) OnSelectedCandidatePairChange(f func(Candidate, Candidate)) error {
- a.onSelectedCandidatePairChangeHdlr.Store(f)
- return nil
-}
-
-// OnCandidate sets a handler that is fired when new candidates gathered. When
-// the gathering process complete the last candidate is nil.
-func (a *Agent) OnCandidate(f func(Candidate)) error {
- a.onCandidateHdlr.Store(f)
- return nil
-}
-
-func (a *Agent) onSelectedCandidatePairChange(p *CandidatePair) {
- if h, ok := a.onSelectedCandidatePairChangeHdlr.Load().(func(Candidate, Candidate)); ok {
- h(p.Local, p.Remote)
- }
-}
-
-func (a *Agent) onCandidate(c Candidate) {
- if onCandidateHdlr, ok := a.onCandidateHdlr.Load().(func(Candidate)); ok {
- onCandidateHdlr(c)
- }
-}
-
-func (a *Agent) onConnectionStateChange(s ConnectionState) {
- if hdlr, ok := a.onConnectionStateChangeHdlr.Load().(func(ConnectionState)); ok {
- hdlr(s)
- }
-}
-
-func (a *Agent) startOnConnectionStateChangeRoutine() {
- go func() {
- for {
- // CandidatePair and ConnectionState are usually changed at once.
- // Blocking one by the other one causes deadlock.
- p, isOpen := <-a.chanCandidatePair
- if !isOpen {
- return
- }
- a.onSelectedCandidatePairChange(p)
- }
- }()
- go func() {
- for {
- select {
- case s, isOpen := <-a.chanState:
- if !isOpen {
- for c := range a.chanCandidate {
- a.onCandidate(c)
- }
- return
- }
- go a.onConnectionStateChange(s)
-
- case c, isOpen := <-a.chanCandidate:
- if !isOpen {
- for s := range a.chanState {
- go a.onConnectionStateChange(s)
- }
- return
- }
- a.onCandidate(c)
- }
- }
- }()
-}
-
func (a *Agent) startConnectivityChecks(isControlling bool, remoteUfrag, remotePwd string) error {
a.muHaveStarted.Lock()
defer a.muHaveStarted.Unlock()
@@ -447,7 +384,7 @@ func (a *Agent) startConnectivityChecks(isControlling bool, remoteUfrag, remoteP
return ErrMultipleStart
default:
}
- if err := a.SetRemoteCredentials(remoteUfrag, remotePwd); err != nil {
+ if err := a.SetRemoteCredentials(remoteUfrag, remotePwd); err != nil { //nolint:contextcheck
return err
}
@@ -474,7 +411,7 @@ func (a *Agent) startConnectivityChecks(isControlling bool, remoteUfrag, remoteP
agent.updateConnectionState(ConnectionStateChecking)
a.requestConnectivityCheck()
- go a.connectivityChecks()
+ go a.connectivityChecks() //nolint:contextcheck
})
}
@@ -504,11 +441,12 @@ func (a *Agent) connectivityChecks() {
a.updateConnectionState(ConnectionStateFailed)
return
}
+ default:
}
a.selector.ContactCandidates()
}); err != nil {
- a.log.Warnf("taskLoop failed: %v", err)
+ a.log.Warnf("Failed to start connectivity checks: %v", err)
}
}
@@ -565,28 +503,26 @@ func (a *Agent) updateConnectionState(newState ConnectionState) {
}
func (a *Agent) setSelectedPair(p *CandidatePair) {
- a.log.Tracef("Set selected candidate pair: %s", p)
-
if p == nil {
var nilPair *CandidatePair
a.selectedPair.Store(nilPair)
+ a.log.Tracef("Unset selected candidate pair")
return
}
p.nominated = true
a.selectedPair.Store(p)
+ a.log.Tracef("Set selected candidate pair: %s", p)
a.updateConnectionState(ConnectionStateConnected)
// Notify when the selected pair changes
- if p != nil {
- a.afterRun(func(ctx context.Context) {
- select {
- case a.chanCandidatePair <- p:
- case <-ctx.Done():
- }
- })
- }
+ a.afterRun(func(ctx context.Context) {
+ select {
+ case a.chanCandidatePair <- p:
+ case <-ctx.Done():
+ }
+ })
// Signal connected
a.onConnectedOnce.Do(func() { close(a.onConnected) })
@@ -596,7 +532,7 @@ func (a *Agent) pingAllCandidates() {
a.log.Trace("pinging all candidates")
if len(a.checklist) == 0 {
- a.log.Warn("pingAllCandidates called with no candidate pairs. Connection is not possible yet.")
+ a.log.Warn("Failed to ping without candidate pairs. Connection is not possible yet.")
}
for _, p := range a.checklist {
@@ -607,7 +543,7 @@ func (a *Agent) pingAllCandidates() {
}
if p.bindingRequestCount > a.maxBindingRequests {
- a.log.Tracef("max requests reached for pair %s, marking it as failed\n", p)
+ a.log.Tracef("max requests reached for pair %s, marking it as failed", p)
p.state = CandidatePairStateFailed
} else {
a.selector.PingCandidate(p.Local, p.Remote)
@@ -703,7 +639,7 @@ func (a *Agent) checkKeepalive() {
if (a.keepaliveInterval != 0) &&
((time.Since(selectedPair.Local.LastSent()) > a.keepaliveInterval) ||
(time.Since(selectedPair.Remote.LastReceived()) > a.keepaliveInterval)) {
- // we use binding request instead of indication to support refresh consent schemas
+ // We use binding request instead of indication to support refresh consent schemas
// see https://tools.ietf.org/html/rfc7675
a.selector.PingCandidate(selectedPair.Local, selectedPair.Remote)
}
@@ -715,10 +651,10 @@ func (a *Agent) AddRemoteCandidate(c Candidate) error {
return nil
}
- // cannot check for network yet because it might not be applied
- // when mDNS hostame is used.
+ // Cannot check for network yet because it might not be applied
+ // when mDNS hostname is used.
if c.TCPType() == TCPTypeActive {
- // TCP Candidates with tcptype active will probe server passive ones, so
+ // TCP Candidates with TCP type active will probe server passive ones, so
// no need to do anything with them.
a.log.Infof("Ignoring remote candidate with tcpType active: %s", c)
return nil
@@ -727,7 +663,7 @@ func (a *Agent) AddRemoteCandidate(c Candidate) error {
// If we have a mDNS Candidate lets fully resolve it before adding it locally
if c.Type() == CandidateTypeHost && strings.HasSuffix(c.Address(), ".local") {
if a.mDNSMode == MulticastDNSModeDisabled {
- a.log.Warnf("remote mDNS candidate added, but mDNS is disabled: (%s)", c.Address())
+ a.log.Warnf("Remote mDNS candidate added, but mDNS is disabled: (%s)", c.Address())
return nil
}
@@ -761,8 +697,8 @@ func (a *Agent) resolveAndAddMulticastCandidate(c *CandidateHost) {
return
}
- ip, _, _, _ := parseAddr(src) //nolint:dogsled
- if ip == nil {
+ ip, ipOk := parseMulticastAnswerAddr(src)
+ if !ipOk {
a.log.Warnf("Failed to discover mDNS candidate %s: failed to parse IP", c.Address())
return
}
@@ -818,6 +754,9 @@ func (a *Agent) addCandidate(ctx context.Context, c Candidate, candidateConn net
if err := c.close(); err != nil {
a.log.Warnf("Failed to close duplicate candidate: %v", err)
}
+ if err := candidateConn.Close(); err != nil {
+ a.log.Warnf("Failed to close duplicate candidate connection: %v", err)
+ }
return
}
}
@@ -888,10 +827,15 @@ func (a *Agent) GetRemoteUserCredentials() (frag string, pwd string, err error)
}
func (a *Agent) removeUfragFromMux() {
- a.tcpMux.RemoveConnByUfrag(a.localUfrag)
+ if a.tcpMux != nil {
+ a.tcpMux.RemoveConnByUfrag(a.localUfrag)
+ }
if a.udpMux != nil {
a.udpMux.RemoveConnByUfrag(a.localUfrag)
}
+ if a.udpMuxSrflx != nil {
+ a.udpMuxSrflx.RemoveConnByUfrag(a.localUfrag)
+ }
}
// Close cleans up the Agent
@@ -902,6 +846,9 @@ func (a *Agent) Close() error {
a.afterRun(func(context.Context) {
a.gatherCandidateCancel()
+ if a.gatherCandidateDone != nil {
+ <-a.gatherCandidateDone
+ }
})
a.err.Store(ErrClosed)
@@ -938,7 +885,7 @@ func (a *Agent) deleteAllCandidates() {
func (a *Agent) findRemoteCandidate(networkType NetworkType, addr net.Addr) Candidate {
ip, port, _, ok := parseAddr(addr)
if !ok {
- a.log.Warnf("Error parsing addr: %s", addr)
+ a.log.Warnf("Failed to parse address: %s", addr)
return nil
}
@@ -952,7 +899,7 @@ func (a *Agent) findRemoteCandidate(networkType NetworkType, addr net.Addr) Cand
}
func (a *Agent) sendBindingRequest(m *stun.Message, local, remote Candidate) {
- a.log.Tracef("ping STUN from %s to %s\n", local.String(), remote.String())
+ a.log.Tracef("ping STUN from %s to %s", local.String(), remote.String())
a.invalidatePendingBindingRequests(time.Now())
a.pendingBindingRequests = append(a.pendingBindingRequests, bindingRequest{
@@ -970,7 +917,7 @@ func (a *Agent) sendBindingSuccess(m *stun.Message, local, remote Candidate) {
ip, port, _, ok := parseAddr(base.addr())
if !ok {
- a.log.Warnf("Error parsing addr: %s", base.addr())
+ a.log.Warnf("Failed to parse address: %s", base.addr())
return
}
@@ -988,12 +935,11 @@ func (a *Agent) sendBindingSuccess(m *stun.Message, local, remote Candidate) {
}
}
-/* Removes pending binding requests that are over maxBindingRequestTimeout old
-
- Let HTO be the transaction timeout, which SHOULD be 2*RTT if
- RTT is known or 500 ms otherwise.
- https://tools.ietf.org/html/rfc8445#appendix-B.1
-*/
+// Removes pending binding requests that are over maxBindingRequestTimeout old
+//
+// Let HTO be the transaction timeout, which SHOULD be 2*RTT if
+// RTT is known or 500 ms otherwise.
+// https://tools.ietf.org/html/rfc8445#appendix-B.1
func (a *Agent) invalidatePendingBindingRequests(filterTime time.Time) {
initialSize := len(a.pendingBindingRequests)
@@ -1041,38 +987,38 @@ func (a *Agent) handleInbound(m *stun.Message, local Candidate, remote net.Addr)
if a.isControlling {
if m.Contains(stun.AttrICEControlling) {
- a.log.Debug("inbound isControlling && a.isControlling == true")
+ a.log.Debug("Inbound STUN message: isControlling && a.isControlling == true")
return
} else if m.Contains(stun.AttrUseCandidate) {
- a.log.Debug("useCandidate && a.isControlling == true")
+ a.log.Debug("Inbound STUN message: useCandidate && a.isControlling == true")
return
}
} else {
if m.Contains(stun.AttrICEControlled) {
- a.log.Debug("inbound isControlled && a.isControlling == false")
+ a.log.Debug("Inbound STUN message: isControlled && a.isControlling == false")
return
}
}
remoteCandidate := a.findRemoteCandidate(local.NetworkType(), remote)
if m.Type.Class == stun.ClassSuccessResponse {
- if err = assertInboundMessageIntegrity(m, []byte(a.remotePwd)); err != nil {
- a.log.Warnf("discard message from (%s), %v", remote, err)
+ if err = stun.MessageIntegrity([]byte(a.remotePwd)).Check(m); err != nil {
+ a.log.Warnf("Discard message from (%s), %v", remote, err)
return
}
if remoteCandidate == nil {
- a.log.Warnf("discard success message from (%s), no such remote", remote)
+ a.log.Warnf("Discard success message from (%s), no such remote", remote)
return
}
a.selector.HandleSuccessResponse(m, local, remoteCandidate, remote)
} else if m.Type.Class == stun.ClassRequest {
- if err = assertInboundUsername(m, a.localUfrag+":"+a.remoteUfrag); err != nil {
- a.log.Warnf("discard message from (%s), %v", remote, err)
+ if err = stunx.AssertUsername(m, a.localUfrag+":"+a.remoteUfrag); err != nil {
+ a.log.Warnf("Discard message from (%s), %v", remote, err)
return
- } else if err = assertInboundMessageIntegrity(m, []byte(a.localPwd)); err != nil {
- a.log.Warnf("discard message from (%s), %v", remote, err)
+ } else if err = stun.MessageIntegrity([]byte(a.localPwd)).Check(m); err != nil {
+ a.log.Warnf("Discard message from (%s), %v", remote, err)
return
}
@@ -1099,7 +1045,7 @@ func (a *Agent) handleInbound(m *stun.Message, local Candidate, remote net.Addr)
}
remoteCandidate = prflxCandidate
- a.log.Debugf("adding a new peer-reflexive candidate: %s ", remote)
+ a.log.Debugf("Adding a new peer-reflexive candidate: %s ", remote)
a.addRemoteCandidate(remoteCandidate)
}
@@ -1115,26 +1061,25 @@ func (a *Agent) handleInbound(m *stun.Message, local Candidate, remote net.Addr)
// validateNonSTUNTraffic processes non STUN traffic from a remote candidate,
// and returns true if it is an actual remote candidate
-func (a *Agent) validateNonSTUNTraffic(local Candidate, remote net.Addr) bool {
- var isValidCandidate uint64
+func (a *Agent) validateNonSTUNTraffic(local Candidate, remote net.Addr) (Candidate, bool) {
+ var remoteCandidate Candidate
if err := a.run(local.context(), func(ctx context.Context, agent *Agent) {
- remoteCandidate := a.findRemoteCandidate(local.NetworkType(), remote)
+ remoteCandidate = a.findRemoteCandidate(local.NetworkType(), remote)
if remoteCandidate != nil {
remoteCandidate.seen(false)
- atomic.AddUint64(&isValidCandidate, 1)
}
}); err != nil {
- a.log.Warnf("failed to validate remote candidate: %v", err)
+ a.log.Warnf("Failed to validate remote candidate: %v", err)
}
- return atomic.LoadUint64(&isValidCandidate) == 1
+ return remoteCandidate, remoteCandidate != nil
}
// GetSelectedCandidatePair returns the selected pair or nil if there is none
func (a *Agent) GetSelectedCandidatePair() (*CandidatePair, error) {
selectedPair := a.getSelectedPair()
if selectedPair == nil {
- return nil, nil
+ return nil, nil //nolint:nilnil
}
local, err := selectedPair.Local.copy()
@@ -1151,18 +1096,17 @@ func (a *Agent) GetSelectedCandidatePair() (*CandidatePair, error) {
}
func (a *Agent) getSelectedPair() *CandidatePair {
- selectedPair := a.selectedPair.Load()
- if selectedPair == nil {
- return nil
+ if selectedPair, ok := a.selectedPair.Load().(*CandidatePair); ok {
+ return selectedPair
}
- return selectedPair.(*CandidatePair)
+ return nil
}
func (a *Agent) closeMulticastConn() {
if a.mDNSConn != nil {
if err := a.mDNSConn.Close(); err != nil {
- a.log.Warnf("failed to close mDNS Conn: %v", err)
+ a.log.Warnf("Failed to close mDNS Conn: %v", err)
}
}
}
@@ -1185,8 +1129,10 @@ func (a *Agent) SetRemoteCredentials(remoteUfrag, remotePwd string) error {
// Restart restarts the ICE Agent with the provided ufrag/pwd
// If no ufrag/pwd is provided the Agent will generate one itself
//
-// Restart must only be called when GatheringState is GatheringStateComplete
-// a user must then call GatherCandidates explicitly to start generating new ones
+// If there is a gatherer routine currently running, Restart will
+// cancel it.
+// After a Restart, the user must then call GatherCandidates explicitly
+// to start generating new ones.
func (a *Agent) Restart(ufrag, pwd string) error {
if ufrag == "" {
var err error
@@ -1213,8 +1159,7 @@ func (a *Agent) Restart(ufrag, pwd string) error {
var err error
if runErr := a.run(a.context(), func(ctx context.Context, agent *Agent) {
if agent.gatheringState == GatheringStateGathering {
- err = ErrRestartWhenGathering
- return
+ agent.gatherCandidateCancel()
}
// Clear all agent needed to take back to fresh state
diff --git a/vendor/github.com/pion/ice/v2/agent_config.go b/vendor/github.com/pion/ice/v2/agent_config.go
index e577af101..f5897cd4a 100644
--- a/vendor/github.com/pion/ice/v2/agent_config.go
+++ b/vendor/github.com/pion/ice/v2/agent_config.go
@@ -1,10 +1,15 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
+ "net"
"time"
"github.com/pion/logging"
- "github.com/pion/transport/vnet"
+ "github.com/pion/stun"
+ "github.com/pion/transport/v2"
"golang.org/x/net/proxy"
)
@@ -21,25 +26,25 @@ const (
// defaultFailedTimeout is the default time till an Agent transitions to failed after disconnected
defaultFailedTimeout = 25 * time.Second
- // wait time before nominating a host candidate
+ // defaultHostAcceptanceMinWait is the wait time before nominating a host candidate
defaultHostAcceptanceMinWait = 0
- // wait time before nominating a srflx candidate
+ // defaultSrflxAcceptanceMinWait is the wait time before nominating a srflx candidate
defaultSrflxAcceptanceMinWait = 500 * time.Millisecond
- // wait time before nominating a prflx candidate
+ // defaultPrflxAcceptanceMinWait is the wait time before nominating a prflx candidate
defaultPrflxAcceptanceMinWait = 1000 * time.Millisecond
- // wait time before nominating a relay candidate
+ // defaultRelayAcceptanceMinWait is the wait time before nominating a relay candidate
defaultRelayAcceptanceMinWait = 2000 * time.Millisecond
- // max binding request before considering a pair failed
+ // defaultMaxBindingRequests is the maximum number of binding requests before considering a pair failed
defaultMaxBindingRequests = 7
- // the number of bytes that can be buffered before we start to error
+ // maxBufferSize is the number of bytes that can be buffered before we start to error
maxBufferSize = 1000 * 1000 // 1MB
- // wait time before binding requests can be deleted
+ // maxBindingRequestTimeout is the wait time before binding requests can be deleted
maxBindingRequestTimeout = 4000 * time.Millisecond
)
@@ -50,7 +55,7 @@ func defaultCandidateTypes() []CandidateType {
// AgentConfig collects the arguments to ice.Agent construction into
// a single structure, for future-proofness of the interface
type AgentConfig struct {
- Urls []*URL
+ Urls []*stun.URI
// PortMin and PortMax are optional. Leave them 0 for the default UDP port allocation strategy.
PortMin uint16
@@ -108,14 +113,14 @@ type AgentConfig struct {
// NAT1To1IPCandidateType is used along with NAT1To1IPs to specify which candidate type
// the 1:1 NAT IP addresses should be mapped to.
// If unspecified or CandidateTypeHost, NAT1To1IPs are used to replace host candidate IPs.
- // If CandidateTypeServerReflexive, it will insert a srflx candidate (as if it was dervied
+ // If CandidateTypeServerReflexive, it will insert a srflx candidate (as if it was derived
// from a STUN server) with its port number being the one for the actual host candidate.
// Other values will result in an error.
NAT1To1IPCandidateType CandidateType
// NAT1To1IPs contains a list of public IP addresses that are to be used as a host
// candidate or srflx candidate. This is used typically for servers that are behind
- // 1:1 D-NAT (e.g. AWS EC2 instances) and to eliminate the need of server reflexisive
+ // 1:1 D-NAT (e.g. AWS EC2 instances) and to eliminate the need of server reflexive
// candidate gathering.
NAT1To1IPs []string
@@ -129,13 +134,17 @@ type AgentConfig struct {
RelayAcceptanceMinWait *time.Duration
// Net is the our abstracted network interface for internal development purpose only
- // (see github.com/pion/transport/vnet)
- Net *vnet.Net
+ // (see https://github.com/pion/transport)
+ Net transport.Net
- // InterfaceFilter is a function that you can use in order to whitelist or blacklist
+ // InterfaceFilter is a function that you can use in order to whitelist or blacklist
// the interfaces which are used to gather ICE candidates.
InterfaceFilter func(string) bool
+ // IPFilter is a function that you can use in order to whitelist or blacklist
+ // the ips which are used to gather ICE candidates.
+ IPFilter func(net.IP) bool
+
// InsecureSkipVerify controls if self-signed certificates are accepted when connecting
// to TURN servers via TLS or DTLS
InsecureSkipVerify bool
@@ -150,9 +159,21 @@ type AgentConfig struct {
// defer to UDPMux for incoming connections
UDPMux UDPMux
+ // UDPMuxSrflx is used for multiplexing multiple incoming UDP connections of server reflexive candidates
+ // on a single port when this is set, the agent ignores PortMin and PortMax configurations and will
+ // defer to UDPMuxSrflx for incoming connections
+ // It embeds UDPMux to do the actual connection multiplexing
+ UDPMuxSrflx UniversalUDPMux
+
// Proxy Dialer is a dialer that should be implemented by the user based on golang.org/x/net/proxy
// dial interface in order to support corporate proxies
ProxyDialer proxy.Dialer
+
+ // Deprecated: AcceptAggressiveNomination always enabled.
+ AcceptAggressiveNomination bool
+
+ // Include loopback addresses in the candidate list.
+ IncludeLoopback bool
}
// initWithDefaults populates an agent and falls back to defaults if fields are unset
@@ -225,7 +246,7 @@ func (config *AgentConfig) initExtIPMapping(a *Agent) error {
return err
}
if a.extIPMapper == nil {
- return nil // this may happen when config.NAT1To1IPs is an empty array
+ return nil // This may happen when config.NAT1To1IPs is an empty array
}
if a.extIPMapper.candidateType == CandidateTypeHost {
if a.mDNSMode == MulticastDNSModeQueryAndGather {
diff --git a/vendor/github.com/pion/ice/v2/agent_handlers.go b/vendor/github.com/pion/ice/v2/agent_handlers.go
new file mode 100644
index 000000000..c5a5ec03b
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/agent_handlers.go
@@ -0,0 +1,60 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ice
+
+// OnConnectionStateChange sets a handler that is fired when the connection state changes
+func (a *Agent) OnConnectionStateChange(f func(ConnectionState)) error {
+ a.onConnectionStateChangeHdlr.Store(f)
+ return nil
+}
+
+// OnSelectedCandidatePairChange sets a handler that is fired when the final candidate
+// pair is selected
+func (a *Agent) OnSelectedCandidatePairChange(f func(Candidate, Candidate)) error {
+ a.onSelectedCandidatePairChangeHdlr.Store(f)
+ return nil
+}
+
+// OnCandidate sets a handler that is fired when new candidates gathered. When
+// the gathering process complete the last candidate is nil.
+func (a *Agent) OnCandidate(f func(Candidate)) error {
+ a.onCandidateHdlr.Store(f)
+ return nil
+}
+
+func (a *Agent) onSelectedCandidatePairChange(p *CandidatePair) {
+ if h, ok := a.onSelectedCandidatePairChangeHdlr.Load().(func(Candidate, Candidate)); ok {
+ h(p.Local, p.Remote)
+ }
+}
+
+func (a *Agent) onCandidate(c Candidate) {
+ if onCandidateHdlr, ok := a.onCandidateHdlr.Load().(func(Candidate)); ok {
+ onCandidateHdlr(c)
+ }
+}
+
+func (a *Agent) onConnectionStateChange(s ConnectionState) {
+ if hdlr, ok := a.onConnectionStateChangeHdlr.Load().(func(ConnectionState)); ok {
+ hdlr(s)
+ }
+}
+
+func (a *Agent) candidatePairRoutine() {
+ for p := range a.chanCandidatePair {
+ a.onSelectedCandidatePairChange(p)
+ }
+}
+
+func (a *Agent) connectionStateRoutine() {
+ for s := range a.chanState {
+ go a.onConnectionStateChange(s)
+ }
+}
+
+func (a *Agent) candidateRoutine() {
+ for c := range a.chanCandidate {
+ a.onCandidate(c)
+ }
+}
diff --git a/vendor/github.com/pion/ice/v2/agent_stats.go b/vendor/github.com/pion/ice/v2/agent_stats.go
index b249560b6..b9ad7187e 100644
--- a/vendor/github.com/pion/ice/v2/agent_stats.go
+++ b/vendor/github.com/pion/ice/v2/agent_stats.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -45,7 +48,7 @@ func (a *Agent) GetCandidatePairsStats() []CandidatePairStats {
res = result
})
if err != nil {
- a.log.Errorf("error getting candidate pairs stats %v", err)
+ a.log.Errorf("Failed to get candidate pairs stats: %v", err)
return []CandidatePairStats{}
}
return res
@@ -60,7 +63,9 @@ func (a *Agent) GetLocalCandidatesStats() []CandidateStats {
for _, c := range localCandidates {
relayProtocol := ""
if c.Type() == CandidateTypeRelay {
- relayProtocol = c.(*CandidateRelay).RelayProtocol()
+ if cRelay, ok := c.(*CandidateRelay); ok {
+ relayProtocol = cRelay.RelayProtocol()
+ }
}
stat := CandidateStats{
Timestamp: time.Now(),
@@ -80,7 +85,7 @@ func (a *Agent) GetLocalCandidatesStats() []CandidateStats {
res = result
})
if err != nil {
- a.log.Errorf("error getting candidate pairs stats %v", err)
+ a.log.Errorf("Failed to get candidate pair stats: %v", err)
return []CandidateStats{}
}
return res
@@ -91,8 +96,8 @@ func (a *Agent) GetRemoteCandidatesStats() []CandidateStats {
var res []CandidateStats
err := a.run(a.context(), func(ctx context.Context, agent *Agent) {
result := make([]CandidateStats, 0, len(agent.remoteCandidates))
- for networkType, localCandidates := range agent.remoteCandidates {
- for _, c := range localCandidates {
+ for networkType, remoteCandidates := range agent.remoteCandidates {
+ for _, c := range remoteCandidates {
stat := CandidateStats{
Timestamp: time.Now(),
ID: c.ID(),
@@ -110,7 +115,7 @@ func (a *Agent) GetRemoteCandidatesStats() []CandidateStats {
res = result
})
if err != nil {
- a.log.Errorf("error getting candidate pairs stats %v", err)
+ a.log.Errorf("Failed to get candidate pair stats: %v", err)
return []CandidateStats{}
}
return res
diff --git a/vendor/github.com/pion/ice/v2/candidate.go b/vendor/github.com/pion/ice/v2/candidate.go
index c3049dd00..92a007688 100644
--- a/vendor/github.com/pion/ice/v2/candidate.go
+++ b/vendor/github.com/pion/ice/v2/candidate.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
diff --git a/vendor/github.com/pion/ice/v2/candidate_base.go b/vendor/github.com/pion/ice/v2/candidate_base.go
index 7703e7106..8e551d8f2 100644
--- a/vendor/github.com/pion/ice/v2/candidate_base.go
+++ b/vendor/github.com/pion/ice/v2/candidate_base.go
@@ -1,16 +1,20 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
"context"
+ "errors"
"fmt"
"hash/crc32"
+ "io"
"net"
"strconv"
"strings"
"sync/atomic"
"time"
- "github.com/pion/logging"
"github.com/pion/stun"
)
@@ -37,6 +41,8 @@ type candidateBase struct {
foundationOverride string
priorityOverride uint32
+
+ remoteCandidateCaches map[AddrPort]Candidate
}
// Done implements context.Context
@@ -60,7 +66,7 @@ func (c *candidateBase) Deadline() (deadline time.Time, ok bool) {
}
// Value implements context.Context
-func (c *candidateBase) Value(key interface{}) interface{} {
+func (c *candidateBase) Value(interface{}) interface{} {
return nil
}
@@ -206,9 +212,9 @@ func (c *candidateBase) start(a *Agent, conn net.PacketConn, initializedCh <-cha
}
func (c *candidateBase) recvLoop(initializedCh <-chan struct{}) {
- defer func() {
- close(c.closedCh)
- }()
+ a := c.agent()
+
+ defer close(c.closedCh)
select {
case <-initializedCh:
@@ -216,47 +222,73 @@ func (c *candidateBase) recvLoop(initializedCh <-chan struct{}) {
return
}
- log := c.agent().log
- buffer := make([]byte, receiveMTU)
+ buf := make([]byte, receiveMTU)
for {
- n, srcAddr, err := c.conn.ReadFrom(buffer)
+ n, srcAddr, err := c.conn.ReadFrom(buf)
if err != nil {
+ if !(errors.Is(err, io.EOF) || errors.Is(err, net.ErrClosed)) {
+ a.log.Warnf("Failed to read from candidate %s: %v", c, err)
+ }
return
}
- handleInboundCandidateMsg(c, c, buffer[:n], srcAddr, log)
+ c.handleInboundPacket(buf[:n], srcAddr)
}
}
-func handleInboundCandidateMsg(ctx context.Context, c Candidate, buffer []byte, srcAddr net.Addr, log logging.LeveledLogger) {
- if stun.IsMessage(buffer) {
+func (c *candidateBase) validateSTUNTrafficCache(addr net.Addr) bool {
+ if candidate, ok := c.remoteCandidateCaches[toAddrPort(addr)]; ok {
+ candidate.seen(false)
+ return true
+ }
+ return false
+}
+
+func (c *candidateBase) addRemoteCandidateCache(candidate Candidate, srcAddr net.Addr) {
+ if c.validateSTUNTrafficCache(srcAddr) {
+ return
+ }
+ c.remoteCandidateCaches[toAddrPort(srcAddr)] = candidate
+}
+
+func (c *candidateBase) handleInboundPacket(buf []byte, srcAddr net.Addr) {
+ a := c.agent()
+
+ if stun.IsMessage(buf) {
m := &stun.Message{
- Raw: make([]byte, len(buffer)),
+ Raw: make([]byte, len(buf)),
}
+
// Explicitly copy raw buffer so Message can own the memory.
- copy(m.Raw, buffer)
+ copy(m.Raw, buf)
+
if err := m.Decode(); err != nil {
- log.Warnf("Failed to handle decode ICE from %s to %s: %v", c.addr(), srcAddr, err)
+ a.log.Warnf("Failed to handle decode ICE from %s to %s: %v", c.addr(), srcAddr, err)
return
}
- err := c.agent().run(ctx, func(ctx context.Context, agent *Agent) {
- agent.handleInbound(m, c, srcAddr)
- })
- if err != nil {
- log.Warnf("Failed to handle message: %v", err)
+
+ if err := a.run(c, func(ctx context.Context, a *Agent) {
+ a.handleInbound(m, c, srcAddr)
+ }); err != nil {
+ a.log.Warnf("Failed to handle message: %v", err)
}
return
}
- if !c.agent().validateNonSTUNTraffic(c, srcAddr) {
- log.Warnf("Discarded message from %s, not a valid remote candidate", c.addr())
- return
+ if !c.validateSTUNTrafficCache(srcAddr) {
+ remoteCandidate, valid := a.validateNonSTUNTraffic(c, srcAddr) //nolint:contextcheck
+ if !valid {
+ a.log.Warnf("Discarded message from %s, not a valid remote candidate", c.addr())
+ return
+ }
+ c.addRemoteCandidateCache(remoteCandidate, srcAddr)
}
- // NOTE This will return packetio.ErrFull if the buffer ever manages to fill up.
- if _, err := c.agent().buffer.Write(buffer); err != nil {
- log.Warnf("failed to write packet")
+ // Note: This will return packetio.ErrFull if the buffer ever manages to fill up.
+ if _, err := a.buf.Write(buf); err != nil {
+ a.log.Warnf("Failed to write packet: %s", err)
+ return
}
}
@@ -300,7 +332,11 @@ func (c *candidateBase) close() error {
func (c *candidateBase) writeTo(raw []byte, dst Candidate) (int, error) {
n, err := c.conn.WriteTo(raw, dst.addr())
if err != nil {
- c.agent().log.Warnf("%s: %v", errSendPacket, err)
+ // If the connection is closed, we should return the error
+ if errors.Is(err, io.ErrClosedPipe) {
+ return n, err
+ }
+ c.agent().log.Infof("%s: %v", errSendPacket, err)
return n, nil
}
c.seen(true)
@@ -336,17 +372,16 @@ func (c *candidateBase) Equal(other Candidate) bool {
// String makes the candidateBase printable
func (c *candidateBase) String() string {
- return fmt.Sprintf("%s %s %s:%d%s", c.NetworkType(), c.Type(), c.Address(), c.Port(), c.relatedAddress)
+ return fmt.Sprintf("%s %s %s%s", c.NetworkType(), c.Type(), net.JoinHostPort(c.Address(), strconv.Itoa(c.Port())), c.relatedAddress)
}
// LastReceived returns a time.Time indicating the last time
// this candidate was received
func (c *candidateBase) LastReceived() time.Time {
- lastReceived := c.lastReceived.Load()
- if lastReceived == nil {
- return time.Time{}
+ if lastReceived, ok := c.lastReceived.Load().(time.Time); ok {
+ return lastReceived
}
- return lastReceived.(time.Time)
+ return time.Time{}
}
func (c *candidateBase) setLastReceived(t time.Time) {
@@ -356,11 +391,10 @@ func (c *candidateBase) setLastReceived(t time.Time) {
// LastSent returns a time.Time indicating the last time
// this candidate was sent
func (c *candidateBase) LastSent() time.Time {
- lastSent := c.lastSent.Load()
- if lastSent == nil {
- return time.Time{}
+ if lastSent, ok := c.lastSent.Load().(time.Time); ok {
+ return lastSent
}
- return lastSent.(time.Time)
+ return time.Time{}
}
func (c *candidateBase) setLastSent(t time.Time) {
@@ -438,7 +472,7 @@ func UnmarshalCandidate(raw string) (Candidate, error) {
// Component
rawComponent, err := strconv.ParseUint(split[1], 10, 16)
if err != nil {
- return nil, fmt.Errorf("%w: %v", errParseComponent, err)
+ return nil, fmt.Errorf("%w: %v", errParseComponent, err) //nolint:errorlint
}
component := uint16(rawComponent)
@@ -448,7 +482,7 @@ func UnmarshalCandidate(raw string) (Candidate, error) {
// Priority
priorityRaw, err := strconv.ParseUint(split[3], 10, 32)
if err != nil {
- return nil, fmt.Errorf("%w: %v", errParsePriority, err)
+ return nil, fmt.Errorf("%w: %v", errParsePriority, err) //nolint:errorlint
}
priority := uint32(priorityRaw)
@@ -458,7 +492,7 @@ func UnmarshalCandidate(raw string) (Candidate, error) {
// Port
rawPort, err := strconv.ParseUint(split[5], 10, 16)
if err != nil {
- return nil, fmt.Errorf("%w: %v", errParsePort, err)
+ return nil, fmt.Errorf("%w: %v", errParsePort, err) //nolint:errorlint
}
port := int(rawPort)
typ := split[7]
@@ -481,12 +515,12 @@ func UnmarshalCandidate(raw string) (Candidate, error) {
// RelatedPort
rawRelatedPort, parseErr := strconv.ParseUint(split[3], 10, 16)
if parseErr != nil {
- return nil, fmt.Errorf("%w: %v", errParsePort, parseErr)
+ return nil, fmt.Errorf("%w: %v", errParsePort, parseErr) //nolint:errorlint
}
relatedPort = int(rawRelatedPort)
} else if split[0] == "tcptype" {
if len(split) < 2 {
- return nil, fmt.Errorf("%w: incorrect length", errParseTypType)
+ return nil, fmt.Errorf("%w: incorrect length", errParseTCPType)
}
tcpType = NewTCPType(split[1])
diff --git a/vendor/github.com/pion/ice/v2/candidate_host.go b/vendor/github.com/pion/ice/v2/candidate_host.go
index b03dbdb51..5d207dd91 100644
--- a/vendor/github.com/pion/ice/v2/candidate_host.go
+++ b/vendor/github.com/pion/ice/v2/candidate_host.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -34,14 +37,15 @@ func NewCandidateHost(config *CandidateHostConfig) (*CandidateHost, error) {
c := &CandidateHost{
candidateBase: candidateBase{
- id: candidateID,
- address: config.Address,
- candidateType: CandidateTypeHost,
- component: config.Component,
- port: config.Port,
- tcpType: config.TCPType,
- foundationOverride: config.Foundation,
- priorityOverride: config.Priority,
+ id: candidateID,
+ address: config.Address,
+ candidateType: CandidateTypeHost,
+ component: config.Component,
+ port: config.Port,
+ tcpType: config.TCPType,
+ foundationOverride: config.Foundation,
+ priorityOverride: config.Priority,
+ remoteCandidateCaches: map[AddrPort]Candidate{},
},
network: config.Network,
}
diff --git a/vendor/github.com/pion/ice/v2/candidate_peer_reflexive.go b/vendor/github.com/pion/ice/v2/candidate_peer_reflexive.go
index 0b330d1c9..f019ec698 100644
--- a/vendor/github.com/pion/ice/v2/candidate_peer_reflexive.go
+++ b/vendor/github.com/pion/ice/v2/candidate_peer_reflexive.go
@@ -1,4 +1,8 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
// Package ice ...
+//
//nolint:dupl
package ice
@@ -55,6 +59,7 @@ func NewCandidatePeerReflexive(config *CandidatePeerReflexiveConfig) (*Candidate
Address: config.RelAddr,
Port: config.RelPort,
},
+ remoteCandidateCaches: map[AddrPort]Candidate{},
},
}, nil
}
diff --git a/vendor/github.com/pion/ice/v2/candidate_relay.go b/vendor/github.com/pion/ice/v2/candidate_relay.go
index 3d0be3168..449d077a6 100644
--- a/vendor/github.com/pion/ice/v2/candidate_relay.go
+++ b/vendor/github.com/pion/ice/v2/candidate_relay.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -60,6 +63,7 @@ func NewCandidateRelay(config *CandidateRelayConfig) (*CandidateRelay, error) {
Address: config.RelAddr,
Port: config.RelPort,
},
+ remoteCandidateCaches: map[AddrPort]Candidate{},
},
relayProtocol: config.RelayProtocol,
onClose: config.OnClose,
@@ -79,3 +83,16 @@ func (c *CandidateRelay) close() error {
}
return err
}
+
+func (c *CandidateRelay) copy() (Candidate, error) {
+ cc, err := c.candidateBase.copy()
+ if err != nil {
+ return nil, err
+ }
+
+ if ccr, ok := cc.(*CandidateRelay); ok {
+ ccr.relayProtocol = c.relayProtocol
+ }
+
+ return cc, nil
+}
diff --git a/vendor/github.com/pion/ice/v2/candidate_server_reflexive.go b/vendor/github.com/pion/ice/v2/candidate_server_reflexive.go
index 125a53782..3a8ac0ff7 100644
--- a/vendor/github.com/pion/ice/v2/candidate_server_reflexive.go
+++ b/vendor/github.com/pion/ice/v2/candidate_server_reflexive.go
@@ -1,5 +1,6 @@
-// Package ice ...
-//nolint:dupl
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import "net"
@@ -54,6 +55,7 @@ func NewCandidateServerReflexive(config *CandidateServerReflexiveConfig) (*Candi
Address: config.RelAddr,
Port: config.RelPort,
},
+ remoteCandidateCaches: map[AddrPort]Candidate{},
},
}, nil
}
diff --git a/vendor/github.com/pion/ice/v2/candidatepair.go b/vendor/github.com/pion/ice/v2/candidatepair.go
index 79cab1a9f..f33be539c 100644
--- a/vendor/github.com/pion/ice/v2/candidatepair.go
+++ b/vendor/github.com/pion/ice/v2/candidatepair.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -18,12 +21,13 @@ func newCandidatePair(local, remote Candidate, controlling bool) *CandidatePair
// CandidatePair is a combination of a
// local and remote candidate
type CandidatePair struct {
- iceRoleControlling bool
- Remote Candidate
- Local Candidate
- bindingRequestCount uint16
- state CandidatePairState
- nominated bool
+ iceRoleControlling bool
+ Remote Candidate
+ Local Candidate
+ bindingRequestCount uint16
+ state CandidatePairState
+ nominated bool
+ nominateOnBindingSuccess bool
}
func (p *CandidatePair) String() string {
diff --git a/vendor/github.com/pion/ice/v2/candidatepair_state.go b/vendor/github.com/pion/ice/v2/candidatepair_state.go
index 28c7187eb..1a1e827b0 100644
--- a/vendor/github.com/pion/ice/v2/candidatepair_state.go
+++ b/vendor/github.com/pion/ice/v2/candidatepair_state.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
// CandidatePairState represent the ICE candidate pair state
diff --git a/vendor/github.com/pion/ice/v2/candidaterelatedaddress.go b/vendor/github.com/pion/ice/v2/candidaterelatedaddress.go
index 18cf31831..e87c70514 100644
--- a/vendor/github.com/pion/ice/v2/candidaterelatedaddress.go
+++ b/vendor/github.com/pion/ice/v2/candidaterelatedaddress.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import "fmt"
diff --git a/vendor/github.com/pion/ice/v2/candidatetype.go b/vendor/github.com/pion/ice/v2/candidatetype.go
index 376c4089f..3972934cb 100644
--- a/vendor/github.com/pion/ice/v2/candidatetype.go
+++ b/vendor/github.com/pion/ice/v2/candidatetype.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
// CandidateType represents the type of candidate
diff --git a/vendor/github.com/pion/ice/v2/codecov.yml b/vendor/github.com/pion/ice/v2/codecov.yml
index 085200a48..263e4d45c 100644
--- a/vendor/github.com/pion/ice/v2/codecov.yml
+++ b/vendor/github.com/pion/ice/v2/codecov.yml
@@ -3,6 +3,8 @@
#
# It is automatically copied from https://github.com/pion/.goassets repository.
#
+# SPDX-FileCopyrightText: 2023 The Pion community
+# SPDX-License-Identifier: MIT
coverage:
status:
diff --git a/vendor/github.com/pion/ice/v2/context.go b/vendor/github.com/pion/ice/v2/context.go
index 627d81ef4..36454450c 100644
--- a/vendor/github.com/pion/ice/v2/context.go
+++ b/vendor/github.com/pion/ice/v2/context.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -32,6 +35,6 @@ func (a agentContext) Deadline() (deadline time.Time, ok bool) {
}
// Value implements context.Context
-func (a agentContext) Value(key interface{}) interface{} {
+func (a agentContext) Value(interface{}) interface{} {
return nil
}
diff --git a/vendor/github.com/pion/ice/v2/errors.go b/vendor/github.com/pion/ice/v2/errors.go
index 8ca9c2cde..e05cce898 100644
--- a/vendor/github.com/pion/ice/v2/errors.go
+++ b/vendor/github.com/pion/ice/v2/errors.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import "errors"
@@ -10,7 +13,7 @@ var (
ErrSchemeType = errors.New("unknown scheme type")
// ErrSTUNQuery indicates query arguments are provided in a STUN URL.
- ErrSTUNQuery = errors.New("queries not supported in stun address")
+ ErrSTUNQuery = errors.New("queries not supported in STUN address")
// ErrInvalidQuery indicates an malformed query is provided.
ErrInvalidQuery = errors.New("invalid query")
@@ -25,7 +28,7 @@ var (
// Have to be at least 24 bits long
ErrLocalUfragInsufficientBits = errors.New("local username fragment is less than 24 bits long")
- // ErrLocalPwdInsufficientBits indicates local passoword insufficient bits are provided.
+ // ErrLocalPwdInsufficientBits indicates local password insufficient bits are provided.
// Have to be at least 128 bits long
ErrLocalPwdInsufficientBits = errors.New("local password is less than 128 bits long")
@@ -97,15 +100,9 @@ var (
// ErrInvalidMulticastDNSHostName indicates an invalid MulticastDNSHostName
ErrInvalidMulticastDNSHostName = errors.New("invalid mDNS HostName, must end with .local and can only contain a single '.'")
- // ErrRestartWhenGathering indicates Restart was called when Agent is in GatheringStateGathering
- ErrRestartWhenGathering = errors.New("ICE Agent can not be restarted when gathering")
-
// ErrRunCanceled indicates a run operation was canceled by its individual done
ErrRunCanceled = errors.New("run was canceled by done")
- // ErrTCPMuxNotInitialized indicates TCPMux is not initialized and that invalidTCPMux is used.
- ErrTCPMuxNotInitialized = errors.New("TCPMux is not initialized")
-
// ErrTCPRemoteAddrAlreadyExists indicates we already have the connection with same remote addr.
ErrTCPRemoteAddrAlreadyExists = errors.New("conn with same remote addr already exists")
@@ -121,18 +118,25 @@ var (
errParsePriority = errors.New("could not parse priority")
errParsePort = errors.New("could not parse port")
errParseRelatedAddr = errors.New("could not parse related addresses")
- errParseTypType = errors.New("could not parse typtype")
+ errParseTCPType = errors.New("could not parse TCP type")
errGetXorMappedAddrResponse = errors.New("failed to get XOR-MAPPED-ADDRESS response")
errConnectionAddrAlreadyExist = errors.New("connection with same remote address already exists")
errReadingStreamingPacket = errors.New("error reading streaming packet")
errWriting = errors.New("error writing to")
errClosingConnection = errors.New("error closing connection")
- errMissingProtocolScheme = errors.New("missing protocol scheme")
- errTooManyColonsAddr = errors.New("too many colons in address")
errRead = errors.New("unexpected error trying to read")
errUnknownRole = errors.New("unknown role")
- errMismatchUsername = errors.New("username mismatch")
errICEWriteSTUNMessage = errors.New("the ICE conn can't write STUN messages")
errUDPMuxDisabled = errors.New("UDPMux is not enabled")
- errCandidateIPNotFound = errors.New("could not determine local IP for Mux candidate")
+ errNoXorAddrMapping = errors.New("no address mapping")
+ errSendSTUNPacket = errors.New("failed to send STUN packet")
+ errXORMappedAddrTimeout = errors.New("timeout while waiting for XORMappedAddr")
+ errNotImplemented = errors.New("not implemented yet")
+ errNoUDPMuxAvailable = errors.New("no UDP mux is available")
+ errNoTCPMuxAvailable = errors.New("no TCP mux is available")
+ errInvalidAddress = errors.New("invalid address")
+
+ // UDPMuxDefault should not listen on unspecified address, but to keep backward compatibility, don't return error now.
+ // will be used in the future.
+ // errListenUnspecified = errors.New("can't listen on unspecified address")
)
diff --git a/vendor/github.com/pion/ice/v2/external_ip_mapper.go b/vendor/github.com/pion/ice/v2/external_ip_mapper.go
index 5310cc0ae..3d542fb1a 100644
--- a/vendor/github.com/pion/ice/v2/external_ip_mapper.go
+++ b/vendor/github.com/pion/ice/v2/external_ip_mapper.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -15,8 +18,9 @@ func validateIPString(ipStr string) (net.IP, bool, error) {
// ipMapping holds the mapping of local and external IP address for a particular IP family
type ipMapping struct {
- ipSole net.IP // when non-nil, this is the sole external IP for one local IP assumed
- ipMap map[string]net.IP // local-to-external IP mapping (k: local, v: external)
+ ipSole net.IP // When non-nil, this is the sole external IP for one local IP assumed
+ ipMap map[string]net.IP // Local-to-external IP mapping (k: local, v: external)
+ valid bool // If not set any external IP, valid is false
}
func (m *ipMapping) setSoleIP(ip net.IP) error {
@@ -25,6 +29,7 @@ func (m *ipMapping) setSoleIP(ip net.IP) error {
}
m.ipSole = ip
+ m.valid = true
return nil
}
@@ -36,17 +41,22 @@ func (m *ipMapping) addIPMapping(locIP, extIP net.IP) error {
locIPStr := locIP.String()
- // check if dup of local IP
+ // Check if dup of local IP
if _, ok := m.ipMap[locIPStr]; ok {
return ErrInvalidNAT1To1IPMapping
}
m.ipMap[locIPStr] = extIP
+ m.valid = true
return nil
}
func (m *ipMapping) findExternalIP(locIP net.IP) (net.IP, error) {
+ if !m.valid {
+ return locIP, nil
+ }
+
if m.ipSole != nil {
return m.ipSole, nil
}
@@ -67,10 +77,10 @@ type externalIPMapper struct {
func newExternalIPMapper(candidateType CandidateType, ips []string) (*externalIPMapper, error) { //nolint:gocognit
if len(ips) == 0 {
- return nil, nil
+ return nil, nil //nolint:nilnil
}
if candidateType == CandidateTypeUnspecified {
- candidateType = CandidateTypeHost // defaults to host
+ candidateType = CandidateTypeHost // Defaults to host
} else if candidateType != CandidateTypeHost && candidateType != CandidateTypeServerReflexive {
return nil, ErrUnsupportedNAT1To1IPCandidateType
}
diff --git a/vendor/github.com/pion/ice/v2/gather.go b/vendor/github.com/pion/ice/v2/gather.go
index e248c08de..15e2da146 100644
--- a/vendor/github.com/pion/ice/v2/gather.go
+++ b/vendor/github.com/pion/ice/v2/gather.go
@@ -1,17 +1,23 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
"context"
"crypto/tls"
- "errors"
"fmt"
+ "io"
"net"
"reflect"
"sync"
"time"
"github.com/pion/dtls/v2"
+ "github.com/pion/ice/v2/internal/fakenet"
+ stunx "github.com/pion/ice/v2/internal/stun"
"github.com/pion/logging"
+ "github.com/pion/stun"
"github.com/pion/turn/v2"
)
@@ -19,42 +25,19 @@ const (
stunGatherTimeout = time.Second * 5
)
-type closeable interface {
- Close() error
-}
-
// Close a net.Conn and log if we have a failure
-func closeConnAndLog(c closeable, log logging.LeveledLogger, msg string) {
+func closeConnAndLog(c io.Closer, log logging.LeveledLogger, msg string, args ...interface{}) {
if c == nil || (reflect.ValueOf(c).Kind() == reflect.Ptr && reflect.ValueOf(c).IsNil()) {
- log.Warnf("Conn is not allocated (%s)", msg)
+ log.Warnf("Connection is not allocated: "+msg, args...)
return
}
log.Warnf(msg)
if err := c.Close(); err != nil {
- log.Warnf("Failed to close conn: %v", err)
+ log.Warnf("Failed to close connection: %v", err)
}
}
-// fakePacketConn wraps a net.Conn and emulates net.PacketConn
-type fakePacketConn struct {
- nextConn net.Conn
-}
-
-func (f *fakePacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error) {
- n, err = f.nextConn.Read(p)
- addr = f.nextConn.RemoteAddr()
- return
-}
-func (f *fakePacketConn) Close() error { return f.nextConn.Close() }
-func (f *fakePacketConn) LocalAddr() net.Addr { return f.nextConn.LocalAddr() }
-func (f *fakePacketConn) SetDeadline(t time.Time) error { return f.nextConn.SetDeadline(t) }
-func (f *fakePacketConn) SetReadDeadline(t time.Time) error { return f.nextConn.SetReadDeadline(t) }
-func (f *fakePacketConn) SetWriteDeadline(t time.Time) error { return f.nextConn.SetWriteDeadline(t) }
-func (f *fakePacketConn) WriteTo(p []byte, addr net.Addr) (n int, err error) {
- return f.nextConn.Write(p)
-}
-
// GatherCandidates initiates the trickle based gathering process.
func (a *Agent) GatherCandidates() error {
var gatherErr error
@@ -71,17 +54,20 @@ func (a *Agent) GatherCandidates() error {
a.gatherCandidateCancel() // Cancel previous gathering routine
ctx, cancel := context.WithCancel(ctx)
a.gatherCandidateCancel = cancel
+ done := make(chan struct{})
+ a.gatherCandidateDone = done
- go a.gatherCandidates(ctx)
+ go a.gatherCandidates(ctx, done)
}); runErr != nil {
return runErr
}
return gatherErr
}
-func (a *Agent) gatherCandidates(ctx context.Context) {
- if err := a.setGatheringState(GatheringStateGathering); err != nil {
- a.log.Warnf("failed to set gatheringState to GatheringStateGathering: %v", err)
+func (a *Agent) gatherCandidates(ctx context.Context, done chan struct{}) {
+ defer close(done)
+ if err := a.setGatheringState(GatheringStateGathering); err != nil { //nolint:contextcheck
+ a.log.Warnf("Failed to set gatheringState to GatheringStateGathering: %v", err)
return
}
@@ -97,7 +83,11 @@ func (a *Agent) gatherCandidates(ctx context.Context) {
case CandidateTypeServerReflexive:
wg.Add(1)
go func() {
- a.gatherCandidatesSrflx(ctx, a.urls, a.networkTypes)
+ if a.udpMuxSrflx != nil {
+ a.gatherCandidatesSrflxUDPMux(ctx, a.urls, a.networkTypes)
+ } else {
+ a.gatherCandidatesSrflx(ctx, a.urls, a.networkTypes)
+ }
wg.Done()
}()
if a.extIPMapper != nil && a.extIPMapper.candidateType == CandidateTypeServerReflexive {
@@ -116,11 +106,12 @@ func (a *Agent) gatherCandidates(ctx context.Context) {
case CandidateTypePeerReflexive, CandidateTypeUnspecified:
}
}
+
// Block until all STUN and TURN URLs have been gathered (or timed out)
wg.Wait()
- if err := a.setGatheringState(GatheringStateComplete); err != nil {
- a.log.Warnf("failed to set gatheringState to GatheringStateComplete: %v", err)
+ if err := a.setGatheringState(GatheringStateComplete); err != nil { //nolint:contextcheck
+ a.log.Warnf("Failed to set gatheringState to GatheringStateComplete: %v", err)
}
}
@@ -134,27 +125,27 @@ func (a *Agent) gatherCandidatesLocal(ctx context.Context, networkTypes []Networ
}
}
- // when UDPMux is enabled, skip other UDP candidates
+ // When UDPMux is enabled, skip other UDP candidates
if a.udpMux != nil {
if err := a.gatherCandidatesLocalUDPMux(ctx); err != nil {
- a.log.Warnf("could not create host candidate for UDPMux")
+ a.log.Warnf("Failed to create host candidate for UDPMux: %s", err)
}
delete(networks, udp)
}
- localIPs, err := localInterfaces(a.net, a.interfaceFilter, networkTypes)
+ localIPs, err := localInterfaces(a.net, a.interfaceFilter, a.ipFilter, networkTypes, a.includeLoopback)
if err != nil {
- a.log.Warnf("failed to iterate local interfaces, host candidates will not be gathered %s", err)
+ a.log.Warnf("Failed to iterate local interfaces, host candidates will not be gathered %s", err)
return
}
for _, ip := range localIPs {
mappedIP := ip
if a.mDNSMode != MulticastDNSModeQueryAndGather && a.extIPMapper != nil && a.extIPMapper.candidateType == CandidateTypeHost {
- if _mappedIP, err := a.extIPMapper.findExternalIP(ip.String()); err == nil {
+ if _mappedIP, innerErr := a.extIPMapper.findExternalIP(ip.String()); innerErr == nil {
mappedIP = _mappedIP
} else {
- a.log.Warnf("1:1 NAT mapping is enabled but no external IP is found for %s\n", ip.String())
+ a.log.Warnf("1:1 NAT mapping is enabled but no external IP is found for %s", ip.String())
}
}
@@ -164,115 +155,163 @@ func (a *Agent) gatherCandidatesLocal(ctx context.Context, networkTypes []Networ
}
for network := range networks {
- var port int
- var conn net.PacketConn
- var err error
- var tcpType TCPType
+ type connAndPort struct {
+ conn net.PacketConn
+ port int
+ }
+ var (
+ conns []connAndPort
+ tcpType TCPType
+ )
switch network {
case tcp:
- // Handle ICE TCP passive mode
- a.log.Debugf("GetConn by ufrag: %s\n", a.localUfrag)
- conn, err = a.tcpMux.GetConnByUfrag(a.localUfrag)
- if err != nil {
- if !errors.Is(err, ErrTCPMuxNotInitialized) {
- a.log.Warnf("error getting tcp conn by ufrag: %s %s %s\n", network, ip, a.localUfrag)
- }
+ if a.tcpMux == nil {
+ continue
+ }
+
+ // Handle ICE TCP passive mode
+ var muxConns []net.PacketConn
+ if multi, ok := a.tcpMux.(AllConnsGetter); ok {
+ a.log.Debugf("GetAllConns by ufrag: %s", a.localUfrag)
+ muxConns, err = multi.GetAllConns(a.localUfrag, mappedIP.To4() == nil, ip)
+ if err != nil {
+ a.log.Warnf("Failed to get all TCP connections by ufrag: %s %s %s", network, ip, a.localUfrag)
+ continue
+ }
+ } else {
+ a.log.Debugf("GetConn by ufrag: %s", a.localUfrag)
+ conn, err := a.tcpMux.GetConnByUfrag(a.localUfrag, mappedIP.To4() == nil, ip)
+ if err != nil {
+ a.log.Warnf("Failed to get TCP connections by ufrag: %s %s %s", network, ip, a.localUfrag)
+ continue
+ }
+ muxConns = []net.PacketConn{conn}
+ }
+
+ // Extract the port for each PacketConn we got.
+ for _, conn := range muxConns {
+ if tcpConn, ok := conn.LocalAddr().(*net.TCPAddr); ok {
+ conns = append(conns, connAndPort{conn, tcpConn.Port})
+ } else {
+ a.log.Warnf("Failed to get port of connection from TCPMux: %s %s %s", network, ip, a.localUfrag)
+ }
+ }
+ if len(conns) == 0 {
+ // Didn't succeed with any, try the next network.
continue
}
- port = conn.LocalAddr().(*net.TCPAddr).Port
tcpType = TCPTypePassive
- // is there a way to verify that the listen address is even
+ // Is there a way to verify that the listen address is even
// accessible from the current interface.
case udp:
- conn, err = listenUDPInPortRange(a.net, a.log, int(a.portmax), int(a.portmin), network, &net.UDPAddr{IP: ip, Port: 0})
+ conn, err := listenUDPInPortRange(a.net, a.log, int(a.portMax), int(a.portMin), network, &net.UDPAddr{IP: ip, Port: 0})
if err != nil {
- a.log.Warnf("could not listen %s %s\n", network, ip)
+ a.log.Warnf("Failed to listen %s %s", network, ip)
continue
}
- port = conn.LocalAddr().(*net.UDPAddr).Port
- }
- hostConfig := CandidateHostConfig{
- Network: network,
- Address: address,
- Port: port,
- Component: ComponentRTP,
- TCPType: tcpType,
- }
-
- c, err := NewCandidateHost(&hostConfig)
- if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to create host candidate: %s %s %d: %v\n", network, mappedIP, port, err))
- continue
- }
-
- if a.mDNSMode == MulticastDNSModeQueryAndGather {
- if err = c.setIP(ip); err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to create host candidate: %s %s %d: %v\n", network, mappedIP, port, err))
+ if udpConn, ok := conn.LocalAddr().(*net.UDPAddr); ok {
+ conns = append(conns, connAndPort{conn, udpConn.Port})
+ } else {
+ a.log.Warnf("Failed to get port of UDPAddr from ListenUDPInPortRange: %s %s %s", network, ip, a.localUfrag)
continue
}
}
- if err := a.addCandidate(ctx, c, conn); err != nil {
- if closeErr := c.close(); closeErr != nil {
- a.log.Warnf("Failed to close candidate: %v", closeErr)
+ for _, connAndPort := range conns {
+ hostConfig := CandidateHostConfig{
+ Network: network,
+ Address: address,
+ Port: connAndPort.port,
+ Component: ComponentRTP,
+ TCPType: tcpType,
+ }
+
+ c, err := NewCandidateHost(&hostConfig)
+ if err != nil {
+ closeConnAndLog(connAndPort.conn, a.log, "failed to create host candidate: %s %s %d: %v", network, mappedIP, connAndPort.port, err)
+ continue
+ }
+
+ if a.mDNSMode == MulticastDNSModeQueryAndGather {
+ if err = c.setIP(ip); err != nil {
+ closeConnAndLog(connAndPort.conn, a.log, "failed to create host candidate: %s %s %d: %v", network, mappedIP, connAndPort.port, err)
+ continue
+ }
+ }
+
+ if err := a.addCandidate(ctx, c, connAndPort.conn); err != nil {
+ if closeErr := c.close(); closeErr != nil {
+ a.log.Warnf("Failed to close candidate: %v", closeErr)
+ }
+ a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v", err)
}
- a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v\n", err)
}
}
}
}
-func (a *Agent) gatherCandidatesLocalUDPMux(ctx context.Context) error {
+func (a *Agent) gatherCandidatesLocalUDPMux(ctx context.Context) error { //nolint:gocognit
if a.udpMux == nil {
return errUDPMuxDisabled
}
- localIPs, err := localInterfaces(a.net, a.interfaceFilter, []NetworkType{NetworkTypeUDP4})
- switch {
- case err != nil:
- return err
- case len(localIPs) == 0:
- return errCandidateIPNotFound
- }
+ localAddresses := a.udpMux.GetListenAddresses()
+ existingConfigs := make(map[CandidateHostConfig]struct{})
- for _, candidateIP := range localIPs {
+ for _, addr := range localAddresses {
+ udpAddr, ok := addr.(*net.UDPAddr)
+ if !ok {
+ return errInvalidAddress
+ }
+ candidateIP := udpAddr.IP
if a.extIPMapper != nil && a.extIPMapper.candidateType == CandidateTypeHost {
- if mappedIP, err := a.extIPMapper.findExternalIP(candidateIP.String()); err != nil {
+ mappedIP, err := a.extIPMapper.findExternalIP(candidateIP.String())
+ if err != nil {
a.log.Warnf("1:1 NAT mapping is enabled but no external IP is found for %s", candidateIP.String())
continue
- } else {
- candidateIP = mappedIP
}
- }
- conn, err := a.udpMux.GetConn(a.localUfrag)
- if err != nil {
- return err
+ candidateIP = mappedIP
}
- port := conn.LocalAddr().(*net.UDPAddr).Port
hostConfig := CandidateHostConfig{
Network: udp,
Address: candidateIP.String(),
- Port: port,
+ Port: udpAddr.Port,
Component: ComponentRTP,
}
+ // Detect a duplicate candidate before calling addCandidate().
+ // otherwise, addCandidate() detects the duplicate candidate
+ // and close its connection, invalidating all candidates
+ // that share the same connection.
+ if _, ok := existingConfigs[hostConfig]; ok {
+ continue
+ }
+
+ conn, err := a.udpMux.GetConn(a.localUfrag, udpAddr)
+ if err != nil {
+ return err
+ }
+
c, err := NewCandidateHost(&hostConfig)
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to create host mux candidate: %s %d: %v\n", candidateIP, port, err))
- // already logged error
- return nil
+ closeConnAndLog(conn, a.log, "failed to create host mux candidate: %s %d: %v", candidateIP, udpAddr.Port, err)
+ continue
}
if err := a.addCandidate(ctx, c, conn); err != nil {
if closeErr := c.close(); closeErr != nil {
a.log.Warnf("Failed to close candidate: %v", closeErr)
}
- return err
+
+ closeConnAndLog(conn, a.log, "failed to add candidate: %s %d: %v", candidateIP, udpAddr.Port, err)
+ continue
}
+
+ existingConfigs[hostConfig] = struct{}{}
}
return nil
@@ -292,34 +331,39 @@ func (a *Agent) gatherCandidatesSrflxMapped(ctx context.Context, networkTypes []
go func() {
defer wg.Done()
- conn, err := listenUDPInPortRange(a.net, a.log, int(a.portmax), int(a.portmin), network, &net.UDPAddr{IP: nil, Port: 0})
+ conn, err := listenUDPInPortRange(a.net, a.log, int(a.portMax), int(a.portMin), network, &net.UDPAddr{IP: nil, Port: 0})
if err != nil {
- a.log.Warnf("Failed to listen %s: %v\n", network, err)
+ a.log.Warnf("Failed to listen %s: %v", network, err)
return
}
- laddr := conn.LocalAddr().(*net.UDPAddr)
- mappedIP, err := a.extIPMapper.findExternalIP(laddr.IP.String())
+ lAddr, ok := conn.LocalAddr().(*net.UDPAddr)
+ if !ok {
+ closeConnAndLog(conn, a.log, "1:1 NAT mapping is enabled but LocalAddr is not a UDPAddr")
+ return
+ }
+
+ mappedIP, err := a.extIPMapper.findExternalIP(lAddr.IP.String())
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("1:1 NAT mapping is enabled but no external IP is found for %s\n", laddr.IP.String()))
+ closeConnAndLog(conn, a.log, "1:1 NAT mapping is enabled but no external IP is found for %s", lAddr.IP.String())
return
}
srflxConfig := CandidateServerReflexiveConfig{
Network: network,
Address: mappedIP.String(),
- Port: laddr.Port,
+ Port: lAddr.Port,
Component: ComponentRTP,
- RelAddr: laddr.IP.String(),
- RelPort: laddr.Port,
+ RelAddr: lAddr.IP.String(),
+ RelPort: lAddr.Port,
}
c, err := NewCandidateServerReflexive(&srflxConfig)
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to create server reflexive candidate: %s %s %d: %v\n",
+ closeConnAndLog(conn, a.log, "failed to create server reflexive candidate: %s %s %d: %v",
network,
mappedIP.String(),
- laddr.Port,
- err))
+ lAddr.Port,
+ err)
return
}
@@ -327,13 +371,81 @@ func (a *Agent) gatherCandidatesSrflxMapped(ctx context.Context, networkTypes []
if closeErr := c.close(); closeErr != nil {
a.log.Warnf("Failed to close candidate: %v", closeErr)
}
- a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v\n", err)
+ a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v", err)
}
}()
}
}
-func (a *Agent) gatherCandidatesSrflx(ctx context.Context, urls []*URL, networkTypes []NetworkType) {
+func (a *Agent) gatherCandidatesSrflxUDPMux(ctx context.Context, urls []*stun.URI, networkTypes []NetworkType) { //nolint:gocognit
+ var wg sync.WaitGroup
+ defer wg.Wait()
+
+ for _, networkType := range networkTypes {
+ if networkType.IsTCP() {
+ continue
+ }
+
+ for i := range urls {
+ for _, listenAddr := range a.udpMuxSrflx.GetListenAddresses() {
+ udpAddr, ok := listenAddr.(*net.UDPAddr)
+ if !ok {
+ a.log.Warn("Failed to cast udpMuxSrflx listen address to UDPAddr")
+ continue
+ }
+ wg.Add(1)
+ go func(url stun.URI, network string, localAddr *net.UDPAddr) {
+ defer wg.Done()
+
+ hostPort := fmt.Sprintf("%s:%d", url.Host, url.Port)
+ serverAddr, err := a.net.ResolveUDPAddr(network, hostPort)
+ if err != nil {
+ a.log.Warnf("Failed to resolve STUN host: %s: %v", hostPort, err)
+ return
+ }
+
+ xorAddr, err := a.udpMuxSrflx.GetXORMappedAddr(serverAddr, stunGatherTimeout)
+ if err != nil {
+ a.log.Warnf("Failed get server reflexive address %s %s: %v", network, url, err)
+ return
+ }
+
+ conn, err := a.udpMuxSrflx.GetConnForURL(a.localUfrag, url.String(), localAddr)
+ if err != nil {
+ a.log.Warnf("Failed to find connection in UDPMuxSrflx %s %s: %v", network, url, err)
+ return
+ }
+
+ ip := xorAddr.IP
+ port := xorAddr.Port
+
+ srflxConfig := CandidateServerReflexiveConfig{
+ Network: network,
+ Address: ip.String(),
+ Port: port,
+ Component: ComponentRTP,
+ RelAddr: localAddr.IP.String(),
+ RelPort: localAddr.Port,
+ }
+ c, err := NewCandidateServerReflexive(&srflxConfig)
+ if err != nil {
+ closeConnAndLog(conn, a.log, "failed to create server reflexive candidate: %s %s %d: %v", network, ip, port, err)
+ return
+ }
+
+ if err := a.addCandidate(ctx, c, conn); err != nil {
+ if closeErr := c.close(); closeErr != nil {
+ a.log.Warnf("Failed to close candidate: %v", closeErr)
+ }
+ a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v", err)
+ }
+ }(*urls[i], networkType.String(), udpAddr)
+ }
+ }
+ }
+}
+
+func (a *Agent) gatherCandidatesSrflx(ctx context.Context, urls []*stun.URI, networkTypes []NetworkType) { //nolint:gocognit
var wg sync.WaitGroup
defer wg.Wait()
@@ -344,43 +456,55 @@ func (a *Agent) gatherCandidatesSrflx(ctx context.Context, urls []*URL, networkT
for i := range urls {
wg.Add(1)
- go func(url URL, network string) {
+ go func(url stun.URI, network string) {
defer wg.Done()
hostPort := fmt.Sprintf("%s:%d", url.Host, url.Port)
serverAddr, err := a.net.ResolveUDPAddr(network, hostPort)
if err != nil {
- a.log.Warnf("failed to resolve stun host: %s: %v", hostPort, err)
+ a.log.Warnf("Failed to resolve STUN host: %s: %v", hostPort, err)
return
}
- conn, err := listenUDPInPortRange(a.net, a.log, int(a.portmax), int(a.portmin), network, &net.UDPAddr{IP: nil, Port: 0})
+ conn, err := listenUDPInPortRange(a.net, a.log, int(a.portMax), int(a.portMin), network, &net.UDPAddr{IP: nil, Port: 0})
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to listen for %s: %v\n", serverAddr.String(), err))
+ closeConnAndLog(conn, a.log, "failed to listen for %s: %v", serverAddr.String(), err)
return
}
+ // If the agent closes midway through the connection
+ // we end it early to prevent close delay.
+ cancelCtx, cancelFunc := context.WithCancel(ctx)
+ defer cancelFunc()
+ go func() {
+ select {
+ case <-cancelCtx.Done():
+ return
+ case <-a.done:
+ _ = conn.Close()
+ }
+ }()
- xoraddr, err := getXORMappedAddr(conn, serverAddr, stunGatherTimeout)
+ xorAddr, err := stunx.GetXORMappedAddr(conn, serverAddr, stunGatherTimeout)
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("could not get server reflexive address %s %s: %v\n", network, url, err))
+ closeConnAndLog(conn, a.log, "failed to get server reflexive address %s %s: %v", network, url, err)
return
}
- ip := xoraddr.IP
- port := xoraddr.Port
+ ip := xorAddr.IP
+ port := xorAddr.Port
- laddr := conn.LocalAddr().(*net.UDPAddr)
+ lAddr := conn.LocalAddr().(*net.UDPAddr) //nolint:forcetypeassert
srflxConfig := CandidateServerReflexiveConfig{
Network: network,
Address: ip.String(),
Port: port,
Component: ComponentRTP,
- RelAddr: laddr.IP.String(),
- RelPort: laddr.Port,
+ RelAddr: lAddr.IP.String(),
+ RelPort: lAddr.Port,
}
c, err := NewCandidateServerReflexive(&srflxConfig)
if err != nil {
- closeConnAndLog(conn, a.log, fmt.Sprintf("Failed to create server reflexive candidate: %s %s %d: %v\n", network, ip, port, err))
+ closeConnAndLog(conn, a.log, "failed to create server reflexive candidate: %s %s %d: %v", network, ip, port, err)
return
}
@@ -388,21 +512,21 @@ func (a *Agent) gatherCandidatesSrflx(ctx context.Context, urls []*URL, networkT
if closeErr := c.close(); closeErr != nil {
a.log.Warnf("Failed to close candidate: %v", closeErr)
}
- a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v\n", err)
+ a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v", err)
}
}(*urls[i], networkType.String())
}
}
}
-func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*URL) { //nolint:gocognit
+func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*stun.URI) { //nolint:gocognit
var wg sync.WaitGroup
defer wg.Wait()
network := NetworkTypeUDP4.String()
for i := range urls {
switch {
- case urls[i].Scheme != SchemeTypeTURN && urls[i].Scheme != SchemeTypeTURNS:
+ case urls[i].Scheme != stun.SchemeTypeTURN && urls[i].Scheme != stun.SchemeTypeTURNS:
continue
case urls[i].Username == "":
a.log.Errorf("Failed to gather relay candidates: %v", ErrUsernameEmpty)
@@ -413,100 +537,124 @@ func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*URL) { //noli
}
wg.Add(1)
- go func(url URL) {
+ go func(url stun.URI) {
defer wg.Done()
- TURNServerAddr := fmt.Sprintf("%s:%d", url.Host, url.Port)
+ turnServerAddr := fmt.Sprintf("%s:%d", url.Host, url.Port)
var (
locConn net.PacketConn
err error
- RelAddr string
- RelPort int
+ relAddr string
+ relPort int
relayProtocol string
)
switch {
- case url.Proto == ProtoTypeUDP && url.Scheme == SchemeTypeTURN:
+ case url.Proto == stun.ProtoTypeUDP && url.Scheme == stun.SchemeTypeTURN:
if locConn, err = a.net.ListenPacket(network, "0.0.0.0:0"); err != nil {
- a.log.Warnf("Failed to listen %s: %v\n", network, err)
+ a.log.Warnf("Failed to listen %s: %v", network, err)
return
}
- RelAddr = locConn.LocalAddr().(*net.UDPAddr).IP.String()
- RelPort = locConn.LocalAddr().(*net.UDPAddr).Port
+ relAddr = locConn.LocalAddr().(*net.UDPAddr).IP.String() //nolint:forcetypeassert
+ relPort = locConn.LocalAddr().(*net.UDPAddr).Port //nolint:forcetypeassert
relayProtocol = udp
- case a.proxyDialer != nil && url.Proto == ProtoTypeTCP &&
- (url.Scheme == SchemeTypeTURN || url.Scheme == SchemeTypeTURNS):
- conn, connectErr := a.proxyDialer.Dial(NetworkTypeTCP4.String(), TURNServerAddr)
+ case a.proxyDialer != nil && url.Proto == stun.ProtoTypeTCP &&
+ (url.Scheme == stun.SchemeTypeTURN || url.Scheme == stun.SchemeTypeTURNS):
+ conn, connectErr := a.proxyDialer.Dial(NetworkTypeTCP4.String(), turnServerAddr)
if connectErr != nil {
- a.log.Warnf("Failed to Dial TCP Addr %s via proxy dialer: %v\n", TURNServerAddr, connectErr)
+ a.log.Warnf("Failed to dial TCP address %s via proxy dialer: %v", turnServerAddr, connectErr)
return
}
- RelAddr = conn.LocalAddr().(*net.TCPAddr).IP.String()
- RelPort = conn.LocalAddr().(*net.TCPAddr).Port
- if url.Scheme == SchemeTypeTURN {
+ relAddr = conn.LocalAddr().(*net.TCPAddr).IP.String() //nolint:forcetypeassert
+ relPort = conn.LocalAddr().(*net.TCPAddr).Port //nolint:forcetypeassert
+ if url.Scheme == stun.SchemeTypeTURN {
relayProtocol = tcp
- } else if url.Scheme == SchemeTypeTURNS {
+ } else if url.Scheme == stun.SchemeTypeTURNS {
relayProtocol = "tls"
}
locConn = turn.NewSTUNConn(conn)
- case url.Proto == ProtoTypeTCP && url.Scheme == SchemeTypeTURN:
- tcpAddr, connectErr := net.ResolveTCPAddr(NetworkTypeTCP4.String(), TURNServerAddr)
+ case url.Proto == stun.ProtoTypeTCP && url.Scheme == stun.SchemeTypeTURN:
+ tcpAddr, connectErr := a.net.ResolveTCPAddr(NetworkTypeTCP4.String(), turnServerAddr)
if connectErr != nil {
- a.log.Warnf("Failed to resolve TCP Addr %s: %v\n", TURNServerAddr, connectErr)
+ a.log.Warnf("Failed to resolve TCP address %s: %v", turnServerAddr, connectErr)
return
}
- conn, connectErr := net.DialTCP(NetworkTypeTCP4.String(), nil, tcpAddr)
+ conn, connectErr := a.net.DialTCP(NetworkTypeTCP4.String(), nil, tcpAddr)
if connectErr != nil {
- a.log.Warnf("Failed to Dial TCP Addr %s: %v\n", TURNServerAddr, connectErr)
+ a.log.Warnf("Failed to dial TCP address %s: %v", turnServerAddr, connectErr)
return
}
- RelAddr = conn.LocalAddr().(*net.TCPAddr).IP.String()
- RelPort = conn.LocalAddr().(*net.TCPAddr).Port
+ relAddr = conn.LocalAddr().(*net.TCPAddr).IP.String() //nolint:forcetypeassert
+ relPort = conn.LocalAddr().(*net.TCPAddr).Port //nolint:forcetypeassert
relayProtocol = tcp
locConn = turn.NewSTUNConn(conn)
- case url.Proto == ProtoTypeUDP && url.Scheme == SchemeTypeTURNS:
- udpAddr, connectErr := net.ResolveUDPAddr(network, TURNServerAddr)
+ case url.Proto == stun.ProtoTypeUDP && url.Scheme == stun.SchemeTypeTURNS:
+ udpAddr, connectErr := a.net.ResolveUDPAddr(network, turnServerAddr)
if connectErr != nil {
- a.log.Warnf("Failed to resolve UDP Addr %s: %v\n", TURNServerAddr, connectErr)
+ a.log.Warnf("Failed to resolve UDP address %s: %v", turnServerAddr, connectErr)
return
}
- conn, connectErr := dtls.Dial(network, udpAddr, &dtls.Config{
+ udpConn, dialErr := a.net.DialUDP("udp", nil, udpAddr)
+ if dialErr != nil {
+ a.log.Warnf("Failed to dial DTLS address %s: %v", turnServerAddr, dialErr)
+ return
+ }
+
+ conn, connectErr := dtls.ClientWithContext(ctx, udpConn, &dtls.Config{
ServerName: url.Host,
InsecureSkipVerify: a.insecureSkipVerify, //nolint:gosec
})
if connectErr != nil {
- a.log.Warnf("Failed to Dial DTLS Addr %s: %v\n", TURNServerAddr, connectErr)
+ a.log.Warnf("Failed to create DTLS client: %v", turnServerAddr, connectErr)
return
}
- RelAddr = conn.LocalAddr().(*net.UDPAddr).IP.String()
- RelPort = conn.LocalAddr().(*net.UDPAddr).Port
+ relAddr = conn.LocalAddr().(*net.UDPAddr).IP.String() //nolint:forcetypeassert
+ relPort = conn.LocalAddr().(*net.UDPAddr).Port //nolint:forcetypeassert
relayProtocol = "dtls"
- locConn = &fakePacketConn{conn}
- case url.Proto == ProtoTypeTCP && url.Scheme == SchemeTypeTURNS:
- conn, connectErr := tls.Dial(NetworkTypeTCP4.String(), TURNServerAddr, &tls.Config{
- InsecureSkipVerify: a.insecureSkipVerify, //nolint:gosec
- })
- if connectErr != nil {
- a.log.Warnf("Failed to Dial TLS Addr %s: %v\n", TURNServerAddr, connectErr)
+ locConn = &fakenet.PacketConn{Conn: conn}
+ case url.Proto == stun.ProtoTypeTCP && url.Scheme == stun.SchemeTypeTURNS:
+ tcpAddr, resolvErr := a.net.ResolveTCPAddr(NetworkTypeTCP4.String(), turnServerAddr)
+ if resolvErr != nil {
+ a.log.Warnf("Failed to resolve relay address %s: %v", turnServerAddr, resolvErr)
return
}
- RelAddr = conn.LocalAddr().(*net.TCPAddr).IP.String()
- RelPort = conn.LocalAddr().(*net.TCPAddr).Port
+
+ tcpConn, dialErr := a.net.DialTCP(NetworkTypeTCP4.String(), nil, tcpAddr)
+ if dialErr != nil {
+ a.log.Warnf("Failed to connect to relay: %v", dialErr)
+ return
+ }
+
+ conn := tls.Client(tcpConn, &tls.Config{
+ ServerName: url.Host,
+ InsecureSkipVerify: a.insecureSkipVerify, //nolint:gosec
+ })
+
+ if hsErr := conn.HandshakeContext(ctx); hsErr != nil {
+ if closeErr := tcpConn.Close(); closeErr != nil {
+ a.log.Errorf("Failed to close relay connection: %v", closeErr)
+ }
+ a.log.Warnf("Failed to connect to relay: %v", hsErr)
+ return
+ }
+
+ relAddr = conn.LocalAddr().(*net.TCPAddr).IP.String() //nolint:forcetypeassert
+ relPort = conn.LocalAddr().(*net.TCPAddr).Port //nolint:forcetypeassert
relayProtocol = "tls"
locConn = turn.NewSTUNConn(conn)
default:
- a.log.Warnf("Unable to handle URL in gatherCandidatesRelay %v\n", url)
+ a.log.Warnf("Unable to handle URL in gatherCandidatesRelay %v", url)
return
}
client, err := turn.NewClient(&turn.ClientConfig{
- TURNServerAddr: TURNServerAddr,
+ TURNServerAddr: turnServerAddr,
Conn: locConn,
Username: url.Username,
Password: url.Password,
@@ -514,31 +662,31 @@ func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*URL) { //noli
Net: a.net,
})
if err != nil {
- closeConnAndLog(locConn, a.log, fmt.Sprintf("Failed to build new turn.Client %s %s\n", TURNServerAddr, err))
+ closeConnAndLog(locConn, a.log, "failed to create new TURN client %s %s", turnServerAddr, err)
return
}
if err = client.Listen(); err != nil {
client.Close()
- closeConnAndLog(locConn, a.log, fmt.Sprintf("Failed to listen on turn.Client %s %s\n", TURNServerAddr, err))
+ closeConnAndLog(locConn, a.log, "failed to listen on TURN client %s %s", turnServerAddr, err)
return
}
relayConn, err := client.Allocate()
if err != nil {
client.Close()
- closeConnAndLog(locConn, a.log, fmt.Sprintf("Failed to allocate on turn.Client %s %s\n", TURNServerAddr, err))
+ closeConnAndLog(locConn, a.log, "failed to allocate on TURN client %s %s", turnServerAddr, err)
return
}
- raddr := relayConn.LocalAddr().(*net.UDPAddr)
+ rAddr := relayConn.LocalAddr().(*net.UDPAddr) //nolint:forcetypeassert
relayConfig := CandidateRelayConfig{
Network: network,
Component: ComponentRTP,
- Address: raddr.IP.String(),
- Port: raddr.Port,
- RelAddr: RelAddr,
- RelPort: RelPort,
+ Address: rAddr.IP.String(),
+ Port: rAddr.Port,
+ RelAddr: relAddr,
+ RelPort: relPort,
RelayProtocol: relayProtocol,
OnClose: func() error {
client.Close()
@@ -555,7 +703,7 @@ func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*URL) { //noli
relayConnClose()
client.Close()
- closeConnAndLog(locConn, a.log, fmt.Sprintf("Failed to create relay candidate: %s %s: %v\n", network, raddr.String(), err))
+ closeConnAndLog(locConn, a.log, "failed to create relay candidate: %s %s: %v", network, rAddr.String(), err)
return
}
@@ -565,7 +713,7 @@ func (a *Agent) gatherCandidatesRelay(ctx context.Context, urls []*URL) { //noli
if closeErr := candidate.close(); closeErr != nil {
a.log.Warnf("Failed to close candidate: %v", closeErr)
}
- a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v\n", err)
+ a.log.Warnf("Failed to append to localCandidates and run onCandidateHdlr: %v", err)
}
}(*urls[i])
}
diff --git a/vendor/github.com/pion/ice/v2/ice.go b/vendor/github.com/pion/ice/v2/ice.go
index d7094f6db..bd551206e 100644
--- a/vendor/github.com/pion/ice/v2/ice.go
+++ b/vendor/github.com/pion/ice/v2/ice.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
// ConnectionState is an enum showing the state of a ICE Connection
@@ -5,8 +8,11 @@ type ConnectionState int
// List of supported States
const (
+ // ConnectionStateUnknown represents an unknown state
+ ConnectionStateUnknown ConnectionState = iota
+
// ConnectionStateNew ICE agent is gathering addresses
- ConnectionStateNew = iota + 1
+ ConnectionStateNew
// ConnectionStateChecking ICE agent has been given local and remote candidates, and is attempting to find a match
ConnectionStateChecking
@@ -52,13 +58,16 @@ func (c ConnectionState) String() string {
type GatheringState int
const (
- // GatheringStateNew indicates candidate gatering is not yet started
- GatheringStateNew GatheringState = iota + 1
+ // GatheringStateUnknown represents an unknown state
+ GatheringStateUnknown GatheringState = iota
- // GatheringStateGathering indicates candidate gatering is ongoing
+ // GatheringStateNew indicates candidate gathering is not yet started
+ GatheringStateNew
+
+ // GatheringStateGathering indicates candidate gathering is ongoing
GatheringStateGathering
- // GatheringStateComplete indicates candidate gatering has been completed
+ // GatheringStateComplete indicates candidate gathering has been completed
GatheringStateComplete
)
diff --git a/vendor/github.com/pion/ice/v2/icecontrol.go b/vendor/github.com/pion/ice/v2/icecontrol.go
index ede2e09cb..b086bd892 100644
--- a/vendor/github.com/pion/ice/v2/icecontrol.go
+++ b/vendor/github.com/pion/ice/v2/icecontrol.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
diff --git a/vendor/github.com/pion/ice/v2/internal/atomic/atomic.go b/vendor/github.com/pion/ice/v2/internal/atomic/atomic.go
new file mode 100644
index 000000000..f8caf5a2e
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/internal/atomic/atomic.go
@@ -0,0 +1,23 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+// Package atomic contains custom atomic types
+package atomic
+
+import "sync/atomic"
+
+// Error is an atomic error
+type Error struct {
+ v atomic.Value
+}
+
+// Store updates the value of the atomic variable
+func (a *Error) Store(err error) {
+ a.v.Store(struct{ error }{err})
+}
+
+// Load retrieves the current value of the atomic variable
+func (a *Error) Load() error {
+ err, _ := a.v.Load().(struct{ error })
+ return err.error
+}
diff --git a/vendor/github.com/pion/ice/v2/internal/fakenet/mock_conn.go b/vendor/github.com/pion/ice/v2/internal/fakenet/mock_conn.go
new file mode 100644
index 000000000..cc98849d5
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/internal/fakenet/mock_conn.go
@@ -0,0 +1,23 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+//go:build !js
+// +build !js
+
+package fakenet
+
+import (
+ "net"
+ "time"
+)
+
+// MockPacketConn for tests
+type MockPacketConn struct{}
+
+func (m *MockPacketConn) ReadFrom([]byte) (n int, addr net.Addr, err error) { return 0, nil, nil } //nolint:revive
+func (m *MockPacketConn) WriteTo([]byte, net.Addr) (n int, err error) { return 0, nil } //nolint:revive
+func (m *MockPacketConn) Close() error { return nil } //nolint:revive
+func (m *MockPacketConn) LocalAddr() net.Addr { return nil } //nolint:revive
+func (m *MockPacketConn) SetDeadline(time.Time) error { return nil } //nolint:revive
+func (m *MockPacketConn) SetReadDeadline(time.Time) error { return nil } //nolint:revive
+func (m *MockPacketConn) SetWriteDeadline(time.Time) error { return nil } //nolint:revive
diff --git a/vendor/github.com/pion/ice/v2/internal/fakenet/packet_conn.go b/vendor/github.com/pion/ice/v2/internal/fakenet/packet_conn.go
new file mode 100644
index 000000000..0b9faaa84
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/internal/fakenet/packet_conn.go
@@ -0,0 +1,29 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+// Package fakenet contains fake network abstractions
+package fakenet
+
+import (
+ "net"
+)
+
+// Compile-time assertion
+var _ net.PacketConn = (*PacketConn)(nil)
+
+// PacketConn wraps a net.Conn and emulates net.PacketConn
+type PacketConn struct {
+ net.Conn
+}
+
+// ReadFrom reads a packet from the connection,
+func (f *PacketConn) ReadFrom(p []byte) (n int, addr net.Addr, err error) {
+ n, err = f.Conn.Read(p)
+ addr = f.Conn.RemoteAddr()
+ return
+}
+
+// WriteTo writes a packet with payload p to addr.
+func (f *PacketConn) WriteTo(p []byte, _ net.Addr) (int, error) {
+ return f.Conn.Write(p)
+}
diff --git a/vendor/github.com/pion/ice/v2/internal/stun/stun.go b/vendor/github.com/pion/ice/v2/internal/stun/stun.go
new file mode 100644
index 000000000..230cf850a
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/internal/stun/stun.go
@@ -0,0 +1,72 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+// Package stun contains ICE specific STUN code
+package stun
+
+import (
+ "errors"
+ "fmt"
+ "net"
+ "time"
+
+ "github.com/pion/stun"
+)
+
+var (
+ errGetXorMappedAddrResponse = errors.New("failed to get XOR-MAPPED-ADDRESS response")
+ errMismatchUsername = errors.New("username mismatch")
+)
+
+// GetXORMappedAddr initiates a STUN requests to serverAddr using conn, reads the response and returns
+// the XORMappedAddress returned by the STUN server.
+func GetXORMappedAddr(conn net.PacketConn, serverAddr net.Addr, timeout time.Duration) (*stun.XORMappedAddress, error) {
+ if timeout > 0 {
+ if err := conn.SetReadDeadline(time.Now().Add(timeout)); err != nil {
+ return nil, err
+ }
+
+ // Reset timeout after completion
+ defer conn.SetReadDeadline(time.Time{}) //nolint:errcheck
+ }
+
+ req, err := stun.Build(stun.BindingRequest, stun.TransactionID)
+ if err != nil {
+ return nil, err
+ }
+
+ if _, err = conn.WriteTo(req.Raw, serverAddr); err != nil {
+ return nil, err
+ }
+
+ const maxMessageSize = 1280
+ buf := make([]byte, maxMessageSize)
+ n, _, err := conn.ReadFrom(buf)
+ if err != nil {
+ return nil, err
+ }
+
+ res := &stun.Message{Raw: buf[:n]}
+ if err = res.Decode(); err != nil {
+ return nil, err
+ }
+
+ var addr stun.XORMappedAddress
+ if err = addr.GetFrom(res); err != nil {
+ return nil, fmt.Errorf("%w: %v", errGetXorMappedAddrResponse, err) //nolint:errorlint
+ }
+
+ return &addr, nil
+}
+
+// AssertUsername checks that the given STUN message m has a USERNAME attribute with a given value
+func AssertUsername(m *stun.Message, expectedUsername string) error {
+ var username stun.Username
+ if err := username.GetFrom(m); err != nil {
+ return err
+ } else if string(username) != expectedUsername {
+ return fmt.Errorf("%w expected(%x) actual(%x)", errMismatchUsername, expectedUsername, string(username))
+ }
+
+ return nil
+}
diff --git a/vendor/github.com/pion/ice/v2/mdns.go b/vendor/github.com/pion/ice/v2/mdns.go
index 5a431d152..aa8231648 100644
--- a/vendor/github.com/pion/ice/v2/mdns.go
+++ b/vendor/github.com/pion/ice/v2/mdns.go
@@ -1,11 +1,13 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
- "net"
-
"github.com/google/uuid"
"github.com/pion/logging"
"github.com/pion/mdns"
+ "github.com/pion/transport/v2"
"golang.org/x/net/ipv4"
)
@@ -31,17 +33,17 @@ func generateMulticastDNSName() (string, error) {
return u.String() + ".local", err
}
-func createMulticastDNS(mDNSMode MulticastDNSMode, mDNSName string, log logging.LeveledLogger) (*mdns.Conn, MulticastDNSMode, error) {
+func createMulticastDNS(n transport.Net, mDNSMode MulticastDNSMode, mDNSName string, log logging.LeveledLogger) (*mdns.Conn, MulticastDNSMode, error) {
if mDNSMode == MulticastDNSModeDisabled {
return nil, mDNSMode, nil
}
- addr, mdnsErr := net.ResolveUDPAddr("udp4", mdns.DefaultAddress)
+ addr, mdnsErr := n.ResolveUDPAddr("udp4", mdns.DefaultAddress)
if mdnsErr != nil {
return nil, mDNSMode, mdnsErr
}
- l, mdnsErr := net.ListenUDP("udp4", addr)
+ l, mdnsErr := n.ListenUDP("udp4", addr)
if mdnsErr != nil {
// If ICE fails to start MulticastDNS server just warn the user and continue
log.Errorf("Failed to enable mDNS, continuing in mDNS disabled mode: (%s)", mdnsErr)
diff --git a/vendor/github.com/pion/ice/v2/net.go b/vendor/github.com/pion/ice/v2/net.go
new file mode 100644
index 000000000..d716bc19c
--- /dev/null
+++ b/vendor/github.com/pion/ice/v2/net.go
@@ -0,0 +1,137 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
+package ice
+
+import (
+ "net"
+
+ "github.com/pion/logging"
+ "github.com/pion/transport/v2"
+)
+
+// The conditions of invalidation written below are defined in
+// https://tools.ietf.org/html/rfc8445#section-5.1.1.1
+func isSupportedIPv6(ip net.IP) bool {
+ if len(ip) != net.IPv6len ||
+ isZeros(ip[0:12]) || // !(IPv4-compatible IPv6)
+ ip[0] == 0xfe && ip[1]&0xc0 == 0xc0 || // !(IPv6 site-local unicast)
+ ip.IsLinkLocalUnicast() ||
+ ip.IsLinkLocalMulticast() {
+ return false
+ }
+ return true
+}
+
+func isZeros(ip net.IP) bool {
+ for i := 0; i < len(ip); i++ {
+ if ip[i] != 0 {
+ return false
+ }
+ }
+ return true
+}
+
+func localInterfaces(n transport.Net, interfaceFilter func(string) bool, ipFilter func(net.IP) bool, networkTypes []NetworkType, includeLoopback bool) ([]net.IP, error) { //nolint:gocognit
+ ips := []net.IP{}
+ ifaces, err := n.Interfaces()
+ if err != nil {
+ return ips, err
+ }
+
+ var IPv4Requested, IPv6Requested bool
+ for _, typ := range networkTypes {
+ if typ.IsIPv4() {
+ IPv4Requested = true
+ }
+
+ if typ.IsIPv6() {
+ IPv6Requested = true
+ }
+ }
+
+ for _, iface := range ifaces {
+ if iface.Flags&net.FlagUp == 0 {
+ continue // Interface down
+ }
+ if (iface.Flags&net.FlagLoopback != 0) && !includeLoopback {
+ continue // Loopback interface
+ }
+
+ if interfaceFilter != nil && !interfaceFilter(iface.Name) {
+ continue
+ }
+
+ addrs, err := iface.Addrs()
+ if err != nil {
+ continue
+ }
+
+ for _, addr := range addrs {
+ var ip net.IP
+ switch addr := addr.(type) {
+ case *net.IPNet:
+ ip = addr.IP
+ case *net.IPAddr:
+ ip = addr.IP
+ }
+ if ip == nil || (ip.IsLoopback() && !includeLoopback) {
+ continue
+ }
+
+ if ipv4 := ip.To4(); ipv4 == nil {
+ if !IPv6Requested {
+ continue
+ } else if !isSupportedIPv6(ip) {
+ continue
+ }
+ } else if !IPv4Requested {
+ continue
+ }
+
+ if ipFilter != nil && !ipFilter(ip) {
+ continue
+ }
+
+ ips = append(ips, ip)
+ }
+ }
+ return ips, nil
+}
+
+func listenUDPInPortRange(n transport.Net, log logging.LeveledLogger, portMax, portMin int, network string, lAddr *net.UDPAddr) (transport.UDPConn, error) {
+ if (lAddr.Port != 0) || ((portMin == 0) && (portMax == 0)) {
+ return n.ListenUDP(network, lAddr)
+ }
+ var i, j int
+ i = portMin
+ if i == 0 {
+ i = 1
+ }
+ j = portMax
+ if j == 0 {
+ j = 0xFFFF
+ }
+ if i > j {
+ return nil, ErrPort
+ }
+
+ portStart := globalMathRandomGenerator.Intn(j-i+1) + i
+ portCurrent := portStart
+ for {
+ lAddr = &net.UDPAddr{IP: lAddr.IP, Port: portCurrent}
+ c, e := n.ListenUDP(network, lAddr)
+ if e == nil {
+ return c, e //nolint:nilerr
+ }
+ log.Debugf("Failed to listen %s: %v", lAddr.String(), e)
+ portCurrent++
+ if portCurrent > j {
+ portCurrent = i
+ }
+ if portCurrent == portStart {
+ break
+ }
+ }
+ return nil, ErrPort
+}
diff --git a/vendor/github.com/pion/ice/v2/networktype.go b/vendor/github.com/pion/ice/v2/networktype.go
index 95091018e..57df18631 100644
--- a/vendor/github.com/pion/ice/v2/networktype.go
+++ b/vendor/github.com/pion/ice/v2/networktype.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -7,8 +10,12 @@ import (
)
const (
- udp = "udp"
- tcp = "tcp"
+ udp = "udp"
+ tcp = "tcp"
+ udp4 = "udp4"
+ udp6 = "udp6"
+ tcp4 = "tcp4"
+ tcp6 = "tcp6"
)
func supportedNetworkTypes() []NetworkType {
@@ -40,13 +47,13 @@ const (
func (t NetworkType) String() string {
switch t {
case NetworkTypeUDP4:
- return "udp4"
+ return udp4
case NetworkTypeUDP6:
- return "udp6"
+ return udp6
case NetworkTypeTCP4:
- return "tcp4"
+ return tcp4
case NetworkTypeTCP6:
- return "tcp6"
+ return tcp6
default:
return ErrUnknownType.Error()
}
diff --git a/vendor/github.com/pion/ice/v2/priority.go b/vendor/github.com/pion/ice/v2/priority.go
index 421829938..16ac5cc73 100644
--- a/vendor/github.com/pion/ice/v2/priority.go
+++ b/vendor/github.com/pion/ice/v2/priority.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
diff --git a/vendor/github.com/pion/ice/v2/rand.go b/vendor/github.com/pion/ice/v2/rand.go
index 918783e02..3de1f0407 100644
--- a/vendor/github.com/pion/ice/v2/rand.go
+++ b/vendor/github.com/pion/ice/v2/rand.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import "github.com/pion/randutil"
diff --git a/vendor/github.com/pion/ice/v2/renovate.json b/vendor/github.com/pion/ice/v2/renovate.json
index f1614058a..f1bb98c6a 100644
--- a/vendor/github.com/pion/ice/v2/renovate.json
+++ b/vendor/github.com/pion/ice/v2/renovate.json
@@ -1,27 +1,6 @@
{
+ "$schema": "https://docs.renovatebot.com/renovate-schema.json",
"extends": [
- "config:base",
- ":disableDependencyDashboard"
- ],
- "postUpdateOptions": [
- "gomodTidy"
- ],
- "commitBody": "Generated by renovateBot",
- "packageRules": [
- {
- "matchUpdateTypes": ["minor", "patch", "pin", "digest"],
- "automerge": true
- },
- {
- "packagePatterns": ["^golang.org/x/"],
- "schedule": ["on the first day of the month"]
- }
- ],
- "ignorePaths": [
- ".github/workflows/generate-authors.yml",
- ".github/workflows/lint.yaml",
- ".github/workflows/renovate-go-mod-fix.yaml",
- ".github/workflows/test.yaml",
- ".github/workflows/tidy-check.yaml"
+ "github>pion/renovate-config"
]
}
diff --git a/vendor/github.com/pion/ice/v2/role.go b/vendor/github.com/pion/ice/v2/role.go
index 7a8bc064a..e9a7bda94 100644
--- a/vendor/github.com/pion/ice/v2/role.go
+++ b/vendor/github.com/pion/ice/v2/role.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
diff --git a/vendor/github.com/pion/ice/v2/selection.go b/vendor/github.com/pion/ice/v2/selection.go
index 72484148d..9f312637f 100644
--- a/vendor/github.com/pion/ice/v2/selection.go
+++ b/vendor/github.com/pion/ice/v2/selection.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community
+// SPDX-License-Identifier: MIT
+
package ice
import (
@@ -40,7 +43,7 @@ func (s *controllingSelector) isNominatable(c Candidate) bool {
return time.Since(s.startTime).Nanoseconds() > s.agent.relayAcceptanceMinWait.Nanoseconds()
}
- s.log.Errorf("isNominatable invalid candidate type %s", c.Type().String())
+ s.log.Errorf("Invalid candidate type: %s", c.Type())
return false
}
@@ -84,7 +87,7 @@ func (s *controllingSelector) nominatePair(pair *CandidatePair) {
return
}
- s.log.Tracef("ping STUN (nominate candidate pair) from %s to %s\n", pair.Local.String(), pair.Remote.String())
+ s.log.Tracef("ping STUN (nominate candidate pair) from %s to %s", pair.Local.String(), pair.Remote.String())
s.agent.sendBindingRequest(msg, pair.Local, pair.Remote)
}
@@ -101,9 +104,9 @@ func (s *controllingSelector) HandleBindingRequest(m *stun.Message, local, remot
if p.state == CandidatePairStateSucceeded && s.nominatedPair == nil && s.agent.getSelectedPair() == nil {
bestPair := s.agent.getBestAvailableCandidatePair()
if bestPair == nil {
- s.log.Tracef("No best pair available\n")
+ s.log.Tracef("No best pair available")
} else if bestPair.equal(p) && s.isNominatable(p.Local) && s.isNominatable(p.Remote) {
- s.log.Tracef("The candidate (%s, %s) is the best candidate available, marking it as nominated\n",
+ s.log.Tracef("The candidate (%s, %s) is the best candidate available, marking it as nominated",
p.Local.String(), p.Remote.String())
s.nominatedPair = p
s.nominatePair(p)
@@ -114,7 +117,7 @@ func (s *controllingSelector) HandleBindingRequest(m *stun.Message, local, remot
func (s *controllingSelector) HandleSuccessResponse(m *stun.Message, local, remote Candidate, remoteAddr net.Addr) {
ok, pendingRequest := s.agent.handleInboundBindingSuccess(m.TransactionID)
if !ok {
- s.log.Warnf("discard message from (%s), unknown TransactionID 0x%x", remote, m.TransactionID)
+ s.log.Warnf("Discard message from (%s), unknown TransactionID 0x%x", remote, m.TransactionID)
return
}
@@ -123,7 +126,7 @@ func (s *controllingSelector) HandleSuccessResponse(m *stun.Message, local, remo
// Assert that NAT is not symmetric
// https://tools.ietf.org/html/rfc8445#section-7.2.5.2.1
if !addrEqual(transactionAddr, remoteAddr) {
- s.log.Debugf("discard message: transaction source and destination does not match expected(%s), actual(%s)", transactionAddr, remote)
+ s.log.Debugf("Discard message: transaction source and destination does not match expected(%s), actual(%s)", transactionAddr, remote)
return
}
@@ -195,7 +198,7 @@ func (s *controlledSelector) PingCandidate(local, remote Candidate) {
}
func (s *controlledSelector) HandleSuccessResponse(m *stun.Message, local, remote Candidate, remoteAddr net.Addr) {
- // nolint:godox
+ //nolint:godox
// TODO according to the standard we should specifically answer a failed nomination:
// https://tools.ietf.org/html/rfc8445#section-7.3.1.5
// If the controlled agent does not accept the request from the
@@ -205,7 +208,7 @@ func (s *controlledSelector) HandleSuccessResponse(m *stun.Message, local, remot
ok, pendingRequest := s.agent.handleInboundBindingSuccess(m.TransactionID)
if !ok {
- s.log.Warnf("discard message from (%s), unknown TransactionID 0x%x", remote, m.TransactionID)
+ s.log.Warnf("Discard message from (%s), unknown TransactionID 0x%x", remote, m.TransactionID)
return
}
@@ -214,7 +217,7 @@ func (s *controlledSelector) HandleSuccessResponse(m *stun.Message, local, remot
// Assert that NAT is not symmetric
// https://tools.ietf.org/html/rfc8445#section-7.2.5.2.1
if !addrEqual(transactionAddr, remoteAddr) {
- s.log.Debugf("discard message: transaction source and destination does not match expected(%s), actual(%s)", transactionAddr, remote)
+ s.log.Debugf("Discard message: transaction source and destination does not match expected(%s), actual(%s)", transactionAddr, remote)
return
}
@@ -229,13 +232,20 @@ func (s *controlledSelector) HandleSuccessResponse(m *stun.Message, local, remot
p.state = CandidatePairStateSucceeded
s.log.Tracef("Found valid candidate pair: %s", p)
+ if p.nominateOnBindingSuccess {
+ if selectedPair := s.agent.getSelectedPair(); selectedPair == nil ||
+ (selectedPair != p && selectedPair.priority() <= p.priority()) {
+ s.agent.setSelectedPair(p)
+ } else if selectedPair != p {
+ s.log.Tracef("ignore nominate new pair %s, already nominated pair %s", p, selectedPair)
+ }
+ }
}
func (s *controlledSelector) HandleBindingRequest(m *stun.Message, local, remote Candidate) {
useCandidate := m.Contains(stun.AttrUseCandidate)
p := s.agent.findPair(local, remote)
-
if p == nil {
p = s.agent.addPair(local, remote)
}
@@ -248,10 +258,12 @@ func (s *controlledSelector) HandleBindingRequest(m *stun.Message, local, remote
// previously sent by this pair produced a successful response and
// generated a valid pair (Section 7.2.5.3.2). The agent sets the
// nominated flag value of the valid pair to true.
- if selectedPair := s.agent.getSelectedPair(); selectedPair == nil {
+ if selectedPair := s.agent.getSelectedPair(); selectedPair == nil ||
+ (selectedPair != p && selectedPair.priority() <= p.priority()) {
s.agent.setSelectedPair(p)
+ } else if selectedPair != p {
+ s.log.Tracef("ignore nominate new pair %s, already nominated pair %s", p, selectedPair)
}
- s.agent.sendBindingSuccess(m, local, remote)
} else {
// If the received Binding request triggered a new check to be
// enqueued in the triggered-check queue (Section 7.3.1.4), once the
@@ -261,12 +273,12 @@ func (s *controlledSelector) HandleBindingRequest(m *stun.Message, local, remote
// MUST remove the candidate pair from the valid list, set the
// candidate pair state to Failed, and set the checklist state to
// Failed.
- s.PingCandidate(local, remote)
+ p.nominateOnBindingSuccess = true
}
- } else {
- s.agent.sendBindingSuccess(m, local, remote)
- s.PingCandidate(local, remote)
}
+
+ s.agent.sendBindingSuccess(m, local, remote)
+ s.PingCandidate(local, remote)
}
type liteSelector struct {
@@ -276,8 +288,8 @@ type liteSelector struct {
// A lite selector should not contact candidates
func (s *liteSelector) ContactCandidates() {
if _, ok := s.pairCandidateSelector.(*controllingSelector); ok {
- // nolint:godox
- // pion/ice#96
+ //nolint:godox
+ // https://github.com/pion/ice/issues/96
// TODO: implement lite controlling agent. For now falling back to full agent.
// This only happens if both peers are lite. See RFC 8445 S6.1.1 and S6.2
s.pairCandidateSelector.ContactCandidates()
diff --git a/vendor/github.com/pion/ice/v2/stats.go b/vendor/github.com/pion/ice/v2/stats.go
index f59d89ff9..9b83bea85 100644
--- a/vendor/github.com/pion/ice/v2/stats.go
+++ b/vendor/github.com/pion/ice/v2/stats.go
@@ -1,3 +1,6 @@
+// SPDX-FileCopyrightText: 2023 The Pion community