BitTorrent磁铁链是如何工作的?

我第一次使用磁铁链。好奇它是如何工作的,我查了一下规格,没有找到任何答案。Wiki显示xt表示“确切主题”,后面是带有SHA1哈希的格式(本例中为btih)。我看到上面提到的Base32,知道它是每个字符5位和32个字符,我发现它正好可以容纳160位,这正好是SHA1的大小。

没有IP地址或任何东西的空间,它只是一个SHA1。那么BitTorrent客户端如何找到实际的文件呢?我打开了URL Snooper来查看它是否访问页面(使用TCP)或执行查找之类的操作,但什么也没有发生。我不知道客户如何找到同行。这是如何工作的?

还有,哈希是什么?它是所有文件哈希一起的数组的哈希吗?也许它是所需的实际Torrent文件的哈希(剥离某些信息)?


在虚拟机中,我尝试使用uTorrent(新安装的)的磁铁链接,它设法找到了对等点。第一个同行从哪里来?它是新鲜的,没有其他的激流。

69130 次浏览

当我开始回答你的问题时,我没有意识到你问的是磁铁方案是如何工作的。我只是觉得你想知道与BitTorrent协议相关的部分是如何生成的。


MagnetURI中列出的哈希是以base32编码的Torrent的信息哈希。信息哈希是种子的BenCoded信息块的SHA1哈希。

这个Python代码演示了如何计算它。

我写了一个(非常简单的)C#实现来测试这一点,因为我手头没有BenCoder,它符合客户的期望。

static string CalculateInfoHash(string path)
{
// assumes info block is last entry in dictionary
var infokey = "e4:info";
var offset = File.ReadAllText(path).IndexOf(infokey) + infokey.Length;
byte[] fileHash = File.ReadAllBytes(path).Skip(offset).ToArray();
byte[] bytes;
using (SHA1 sha1 = SHA1.Create())
bytes = sha1.ComputeHash(fileHash, 0, fileHash.Length - 1); // need to remove last 'e' to compensate for bencoding
return String.Join("", bytes.Select(b => b.ToString("X2")));
}

据我所知,这个哈希不包括任何关于如何定位跟踪器的信息,客户端需要通过其他方式(提供的公告URL)找到这一点。这就是追踪器上一个激流与另一个激流的区别。

__,与BitTorrent协议相关的ABC__1仍然围绕跟踪器。它仍然是蜂群之间的主要通信手段。Magnet URI方案并不是专门为BitTorrent设计的。它被任何P2P协议用作通信的替代形式。BitTorrent客户端调整为接受磁铁链接作为识别种子的另一种方式,这样您就不再需要下载.torrent文件。磁体URI仍然需要指定trACKER,以便对其进行定位,从而客户端可以参与。它可以包含有关其他协议的信息,但与BitTorrent协议无关。如果没有追踪器,BitTorrent协议最终将无法工作。

我终于找到了规范。谷歌第一次没有帮忙。。(Wiki链接到主站点BitTorrent.com.我点击了开发者链接,注意到右边的BitTorrent.org标签,然后从那里开始就很容易了。它很难找到链接,当你不知道他们的标签和许多点击时)。

似乎所有的激流都有一个对等网络。你从追踪器中找到对等点,并在会话之间保留它们。网络可以让你找到同伴和其他东西。我还没有读到它是如何与磁铁链一起使用的,但似乎还没有定义新客户端如何找到对等体。也许有些是内置的,或者他们使用他们的家庭服务器或嵌入到客户端中的已知跟踪器来获得网络中的第一个对等体。

对等点列表可能是从升级客户端的种子中填充的(例如,有一个升级客户端的uTorrent种子)。只要每个人都使用相同的客户端,它应该是好的,因为你别无选择,只能共享升级。

我自己也对同样的问题感到好奇。阅读传输代码时,我在libtrnasmission/tr-dht.c中发现以下内容:

3248:     bootstrap_from_name( "dht.transmissionbt.com", 6881,
bootstrap_af(session) );

它尝试了6次,每次尝试之间等待40(!)秒。我猜您可以通过删除配置文件(在UNIX上~/.config/transmission)并阻止与dht.transmissionbt.com的所有通信来测试它,然后看看会发生什么(至少等待240秒)。

因此,客户端似乎一开始就内置了一个引导节点。当然,一旦它进入网络,它就不再需要引导节点了。

