Пример #1
0
 public BEncodedDictionary Encode()
 {
     var dict = new BEncodedDictionary();
     dict.Add(VersionKey, (BEncodedNumber) 1);
     dict.Add(InfoHashKey, new BEncodedString(Infohash.Hash));
     dict.Add(BitfieldKey, new BEncodedString(Bitfield.ToByteArray()));
     dict.Add(BitfieldLengthKey, (BEncodedNumber) Bitfield.Length);
     return dict;
 }
Пример #2
0
 public BEncodedValue Encode()
 {
     BEncodedDictionary result = new BEncodedDictionary();
     result.Add(new BEncodedString("MaxDownloadSpeed"), new BEncodedNumber(MaxDownloadSpeed));
     result.Add(new BEncodedString("MaxUploadSpeed"), new BEncodedNumber(MaxUploadSpeed));
     result.Add(new BEncodedString("MaxConnections"), new BEncodedNumber(MaxConnections));
     result.Add(new BEncodedString("UploadSlots"), new BEncodedNumber(UploadSlots));
     result.Add(new BEncodedString("SavePath"), new BEncodedString(savePath));
     return result;
 }
Пример #3
0
 public override void Decode(byte[] buffer, int offset, int length)
 {
     peerDict = BEncodedValue.Decode<BEncodedDictionary>(buffer, offset, length, false);
     if (!peerDict.ContainsKey(AddedKey))
         peerDict.Add(AddedKey, (BEncodedString)"");
     if (!peerDict.ContainsKey(AddedDotFKey))
         peerDict.Add(AddedDotFKey, (BEncodedString)"");
     if (!peerDict.ContainsKey(DroppedKey))
         peerDict.Add(DroppedKey, (BEncodedString)"");
 }
Пример #4
0
        public BEncodedDictionary Serialize()
        {
            BEncodedDictionary d = new BEncodedDictionary ();
            d.Add ("FastResume", FastResume.Encode ());
            d.Add ("SavePath", (BEncodedString) SavePath);
            d.Add ("TorrentPath", (BEncodedString) TorrentPath);

            StringBuilder sb = new System.Text.StringBuilder();
            XmlSerializer s = new XmlSerializer (typeof (TorrentSettings));
            using (System.IO.TextWriter writer = new System.IO.StringWriter (sb))
                s.Serialize (writer, Settings);

            d.Add ("Settings", (BEncodedString) sb.ToString ());

            return d;
        }
Пример #5
0
 private BEncodedDictionary CreateInfoDict()
 {
     BEncodedDictionary dict = new BEncodedDictionary();
     dict.Add("source", new BEncodedString("http://www.thisiswhohostedit.com"));
     dict.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("this is a sha1 hash string"))));
     dict.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("ed2k isn't a sha, but who cares"))));
     dict.Add("publisher-url.utf-8", new BEncodedString("http://www.iamthepublisher.com"));
     dict.Add("publisher-url", new BEncodedString("http://www.iamthepublisher.com"));
     dict.Add("publisher.utf-8", new BEncodedString("MonoTorrent Inc."));
     dict.Add("publisher", new BEncodedString("MonoTorrent Inc."));
     dict.Add("files", CreateFiles());
     dict.Add("name.utf-8", new BEncodedString("MyBaseFolder"));
     dict.Add("name", new BEncodedString("MyBaseFolder"));
     dict.Add("piece length", new BEncodedNumber(512));
     dict.Add("private", new BEncodedString("1"));
     dict.Add("pieces", new BEncodedString(new byte[((26000 + 512) / 512) * 20])); // Total size is 26000, piecelength is 512
     return dict;
 }
Пример #6
0
        public LTMetadata(byte extensionId, eMessageType type, int piece, byte[] metadata)
            : this()
        {
            ExtensionId = extensionId;
            MetadataMessageType = type;
            MetadataPiece = metadata;
            Piece = piece;

            dict = new BEncodedDictionary();
            dict.Add(MessageTypeKey, (BEncodedNumber) (int) MetadataMessageType);
            dict.Add(PieceKey, (BEncodedNumber) piece);

            if (MetadataMessageType == eMessageType.Data)
            {
                Check.Metadata(metadata);
                dict.Add(TotalSizeKey, (BEncodedNumber) metadata.Length);
            }
        }
Пример #7
0
        public void StartUp()
        {
            DateTime current = new DateTime(2006, 7, 1, 5, 5, 5);
            DateTime epochStart = new DateTime(1970, 1, 1, 0, 0, 0);
            TimeSpan span = current - epochStart;
            creationTime = (long)span.TotalSeconds;
            Console.WriteLine(creationTime.ToString() + "Creation seconds");

            BEncodedDictionary torrentInfo = new BEncodedDictionary();
            torrentInfo.Add("announce", new BEncodedString("http://myannouceurl/announce"));
            torrentInfo.Add("creation date", new BEncodedNumber(creationTime));
            torrentInfo.Add("nodes", new BEncodedList());                    //FIXME: What is this?
            torrentInfo.Add("comment.utf-8", new BEncodedString("my big long comment"));
            torrentInfo.Add("comment", new BEncodedString("my big long comment"));
            torrentInfo.Add("azureus_properties", new BEncodedDictionary()); //FIXME: What is this?
            torrentInfo.Add("created by", new BEncodedString("MonoTorrent/" + VersionInfo.ClientVersion));
            torrentInfo.Add("encoding", new BEncodedString("UTF-8"));
            torrentInfo.Add("info", CreateInfoDict());
            torrentInfo.Add("private", new BEncodedString("1"));
            torrent = Torrent.Load(torrentInfo);
        }
Пример #8
0
        public void benDictionaryEncoding()
        {
            var data = Encoding.UTF8.GetBytes("d4:spaml1:a1:bee");

            var dict = new BEncodedDictionary();
            var list = new BEncodedList();
            list.Add(new BEncodedString("a"));
            list.Add(new BEncodedString("b"));
            dict.Add("spam", list);
            Assert.Equal(Encoding.UTF8.GetString(data), Encoding.UTF8.GetString(dict.Encode()));
            Assert.True(Toolbox.ByteMatch(data, dict.Encode()));
        }
Пример #9
0
 public void benDictionaryEncodingBuffered()
 {
     var data = Encoding.UTF8.GetBytes("d4:spaml1:a1:bee");
     var dict = new BEncodedDictionary();
     var list = new BEncodedList();
     list.Add(new BEncodedString("a"));
     list.Add(new BEncodedString("b"));
     dict.Add("spam", list);
     var result = new byte[dict.LengthInBytes()];
     dict.Encode(result, 0);
     Assert.True(Toolbox.ByteMatch(data, result));
 }
Пример #10
0
        public void benDictionaryEncoding()
        {
            byte[] data = System.Text.Encoding.UTF8.GetBytes("d4:spaml1:a1:bee");

            BEncodedDictionary dict = new BEncodedDictionary();
            BEncodedList list = new BEncodedList();
            list.Add(new BEncodedString("a"));
            list.Add(new BEncodedString("b"));
            dict.Add("spam", list);
            Assert.AreEqual(System.Text.Encoding.UTF8.GetString(data), System.Text.Encoding.UTF8.GetString(dict.Encode()));
            Assert.IsTrue(Toolbox.ByteMatch(data, dict.Encode()));
        }
