예제 #1
0
        public InfoHashTrackable(Torrent torrent)
        {
            Check.Torrent(torrent);

            name = torrent.Name;
            infoHash = torrent.InfoHash;
        }
예제 #2
0
        public void MultipleAnnounce()
        {
            var announceCount = 0;
            var r = new Random();
            var handle = new ManualResetEvent(false);

            for (var i = 0; i < 20; i++)
            {
                var infoHash = new InfoHash(new byte[20]);
                r.NextBytes(infoHash.Hash);
                var tier = new TrackerTier(new[] {uri.ToString()});
                tier.Trackers[0].AnnounceComplete += delegate
                {
                    if (++announceCount == 20)
                        handle.Set();
                };
                var id = new TrackerConnectionID(tier.Trackers[0], false, TorrentEvent.Started,
                    new ManualResetEvent(false));
                MonoTorrent.Client.Tracker.AnnounceParameters parameters;
                parameters = new MonoTorrent.Client.Tracker.AnnounceParameters(0, 0, 0, TorrentEvent.Started,
                    infoHash, false, new string('1', 20), "", 1411);
                tier.Trackers[0].Announce(parameters, id);
            }

            Assert.True(handle.WaitOne(5000, true), "Some of the responses weren't received");
        }
예제 #3
0
 public TorrentBDecoder(Stream stream, Encoding encoding)
 {
     _reader = new BinaryReader(stream);
     _streamEncoding = encoding;
     _infoHash = new InfoHash();
     _indicator = 0;
     _inInfoMap = false;
 }
예제 #4
0
        public PeerBEncryption(InfoHash[] possibleSkeYs, EncryptionTypes allowedEncryption)
            : base(allowedEncryption)
        {
            _possibleSkeYs = possibleSkeYs;

            _gotVerificationCallback = GotVerification;
            _gotPadCCallback = GotPadC;
        }
예제 #5
0
        public PeerAEncryption(InfoHash InfoHash, EncryptionTypes allowedEncryption)
            : base(allowedEncryption)
        {
            gotVerificationCallback = new AsyncCallback(gotVerification);
            gotPadDCallback = new AsyncCallback(gotPadD);

            SKEY = InfoHash;
        }
예제 #6
0
        public PeerBEncryption(InfoHash[] possibleSKEYs, EncryptionTypes allowedEncryption)
            : base(allowedEncryption)
        {
            this.possibleSKEYs = possibleSKEYs;

            gotVerificationCallback = new AsyncCallback(gotVerification);
            gotPadCCallback = new AsyncCallback(gotPadC);
        }
예제 #7
0
        public PeerAEncryption(InfoHash infoHash, EncryptionTypes allowedEncryption)
            : base(allowedEncryption)
        {
            _gotVerificationCallback = GotVerification;
            _gotPadDCallback = GotPadD;

            Skey = infoHash;
        }
예제 #8
0
파일: Main.cs 프로젝트: stojy/monotorrent
 public CustomITrackable(Torrent t)
 {
     // Note: I'm just storing the files, infohash and name. A typical Torrent instance
     // is ~100kB in memory. A typical CustomITrackable will be ~100 bytes.
     files = t.Files;
     infoHash = t.InfoHash;
     name = t.Name;
 }
예제 #9
0
        public PeerAEncryption(InfoHash InfoHash, EncryptionTypes allowedEncryption)
            : base(allowedEncryption)
        {
            gotVerificationCallback = gotVerification;
            gotPadDCallback = gotPadD;

            SKEY = InfoHash;
        }
