client_test.go | 5 ++++- torrent.go | 11 ++++++++--- diff --git a/client_test.go b/client_test.go index e06601f416011baa8beecc5d8bb102751bb6f9a6..49b4d1ecfbaf20ec3c69d8ddc54f7c43ed0ba5de 100644 --- a/client_test.go +++ b/client_test.go @@ -370,11 +370,14 @@ cfg.DataDir = greetingTempDir } seeder, err := NewClient(cfg) require.NoError(t, err) - defer seeder.Close() if ps.ExportClientStatus { testutil.ExportStatusWriter(seeder, "s") } seederTorrent, _, _ := seeder.AddTorrentSpec(TorrentSpecFromMetaInfo(mi)) + // Run a Stats right after Closing the Client. This will trigger the Stats + // panic in #214 caused by RemoteAddr on Closed uTP sockets. + defer seederTorrent.Stats() + defer seeder.Close() seederTorrent.VerifyData() // Create leecher and a Torrent. leecherDataDir, err := ioutil.TempDir("", "") diff --git a/torrent.go b/torrent.go index 8f93281c05614943e441948e0f108df8ad685e96..4c5fd153b7aa441379b09de7488b6a01168cf328 100644 --- a/torrent.go +++ b/torrent.go @@ -1345,7 +1345,12 @@ // The total number of peers in the torrent. func (t *Torrent) numTotalPeers() int { peers := make(map[string]struct{}) for conn := range t.conns { - peers[conn.conn.RemoteAddr().String()] = struct{}{} + ra := conn.conn.RemoteAddr() + if ra == nil { + // It's been closed and doesn't support RemoteAddr. + continue + } + peers[ra.String()] = struct{}{} } for addr := range t.halfOpen { peers[addr] = struct{}{} @@ -1374,8 +1379,8 @@ // higher. if outgoing == lower { // Close the other one. c0.Close() - // Is it safe to delete from the map while we're iterating - // over it? + // TODO: Is it safe to delete from the map while we're + // iterating over it? t.deleteConnection(c0) } else { // Abandon this one.