Пример #11
0
        public void StartUp()
        {
            DateTime current    = new DateTime(2006, 7, 1, 5, 5, 5);
            DateTime epochStart = new DateTime(1970, 1, 1, 0, 0, 0);
            TimeSpan span       = current - epochStart;

            creationTime = (long)span.TotalSeconds;
            Console.WriteLine(creationTime.ToString() + "Creation seconds");

            BEncodedDictionary torrentInfo = new BEncodedDictionary();

            torrentInfo.Add("announce", new BEncodedString("http://myannouceurl/announce"));
            torrentInfo.Add("creation date", new BEncodedNumber(creationTime));
            torrentInfo.Add("nodes", new BEncodedList());                    //FIXME: What is this?
            torrentInfo.Add("comment.utf-8", new BEncodedString("my big long comment"));
            torrentInfo.Add("comment", new BEncodedString("my big long comment"));
            torrentInfo.Add("azureus_properties", new BEncodedDictionary()); //FIXME: What is this?
            torrentInfo.Add("created by", new BEncodedString("MonoTorrent/" + VersionInfo.ClientVersion));
            torrentInfo.Add("encoding", new BEncodedString("UTF-8"));
            torrentInfo.Add("info", CreateInfoDict());
            torrentInfo.Add("private", new BEncodedString("1"));
            torrent = Torrent.Load(torrentInfo);
        }
Пример #12
0
        internal Torrent GetTorrent()
        {
            byte[] calculatedInfoHash;
            using (SHA1 sha = HashAlgoFactory.Create<SHA1>())
                calculatedInfoHash = sha.ComputeHash(stream.ToArray());
            if (!Manager.InfoHash.Equals (calculatedInfoHash))
                throw new Exception("invalid metadata");//restart ?

            BEncodedValue d = BEncodedValue.Decode(stream);
            BEncodedDictionary dict = new BEncodedDictionary();
            dict.Add("info", d);

            return Torrent.LoadCore(dict);
        }
Пример #13
0
        private BEncodedDictionary Create()
        {
            if (!ClientEngine.SupportsExtended)
            {
                throw new MessageException("Libtorrent extension messages not supported");
            }

            BEncodedDictionary mainDict     = new BEncodedDictionary();
            BEncodedDictionary supportsDict = new BEncodedDictionary();

            mainDict.Add(MaxRequestKey, (BEncodedNumber)maxRequests);
            mainDict.Add(VersionKey, (BEncodedString)Version);
            mainDict.Add(PortKey, (BEncodedNumber)localPort);

            foreach (ExtensionSupport s in SupportedMessages)
            {
                supportsDict.Add(s.Name, (BEncodedNumber)s.MessageId);
            }
            mainDict.Add(SupportsKey, supportsDict);

            mainDict.Add(MetadataSizeKey, (BEncodedNumber)metadataSize);

            return(mainDict);
        }
Пример #14
0
        public void benDictionaryEncoding()
        {
            var data = Encoding.UTF8.GetBytes("d4:spaml1:a1:bee");

            var dict = new BEncodedDictionary();
            var list = new BEncodedList
            {
                new BEncodedString("a"),
                new BEncodedString("b")
            };

            dict.Add("spam", list);
            Assert.AreEqual(Encoding.UTF8.GetString(data), Encoding.UTF8.GetString(dict.Encode()));
            Assert.IsTrue(Toolbox.ByteMatch(data, dict.Encode()));
        }
        BEncodedDictionary Create()
        {
            if (!ClientEngine.SupportsExtended)
            {
                throw new MessageException("Libtorrent extension messages not supported");
            }

            var mainDict     = new BEncodedDictionary();
            var supportsDict = new BEncodedDictionary();

            mainDict.Add(MaxRequestKey, (BEncodedNumber)MaxRequests);
            mainDict.Add(VersionKey, (BEncodedString)Version);
            mainDict.Add(PortKey, (BEncodedNumber)LocalPort);

            SupportedMessages.ForEach(delegate(ExtensionSupport s) { supportsDict.Add(s.Name, (BEncodedNumber)s.MessageId); });
            mainDict.Add(SupportsKey, supportsDict);

            if (MetadataSize.HasValue)
            {
                mainDict.Add(MetadataSizeKey, (BEncodedNumber)MetadataSize);
            }

            return(mainDict);
        }
Пример #16
0
        public void SaveFastResume()
        {
            BEncodedDictionary dict = new BEncodedDictionary();

            foreach (TorrentManager manager in items)
            {
                dict.Add(manager.Torrent.InfoHash, manager.SaveFastResume().Encode());
            }
            try
            {
                File.WriteAllBytes(TorrentCurses.fast_resume, dict.Encode());
            }
            catch
            {
            }
        }
Пример #17
0
        /// <summary>
        /// Shuts down the download action.
        /// </summary>
        private void Shutdown()
        {
            BEncodedDictionary fastResume = new BEncodedDictionary();

            for (int i = 0; i < torrentManagers.Count; ++i)
            {
                torrentManagers[i].Stop();
                while (torrentManagers[i].State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrentManagers[i].Torrent.Name, torrentManagers[i].State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrentManagers[i].Torrent.InfoHash.ToHex(), torrentManagers[i].SaveFastResume().Encode());
            }
        }
Пример #18
0
        void ListenerReceivedScrape(object?sender, ScrapeRequest e)
        {
            if (Disposed)
            {
                e.Response.Add(TrackerRequest.FailureKey, (BEncodedString)"The tracker has been shut down");
                return;
            }

            Requests.ScrapeReceived();
            if (!AllowScrape)
            {
                e.Response.Add(TrackerRequest.FailureKey, (BEncodedString)"This tracker does not allow scraping");
                return;
            }

            if (e.InfoHashes.Count == 0)
            {
                e.Response.Add(TrackerRequest.FailureKey, (BEncodedString)"You must specify at least one infohash when scraping this tracker");
                return;
            }

            var managers = new List <ITrackerItem> ();
            var files    = new BEncodedDictionary();

            for (int i = 0; i < e.InfoHashes.Count; i++)
            {
                if (!Torrents.TryGetValue(e.InfoHashes[i], out SimpleTorrentManager? manager))
                {
                    continue;
                }

                managers.Add(manager);

                var dict = new BEncodedDictionary {
                    { "complete", new BEncodedNumber(manager.Complete) },
                    { "downloaded", new BEncodedNumber(manager.Downloaded) },
                    { "incomplete", new BEncodedNumber(manager.Incomplete) },
                    { "name", new BEncodedString(manager.Trackable.Name) }
                };
                files.Add(new BEncodedString(e.InfoHashes[i].Span.ToArray()), dict);
            }
            RaisePeerScraped(new ScrapeEventArgs(managers));
            if (files.Count > 0)
            {
                e.Response.Add("files", files);
            }
        }
Пример #19
0
        public void BenDictionaryEncodingBuffered()
        {
            var data = Encoding.UTF8.GetBytes("d4:spaml1:a1:bee");
            var dict = new BEncodedDictionary();
            var list = new BEncodedList
            {
                new BEncodedString("a"),
                new BEncodedString("b")
            };

            dict.Add("spam", list);
            var result = new byte[dict.LengthInBytes()];

            dict.Encode(result, 0);

            Assert.IsTrue(Toolbox.ByteMatch(data, result));
        }
Пример #20
0
        public void Stop()
        {
            try
            {
                BEncodedDictionary fastResume = new BEncodedDictionary();

                External.Manager.StopAsync();
                fastResume.Add(External.Manager.Torrent.InfoHash.ToHex(), External.Manager.SaveFastResume().Encode());

                File.WriteAllBytes(Settings.GetResumeFile(), fastResume.Encode());
                External.Engine.Dispose();
            }
            catch (Exception ex)
            {
                ex.ToLog(LogLevel.Error);
            }
        }
Пример #21
0
        public LTMetadata(byte extensionId, eMessageType type, int piece, byte[] metadata)
            : this()
        {
            ExtensionId         = extensionId;
            MetadataMessageType = type;
            MetadataPiece       = metadata;
            Piece = piece;

            dict = new BEncodedDictionary {
                { MessageTypeKey, (BEncodedNumber)(int)MetadataMessageType },
                { PieceKey, (BEncodedNumber)piece }
            };

            if (MetadataMessageType == eMessageType.Data)
            {
                Check.Metadata(metadata);
                dict.Add(TotalSizeKey, (BEncodedNumber)metadata.Length);
            }
        }
