From 7600ac70e3a74606c30acb059e1ec03696b65634 Mon Sep 17 00:00:00 2001 From: Matt Joiner Date: Thu, 19 May 2016 22:49:37 +1000 Subject: [PATCH] Move torrent tracker methods into torrent.go --- client.go | 104 ----------------------------------------------------- torrent.go | 104 +++++++++++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 104 insertions(+), 104 deletions(-) diff --git a/client.go b/client.go index dbebd1ba..ab7583a1 100644 --- a/client.go +++ b/client.go @@ -33,7 +33,6 @@ import ( "github.com/anacrolix/torrent/mse" pp "github.com/anacrolix/torrent/peer_protocol" "github.com/anacrolix/torrent/storage" - "github.com/anacrolix/torrent/tracker" ) // Currently doesn't really queue, but should in the future. @@ -1647,109 +1646,6 @@ func (cl *Client) trackerBlockedUnlocked(trRawURL string) (blocked bool, err err return } -func (cl *Client) announceTorrentSingleTracker(tr string, req *tracker.AnnounceRequest, t *Torrent) (interval time.Duration, err error) { - blocked, err := cl.trackerBlockedUnlocked(tr) - if err != nil { - err = fmt.Errorf("error determining if tracker blocked: %s", err) - return - } - if blocked { - err = errors.New("tracker has blocked IP") - return - } - resp, err := tracker.Announce(tr, req) - if err != nil { - return - } - var peers []Peer - for _, peer := range resp.Peers { - peers = append(peers, Peer{ - IP: peer.IP, - Port: peer.Port, - }) - } - t.AddPeers(peers) - interval = time.Second * time.Duration(resp.Interval) - return -} - -func (cl *Client) announceTorrentTrackersFastStart(req *tracker.AnnounceRequest, trackers []trackerTier, t *Torrent) (atLeastOne bool) { - oks := make(chan bool) - outstanding := 0 - for _, tier := range trackers { - for _, tr := range tier { - outstanding++ - go func(tr string) { - _, err := cl.announceTorrentSingleTracker(tr, req, t) - oks <- err == nil - }(tr) - } - } - for outstanding > 0 { - ok := <-oks - outstanding-- - if ok { - atLeastOne = true - } - } - return -} - -// Announce torrent to its trackers. -func (cl *Client) announceTorrentTrackers(t *Torrent) { - req := tracker.AnnounceRequest{ - Event: tracker.Started, - NumWant: -1, - Port: uint16(cl.incomingPeerPort()), - PeerId: cl.peerID, - InfoHash: t.infoHash, - } - if !t.waitWantPeers() { - return - } - cl.mu.RLock() - req.Left = t.bytesLeftAnnounce() - trackers := t.trackers - cl.mu.RUnlock() - if cl.announceTorrentTrackersFastStart(&req, trackers, t) { - req.Event = tracker.None - } -newAnnounce: - for t.waitWantPeers() { - cl.mu.RLock() - req.Left = t.bytesLeftAnnounce() - trackers = t.trackers - cl.mu.RUnlock() - numTrackersTried := 0 - for _, tier := range trackers { - for trIndex, tr := range tier { - numTrackersTried++ - interval, err := cl.announceTorrentSingleTracker(tr, &req, t) - if err != nil { - // Try the next tracker. - continue - } - // Float the successful announce to the top of the tier. If - // the trackers list has been changed, we'll be modifying an - // old copy so it won't matter. - cl.mu.Lock() - tier[0], tier[trIndex] = tier[trIndex], tier[0] - cl.mu.Unlock() - - req.Event = tracker.None - // Wait the interval before attempting another announce. - time.Sleep(interval) - continue newAnnounce - } - } - if numTrackersTried != 0 { - log.Printf("%s: all trackers failed", t) - } - // TODO: Wait until trackers are added if there are none. - time.Sleep(10 * time.Second) - } -} - func (cl *Client) allTorrentsCompleted() bool { for _, t := range cl.torrents { if !t.haveInfo() { diff --git a/torrent.go b/torrent.go index b89ce948..124753bd 100644 --- a/torrent.go +++ b/torrent.go @@ -25,6 +25,7 @@ import ( "github.com/anacrolix/torrent/metainfo" pp "github.com/anacrolix/torrent/peer_protocol" "github.com/anacrolix/torrent/storage" + "github.com/anacrolix/torrent/tracker" ) func (t *Torrent) chunkIndexSpec(chunkIndex, piece int) chunkSpec { @@ -1135,3 +1136,106 @@ func (t *Torrent) seeding() bool { } return true } + +// Announce torrent to its trackers. +func (cl *Client) announceTorrentTrackers(t *Torrent) { + req := tracker.AnnounceRequest{ + Event: tracker.Started, + NumWant: -1, + Port: uint16(cl.incomingPeerPort()), + PeerId: cl.peerID, + InfoHash: t.infoHash, + } + if !t.waitWantPeers() { + return + } + cl.mu.RLock() + req.Left = t.bytesLeftAnnounce() + trackers := t.trackers + cl.mu.RUnlock() + if cl.announceTorrentTrackersFastStart(&req, trackers, t) { + req.Event = tracker.None + } +newAnnounce: + for t.waitWantPeers() { + cl.mu.RLock() + req.Left = t.bytesLeftAnnounce() + trackers = t.trackers + cl.mu.RUnlock() + numTrackersTried := 0 + for _, tier := range trackers { + for trIndex, tr := range tier { + numTrackersTried++ + interval, err := cl.announceTorrentSingleTracker(tr, &req, t) + if err != nil { + // Try the next tracker. + continue + } + // Float the successful announce to the top of the tier. If + // the trackers list has been changed, we'll be modifying an + // old copy so it won't matter. + cl.mu.Lock() + tier[0], tier[trIndex] = tier[trIndex], tier[0] + cl.mu.Unlock() + + req.Event = tracker.None + // Wait the interval before attempting another announce. + time.Sleep(interval) + continue newAnnounce + } + } + if numTrackersTried != 0 { + log.Printf("%s: all trackers failed", t) + } + // TODO: Wait until trackers are added if there are none. + time.Sleep(10 * time.Second) + } +} + +func (cl *Client) announceTorrentTrackersFastStart(req *tracker.AnnounceRequest, trackers []trackerTier, t *Torrent) (atLeastOne bool) { + oks := make(chan bool) + outstanding := 0 + for _, tier := range trackers { + for _, tr := range tier { + outstanding++ + go func(tr string) { + _, err := cl.announceTorrentSingleTracker(tr, req, t) + oks <- err == nil + }(tr) + } + } + for outstanding > 0 { + ok := <-oks + outstanding-- + if ok { + atLeastOne = true + } + } + return +} + +func (cl *Client) announceTorrentSingleTracker(tr string, req *tracker.AnnounceRequest, t *Torrent) (interval time.Duration, err error) { + blocked, err := cl.trackerBlockedUnlocked(tr) + if err != nil { + err = fmt.Errorf("error determining if tracker blocked: %s", err) + return + } + if blocked { + err = errors.New("tracker has blocked IP") + return + } + resp, err := tracker.Announce(tr, req) + if err != nil { + return + } + var peers []Peer + for _, peer := range resp.Peers { + peers = append(peers, Peer{ + IP: peer.IP, + Port: peer.Port, + }) + } + t.AddPeers(peers) + interval = time.Second * time.Duration(resp.Interval) + return +} -- 2.48.1