]> Sergey Matveev's repositories - btrtrc.git/blobdiff - ut-holepunching_test.go
Ignore dial rate limits for holepunch connects
[btrtrc.git] / ut-holepunching_test.go
index 29be6d1e6bffc426eb02ff04210eb3a96ac830e6..18521195cec547999f9e09fc436a714ceb6bceb1 100644 (file)
@@ -18,6 +18,7 @@ import (
        qt "github.com/frankban/quicktest"
        "github.com/stretchr/testify/assert"
        "github.com/stretchr/testify/require"
+       "golang.org/x/time/rate"
 
        "github.com/anacrolix/torrent/internal/testutil"
 )
@@ -36,9 +37,12 @@ func TestHolepunchConnect(t *testing.T) {
        cfg.DisablePEX = true
        cfg.Debug = true
        cfg.AcceptPeerConnections = false
-       // Listening, even without accepting, still means the leecher-leecher completes the dial to the seeder, and so it
-       // won't attempt to holepunch.
+       // Listening, even without accepting, still means the leecher-leecher completes the dial to the
+       // seeder, and so it won't attempt to holepunch.
        cfg.DisableTCP = true
+       // Ensure that responding to holepunch connects don't wait around for the dial limit. We also
+       // have to allow the initial connection to the leecher though, so it can rendezvous for us.
+       cfg.DialRateLimiter = rate.NewLimiter(0, 1)
        seeder, err := NewClient(cfg)
        require.NoError(t, err)
        defer seeder.Close()
@@ -65,7 +69,7 @@ func TestHolepunchConnect(t *testing.T) {
        cfg.Seed = false
        cfg.DataDir = t.TempDir()
        cfg.MaxAllocPeerRequestDataPerConn = 4
-       cfg.Debug = true
+       //cfg.Debug = true
        cfg.NominalDialTimeout = time.Second
        //cfg.DisableUTP = true
        leecherLeecher, _ := NewClient(cfg)
@@ -153,6 +157,7 @@ func TestTcpSimultaneousOpen(t *testing.T) {
        makeDialer := func(localPort int, remoteAddr string) func() (net.Conn, error) {
                dialer := net.Dialer{
                        LocalAddr: &net.TCPAddr{
+                               //IP:   net.IPv6loopback,
                                Port: localPort,
                        },
                }
@@ -161,14 +166,28 @@ func TestTcpSimultaneousOpen(t *testing.T) {
                }
        }
        c := qt.New(t)
-       first, second := randPortPair()
-       t.Logf("ports are %v and %v", first, second)
-       err := testSimultaneousOpen(
-               c.Cleanup,
-               makeDialer(first, fmt.Sprintf("localhost:%d", second)),
-               makeDialer(second, fmt.Sprintf("localhost:%d", first)),
-       )
-       c.Assert(err, qt.IsNil)
+       // I really hate doing this in unit tests, but we would need to pick apart Dialer to get
+       // perfectly synchronized simultaneous dials.
+       for range iter.N(10) {
+               first, second := randPortPair()
+               t.Logf("ports are %v and %v", first, second)
+               err := testSimultaneousOpen(
+                       c.Cleanup,
+                       makeDialer(first, fmt.Sprintf("localhost:%d", second)),
+                       makeDialer(second, fmt.Sprintf("localhost:%d", first)),
+               )
+               if err == nil {
+                       return
+               }
+               // This proves that the connections are not the same.
+               if errors.Is(err, errMsgNotReceived) {
+                       t.Fatal(err)
+               }
+               // Could be a timing issue, so try again.
+               t.Log(err)
+       }
+       // If we weren't able to get a simultaneous dial to occur, then we can't call it a failure.
+       t.Skip("couldn't synchronize dials")
 }
 
 func randIntInRange(low, high int) int {