Пример #22
0
        ///<summary>calculate md5sum of a file</summary>
        ///<param name="fileName">the file to sum with md5</param>
        void AddMD5(BEncodedDictionary dict, string fileName)
        {
            var hasher = MD5.Create();
            var sb     = new StringBuilder();

            using (var stream = new FileStream(fileName, FileMode.Open, FileAccess.Read, FileShare.Read))
            {
                var hash = hasher.ComputeHash(stream);

                foreach (var b in hash)
                {
                    var hex = b.ToString("X");
                    hex = hex.Length > 1 ? hex : "0" + hex;
                    sb.Append(hex);
                }
                Logger.Log(null, "Sum for: '{0}' = {1}", fileName, sb.ToString());
            }
            dict.Add("md5sum", new BEncodedString(sb.ToString()));
        }
Пример #23
0
        private void ListenerReceivedScrape(object sender, ScrapeParameters e)
        {
            if (disposed)
            {
                e.Response.Add(RequestParameters.FailureKey, (BEncodedString)"The tracker has been shut down");
                return;
            }

            monitor.ScrapeReceived();
            if (!AllowScrape)
            {
                e.Response.Add(RequestParameters.FailureKey, (BEncodedString)"This tracker does not allow scraping");
                return;
            }

            if (e.InfoHashes.Count == 0)
            {
                e.Response.Add(RequestParameters.FailureKey, (BEncodedString)"You must specify at least one infohash when scraping this tracker");
                return;
            }
            List <SimpleTorrentManager> managers = new List <SimpleTorrentManager>();
            BEncodedDictionary          files    = new BEncodedDictionary();

            for (int i = 0; i < e.InfoHashes.Count; i++)
            {
                SimpleTorrentManager manager;
                if (!torrents.TryGetValue(e.InfoHashes[i], out manager))
                {
                    continue;
                }

                managers.Add(manager);

                BEncodedDictionary dict = new BEncodedDictionary();
                dict.Add("complete", new BEncodedNumber(manager.Complete));
                dict.Add("downloaded", new BEncodedNumber(manager.Downloaded));
                dict.Add("incomplete", new BEncodedNumber(manager.Incomplete));
                dict.Add("name", new BEncodedString(manager.Trackable.Name));
                files.Add(e.InfoHashes[i].ToHex(), dict);
            }
            RaisePeerScraped(new ScrapeEventArgs(managers));
            e.Response.Add("files", files);
        }
Пример #24
0
        BEncodedDictionary Create()
        {
            var mainDict     = new BEncodedDictionary();
            var supportsDict = new BEncodedDictionary();

            mainDict.Add(MaxRequestKey, (BEncodedNumber)MaxRequests);
            mainDict.Add(VersionKey, (BEncodedString)Version);
            mainDict.Add(PortKey, (BEncodedNumber)LocalPort);

            SupportedMessages.ForEach(delegate(ExtensionSupport s) { supportsDict.Add(s.Name, (BEncodedNumber)s.MessageId); });
            mainDict.Add(SupportsKey, supportsDict);

            if (MetadataSize.HasValue)
            {
                mainDict.Add(MetadataSizeKey, (BEncodedNumber)MetadataSize);
            }

            return(mainDict);
        }
        internal System.Net.BitTorrent.Common.Torrent GetTorrent()
        {
            byte[] calculatedInfoHash;
#if NETSTANDARD1_5
            using (SHA1 sha = SHA1.Create())
#else
            using (SHA1 sha = HashAlgoFactory.Create <SHA1>())
#endif
                calculatedInfoHash = sha.ComputeHash(stream.ToArray());
            if (!Manager.InfoHash.Equals(calculatedInfoHash))
            {
                throw new Exception("invalid metadata");//restart ?
            }
            BEncodedValue      d    = BEncodedValue.Decode(stream);
            BEncodedDictionary dict = new BEncodedDictionary();
            dict.Add("info", d);

            return(System.Net.BitTorrent.Common.Torrent.LoadCore(dict));
        }
Пример #26
0
        public LTMetadata(byte extensionId, eMessageType type, int piece, byte[] metadata)
            : this()
        {
            ExtensionId = extensionId;
            _messageType = type;
            MetadataPiece = metadata;
            Piece = piece;

            _dict = new BEncodedDictionary
                        {
                            {MessageTypeKey, (BEncodedNumber) (int) _messageType},
                            {PieceKey, (BEncodedNumber) piece}
                        };

            if (_messageType != eMessageType.Data)
                return;

            Check.Metadata(metadata);
            _dict.Add(TotalSizeKey, (BEncodedNumber) metadata.Length);
        }
Пример #27
0
        private BEncodedDictionary Create()
        {
            if (!ClientEngine.SupportsExtended)
            {
                throw new MessageException("Libtorrent extension messages not supported");
            }

            var mainDict     = new BEncodedDictionary();
            var supportsDict = new BEncodedDictionary();

            mainDict.Add(MaxRequestKey, (BEncodedNumber)_maxRequests);
            mainDict.Add(VersionKey, (BEncodedString)Version);
            mainDict.Add(PortKey, (BEncodedNumber)_localPort);

            SupportedMessages.ForEach(s => supportsDict.Add(s.Name, (BEncodedNumber)s.MessageId));
            mainDict.Add(SupportsKey, supportsDict);

            mainDict.Add(MetadataSizeKey, (BEncodedNumber)_metadataSize);

            return(mainDict);
        }
Пример #28
0
        private static async Task shutdown()
        {
            BEncodedDictionary fastResume = new BEncodedDictionary();

            for (int i = 0; i < torrents.Count; i++)
            {
                await torrents[i].StopAsync();;
                while (torrents[i].State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrents[i].Torrent.Name, torrents[i].State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrents[i].Torrent.InfoHash.ToHex(), torrents[i].SaveFastResume().Encode());
            }

            File.WriteAllBytes(dhtNodeFile, engine.DhtEngine.SaveNodes());
            File.WriteAllBytes(fastResumeFile, fastResume.Encode());
            engine.Dispose();

            System.Threading.Thread.Sleep(2000);
        }
Пример #29
0
        public LTMetadata(byte extensionId, MessageType type, int piece, byte[] metadata)
            : this()
        {
            ExtensionId         = extensionId;
            MetadataMessageType = type;
            MetadataPiece       = metadata;
            Piece = piece;

            dict = new BEncodedDictionary {
                { MessageTypeKey, (BEncodedNumber)(int)MetadataMessageType },
                { PieceKey, (BEncodedNumber)piece }
            };

            if (MetadataMessageType == MessageType.Data)
            {
                if (metadata is null)
                {
                    throw new InvalidDataException("The metadata data message did not contain any data.");
                }
                dict.Add(TotalSizeKey, (BEncodedNumber)metadata.Length);
            }
        }
Пример #30
0
        void Initialise(BEncodedDictionary metadata)
        {
            Metadata = metadata;

            BEncodedValue value;

            if (!Metadata.TryGetValue(AnnounceListKey, out value))
            {
                value = new BEncodedList();
                Metadata.Add(AnnounceListKey, value);
            }
            Announces = new RawTrackerTiers((BEncodedList)value);

            if (string.IsNullOrEmpty(Encoding))
            {
                Encoding = "UTF-8";
            }

            if (InfoDict == null)
            {
                InfoDict = new BEncodedDictionary();
            }
        }
Пример #31
0
        private static void shutdown()
        {
            BEncodedDictionary fastResume = new BEncodedDictionary();

            foreach (var torrentManager in torrents)
            {
                torrentManager.Stop();;
                while (torrentManager.State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrentManager.Torrent.Name, torrentManager.State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrentManager.Torrent.InfoHash.ToHex(), torrentManager.SaveFastResume().Encode());
            }

#if !DISABLE_DHT
            File.WriteAllBytes(dhtNodeFile, engine.DhtEngine.SaveNodes());
#endif
            File.WriteAllBytes(fastResumeFile, fastResume.Encode());
            engine.Dispose();

            System.Threading.Thread.Sleep(2000);
        }
