public static void FindFiles(Torrent torrent, List <FileInfo> files, string destinationPath, bool copyFile, bool checkFirstOnly) { //int i = 0; for (int i = 0; i < torrent.Files.Count; i++) { LostFile fileInTorrent = torrent.Files[i]; for (int j = 0; j < files.Count; j++) { FileInfo fileOnDisk = files[j]; // Ищем файл с таким разширением if (fileOnDisk.Extension.ToLower() != Path.GetExtension(fileInTorrent.Name).ToLower()) { continue; } // Проверяем хэш if (!torrent.CheckHash(i, fileOnDisk, checkFirstOnly)) { continue; } // Все проверки пройдены. перед нами искомый файл // Перемещаем его FileInfo fileToMove = new FileInfo(destinationPath + @"\" + fileInTorrent.Name); if (!Directory.Exists(fileToMove.DirectoryName)) { Directory.CreateDirectory(fileToMove.DirectoryName); } if (!fileToMove.Exists) { if (copyFile) { File.Copy(fileOnDisk.FullName, fileToMove.FullName); } else { File.Move(fileOnDisk.FullName, fileToMove.FullName); } // И убираем из списка рассматириваемых files.Remove(fileOnDisk); // Убираем из описания торрента torrent.Files.RemoveAt(i--); break; } } } }
public bool CheckHash(int index, FileInfo fileOnDisk, bool checkFirstOnly) { LostFile checkingFile = this.Files[index]; if (checkingFile.Length < this.PieceLength * 2 - 1) { return(false); } long start = 0; long firstChunkNumber = 0; long bytesOverhead = checkingFile.BeginFrom % this.PieceLength; if (bytesOverhead == 0) { start = checkingFile.BeginFrom; firstChunkNumber = checkingFile.BeginFrom / this.PieceLength; } else { firstChunkNumber = checkingFile.BeginFrom / this.PieceLength + 1; start = firstChunkNumber * this.PieceLength - checkingFile.BeginFrom; } char[] hashInTorrent = new char[20]; // считаем хэш файла с start до finish char[] fileHash = new char[this.PieceLength]; using (BinaryReader fs = new BinaryReader(new FileStream(fileOnDisk.FullName, FileMode.Open))) { using (SHA1CryptoServiceProvider sha1 = new SHA1CryptoServiceProvider()) { byte[] piece = new byte[this.PieceLength]; fs.BaseStream.Position = start; while (fs.BaseStream.Position + this.PieceLength < checkingFile.Length) { Array.Copy(this.Hash, firstChunkNumber * 20, hashInTorrent, 0, 20); firstChunkNumber++; fs.Read(piece, 0, this.PieceLength); fileHash = Encoding.GetEncoding(437).GetString(sha1.ComputeHash(piece)).ToCharArray(); for (int i = 0; i < fileHash.Length; i++) { if (fileHash[i] != hashInTorrent[i]) { return(false); } } if (checkFirstOnly) { break; } } } } return(true); }