]> Sergey Matveev's repositories - btrtrc.git/blobdiff - request-strategy/order.go
Drop support for go 1.20
[btrtrc.git] / request-strategy / order.go
index 130c698b9f9e6e75235ef0987fa4b68a73d762dc..df656f6db06c941d0ba4e442cee472b2ec038784 100644 (file)
@@ -1,18 +1,19 @@
-package request_strategy
+package requestStrategy
 
 import (
        "bytes"
        "expvar"
 
+       g "github.com/anacrolix/generics"
        "github.com/anacrolix/multiless"
-       "github.com/anacrolix/torrent/metainfo"
 
+       "github.com/anacrolix/torrent/metainfo"
        "github.com/anacrolix/torrent/types"
 )
 
 type (
-       RequestIndex  uint32
-       ChunkIndex    = uint32
+       RequestIndex  uint32
+       ChunkIndex    = RequestIndex
        Request       = types.Request
        pieceIndex    = types.PieceIndex
        piecePriority = types.PiecePriority
@@ -43,7 +44,10 @@ func pieceOrderLess(i, j *pieceRequestOrderItem) multiless.Computation {
 var packageExpvarMap = expvar.NewMap("request-strategy")
 
 // Calls f with requestable pieces in order.
-func GetRequestablePieces(input Input, pro *PieceRequestOrder, f func(ih metainfo.Hash, pieceIndex int)) {
+func GetRequestablePieces(
+       input Input, pro *PieceRequestOrder,
+       f func(ih metainfo.Hash, pieceIndex int, orderState PieceRequestOrderState),
+) {
        // Storage capacity left for this run, keyed by the storage capacity pointer on the storage
        // TorrentImpl. A nil value means no capacity limit.
        var storageLeft *int64
@@ -51,10 +55,18 @@ func GetRequestablePieces(input Input, pro *PieceRequestOrder, f func(ih metainf
                storageLeft = &cap
        }
        var allTorrentsUnverifiedBytes int64
+       var lastItem g.Option[pieceRequestOrderItem]
        pro.tree.Scan(func(_i pieceRequestOrderItem) bool {
+               // Check that scan emits pieces in priority order.
+               if lastItem.Ok {
+                       if _i.Less(&lastItem.Value) {
+                               panic("scan not in order")
+                       }
+               }
+               lastItem.Set(_i)
+
                ih := _i.key.InfoHash
-               var t Torrent = input.Torrent(ih)
-               var piece Piece = t.Piece(_i.key.Index)
+               t := input.Torrent(ih)
                pieceLength := t.PieceLength()
                if storageLeft != nil {
                        if *storageLeft < pieceLength {
@@ -62,7 +74,7 @@ func GetRequestablePieces(input Input, pro *PieceRequestOrder, f func(ih metainf
                        }
                        *storageLeft -= pieceLength
                }
-               if !piece.Request() || piece.NumPendingChunks() == 0 {
+               if t.IgnorePiece(_i.key.Index) {
                        // TODO: Clarify exactly what is verified. Stuff that's being hashed should be
                        // considered unverified and hold up further requests.
                        return true
@@ -71,7 +83,7 @@ func GetRequestablePieces(input Input, pro *PieceRequestOrder, f func(ih metainf
                        return true
                }
                allTorrentsUnverifiedBytes += pieceLength
-               f(ih, _i.key.Index)
+               f(ih, _i.key.Index, _i.state)
                return true
        })
        return