Пример #32
0
        private void Shutdown()
        {
            var fastResume = new BEncodedDictionary();

            foreach (var torrentManager in Managers)
            {
                torrentManager.Stop();
                while (torrentManager.State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrentManager.Torrent.Name, torrentManager.State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrentManager.Torrent.InfoHash.ToHex(), torrentManager.SaveFastResume().Encode());
            }

//#if !DISABLE_DHT
//            File.WriteAllBytes(_dhtNodeFile, _engine.DhtEngine.SaveNodes());
//#endif
            File.WriteAllBytes(Path.Combine(Options.Client.Path, "fastresume.data"), fastResume.Encode());
            TorrentClient.Dispose();

            Thread.Sleep(2000);
        }
Пример #33
0
        private static async Task ShutdownV2()
        {
            fastResume = new BEncodedDictionary();
            foreach (var Tmanager in engine.Torrents)
            {
                var stoppingTask = Tmanager.StopAsync();
                while (Tmanager.State != TorrentState.Stopped)
                {
                    Thread.Sleep(250);
                }
                await stoppingTask;
                if (Tmanager.HashChecked)
                {
                    fastResume.Add(Tmanager.Torrent.InfoHash.ToHex(), Tmanager.SaveFastResume().Encode());
                }
            }

            var nodes = await engine.DhtEngine.SaveNodesAsync();

            File.WriteAllBytes(dhtNodeFile, nodes);
            File.WriteAllBytes(fastResumeFile, fastResume.Encode());
            engine.Dispose();
            Thread.Sleep(2000);
        }