BitTorrent磁铁链接使用1(称为“ InfoHash ”的Sha-1或截断的Sha-256哈希值)来标识种子。这与对等点(客户端)在与跟踪器或其他对等点通信时用于识别种子的值相同。传统的.torrent文件包含具有两个顶级密钥的数据结构:announce,标识用于下载的跟踪器;info,包含torrent的文件名和哈希值。“信息散列”是编码的info数据的散列。

一些磁铁链接包括追踪器或网络种子,但它们通常不包括。您的客户可能对Torrent一无所知,只知道它的InfoHash.它需要做的第一件事是找到正在下载种子的其他对等体。它使用单独的对等网络2来操作“分布式哈希表”(DHT)。DHT是一种大型分布式索引,它将种子(由信息散列标识)映射到参与该种子的群(上传/下载数据或元数据)的对等体(由IP地址和端口标识)的列表。

客户端第一次加入DHT网络时,它会从与信息哈希相同的空间生成一个随机的160位ID.然后,它使用由客户端开发人员控制的客户端的硬编码地址或先前在Torrent Swarm中遇到的支持DHT的客户端来引导其到DHT网络的连接。当它想要参与给定种子的群时,它在DHT网络中搜索几个其他客户端,这些客户端的ID尽可能接近InfoHash的3。它通知这些客户端它想要加入群,并向它们询问它们已经知道的正在加入群的任何对等体的连接信息。

当对等体正在上传/下载特定的种子时,他们会尝试告诉对方他们所知道的参与同一洪流群的所有其他对等体。这可以让对等体快速了解彼此,而不会使跟踪器或DHT受到持续请求的影响。一旦您从DHT中了解到一些对等点,您的客户端将能够向这些对等点请求Torrent Swarm中更多对等点的连接信息,直到您拥有所需的所有对等点。

最后,我们可以向这些对等体请求Torrent的info元数据,其中包含文件名和哈希列表。一旦我们下载了此信息,并使用已知的infohash验证了它的正确性,我们实际上就处于与客户端相同的位置,该客户端从常规.torrent文件开始,并从包含的跟踪器中获得对等体列表。

可以开始下载。

1,InfoHash通常是十六进制编码的,但一些旧的客户端使用的是基数32。V1(urn:btih:)直接使用Sha-1摘要,而V2(urn:bimh:)添加多哈希前缀以标识哈希算法和摘要长度。
2,有两个主要的DHT网络:较简单的“主线” DHT和Azureus使用的较复杂的协议。
3通过XOR测量距离。

进一步阅读

对等发现和资源发现(在您的情况下是文件)是两件不同的事情。

我更熟悉JXTA,但所有对等网络都遵循相同的基本原则。

需要做的第一件事是对等发现。

对等点发现

大多数P2P网络都是“种子”网络:首次启动时,对等点将连接到一个已知(硬编码)地址,以检索正在运行的对等点列表。它可以是直接播种(如另一篇文章中提到的连接到dht.transmissionbt.com),也可以是间接播种(通常使用JXTA完成),其中对等体连接到仅提供其他对等体网络地址的纯文本列表的地址。

一旦与第一个(少数几个)对等体建立连接,连接对等体就会执行其他对等体的发现(通过向外发送请求),并维护它们的表。由于其他对等体的数量可能很大,因此连接对等体仅维护对等体的分布式哈希表(DHT)的一部分。确定连接对等体应该维护表的哪一部分的算法因网络而异。BitTorrent使用具有160位标识符/密钥的Kademlia.

资源发现

一旦连接的对等体发现了几个对等体,后者就向它们发送几个发现资源的请求。磁体链接标识这些资源,并以这样一种方式构建,即它们是资源的“签名”,并保证它们在所有对等体中唯一地标识所请求的内容。 然后,连接对等体将向其周围的对等体发送对磁体链路/资源的发现请求。DHT是以这样一种方式构建的,它有助于确定应该首先向哪些对等体请求资源(更多信息请阅读维基百科中的Kademlia)。 如果所请求的对等体不持有所请求的资源,则它通常将查询“传递”到从其自己的DHT获取的其他对等体。

查询可以传递的“跳数”通常是有限的;4是JXTA类型网络的常用数字。

当对等体持有资源时,它会回复其完整的详细信息。然后,连接对等体可以连接到持有资源的对等体(直接或通过中继-我不会在这里详细介绍),并开始获取资源。

P2P网络中的资源/服务是直接连接到网络地址:它们是分布式的,这就是这些高度可扩展网络的美妙之处。