예제 #10
0
        internal static IAsyncResult BeginCheckEncryption(PeerId id, int bytesToReceive, AsyncCallback callback,
            object state, InfoHash[] sKeys)
        {
            var result = new EncryptorAsyncResult(id, callback, state) {SKeys = sKeys};

            var c = id.Connection;
            ClientEngine.MainLoop.QueueTimeout(TimeSpan.FromSeconds(10), delegate
            {
                if (id.Encryptor == null || id.Decryptor == null)
                    id.CloseConnection();
                return false;
            });

            try
            {
                // If the connection is incoming, receive the handshake before
                // trying to decide what encryption to use
                if (id.Connection.IsIncoming)
                {
                    result.Buffer = new byte[bytesToReceive];
                    NetworkIO.EnqueueReceive(c, result.Buffer, 0, result.Buffer.Length, null, null, null,
                        HandshakeReceivedCallback, result);
                }
                else
                {
                    var usable = CheckRc4(id);
                    var hasPlainText = Toolbox.HasEncryption(usable, EncryptionTypes.PlainText);
                    var hasRc4 = Toolbox.HasEncryption(usable, EncryptionTypes.RC4Full) ||
                                 Toolbox.HasEncryption(usable, EncryptionTypes.RC4Header);
                    if (id.Engine.Settings.PreferEncryption)
                    {
                        if (hasRc4)
                        {
                            result.EncSocket = new PeerAEncryption(id.TorrentManager.InfoHash, usable);
                            result.EncSocket.BeginHandshake(id.Connection, CompletedEncryptedHandshakeCallback, result);
                        }
                        result.Complete();
                    }
                    else
                    {
                        if (hasPlainText)
                        {
                            result.Complete();
                        }
                        else
                        {
                            result.EncSocket = new PeerAEncryption(id.TorrentManager.InfoHash, usable);
                            result.EncSocket.BeginHandshake(id.Connection, CompletedEncryptedHandshakeCallback, result);
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                result.Complete(ex);
            }
            return result;
        }
예제 #11
0
        public InfoHashTrackable(string name, InfoHash infoHash)
        {
            Check.InfoHash(infoHash);

            if (string.IsNullOrEmpty(name))
                throw new ArgumentNullException("name cannot be null or empty", "name");

            this.infoHash = infoHash;
            this.name = name;
        }
예제 #12
0
        public FastResume(InfoHash infoHash, BitField bitfield)
        {
            if (infoHash == null)
                throw new ArgumentNullException(nameof(infoHash));
            if (bitfield == null)
                throw new ArgumentNullException(nameof(bitfield));

            Infohash = infoHash;
            Bitfield = bitfield;
        }
예제 #13
0
        public FastResume(InfoHash infoHash, BitField bitfield)
        {
            if (infoHash == null)
                throw new ArgumentNullException("infoHash");
            if (bitfield == null)
                throw new ArgumentNullException("bitfield");

            this.infoHash = infoHash;
            this.bitfield = bitfield;
        }
        public FastResume(InfoHash infoHash, BitField bitfield, IEnumerable<Priority> priorities)
        {
            if (infoHash==null)
                throw new ArgumentNullException("infoHash");
            if(bitfield == null)
                throw new ArgumentNullException("bitfield");

            this.infoHash = infoHash;
            this.bitfield = bitfield;
            this.priorities = priorities.ToArray();
        }
예제 #15
0
        public FastResume(BEncodedDictionary dict)
        {
            CheckContent(dict, VersionKey, 1);
            CheckContent(dict, InfoHashKey);
            CheckContent(dict, BitfieldKey);
            CheckContent(dict, BitfieldLengthKey);

            Infohash = new InfoHash(((BEncodedString) dict[InfoHashKey]).TextBytes);
            Bitfield = new BitField((int) ((BEncodedNumber) dict[BitfieldLengthKey]).Number);
            var data = ((BEncodedString) dict[BitfieldKey]).TextBytes;
            Bitfield.FromArray(data, 0, data.Length);
        }
예제 #16
0
 public TorrentInfo(InfoHash hash, string name, int priority, ActiveStates activestate, DownloadStates downloadstate, IEnumerable<string> labels, ulong size, ulong remaining, ulong uploaded)
 {
     Hash = hash;
     Name = name;
     Priority = priority;
     ActiveState = activestate;
     DownloadState = downloadstate;
     Labels = new ReadOnlyCollection<string>(new List<string>(labels));
     Size = size;
     Remaining = remaining;
     Uploaded = uploaded;
 }
 public AnnounceParameters(long bytesDownloaded, long bytesUploaded, long bytesLeft,
     TorrentEvent clientEvent, InfoHash infohash, bool requireEncryption,
     string peerId, string ipaddress, int port)
 {
     BytesDownloaded = bytesDownloaded;
     BytesUploaded = bytesUploaded;
     BytesLeft = bytesLeft;
     ClientEvent = clientEvent;
     InfoHash = infohash;
     RequireEncryption = requireEncryption;
     PeerId = peerId;
     Ipaddress = ipaddress;
     Port = port;
 }
예제 #18
0
 public AnnounceParameters(long bytesDownloaded, long bytesUploaded, long bytesLeft,
                           TorrentEvent clientEvent, InfoHash infohash, bool requireEncryption,
                           string peerId, string ipaddress, int port)
 {
     this.bytesDownloaded = bytesDownloaded;
     this.bytesUploaded = bytesUploaded;
     this.bytesLeft = bytesLeft;
     this.clientEvent = clientEvent;
     this.infohash = infohash;
     this.requireEncryption = requireEncryption;
     this.peerId = peerId;
     this.ipaddress = ipaddress;
     this.port = port;
 }
예제 #19
0
        public void Setup()
        {
            pair = new ConnectionPair().WithTimeout();

            InfoHash = new InfoHash(Enumerable.Repeat((byte)255, 20).ToArray());
            SKeys    = new[] {
                new InfoHash(Enumerable.Repeat((byte)254, 20).ToArray()),
                new InfoHash(Enumerable.Repeat((byte)253, 20).ToArray()),
                InfoHash,
                new InfoHash(Enumerable.Repeat((byte)252, 20).ToArray())
            };

            IncomingId = new BEncodedString(Enumerable.Repeat((byte)'0', 20).ToArray());
            OutgoingId = new BEncodedString(Enumerable.Repeat((byte)'1', 20).ToArray());
        }
예제 #20
0
        public async Task MultipleAnnounce()
        {
            Random r = new Random();

            for (int i = 0; i < 20; i++)
            {
                InfoHash infoHash = new InfoHash(new byte[20]);
                r.NextBytes(infoHash.Hash);
                TrackerTier tier       = new TrackerTier(new[] { uri.ToString() });
                var         parameters = new AnnounceParameters(0, 0, 0, TorrentEvent.Started,
                                                                infoHash, false, new string ('1', 20), "", 1411, false);
                Assert.IsTrue(tier.ActiveTracker.CanScrape);
                await tier.Trackers[0].AnnounceAsync(parameters, CancellationToken.None);
            }
        }
예제 #21
0
 /// <summary>
 ///     Initializes an instance of the Torrent.Client.TrackerRequest class with the specified parameters.
 /// </summary>
 /// <param name="infoHash">The SHA1 hash of the value of the info key from the torrent metadata.</param>
 /// <param name="peerId">The Peer ID, used to uniquely identify the peer. 20 bytes.</param>
 /// <param name="port">The port at which the client is listening on. Typically 6881-6889.</param>
 /// <param name="uploaded">The total count of uploaded bytes.</param>
 /// <param name="downloaded">The total count of downloaded bytes.</param>
 /// <param name="left">The count of bytes left to download for the download to be complete.</param>
 /// <param name="compact">Whether to request a compact response by the tracker. (binary peers representation)</param>
 /// <param name="omitPeerIds">Whether to request that the tracker should omit peer IDs in the peers dictionary.</param>
 /// <param name="event">Specifies the event that caused the request. None by default.</param>
 public TrackerRequest(InfoHash infoHash, string peerId, ushort port, long uploaded, long downloaded,
                       long left, bool compact, bool omitPeerIds, EventType @event = EventType.None,
                       int?numWant = null)
 {
     InfoHash    = infoHash;
     PeerId      = peerId;
     Port        = port;
     Uploaded    = uploaded;
     Downloaded  = downloaded;
     Left        = left;
     Compact     = compact;
     OmitPeerIds = omitPeerIds;
     Event       = @event;
     NumWant     = numWant;
 }
예제 #22
0
        public override void Decode(byte[] buffer, int offset, int length)
        {
            ProtocolStringLength = ReadByte(buffer, ref offset);                   // First byte is length

            // #warning Fix this hack - is there a better way of verifying the protocol string? Hack
            if (ProtocolStringLength != VersionInfo.ProtocolStringV100.Length)
            {
                ProtocolStringLength = VersionInfo.ProtocolStringV100.Length;
            }

            ProtocolString = ReadString(buffer, ref offset, ProtocolStringLength);
            CheckForSupports(buffer, ref offset);
            InfoHash = new InfoHash(ReadBytes(buffer, ref offset, 20));
            PeerId   = ReadBytes(buffer, ref offset, 20);
        }
예제 #23
0
 internal AnnounceParameters(long bytesDownloaded, long bytesUploaded, long bytesLeft,
                             TorrentEvent clientEvent, InfoHash infoHash, bool requireEncryption,
                             BEncodedString peerId, string ipAddress, int port, bool supportsEncryption)
 {
     BytesDownloaded   = bytesDownloaded;
     BytesUploaded     = bytesUploaded;
     BytesLeft         = bytesLeft;
     ClientEvent       = clientEvent;
     InfoHash          = infoHash;
     RequireEncryption = requireEncryption;
     PeerId            = peerId;
     IPAddress         = ipAddress;
     Port = port;
     SupportsEncryption = supportsEncryption;
 }
        public InfoHashTrackable(string name, InfoHash infoHash)
        {
            if (infoHash == null)
            {
                throw new ArgumentNullException(nameof(infoHash));
            }

            if (string.IsNullOrEmpty(name))
            {
                throw new ArgumentNullException(nameof(name), $"{nameof (name)} cannot be null or empty");
            }

            InfoHash = infoHash;
            Name     = name;
        }
예제 #25
0
        public TorrentManager(InfoHash infoHash, StorageFolder savePath, TorrentSettings settings,
                              StorageFolder torrentSaveFolder,
                              IList <RawTrackerTier> announces)
        {
            Check.InfoHash(infoHash);
            Check.SaveFolder(savePath);
            Check.Settings(settings);
            Check.TorrentSave(torrentSaveFolder);
            Check.Announces(announces);

            InfoHash           = infoHash;
            Settings           = settings;
            _torrentSaveFolder = torrentSaveFolder;

            Initialise(savePath, "", announces);
        }
예제 #26
0
        public async Task MultipleAnnounce()
        {
            Random r = new Random();

            for (int i = 0; i < 20; i++)
            {
                var buffer = new byte[20];
                r.NextBytes(buffer);
                var         infoHash   = new InfoHash(buffer);
                TrackerTier tier       = new TrackerTier(Factories.Default, new[] { uri.ToString() });
                var         parameters = new MonoTorrent.Trackers.AnnounceRequest(0, 0, 0, TorrentEvent.Started,
                                                                                  infoHash, false, new BEncodedString(new string ('1', 20)).Span.ToArray(), "", 1411, false);
                Assert.IsTrue(tier.ActiveTracker.CanScrape);
                await tier.Trackers[0].AnnounceAsync(parameters, CancellationToken.None);
            }
        }
예제 #27
0
        public static void Main(string[] args)
        {
            Listener listener = new UdpListener(new IPEndPoint(IPAddress.Any, 15000));

            listener.Start();

            DhtEngine engine = new DhtEngine(listener);

            engine.PeersFound += EngineOnPeersFound;
            engine.Start();

            Thread.Sleep(25000);
            engine.GetPeers(InfoHash.FromHex("b415c913643e5ff49fe37d304bbb5e6e11ad5101"));

            Console.ReadLine();
        }
예제 #28
0
        public HandshakeMessage(InfoHash infoHash, string peerId, string protocolString, bool enableFastPeer,
                                bool enableExtended)
        {
            if (!ClientEngine.SupportsFastPeer && enableFastPeer)
                throw new ProtocolException("The engine does not support fast peer, but fast peer was requested");

            if (!ClientEngine.SupportsExtended && enableExtended)
                throw new ProtocolException("The engine does not support extended, but extended was requested");

            this.InfoHash = infoHash;
            PeerId = peerId;
            ProtocolString = protocolString;
            ProtocolStringLength = protocolString.Length;
            SupportsFastPeer = enableFastPeer;
            SupportsExtendedMessaging = enableExtended;
        }
예제 #29
0
        public DhtBasedSwarm(InfoHash hash, int port, string nodeSavePath)
            : base(hash,port)
        {
            _nodeSavePath = nodeSavePath;
            _listener = new DhtListener(new IPEndPoint(IPAddress.Any, Port));
            _engine = new DhtEngine(_listener);

            _engine.PeersFound += EnginePeersFound;
            _engine.StateChanged += EngineStateChanged;
            _listener.MessageReceived += ListenerMessageReceived;
            if (!String.IsNullOrWhiteSpace(_nodeSavePath) && File.Exists(_nodeSavePath))
            {
                Log("Node File Found.");
                _nodes = File.ReadAllBytes(_nodeSavePath);
            }
        }
예제 #30
0
        static IList <InfoHash> ParseHashes(string infoHash)
        {
            if (string.IsNullOrEmpty(infoHash))
            {
                return(Array.Empty <InfoHash> ());
            }

            var split  = infoHash.Split(HashSeparators, StringSplitOptions.RemoveEmptyEntries);
            var result = new InfoHash[split.Length];

            for (int i = 0; i < split.Length; i++)
            {
                result [i] = InfoHash.UrlDecode(split [i]);
            }
            return(result);
        }
예제 #31
0
        public async void Announce(InfoHash infoHash, int port)
        {
            CheckDisposed();
            if (infoHash is null)
            {
                throw new ArgumentNullException(nameof(infoHash));
            }

            try {
                await MainLoop;
                var   task = new AnnounceTask(this, infoHash, port);
                await task.ExecuteAsync();
            } catch {
                // Ignore?
            }
        }
예제 #32
0
        public AnnounceRequest(NameValueCollection collection, IPAddress address)
            : base(collection, address)
        {
            InfoHash = CheckMandatoryFields();

            /* If the user has supplied an IP address, we use that instead of
            * the IP address we read from the announce request connection. */
            if (IPAddress.TryParse(Parameters["ip"] ?? "", out IPAddress supplied) && !supplied.Equals(IPAddress.Any))
            {
                ClientAddress = new IPEndPoint(supplied, Port);
            }
            else
            {
                ClientAddress = new IPEndPoint(address, Port);
            }
        }
예제 #33
0
        public async void GetPeers(InfoHash infoHash)
        {
            CheckDisposed();
            if (infoHash == null)
            {
                throw new ArgumentNullException(nameof(infoHash));
            }

            try {
                await MainLoop;
                var   task = new GetPeersTask(this, infoHash);
                await task.ExecuteAsync();
            } catch {
                // Ignore?
            }
        }
        public void InfoHashTest()
        {
            var link = new MagnetLink("magnet:?xt.1=urn:sha1:YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C");
            Assert.Equal(InfoHash.FromBase32("YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C"), link.InfoHash);

            //base32
            var initial = new InfoHash(Encoding.ASCII.GetBytes("foobafoobafoobafooba"));
            link = new MagnetLink("magnet:?xt=urn:sha1:MZXW6YTBMZXW6YTBMZXW6YTBMZXW6YTB");
            Assert.Equal(initial, link.InfoHash);

            //base40 = hex
            var hash = Create();
            var hex = hash.ToHex();
            link = new MagnetLink("magnet:?xt=urn:btih:" + hex);
            Assert.Equal(hash, link.InfoHash);
        }
예제 #35
0
        public void InfoHashTest()
        {
            MagnetLink link = new MagnetLink("magnet:?xt.1=urn:sha1:YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C");
            Assert.AreEqual(InfoHash.FromBase32 ("YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C"), link.InfoHash , "#1");

            //base32
            InfoHash initial = new InfoHash (System.Text.Encoding.ASCII.GetBytes("foobafoobafoobafooba"));
            link = new MagnetLink("magnet:?xt=urn:sha1:MZXW6YTBMZXW6YTBMZXW6YTBMZXW6YTB");
            Assert.AreEqual(initial, link.InfoHash , "#2");

            //base40 = hex
            InfoHash hash = Create();
            string hex = hash.ToHex();
            link = new MagnetLink("magnet:?xt=urn:btih:" + hex);
            Assert.AreEqual(hash, link.InfoHash , "#3");
        }
예제 #36
0
        async ReusableTask <ScrapeResponse> ScrapeReceivedAsync(InfoHash infoHash, HttpResponseMessage response)
        {
            await new ThreadSwitcher();

            int?complete = null, downloaded = null, incomplete = null;
            BEncodedDictionary dict = await DecodeResponseAsync(response).ConfigureAwait(false);

            // FIXME: Log the failure?
            if (!dict.ContainsKey("files"))
            {
                return(new ScrapeResponse(TrackerState.Ok, warningMessage: "Tracker did not have data for this torrent"));
            }

            var files = (BEncodedDictionary)dict["files"];

            if (files.Count != 1)
            {
                throw new TrackerException("The scrape response contained unexpected data");
            }

            var d = (BEncodedDictionary)files[new BEncodedString(infoHash.Span.ToArray())];

            foreach (KeyValuePair <BEncodedString, BEncodedValue> kp in d)
            {
                switch (kp.Key.ToString())
                {
                case "complete":
                    complete = (int)((BEncodedNumber)kp.Value).Number;
                    break;

                case "downloaded":
                    downloaded = (int)((BEncodedNumber)kp.Value).Number;
                    break;

                case "incomplete":
                    incomplete = (int)((BEncodedNumber)kp.Value).Number;
                    break;

                default:
                    logger.InfoFormatted("Unknown scrape tag received: Key {0}  Value {1}", kp.Key, kp.Value);
                    break;
                }
            }

            return(new ScrapeResponse(TrackerState.Ok, complete: complete, incomplete: incomplete, downloaded: downloaded));
        }
예제 #37
0
        public TorrentHandler(InfoHash H, string DownloadDir = DOWNLOAD_DIR, bool ForceHash = false)
        {
            InitBase(DownloadDir);
            var CacheFile = Environment.ExpandEnvironmentVariables(TORRENT_DIR + $"\\{H.ToHex()}.torrent");

            //Use cached torrent file if available
            if (!ForceHash && File.Exists(CacheFile))
            {
                Torrent T = Torrent.Load(File.ReadAllBytes(CacheFile));
                TM = new TorrentManager(T, Environment.ExpandEnvironmentVariables(DownloadDir), TS);
            }
            else
            {
                TM = new TorrentManager(H, Environment.ExpandEnvironmentVariables(DownloadDir), TS, Environment.ExpandEnvironmentVariables(TORRENT_DIR), InitTracker());
            }
            Assign();
        }
예제 #38
0
        internal static MonoTorrentCollection <int> Calculate(byte[] addressBytes, InfoHash infohash, int count, UInt32 numberOfPieces)
        {
            byte[] hashBuffer = new byte[24];                                             // The hash buffer to be used in hashing
            MonoTorrentCollection <int> results = new MonoTorrentCollection <int>(count); // The results array which will be returned

            // 1) Convert the bytes into an int32 and make them Network order
            int ip = IPAddress.HostToNetworkOrder(BitConverter.ToInt32(addressBytes, 0));

            // 2) binary AND this value with 0xFFFFFF00 to select the three most sigificant bytes
            int ipMostSignificant = (int)(0xFFFFFF00 & ip);

            // 3) Make ipMostSignificant into NetworkOrder
            UInt32 ip2 = (UInt32)IPAddress.HostToNetworkOrder(ipMostSignificant);

            // 4) Copy ip2 into the hashBuffer
            Buffer.BlockCopy(BitConverter.GetBytes(ip2), 0, hashBuffer, 0, 4);

            // 5) Copy the infohash into the hashbuffer
            Buffer.BlockCopy(infohash.Hash, 0, hashBuffer, 4, 20);

            // 6) Keep hashing and cycling until we have AllowedFastPieceCount number of results
            // Then return that result
            while (true)
            {
                lock (hasher)
                    hashBuffer = hasher.ComputeHash(hashBuffer);

                for (int i = 0; i < 20; i += 4)
                {
                    UInt32 result = (UInt32)IPAddress.HostToNetworkOrder(BitConverter.ToInt32(hashBuffer, i));

                    result = result % numberOfPieces;
                    if (result > int.MaxValue)
                    {
                        return(results);
                    }

                    results.Add((int)result);

                    if (count == results.Count)
                    {
                        return(results);
                    }
                }
            }
        }
 public override void Decode(byte[] buffer, int offset, int length)
 {
     ConnectionId = ReadLong(buffer, ref offset);
     if (Action != ReadInt(buffer, ref offset))
         ThrowInvalidActionException();
     TransactionId = ReadInt(buffer, ref offset);
     Infohash = new InfoHash(ReadBytes(buffer, ref offset, 20));
     PeerId = ReadString(buffer, ref offset, 20);
     Downloaded = ReadLong(buffer, ref offset);
     Left = ReadLong(buffer, ref offset);
     Uploaded = ReadLong(buffer, ref offset);
     TorrentEvent = (TorrentEvent) ReadInt(buffer, ref offset);
     Ip = (uint) ReadInt(buffer, ref offset);
     Key = (uint) ReadInt(buffer, ref offset);
     NumWanted = ReadInt(buffer, ref offset);
     Port = (ushort) ReadShort(buffer, ref offset);
 }
        public FastResume(BEncodedDictionary dict)
        {
            CheckContent(dict, VersionKey, (BEncodedNumber)1);
            CheckContent(dict, InfoHashKey);
            CheckContent(dict, BitfieldKey);
            CheckContent(dict, BitfieldLengthKey);

            infoHash = new InfoHash(((BEncodedString)dict[InfoHashKey]).TextBytes);
            bitfield = new BitField((int)((BEncodedNumber)dict[BitfieldLengthKey]).Number);
            byte[] data = ((BEncodedString)dict[BitfieldKey]).TextBytes;
            bitfield.FromArray(data, 0, data.Length);

            if (dict.ContainsKey(PrioritiesKey))
            {
                var list = (BEncodedList)dict[PrioritiesKey];
                priorities = list.Select(v => (Priority)((BEncodedNumber)v).Number).ToArray();
            }
        }
예제 #41
0
        public FastResume(BEncodedDictionary dict)
        {
            CheckContent(dict, VersionKey, (BEncodedNumber)1);
            CheckContent(dict, InfoHashKey);
            CheckContent(dict, BitfieldKey);
            CheckContent(dict, BitfieldLengthKey);

            infoHash = new InfoHash(((BEncodedString)dict[InfoHashKey]).TextBytes);
            bitfield = new BitField((int)((BEncodedNumber)dict[BitfieldLengthKey]).Number);
            byte[] data = ((BEncodedString)dict[BitfieldKey]).TextBytes;
            bitfield.FromArray(data, 0, data.Length);

            if (dict.ContainsKey(PrioritiesKey))
            {
                var list = (BEncodedList)dict[PrioritiesKey];
                priorities = list.Select(v => (Priority)((BEncodedNumber)v).Number).ToArray();
            }
        }
예제 #42
0
        public void GetPeersQuery_Encoding()
        {
            TransactionID transactionId = new TransactionID(Encoding.UTF8.GetBytes("aa"));
            NodeID        senderId      = new NodeID(Encoding.UTF8.GetBytes("abcdefghij0123456789"));
            InfoHash      infoHash      = new InfoHash(Encoding.UTF8.GetBytes("mnopqrstuvwxyz123456"));
            GetPeersQuery testQuery     = new GetPeersQuery(transactionId, senderId, infoHash);

            byte[] bencodedMessageBytes = testQuery.Construct().Encode();

            Assert.Equal(MessageType.Query, KademliaRPC.TryParseMessage(bencodedMessageBytes, out BDictionary message));
            Assert.Equal(QueryType.get_peers, KademliaRPC.TryGetQuery(message, out Query query));
            Assert.True(query is GetPeersQuery);
            Assert.Equal(testQuery.TransactionID, query.TransactionID);
            Assert.Equal(testQuery.SenderNode, ((GetPeersQuery)query).SenderNode);
            Assert.Equal(testQuery.InfoHash, ((GetPeersQuery)query).InfoHash);

            Assert.Equal(TestBencodedMessage, Encoding.UTF8.GetString(bencodedMessageBytes));
        }
예제 #43
0
        public AnnounceMessage(int transactionId, long connectionId, AnnounceParameters parameters)
            : base(1, transactionId)
        {
            this.connectionId = connectionId;
            if (parameters == null)
                return;

            downloaded = parameters.BytesDownloaded;
            infoHash = parameters.InfoHash;
            ip = 0;
            key = (uint) DateTime.Now.GetHashCode(); // FIXME: Don't do this! It should be constant
            left = parameters.BytesLeft;
            numWanted = 50;
            peerId = parameters.PeerId;
            port = (ushort) parameters.Port;
            torrentEvent = parameters.ClientEvent;
            uploaded = parameters.BytesUploaded;
        }
예제 #44
0
        private ScrapeResponse HandleScrapeResponse(BEncoding.Dictionary info)
        {
            BEncoding.Dictionary files;
            if (!info.TryGetDictionary("files", out files))
            {
                return(null);
            }

            var torrentInfos = new List <ScrapeResponse.TorrentInfo>(files.Count);

            foreach (var torrentInfo in files)
            {
                var torrentInfoDict = (torrentInfo.Value as BEncoding.Dictionary);
                if (torrentInfoDict == null)
                {
                    continue;
                }

                long   completeCount, incompleteCount, downloadedCount;
                string torrentName;
                if (!torrentInfoDict.TryGetInteger("complete", out completeCount))
                {
                    completeCount = 0;
                }
                if (!torrentInfoDict.TryGetInteger("incomplete", out incompleteCount))
                {
                    incompleteCount = 0;
                }
                if (!torrentInfoDict.TryGetInteger("downloaded", out downloadedCount))
                {
                    downloadedCount = 0;
                }
                if (!torrentInfoDict.TryGetString("name", out torrentName))
                {
                    torrentName = null;
                }

                byte[] infoHashBytes = Encoding.UTF8.GetBytes(torrentInfo.Key); // TODO: Is this okay to do?
                var    infoHash      = new InfoHash(infoHashBytes);
                torrentInfos.Add(new ScrapeResponse.TorrentInfo(infoHash, (int)completeCount, (int)incompleteCount, (int)downloadedCount, torrentName));
            }

            return(new ScrapeResponse(this, torrentInfos.ToArray()));
        }
        internal static MonoTorrentCollection<int> Calculate(byte[] addressBytes, InfoHash infohash, int count,
            uint numberOfPieces)
        {
            var hashBuffer = new byte[24]; // The hash buffer to be used in hashing
            var results = new MonoTorrentCollection<int>(count);
            // The results array which will be returned

            // 1) Convert the bytes into an int32 and make them Network order
            var ip = IPAddress.HostToNetworkOrder(BitConverter.ToInt32(addressBytes, 0));

            // 2) binary AND this value with 0xFFFFFF00 to select the three most sigificant bytes
            var ipMostSignificant = (int) (0xFFFFFF00 & ip);

            // 3) Make ipMostSignificant into NetworkOrder
            var ip2 = (uint) IPAddress.HostToNetworkOrder(ipMostSignificant);

            // 4) Copy ip2 into the hashBuffer
            Buffer.BlockCopy(BitConverter.GetBytes(ip2), 0, hashBuffer, 0, 4);

            // 5) Copy the infohash into the hashbuffer
            Buffer.BlockCopy(infohash.Hash, 0, hashBuffer, 4, 20);

            // 6) Keep hashing and cycling until we have AllowedFastPieceCount number of results
            // Then return that result
            while (true)
            {
                lock (hasher)
                    hashBuffer = hasher.ComputeHash(hashBuffer);

                for (var i = 0; i < 20; i += 4)
                {
                    var result = (uint) IPAddress.HostToNetworkOrder(BitConverter.ToInt32(hashBuffer, i));

                    result = result%numberOfPieces;
                    if (result > int.MaxValue)
                        return results;

                    results.Add((int) result);

                    if (count == results.Count)
                        return results;
                }
            }
        }
        async void ReceiveAsync(UdpClient client, CancellationToken token)
        {
            while (!token.IsCancellationRequested)
            {
                try {
                    UdpReceiveResult result = await client.ReceiveAsync().ConfigureAwait(false);

                    string[] receiveString = Encoding.ASCII.GetString(result.Buffer)
                                             .Split(new[] { "\r\n" }, StringSplitOptions.RemoveEmptyEntries);

                    string portString   = receiveString.FirstOrDefault(t => t.StartsWith("Port: ", StringComparison.Ordinal));
                    string hashString   = receiveString.FirstOrDefault(t => t.StartsWith("Infohash: ", StringComparison.Ordinal));
                    string cookieString = receiveString.FirstOrDefault(t => t.StartsWith("cookie", StringComparison.Ordinal));

                    // An invalid response was received if these are missing.
                    if (portString == null || hashString == null)
                    {
                        continue;
                    }

                    // If we received our own cookie we can ignore the message.
                    if (cookieString != null && cookieString.Contains(Cookie))
                    {
                        continue;
                    }

                    // If the port is invalid, ignore it!
                    int portcheck = int.Parse(portString.Split(' ').Last());
                    if (portcheck <= 0 || portcheck > 65535)
                    {
                        continue;
                    }

                    var infoHash = InfoHash.FromHex(hashString.Split(' ').Last());
                    var uri      = new Uri($"ipv4://{result.RemoteEndPoint.Address}{':'}{portcheck}");

                    PeerFound?.InvokeAsync(this, new LocalPeerFoundEventArgs(infoHash, uri));
                } catch (FileNotFoundException) {
                    throw;
                } catch {
                }
            }
        }
예제 #47
0
        /// <summary>
        /// Creates a new tracker announce request.
        /// </summary>
        /// <param name="infoHash">The info hash.</param>
        /// <param name="peerID">The peer ID.</param>
        /// <param name="port">The port number used to listen for client connections on.</param>
        public AnnounceRequest(InfoHash infoHash, PeerID peerID, int port)
        {
            if (infoHash.Hash == null)
            {
                throw new ArgumentException("The info hash is invalid.", "infoHash");
            }
            else if (peerID.ID == null)
            {
                throw new ArgumentException("The peer ID is invalid.", "infoHash");
            }
            else if (port <= 0 || port > ushort.MaxValue)
            {
                throw new ArgumentOutOfRangeException("port");
            }

            this.infoHash = infoHash;
            this.peerID   = peerID;
            this.port     = port;
        }
예제 #48
0
 public override void Decode(ReadOnlySpan <byte> buffer)
 {
     ConnectionId = ReadLong(ref buffer);
     if (Action != ReadInt(ref buffer))
     {
         ThrowInvalidActionException();
     }
     TransactionId = ReadInt(ref buffer);
     InfoHash      = InfoHash.FromMemory(ReadBytes(ref buffer, 20));
     PeerId        = ReadBytes(ref buffer, 20);
     Downloaded    = ReadLong(ref buffer);
     Left          = ReadLong(ref buffer);
     Uploaded      = ReadLong(ref buffer);
     TorrentEvent  = (TorrentEvent)ReadInt(ref buffer);
     IP            = ReadUInt(ref buffer);
     Key           = ReadUInt(ref buffer);
     NumWanted     = ReadInt(ref buffer);
     Port          = ReadUShort(ref buffer);
 }
예제 #49
0
파일: Program.cs 프로젝트: Ysovuka/DhtNet
        public static void Main()
        {
            //https://wiki.theory.org/BitTorrentSpecification
            Listener listener = new UdpListener(new IPEndPoint(IPAddress.Any, 15000));

            listener.Start();

            DhtEngine engine = new DhtEngine(listener);

            engine.Start();

            //Wait for the DHT to startup
            Task.Delay(30000).Wait();

            engine.PeersFound += EngineOnPeersFound;
            engine.GetPeers(InfoHash.FromHex("0403FB4728BD788FBCB67E87D6FEB241EF38C75A"));

            Console.ReadLine();
        }
예제 #50
0
        /// <summary>
        /// Send an announce request for this InfoHash.
        /// </summary>
        /// <param name="infoHash"></param>
        /// <returns></returns>
        public async Task Announce(InfoHash infoHash)
        {
            var message = string.Format(BaseSearchString, Settings.ListenPort, infoHash.ToHex());
            var data    = Encoding.ASCII.GetBytes(message);

            // If there's another application on the system which joined the bittorrent LPD broadcast group, we'll be unable to
            // join it and will have a PortInUse error. However, we can still *send* broadcast messages using any UDP client.
            using (var sendingClient = new UdpClient())
                foreach (var nic in NetworkInterface.GetAllNetworkInterfaces())
                {
                    try {
                        //if (!nic.SupportsMulticast) continue;
                        sendingClient.Client.SetSocketOption(SocketOptionLevel.IP, SocketOptionName.MulticastInterface, IPAddress.HostToNetworkOrder(nic.GetIPProperties().GetIPv4Properties().Index));
                        await sendingClient.SendAsync(data, data.Length, BroadcastEndPoint);
                    } catch {
                        // If data can't be sent, just ignore the error
                    }
                }
        }
        public TorrentManager(MagnetLink magnetLink, string savePath, TorrentSettings settings, string torrentSave)
        {
            Check.MagnetLink(magnetLink);
            Check.InfoHash(magnetLink.InfoHash);
            Check.SavePath(savePath);
            Check.Settings(settings);
            Check.TorrentSave(torrentSave);

            this.infohash    = magnetLink.InfoHash;
            this.settings    = settings;
            this.torrentSave = torrentSave;
            IList <RawTrackerTier> announces = new RawTrackerTiers();

            if (magnetLink.AnnounceUrls != null)
            {
                announces.Add(magnetLink.AnnounceUrls);
            }
            Initialise(savePath, "", announces);
        }
예제 #52
0
        public HandshakeMessage(InfoHash infoHash, string peerId, string protocolString, bool enableFastPeer, bool enableExtended)
        {
            if (!ClientEngine.SupportsFastPeer && enableFastPeer)
            {
                throw new ProtocolException("The engine does not support fast peer, but fast peer was requested");
            }

            if (!ClientEngine.SupportsExtended && enableExtended)
            {
                throw new ProtocolException("The engine does not support extended, but extended was requested");
            }

            this.infoHash             = infoHash;
            this.peerId               = peerId;
            this.protocolString       = protocolString;
            this.protocolStringLength = protocolString.Length;
            this.supportsFastPeer     = enableFastPeer;
            this.extended             = enableExtended;
        }
예제 #53
0
 public static TorrentManager CreateManager(this InfoHash hash, StorageFolder saveFolder)
 {
     return(new TorrentManager(hash, saveFolder, new TorrentSettings(4, 150, 0, 0)
     {
         UseDht = true,
         EnablePeerExchange = true
     }, RawTrackerTier.CreateTiers(new[]
     {
         "udp://tracker.yify-torrents.com:80",
         "udp://tracker.yify-torrents.com:80",
         "udp://tracker.openbittorrent.com:80",
         "udp://tracker.publicbt.org:80",
         "udp://tracker.coppersurfer.tk:6969",
         "udp://tracker.leechers-paradise.org:6969",
         "udp://open.demonii.com:1337",
         "udp://p4p.arenabg.ch:1337",
         "udp://p4p.arenabg.com:1337"
     })));
 }
 public override void Decode(byte[] buffer, int offset, int length)
 {
     connectionId = ReadLong(buffer, ref offset);
     if (Action != ReadInt(buffer, ref offset))
     {
         ThrowInvalidActionException();
     }
     TransactionId = ReadInt(buffer, ref offset);
     infoHash      = new InfoHash(ReadBytes(buffer, ref offset, 20));
     peerId        = ReadString(buffer, ref offset, 20);
     downloaded    = ReadLong(buffer, ref offset);
     left          = ReadLong(buffer, ref offset);
     uploaded      = ReadLong(buffer, ref offset);
     torrentEvent  = (TorrentEvent)ReadInt(buffer, ref offset);
     ip            = (uint)ReadInt(buffer, ref offset);
     key           = (uint)ReadInt(buffer, ref offset);
     numWanted     = ReadInt(buffer, ref offset);
     port          = (ushort)ReadShort(buffer, ref offset);
 }
예제 #55
0
 public override void Decode(byte[] buffer, int offset, int length)
 {
     ConnectionId = ReadLong(buffer, ref offset);
     if (Action != ReadInt(buffer, ref offset))
     {
         ThrowInvalidActionException();
     }
     TransactionId = ReadInt(buffer, ref offset);
     Infohash      = new InfoHash(ReadBytes(buffer, ref offset, 20));
     PeerId        = ReadString(buffer, ref offset, 20);
     Downloaded    = ReadLong(buffer, ref offset);
     Left          = ReadLong(buffer, ref offset);
     Uploaded      = ReadLong(buffer, ref offset);
     TorrentEvent  = (TorrentEvent)ReadInt(buffer, ref offset);
     Ip            = (uint)ReadInt(buffer, ref offset);
     Key           = (uint)ReadInt(buffer, ref offset);
     NumWanted     = ReadInt(buffer, ref offset);
     Port          = (ushort)ReadShort(buffer, ref offset);
 }
예제 #56
0
        public void InfoHashTest()
        {
            MagnetLink link = new MagnetLink("magnet:?xt.1=urn:sha1:YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C");

            Assert.Equal(InfoHash.FromBase32("YNCKHTQCWBTRNJIV4WNAE52SJUQCZO5C"), link.InfoHash);

            //base32
            InfoHash initial = new InfoHash(System.Text.Encoding.ASCII.GetBytes("foobafoobafoobafooba"));

            link = new MagnetLink("magnet:?xt=urn:sha1:MZXW6YTBMZXW6YTBMZXW6YTBMZXW6YTB");
            Assert.Equal(initial, link.InfoHash);

            //base40 = hex
            InfoHash hash = Create();
            string   hex  = hash.ToHex();

            link = new MagnetLink("magnet:?xt=urn:btih:" + hex);
            Assert.Equal(hash, link.InfoHash);
        }
예제 #57
0
        /// <summary>
        /// Initializes an instance of the Torrent.Client.TrackerRequest class with the specified parameters.
        /// </summary>
        /// <param name="infoHash">The SHA1 hash of the value of the info key from the torrent metadata.</param>
        /// <param name="peerId">The Peer ID, used to uniquely identify the peer. 20 bytes.</param>
        /// <param name="port">The port at which the client is listening on. Typically 6881-6889.</param>
        /// <param name="uploaded">The total count of uploaded bytes.</param>
        /// <param name="downloaded">The total count of downloaded bytes.</param>
        /// <param name="left">The count of bytes left to download for the download to be complete.</param>
        /// <param name="compact">Whether to request a compact response by the tracker. (binary peers representation)</param>
        /// <param name="omitPeerIds">Whether to request that the tracker should omit peer IDs in the peers dictionary.</param>
        /// <param name="event">Specifies the event that caused the request. None by default.</param>
        public TrackerRequest(InfoHash infoHash, string peerId, ushort port, long uploaded, long downloaded,
                              long left, bool compact, bool omitPeerIds, EventType @event = EventType.None,
                              int? numWant = null)
        {
            Contract.Requires(infoHash != null);
            Contract.Requires(peerId != null);
            Contract.Requires(port > 0);
            Contract.Requires(uploaded >= 0);
            Contract.Requires(downloaded >= 0);
            Contract.Requires(left >= 0);

            InfoHash = infoHash;
            PeerId = peerId;
            Port = port;
            Uploaded = uploaded;
            Downloaded = downloaded;
            Left = left;
            Compact = compact;
            OmitPeerIds = omitPeerIds;
            Event = @event;
            NumWant = numWant;
        }
예제 #58
0
 public void GetPeers(InfoHash infohash)
 {
 }
예제 #59
0
파일: Torrent.cs 프로젝트: jcbarton/MUMS
            /// <summary>
            /// Creates a new InfoHash object from an array of bytes.
            /// </summary>
            /// <param name="bytes">The array of bytes used to create this object from.</param>
            /// <returns>A new InfoHash object.</returns>
            public static InfoHash FromByteArray(byte[] bytes)
            {
                InfoHash infohash = new InfoHash();
                infohash.Bytes = bytes;

                return infohash;
            }
예제 #60
0
 public void Announce(InfoHash infohash, int port)
 {
 }