Пример #34
0
        private BEncodedList CreateFiles()
        {
            BEncodedList files = new BEncodedList();
            BEncodedDictionary file;
            BEncodedList path;

            path = new BEncodedList();
            path.Add(new BEncodedString("file1.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(50000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("file2.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(60000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("subfolder2"));
            path.Add(new BEncodedString("file3.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(70000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("subfolder2"));
            path.Add(new BEncodedString("file4.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(80000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);

            return files;
        }
Пример #35
0
        protected override void HandleLtMetadataMessage(PeerId id, LTMetadata message)
        {
            base.HandleLtMetadataMessage(id, message);

            switch (message.MetadataMessageType)
            {
            case LTMetadata.eMessageType.Data:
                if (Stream == null)
                {
                    throw new Exception("Need extention handshake before ut_metadata message.");
                }

                Stream.Seek(message.Piece * LTMetadata.BlockSize, SeekOrigin.Begin);
                Stream.Write(message.MetadataPiece, 0, message.MetadataPiece.Length);
                bitField[message.Piece] = true;
                if (bitField.AllTrue)
                {
                    byte[] hash;
                    Stream.Position = 0;
                    using (SHA1 hasher = HashAlgoFactory.Create <SHA1> ())
                        hash = hasher.ComputeHash(Stream);

                    if (!Manager.InfoHash.Equals(hash))
                    {
                        bitField.SetAll(false);
                    }
                    else
                    {
                        Stream.Position = 0;
                        BEncodedDictionary dict = new BEncodedDictionary();
                        dict.Add("info", BEncodedValue.Decode(Stream));

                        if (Manager.TrackerManager.Tiers != null && Manager.TrackerManager.Tiers.Count > 0)
                        {
                            BEncodedList announceTrackers = new BEncodedList();
                            foreach (var tier in Manager.TrackerManager.Tiers)
                            {
                                BEncodedList announceUrls = new BEncodedList();

                                foreach (var tracker in tier.Trackers)
                                {
                                    announceUrls.Add(new BEncodedString(tracker.Uri.OriginalString));
                                }

                                announceTrackers.Add(announceUrls);
                            }

                            dict.Add("announce-list", announceTrackers);
                        }
                        if (Torrent.TryLoad(dict.Encode(), out Torrent t))
                        {
                            Manager.RaiseMetadataReceived(t, dict);
                            if (stopWhenDone)
                            {
                                return;
                            }

                            try {
                                if (Directory.Exists(savePath))
                                {
                                    savePath = Path.Combine(savePath, $"{Manager.InfoHash.ToHex ()}.torrent");
                                }
                                File.Delete(savePath);
                                File.WriteAllBytes(savePath, dict.Encode());
                            } catch (Exception ex) {
                                Logger.Log(null, "*METADATA EXCEPTION* - Can not write in {0} : {1}", savePath, ex);
                                Manager.TrySetError(Reason.WriteFailure, ex);
                                return;
                            }
                            t.TorrentPath   = savePath;
                            Manager.Torrent = t;
                            SwitchToRegular();
                        }
                        else
                        {
                            bitField.SetAll(false);
                        }
                    }
                }
                //Double test because we can change the bitfield in the other block
                if (!bitField.AllTrue)
                {
                    RequestNextNeededPiece(id);
                }
                break;

            case LTMetadata.eMessageType.Reject:
                //TODO
                //Think to what we do in this situation
                //for moment nothing ;)
                //reject or flood?
                break;

            case LTMetadata.eMessageType.Request:    //ever done in base class but needed to avoid default
                break;

            default:
                throw new MessageException($"Invalid messagetype in LTMetadata: {message.MetadataMessageType}");
            }
        }
Пример #36
0
        /// <summary>
        /// 处理 Tracker 请求的方法。
        /// </summary>
        /// <param name="processor">为此请求生成的 <see cref="Kei.KTracker.HttpProcessor"/> 对象。</param>
        /// <param name="ioStream"><see cref="Kei.KTracker.HttpProcessor"/> 为此请求开启的 <see cref="System.IO.Stream"/>。</param>
        /// <param name="parameters">URL 请求参数。</param>
        private void HandleTrackerRequest(HttpProcessor processor, Stream ioStream, string parameters)
        {
            // parameters 传入类似 info_hash=XXXX&port=XXXX&ipv6=XXXX 的形式
            var args = Utilities.DecomposeParameterString(parameters);

            Logger.Log("[Tracker]请求: " + processor.RequestUrl);

            try
            {
                Logger.Log("[Tracker]解码收到的参数。");
                // 先解码处理各种参数(注意可能会引发异常)
                string     infoHashString = Utilities.UnescapePartialUriEncodedString(args["info_hash"]);
                InfoHash   infoHash       = InfoHash.FromHexString(infoHashString);
                int        portNo         = Convert.ToInt32(args["port"]);
                TaskStatus taskStatus;
                if (args.ContainsKey("event"))
                {
                    switch (args["event"])
                    {
                    case "started":
                        taskStatus = TaskStatus.Started;
                        break;

                    case "stopped":
                        taskStatus = TaskStatus.Stopped;
                        break;

                    case "paused":
                        taskStatus = TaskStatus.Paused;
                        break;

                    default:
                        taskStatus = TaskStatus.None;
                        break;
                    }
                }
                else
                {
                    taskStatus = TaskStatus.None;
                }
                bool compact;
                if (args.ContainsKey("compact"))
                {
                    var n = Convert.ToInt32(args["compact"]);
                    compact = n != 0;
                }
                else
                {
                    compact = false;
                }
                bool noPeerID;
                if (args.ContainsKey("no_peer_id"))
                {
                    var n = Convert.ToInt32(args["no_peer_id"]);
                    noPeerID = n != 0;
                }
                else
                {
                    noPeerID = false;
                }
                var peerIDString = Utilities.UnescapePartialUriEncodedString(args["peer_id"]);

                // 别忘了重新确认自己
                IPEndPoint newMyself = new IPEndPoint(LocalEndPoint.Address, portNo);
                Logger.Log("[Tracker]新的自己(BitTorrent 客户端): " + newMyself.ToString());
                SetMyself(newMyself, peerIDString);

                List <Peer>          peers = null;
                TrackerCommEventArgs eventArgs;

                // 如果接入分布网络完成
                if (FreeToGo)
                {
                    // 触发事件,得到新的可用用户列表
                    if (Seeds.TryGetValue(infoHash, out peers))
                    {
                        peers = Seeds[infoHash];
                        if (peers.IndexOf(_myself) < 0)
                        {
                            // 如果之前我不在种子列表中
                            // TODO: 添加 myself
                            peers.Add(_myself);
                            // 而且此时确认为自己加入网络,强制设定 event=started
                            taskStatus = TaskStatus.Started;
                        }
                    }
                    else
                    {
                        // 如果之前没有相关种子
                        peers = new List <Peer>();
                        // TODO: 添加 myself
                        peers.Add(_myself);
                        Seeds.Add(infoHash, peers);
                        // 而且此时确认为自己加入网络,强制设定 event=started
                        taskStatus = TaskStatus.Started;
                    }
                }
                eventArgs = new TrackerCommEventArgs(infoHash, peers, portNo, peerIDString, compact, noPeerID, taskStatus);
                EventHelper.RaiseEventAsync(TrackerComm, this, eventArgs);
                //if (eventArgs.Peers == null)
                //{
                //    throw new NullReferenceException("Peers list is null");
                //}
                if (eventArgs.Peers != null)
                {
                    peers = eventArgs.Peers;
                }

                // 生成返回给 μTorrent 的信息
                Logger.Log("[Tracker]反馈给 BitTorrent 客户端。");
                if (peers != null)
                {
                    string peersListString = "[Tracker]种子 " + infoHash.ToString() + " 的用户列表如下:";
                    foreach (var p in peers)
                    {
                        peersListString += Environment.NewLine + p.EndPoint.ToString();
                    }
                    Logger.Log(peersListString);
                }
                else
                {
                    Logger.Log("[Tracker]种子 " + infoHash.ToString() + " 的用户列表为空。");
                }
                BEncodedDictionary data = new BEncodedDictionary();
                data.Add("interval", 60);
                if (peers != null)
                {
                    // 如果种子列表里有种子
                    // 为了防止其他线程修改这个 list 导致迭代器失效,先锁定这个对象
                    lock (peers)
                    {
                        if (compact)
                        {
                            // 生成字节数组
                            byte[] peersArray = new byte[peers.Count * 6];
                            byte[] tmp;
                            int    i = 0;
                            foreach (var peer in peers)
                            {
                                tmp = peer.ToByteArray();
                                Array.Copy(tmp, 0, peersArray, i * 6, 6);
                                i++;
                            }
                            data.Add("peers", peersArray);
                        }
                        else
                        {
                            // 生成列表
                            BEncodedList peersList = new BEncodedList(peers.Count);
                            foreach (var peer in peers)
                            {
                                BEncodedDictionary peerDict = new BEncodedDictionary();
                                peerDict.Add("id", peer.ID);
                                peerDict.Add("ip", peer.EndPoint.GetAddressString());
                                peerDict.Add("port", peer.EndPoint.GetPortNumber());
                                peersList.Add(peerDict);
                            }
                            data.Add("peers", peersList);
                        }
                    }
                    data.Add("complete", peers.Count);
                }
                else
                {
                    // 如果没有种子,就返回空列表
                    data.Add("peers", string.Empty);
                }

                // 输出
                Logger.Log("[Tracker]写入“成功”头。");
                processor.WriteSuccess(null, "text/plain");
                Logger.Log("[Tracker]编码返回数据。");
                var dataBytes = data.Encode();
                Logger.Log("[Tracker]写入返回数据。");
                ioStream.Write(dataBytes, 0, dataBytes.Length);
                Logger.Log("[Tracker]向 BitTorrent 客户端返回了: " + Encoding.ASCII.GetString(dataBytes));
                ioStream.Flush();
            }
            catch (Exception ex)
            {
                Logger.Log(ex.Message + Environment.NewLine + ex.StackTrace);
                processor.WriteFailure();
                ioStream.WriteLine(ex.Message);
                ioStream.WriteLine(ex.StackTrace);
            }
        }
Пример #37
0
        public static void Process(string inputFilename, BEncodedDictionary torrent)
        {
            bool successful               = false;
            bool isFgbtTorrent            = false;
            BEncodedDictionary newTorrent = new BEncodedDictionary();

            TryReadKeiGuiConfig();

            if (true && !string.IsNullOrEmpty(inputFilename) && torrent != null)
            {
                FileInfo fi = new FileInfo(inputFilename);
                // 先判断是否是未来花园的种子
                if (fi.Name.StartsWith("[FGBT]."))
                {
                    try
                    {
                        var sourceString = ((torrent["info"] as BEncodedDictionary)["source"] as BEncodedString).Text;
                        if (sourceString.StartsWith("FGBT-"))
                        {
                            // 是原来的未来花园的种子
                            isFgbtTorrent = true;
                        }
                    }
                    catch (Exception)
                    {
                    }
                }

                var kt             = new TrackerServer(new IPEndPoint(IPAddress.Loopback, 10000));
                var announceString = "http://localhost:" + kgOptions.LocalTrackerServerPort.ToString() + kt.AnnouceUrl.TrimEnd('?');

                try
                {
                    newTorrent.Add("announce", announceString);
                    newTorrent.Add("announce-list", new BEncodedList()
                    {
                        new BEncodedList()
                        {
                            announceString,
                        }
                    });
                    newTorrent.Add("created by", (torrent["created by"] as BEncodedString).Text);
                    newTorrent.Add("creation date", (torrent["creation date"] as BEncodedNumber).Number);
                    // 遵循花园的原则,不转码,直接设置编码为 UTF-8
                    newTorrent.Add("encoding", "UTF-8");

                    var info = new BEncodedDictionary();
                    if (isFgbtTorrent)
                    {
                        foreach (var item in (torrent["info"] as BEncodedDictionary))
                        {
                            info.Add(item);
                        }
                    }
                    else
                    {
                        if ((torrent["info"] as BEncodedDictionary).ContainsKey("files"))
                        {
                            // 单文件的种子是没有 files 项的
                            info.Add("files", (torrent["info"] as BEncodedDictionary)["files"]);
                        }
                        else
                        {
                            // 单文件的种子有 length 项
                            info.Add("length", (torrent["info"] as BEncodedDictionary)["length"]);
                        }
                        info.Add("name", (torrent["info"] as BEncodedDictionary)["name"]);
                        info.Add("piece length", (torrent["info"] as BEncodedDictionary)["piece length"]);
                        info.Add("pieces", (torrent["info"] as BEncodedDictionary)["pieces"]);
                        info.Add("private", 1);

                        // 至于 source 呢,要经过编码……
                        var origInfo     = torrent["info"].Encode();
                        var sha1         = SHA1.Create();
                        var origInfoHash = sha1.ComputeHash(origInfo);
                        sha1.Dispose();
                        var origInfoHashString = BitConverter.ToString(origInfoHash);
                        origInfoHashString = new string(origInfoHashString.Where((c) => c != '-').ToArray());
                        info.Add("source", "KS-" + origInfoHashString);
                    }

                    newTorrent.Add("info", info);
                    successful = true;
                }
                catch (Exception)
                {
                    successful = false;
                }
                kt = null;
            }

            if (successful)
            {
                var fi      = new FileInfo(inputFilename);
                var newName = Path.Combine(fi.DirectoryName, "[KS]." + fi.Name);
                // 命令行状态下不提示
                //if (File.Exists(newName))
                //{
                //    var dresult = MessageBox.Show("已存在 " + newName + ",是否覆盖?", Application.ProductName, MessageBoxButtons.YesNo, MessageBoxIcon.Exclamation);
                //    if (dresult == DialogResult.No)
                //    {
                //        return;
                //    }
                //}
                try
                {
                    using (var fs = new FileStream(newName, FileMode.OpenOrCreate, FileAccess.Write))
                    {
                        var buf = newTorrent.Encode();
                        fs.Write(buf, 0, buf.Length);
                    }
                    Console.WriteLine("成功保存到 " + newName + "。");
                }
                catch (Exception ex)
                {
                    Console.WriteLine("无法写入 " + newName + ": " + ex.Message);
                }
            }
            else
            {
                Console.WriteLine("尝试生成并保存种子失败。");
            }
        }
        internal Torrent GetTorrent()
        {
            byte[] calculatedInfoHash;
            using (SHA1 sha = HashAlgoFactory.Create<SHA1>())
                calculatedInfoHash = sha.ComputeHash(stream.ToArray());
            if (!Manager.InfoHash.Equals (calculatedInfoHash))
                throw new Exception("invalid metadata");//restart ?

            BEncodedValue d = BEncodedValue.Decode(stream);
            BEncodedDictionary dict = new BEncodedDictionary();
            dict.Add("info", d);

            return Torrent.LoadCore(dict);
        }
Пример #39
0
        public void DecodeDictionary()
        {
            var list = new BEncodedList();
            foreach (var p in peers)
            {
                var dict = new BEncodedDictionary();
                dict.Add("ip", (BEncodedString) p.ConnectionUri.Host);
                dict.Add("port", (BEncodedNumber) p.ConnectionUri.Port);
                dict.Add("peer id", (BEncodedString) p.PeerId);
                list.Add(dict);
            }

            VerifyDecodedPeers(Peer.Decode(list));
        }
Пример #40
0
        protected override void HandleLtMetadataMessage(PeerId id, LTMetadata message)
        {
            base.HandleLtMetadataMessage(id, message);

            switch (message.MetadataMessageType)
            {
            case LTMetadata.eMessageType.Data:
                if (stream == null)
                {
                    throw new Exception("Need extention handshake before ut_metadata message.");
                }

                stream.Seek(message.Piece * LTMetadata.BlockSize, SeekOrigin.Begin);
                stream.Write(message.MetadataPiece, 0, message.MetadataPiece.Length);
                bitField[message.Piece] = true;
                if (bitField.AllTrue)
                {
                    byte[] hash;
                    stream.Position = 0;
                    using (SHA1 hasher = HashAlgoFactory.Create <SHA1>())
                        hash = hasher.ComputeHash(stream);

                    if (!Manager.InfoHash.Equals(hash))
                    {
                        bitField.SetAll(false);
                    }
                    else
                    {
                        Torrent t;
                        stream.Position = 0;
                        BEncodedDictionary dict = new BEncodedDictionary();
                        dict.Add("info", BEncodedValue.Decode(stream));
                        // FIXME: Add the trackers too
                        if (Torrent.TryLoad(dict.Encode(), out t))
                        {
                            try
                            {
                                if (Directory.Exists(savePath))
                                {
                                    savePath = Path.Combine(savePath, Manager.InfoHash.ToHex() + ".torrent");
                                }
                                File.Delete(savePath);
                                File.WriteAllBytes(savePath, dict.Encode());
                            }
                            catch (Exception ex)
                            {
                                Logger.Log(null, "*METADATA EXCEPTION* - Can not write in {0} : {1}", savePath, ex);
                                Manager.Error = new Error(Reason.WriteFailure, ex);
                                Manager.Mode  = new ErrorMode(Manager);
                                return;
                            }
                            t.TorrentPath   = savePath;
                            Manager.Torrent = t;
                            SwitchToRegular();
                        }
                        else
                        {
                            bitField.SetAll(false);
                        }
                    }
                }
                //Double test because we can change the bitfield in the other block
                if (!bitField.AllTrue)
                {
                    RequestNextNeededPiece(id);
                }
                break;

            case LTMetadata.eMessageType.Reject:
                //TODO
                //Think to what we do in this situation
                //for moment nothing ;)
                //reject or flood?
                break;

            case LTMetadata.eMessageType.Request:    //ever done in base class but needed to avoid default
                break;

            default:
                throw new MessageException(string.Format("Invalid messagetype in LTMetadata: {0}", message.MetadataMessageType));
            }
        }
Пример #41
0
 /// <summary>
 /// Adds a custom value to the main bencoded dictionary
 /// </summary>
 public void AddCustom(BEncodedString key, BEncodedValue value)
 {
     dict.Add(key, value);
 }
		///<summary>
		///this adds stuff common to single and multi file torrents
		///</summary>
		void AddCommonStuff(BEncodedDictionary torrent)
		{
			if (announces.Count > 0 && announces[0].Count > 0) torrent.Add("announce", new BEncodedString(announces[0][0]));

			// If there is more than one tier or the first tier has more than 1 tracker
			if (announces.Count > 1 || (announces.Count > 0 && announces[0].Count > 1))
			{
				var announceList = new BEncodedList();
				for (var i = 0; i < announces.Count; i++)
				{
					var tier = new BEncodedList();
					for (var j = 0; j < announces[i].Count; j++) tier.Add(new BEncodedString(announces[i][j]));

					announceList.Add(tier);
				}

				torrent.Add("announce-list", announceList);
			}

			var epocheStart = new DateTime(1970, 1, 1);
			var span = DateTime.Now - epocheStart;
			Logger.Log(null, "creation date: {0} - {1} = {2}:{3}", DateTime.Now, epocheStart, span, span.TotalSeconds);
			torrent.Add("creation date", new BEncodedNumber((long)span.TotalSeconds));
		}
Пример #43
0
        private BEncodedDictionary CreateInfoDict()
        {
            BEncodedDictionary dict = new BEncodedDictionary();

            dict.Add("source", new BEncodedString("http://www.thisiswhohostedit.com"));
            dict.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("this is a sha1 hash string"))));
            dict.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("ed2k isn't a sha, but who cares"))));
            dict.Add("publisher-url.utf-8", new BEncodedString("http://www.iamthepublisher.com"));
            dict.Add("publisher-url", new BEncodedString("http://www.iamthepublisher.com"));
            dict.Add("publisher.utf-8", new BEncodedString("MonoTorrent Inc."));
            dict.Add("publisher", new BEncodedString("MonoTorrent Inc."));
            dict.Add("files", CreateFiles());
            dict.Add("name.utf-8", new BEncodedString("MyBaseFolder"));
            dict.Add("name", new BEncodedString("MyBaseFolder"));
            dict.Add("piece length", new BEncodedNumber(512));
            dict.Add("private", new BEncodedString("1"));
            dict.Add("pieces", new BEncodedString(new byte[((26000 + 512) / 512) * 20])); // Total size is 26000, piecelength is 512
            return(dict);
        }
		///<summary>
		///this method is used for multi file mode torrents to return a dictionary with
		///file relevant informations. 
		///<param name="file">the file to report the informations for</param>
		///<param name="basePath">used to subtract the absolut path information</param>
		///</summary>
		BEncodedDictionary GetFileInfoDict(TorrentFile file)
		{
			var fileDict = new BEncodedDictionary();

			fileDict.Add("length", new BEncodedNumber(file.Length));

			var filePath = new BEncodedList();
			var splittetPath = file.Path.Split(System.IO.Path.DirectorySeparatorChar);

			foreach (var s in splittetPath)
			{
				if (s.Length > 0) //exclude empties
					filePath.Add(new BEncodedString(s));
			}

			fileDict.Add("path", filePath);

			return fileDict;
		}
