summaryrefslogtreecommitdiff
path: root/src/Network
diff options
context:
space:
mode:
Diffstat (limited to 'src/Network')
-rw-r--r--src/Network/BitTorrent/PeerWire/Selection.hs56
1 files changed, 42 insertions, 14 deletions
diff --git a/src/Network/BitTorrent/PeerWire/Selection.hs b/src/Network/BitTorrent/PeerWire/Selection.hs
index 83ab8311..9d154613 100644
--- a/src/Network/BitTorrent/PeerWire/Selection.hs
+++ b/src/Network/BitTorrent/PeerWire/Selection.hs
@@ -10,7 +10,7 @@
10-- which used to find out which one next piece to download. 10-- which used to find out which one next piece to download.
11-- Selectors considered to be used in the following order: 11-- Selectors considered to be used in the following order:
12-- 12--
13-- * Random first or rarest first selection - at the start. 13-- * Random first - at the start.
14-- 14--
15-- * Rarest first selection - performed to avoid situation when 15-- * Rarest first selection - performed to avoid situation when
16-- rarest piece is unaccessible. 16-- rarest piece is unaccessible.
@@ -19,28 +19,59 @@
19-- the subpieces of the content. 19-- the subpieces of the content.
20-- 20--
21-- Note that BitTorrent applies the strict priority policy for 21-- Note that BitTorrent applies the strict priority policy for
22-- _subpiece_ or _blocks_ selection. 22-- /subpiece/ or /blocks/ selection.
23-- 23--
24module Network.BitTorrent.PeerWire.Selection 24module Network.BitTorrent.PeerWire.Selection
25 ( Selector 25 ( Selector
26
27 -- * Construction
28 , selector, strategyClass
29
30 -- * Strategies
26 , strictFirst, strictLast 31 , strictFirst, strictLast
27 , rarestFirst, randomFirst, endGame 32 , rarestFirst, randomFirst, endGame
28
29 , autoSelector
30 ) where 33 ) where
31 34
32import Data.Bitfield 35import Data.Bitfield
33import Network.BitTorrent.PeerWire.Block 36import Network.BitTorrent.PeerWire.Block
34import Network.BitTorrent.PeerWire.Message
35 37
36 38
37 39type Selector = Bitfield -- ^ Indices of client /have/ pieces.
38type Selector = Bitfield -- ^ Indices of client "have" pieces. 40 -> Bitfield -- ^ Indices of peer /have/ pieces.
39 -> Bitfield -- ^ Indices of peer "have" pieces. 41 -> [Bitfield] -- ^ Indices of other peers /have/ pieces.
40 -> [Bitfield] -- ^ Indices of other peers "have" pieces.
41 -> Maybe PieceIx -- ^ Zero-based index of piece to request 42 -> Maybe PieceIx -- ^ Zero-based index of piece to request
42 -- to, if any. 43 -- to, if any.
43 44
45type PieceThreshold = Int
46
47selector :: Selector -- ^ Selector to use at the start.
48 -> PieceThreshold
49 -> Selector -- ^ Selector to use after the client have the C pieces.
50 -> Selector -- ^ Selector that changes behaviour based on completeness.
51selector start pt ready h a xs =
52 case strategyClass pt h of
53 SCBeginning -> start h a xs
54 SCReady -> ready h a xs
55 SCEnd -> endGame h a xs
56
57data StartegyClass
58 = SCBeginning
59 | SCReady
60 | SCEnd
61 deriving (Show, Eq, Ord, Enum, Bounded)
62
63endThreshold :: PieceThreshold
64endThreshold = 1
65
66strategyClass :: PieceThreshold -> Bitfield -> StartegyClass
67strategyClass pt = classify . completeness
68 where
69 classify (have, total)
70 | have < pt = SCBeginning
71 | total - have > endThreshold = SCReady
72 | otherwise = SCEnd
73
74
44-- | Select the first available piece. 75-- | Select the first available piece.
45strictFirst :: Selector 76strictFirst :: Selector
46strictFirst h a _ = findMin (difference a h) 77strictFirst h a _ = findMin (difference a h)
@@ -56,15 +87,12 @@ rarestFirst h a xs = rarest (frequencies (map (intersection want) xs))
56 want = difference h a 87 want = difference h a
57 rarest = Just . head 88 rarest = Just . head
58 89
59-- | In general random first is faster than rarest first strategy but 90-- | In average random first is faster than rarest first strategy but
60-- only if all pieces are available. 91-- only if all pieces are available.
61randomFirst :: IO Selector 92randomFirst :: Selector
62randomFirst = do 93randomFirst = do
63-- randomIO 94-- randomIO
64 error "randomFirst" 95 error "randomFirst"
65 96
66endGame :: Selector 97endGame :: Selector
67endGame = strictLast 98endGame = strictLast
68
69autoSelector :: Selector
70autoSelector = undefined