Пример #45
0
        private static void Shutdown()
        {
            var fastResume = new BEncodedDictionary();
            foreach (var torrentManager in torrents)
            {
                torrentManager.Stop();
                while (torrentManager.State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrentManager.Torrent.Name, torrentManager.State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrentManager.Torrent.InfoHash.ToHex (), torrentManager.SaveFastResume().Encode());
            }

            #if !DISABLE_DHT
            File.WriteAllBytes(_dhtNodeFile, _engine.DhtEngine.SaveNodes());
            #endif
            File.WriteAllBytes(_fastResumeFile, fastResume.Encode());
            _engine.Dispose();

            foreach (TraceListener lst in Debug.Listeners)
            {
                lst.Flush();
                lst.Close();
            }

            Thread.Sleep(2000);
        }
        protected override void HandleLtMetadataMessage(PeerId id, LTMetadata message)
        {
            base.HandleLtMetadataMessage(id, message);

            switch (message.MetadataMessageType)
            {
                case LTMetadata.eMessageType.Data:
                    if (stream == null)
                        throw new Exception("Need extention handshake before ut_metadata message.");

                    stream.Seek(message.Piece * LTMetadata.BlockSize, SeekOrigin.Begin);
                    stream.Write(message.MetadataPiece, 0, message.MetadataPiece.Length);
                    bitField[message.Piece] = true;
                    if (bitField.AllTrue)
                    {
                        byte[] hash;
                        stream.Position = 0;
                        using (SHA1 hasher = HashAlgoFactory.Create<SHA1>())
                            hash = hasher.ComputeHash(stream);

                        if (!Manager.InfoHash.Equals (hash))
                        {
                            bitField.SetAll(false);
                        }
                        else
                        {
                            Torrent t;
                            stream.Position = 0;
                            BEncodedDictionary dict = new BEncodedDictionary();
                            dict.Add ("info", BEncodedValue.Decode(stream));
                            // FIXME: Add the trackers too
                            if (Torrent.TryLoad(dict.Encode (), out t))
                            {
                                try
                                {
                                    if (Directory.Exists(savePath))
                                        savePath = Path.Combine (savePath, Manager.InfoHash.ToHex() + ".torrent");
                                    File.WriteAllBytes(savePath, dict.Encode ());
                                }
                                catch (Exception ex)
                                {
                                    Logger.Log(null, "*METADATA EXCEPTION* - Can not write in {0} : {1}", savePath, ex);
                                    Manager.Error = new Error (Reason.WriteFailure, ex);
                                    Manager.Mode = new ErrorMode(Manager);
                                    return;
                                }
                                t.TorrentPath = savePath;
                                Manager.Torrent = t;
                                SwitchToRegular();
                            }
                            else
                            {
                                bitField.SetAll(false);
                            }
                        }
                    }
                    //Double test because we can change the bitfield in the other block
                    if (!bitField.AllTrue)
                    {
                        RequestNextNeededPiece(id);
                    }
                    break;
                case LTMetadata.eMessageType.Reject:
                    //TODO
                    //Think to what we do in this situation
                    //for moment nothing ;)
                    //reject or flood?
                    break;
                case LTMetadata.eMessageType.Request://ever done in base class but needed to avoid default
                    break;
                default:
                    throw new MessageException(string.Format("Invalid messagetype in LTMetadata: {0}", message.MetadataMessageType));
            }
        }
Пример #47
0
        protected override void HandleLtMetadataMessage(PeerId id, LTMetadata message)
        {
            base.HandleLtMetadataMessage(id, message);

            switch (message.MetadataMessageType)
            {
            case LTMetadata.eMessageType.Data:
                // If we've already received everything successfully, do nothing!
                if (bitField.AllTrue)
                {
                    return;
                }

                if (Stream == null)
                {
                    throw new Exception("Need extention handshake before ut_metadata message.");
                }

                Stream.Seek(message.Piece * LTMetadata.BlockSize, SeekOrigin.Begin);
                Stream.Write(message.MetadataPiece, 0, message.MetadataPiece.Length);
                bitField[message.Piece] = true;
                if (bitField.AllTrue)
                {
                    byte[] hash;
                    Stream.Position = 0;
                    using (SHA1 hasher = HashAlgoFactory.SHA1())
                        hash = hasher.ComputeHash(Stream);

                    if (!Manager.InfoHash.Equals(hash))
                    {
                        bitField.SetAll(false);
                    }
                    else
                    {
                        Stream.Position = 0;
                        BEncodedDictionary dict = new BEncodedDictionary();
                        dict.Add("info", BEncodedValue.Decode(Stream));

                        if (Manager.TrackerManager.Tiers != null && Manager.TrackerManager.Tiers.Count > 0)
                        {
                            BEncodedList announceTrackers = new BEncodedList();
                            foreach (var tier in Manager.TrackerManager.Tiers)
                            {
                                BEncodedList announceUrls = new BEncodedList();

                                foreach (var tracker in tier.Trackers)
                                {
                                    announceUrls.Add(new BEncodedString(tracker.Uri.OriginalString));
                                }

                                announceTrackers.Add(announceUrls);
                            }

                            dict.Add("announce-list", announceTrackers);
                        }
                        var rawData = dict.Encode();
                        if (Torrent.TryLoad(rawData, out Torrent t))
                        {
                            if (stopWhenDone)
                            {
                                Manager.RaiseMetadataReceived(rawData);
                                return;
                            }

                            try {
                                if (this.Settings.AutoSaveLoadMagnetLinkMetadata)
                                {
                                    if (!Directory.Exists(Path.GetDirectoryName(savePath)))
                                    {
                                        Directory.CreateDirectory(Path.GetDirectoryName(savePath));
                                    }
                                    File.Delete(savePath);
                                    File.WriteAllBytes(savePath, dict.Encode());
                                }
                            } catch (Exception ex) {
                                logger.ExceptionFormated(ex, "Cannot write metadata to path '{0}'", savePath);
                                Manager.TrySetError(Reason.WriteFailure, ex);
                                return;
                            }
                            Manager.SetMetadata(t);
                            _ = Manager.StartAsync();
                            Manager.RaiseMetadataReceived(rawData);
                        }
                        else
                        {
                            bitField.SetAll(false);
                        }
                    }
                }
                RequestNextNeededPiece(id);
                break;

            case LTMetadata.eMessageType.Reject:
                //TODO
                //Think to what we do in this situation
                //for moment nothing ;)
                //reject or flood?
                break;

            case LTMetadata.eMessageType.Request:    //ever done in base class but needed to avoid default
                break;

            default:
                throw new MessageException($"Invalid messagetype in LTMetadata: {message.MetadataMessageType}");
            }
        }
Пример #48
0
        /// <summary>
        /// Retrieves a semi-random list of peers which can be used to fulfill an Announce request
        /// </summary>
        /// <param name="response">The bencoded dictionary to add the peers to</param>
        /// <param name="count">The number of peers to add</param>
        /// <param name="compact">True if the peers should be in compact form</param>
        /// <param name="exlude">The peer to exclude from the list</param>
        internal void GetPeers(BEncodedDictionary response, int count, bool compact)
        {
            byte[] compactResponse = null;
            BEncodedList nonCompactResponse = null;

            int total = Math.Min(peers.Count, count);
            // If we have a compact response, we need to create a single BencodedString
            // Otherwise we need to create a bencoded list of dictionaries
            if (compact)
                compactResponse = new byte[total * 6];
            else
                nonCompactResponse = new BEncodedList(total);

            int start = random.Next(0, peers.Count);

            lock (buffer)
            {
                if (buffer.Count != peers.Values.Count)
                    buffer = new List<Peer>(peers.Values);
            }
            List<Peer> p = buffer;

            while (total > 0)
            {
                Peer current = p[(start++) % p.Count];
                if (compact)
                {
                    Buffer.BlockCopy(current.CompactEntry, 0, compactResponse, (total - 1) * 6, 6);
                }
                else
                {
                    nonCompactResponse.Add(current.NonCompactEntry);
                }
                total--;
            }

            if (compact)
                response.Add(Tracker.PeersKey, (BEncodedString)compactResponse);
            else
                response.Add(Tracker.PeersKey, nonCompactResponse);
        }
Пример #49
0
 BEncodedDictionary Create(string key, string value)
 {
     var d = new BEncodedDictionary ();
     d.Add (key, (BEncodedString) value);
     return d;
 }
        private void Initialise(BEncodedDictionary metadata)
        {
            Metadata = metadata;

            BEncodedValue value;
            if (!Metadata.TryGetValue(AnnounceListKey, out value))
            {
                value = new BEncodedList();
                Metadata.Add(AnnounceListKey, value);
            }
            Announces = new RawTrackerTiers((BEncodedList) value);

            if (string.IsNullOrEmpty(Encoding))
                Encoding = "UTF-8";

            if (InfoDict == null)
                InfoDict = new BEncodedDictionary();
        }
		public TorrentCreator()
		{
			var info = new BEncodedDictionary();
			announces = new List<List<string>>();
			ignoreHiddenFiles = true;
			dict = new BEncodedDictionary();
			dict.Add("info", info);

			// Add in initial values for some of the torrent attributes
			PieceLength = 256*1024; // 256kB default piece size
			Encoding = "UTF-8";
		}
        private BEncodedDictionary Create()
        {
            if (!ClientEngine.SupportsExtended)
                throw new MessageException("Libtorrent extension messages not supported");

            var mainDict = new BEncodedDictionary();
            var supportsDict = new BEncodedDictionary();

            mainDict.Add(MaxRequestKey, (BEncodedNumber) MaxRequests);
            mainDict.Add(VersionKey, (BEncodedString) Version);
            mainDict.Add(PortKey, (BEncodedNumber) LocalPort);

            SupportedMessages.ForEach(
                delegate(ExtensionSupport s) { supportsDict.Add(s.Name, (BEncodedNumber) s.MessageId); });
            mainDict.Add(SupportsKey, supportsDict);

            mainDict.Add(MetadataSizeKey, (BEncodedNumber) MetadataSize);

            return mainDict;
        }
		///<summary>calculate md5sum of a file</summary>
		///<param name="fileName">the file to sum with md5</param>
		void AddMD5(BEncodedDictionary dict, string fileName)
		{
			var hasher = MD5.Create();
			var sb = new StringBuilder();

			using (var stream = new FileStream(fileName, FileMode.Open, FileAccess.Read, FileShare.Read))
			{
				var hash = hasher.ComputeHash(stream);

				foreach (var b in hash)
				{
					var hex = b.ToString("X");
					hex = hex.Length > 1 ? hex : "0" + hex;
					sb.Append(hex);
				}
				Logger.Log(null, "Sum for: '{0}' = {1}", fileName, sb.ToString());
			}
			dict.Add("md5sum", new BEncodedString(sb.ToString()));
		}
Пример #54
0
        private static void shutdown()
        {
            BEncodedDictionary fastResume = new BEncodedDictionary();
            for (int i = 0; i < torrents.Count; i++)
            {
                WaitHandle handle = torrents[i].Stop(); ;
                while (!handle.WaitOne(10, true))
                    Console.WriteLine(handle.ToString());

                Console.WriteLine(handle.ToString());
                fastResume.Add(torrents[i].Torrent.InfoHash, torrents[i].SaveFastResume().Encode());
            }

            File.WriteAllBytes(dhtNodeFile, engine.DhtEngine.SaveNodes());
            File.WriteAllBytes(fastResumeFile, fastResume.Encode());
            engine.Dispose();

            foreach (TraceListener lst in Debug.Listeners)
            {
                lst.Flush();
                lst.Close();
            }

            System.Threading.Thread.Sleep(2000);
        }
		static void Set(BEncodedDictionary dictionary, BEncodedString key, BEncodedValue value)
		{
			if (dictionary.ContainsKey(key)) dictionary[key] = value;
			else dictionary.Add(key, value);
		}
Пример #56
0
		public void SaveFastResume ()
		{
			
			BEncodedDictionary dict = new BEncodedDictionary();
			foreach (TorrentManager manager in items)
				dict.Add (manager.Torrent.InfoHash, manager.SaveFastResume ().Encode ());
			try
			{
				File.WriteAllBytes (TorrentCurses.fast_resume, dict.Encode ());
			}
			catch
			{
			}
		}
Пример #57
0
        private BEncodedList CreateFiles()
        {
            BEncodedList       files = new BEncodedList();
            BEncodedDictionary file;
            BEncodedList       path;

            path = new BEncodedList();
            path.Add(new BEncodedString("file1.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(50000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("file2.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(60000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("subfolder2"));
            path.Add(new BEncodedString("file3.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(70000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);


            path = new BEncodedList();
            path.Add(new BEncodedString("subfolder1"));
            path.Add(new BEncodedString("subfolder2"));
            path.Add(new BEncodedString("file4.txt"));

            file = new BEncodedDictionary();
            file.Add("sha1", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash1"))));
            file.Add("ed2k", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash2"))));
            file.Add("length", new BEncodedNumber(80000));
            file.Add("md5sum", new BEncodedString(sha.ComputeHash(System.Text.Encoding.UTF8.GetBytes("file1 hash3"))));
            file.Add("path.utf-8", path);
            file.Add("path", path);

            files.Add(file);

            return(files);
        }
Пример #58
0
 private void WindowClosed(object sender, EventArgs e)
 {
     if (SettingsManager.SaveSession)
     {
         var resume = new BEncodedDictionary();
         var serializer = new JsonSerializer();
         foreach (var torrent in Client.Torrents)
         {
             torrent.Torrent.Stop();
             var start = DateTime.Now;
             while (torrent.Torrent.State != TorrentState.Stopped && torrent.Torrent.State != TorrentState.Error &&
                 (DateTime.Now - start).TotalSeconds < 2) // Time limit for trying to let it stop on its own
                 Thread.Sleep(100);
             torrent.UpdateInfo();
             using (var writer = new StreamWriter(Path.Combine(SettingsManager.TorrentCachePath,
                 Path.GetFileNameWithoutExtension(torrent.CacheFilePath) + ".info")))
                 serializer.Serialize(new JsonTextWriter(writer), torrent.TorrentInfo);
             // TODO: Notify users on error? The application is shutting down here, it wouldn't be particualry
             // easy to get information to the user
             resume.Add(torrent.Torrent.InfoHash.ToHex(), torrent.Torrent.SaveFastResume().Encode());
         }
         File.WriteAllBytes(SettingsManager.FastResumePath, resume.Encode());
     }
     SettingsManager.WindowWidth = (int)Width;
     SettingsManager.WindowHeight = (int)Height;
     SaveSettings();
     Client.Shutdown();
 }
Пример #59
0
        private static void shutdown()
        {
            BEncodedDictionary fastResume = new BEncodedDictionary();
            for (int i = 0; i < torrents.Count; i++)
            {
                torrents[i].Stop(); ;
                while (torrents[i].State != TorrentState.Stopped)
                {
                    Console.WriteLine("{0} is {1}", torrents[i].Torrent.Name, torrents[i].State);
                    Thread.Sleep(250);
                }

                fastResume.Add(torrents[i].Torrent.InfoHash.ToHex (), torrents[i].SaveFastResume().Encode());
            }

            #if !DISABLE_DHT
            File.WriteAllBytes(dhtNodeFile, engine.DhtEngine.SaveNodes());
            #endif
            File.WriteAllBytes(fastResumeFile, fastResume.Encode());
            engine.Dispose();

            foreach (TraceListener lst in Debug.Listeners)
            {
                lst.Flush();
                lst.Close();
            }

            System.Threading.Thread.Sleep(2000);
        }
Пример #60
0
        ///<summary>
        ///this method is used for multi file mode torrents to return a dictionary with
        ///file relevant informations. 
        ///<param name="file">the file to report the informations for</param>
        ///<param name="basePath">used to subtract the absolut path information</param>
        ///</summary>
        private BEncodedDictionary GetFileInfoDict(TorrentFile file)
        {
            BEncodedDictionary fileDict = new BEncodedDictionary();

            fileDict.Add("length", new BEncodedNumber(file.Length));

            #warning Implement this again
            //if (StoreMD5)
                //AddMD5(fileDict, file);

            Logger.Log(null, "Without base: {0}", file.Path);
            BEncodedList filePath = new BEncodedList();
            string[] splittetPath = file.Path.Split(System.IO.Path.DirectorySeparatorChar);

            foreach (string s in splittetPath)
            {
                if (s.Length > 0)//exclude empties
                    filePath.Add(new BEncodedString(s));
            }

            fileDict.Add("path", filePath);

            return fileDict;
        }