BitTorrent磁铁链接如何工作?


157

我第一次使用磁铁链接。好奇它是如何工作的,所以我查看了规格并没有找到任何答案。Wiki说的xt是“精确的主题”,后跟btih带有SHA1哈希的格式(在这种情况下)。我看到提到base32,知道它是每个字符5位和32个字符,我发现它正好可以容纳160位,这正好是SHA1的大小。

IP地址或其他任何内容都没有空间,只是SHA1。那么,BitTorrent客户端如何找到实际文件?我打开了URL Snooper,以查看它是否访问了页面(使用TCP)或进行了查找等操作,但是没有任何反应。我不知道客户如何找到同龄人。这是如何运作的?

另外,哈希是什么?它是所有文件散列在一起的数组的哈希吗?也许是所需的实际torrent文件的哈希值(去除了某些信息)?


在虚拟机中,我尝试了与uTorrent(已全新安装)的磁力链接,并设法找到了对等节点。第一个同龄人来自哪里?这是新鲜的,没有其他洪流。


3
这甚至与编程有关吗?

Answers:


156

BitTorrent磁链使用1的SHA-1或截断的SHA-256哈希值(称为“ infohash”)来标识洪流。与跟踪器或其他对等方进行通信时,对等方(客户端)用于标识洪流的值与该值相同。传统的.torrent文件包含具有两个顶级密钥的数据结构:announce,标识用于下载的跟踪程序,以及info,包含torrent的文件名和哈希。“ infohash”是已编码的哈希info数据。

一些吸引人的链接包括跟踪器或网络种子,但通常不包含这些链接。您的客户可能除了关于infohash的信息以外,对torrent一无所知。它需要做的第一件事就是找到其他正在下载种子的同龄人。它使用操作“分布式哈希表”(DHT)的单独的对等网络2来做到这一点。DHT是一个大型的分布式索引,它将torrent(由信息哈希标识)映射到参与该洪流群(上传/下载数据或元数据)的对等方列表(由IP地址和端口标识)。

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

当对等方上载/下载特定的洪流时,他们会尝试将彼此知道的其他所有参与同一个洪流群的对等方告诉彼此。这使同伴可以快速相互了解,而无需对跟踪器或DHT进行持续的请求。一旦您从DHT获悉了几个对等节点,您的客户端就可以向这些对等节点请求torrent群中更多对等节点的连接信息,直到您拥有所需的所有对等节点为止。

最后,我们可以向这些同伴索要种子的种子 info元数据,其中包含文件名和哈希列表。一旦下载了此信息并使用known验证了它的正确性infohash,我们就与以常规.torrent文件开头并从随附的跟踪器获得对等项列表的客户端处于实际上的位置。

下载可能会开始。

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

进一步阅读


1
引导节点(例如dht.transmission.com)仅仅是跟踪器吗?我了解的方式是,它需要跟踪每个信息哈希的对等方列表-这正是跟踪器所做的。
2014年

3
@Kate不完全是。典型的DHT节点在DHT网络“空间”中存储“附近” 一些种子的对等列表。跟踪器会尝试为它知道的每个种子存储对等列表。此外,引导DHT节点专门不存储任何种子的对等列表。相反,它们仅分发其他DHT节点的列表,以帮助您连接到整个网络。然后,您可以找到您感兴趣的对等列表典型的DHT节点。
杰里米银行

“有些磁铁链接包括跟踪器或网络种子”-我有点困惑。如您所描述的,使用磁铁来下载种子文件。从磁铁URI规范中,我看到“可接受的来源”和“跟踪器”是可以在URI中编码的信息。现在,该跟踪器显然是特定于Bittorrent的,并且除了torrent文件中列出的跟踪器外,还将很有可能被使用。“可接受的来源”是用于下载种子文件,还是用于通过Torrent文件下载的实际文件(其中之一)?
Frederick Nord

@FrederickNord在支持torrent客户端中,该ws=参数指向实际数据的BEP-19网络种子URL,而该xs=参数指向包含.torrent文件本身的URL 。我认为这与该magnet:计划的其他用途有点不一致,但这就是事实。我忘记了是否有任何客户使用as=任何东西……可能只是作为xs=IIRC 的后备,但并未得到广泛支持。
Jeremy Banks

46

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

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

首先需要发生的是对等发现。

同行发现

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

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

资源发现

一旦连接对等方发现了几个对等方,连接对等方就会向其发送一些发现资源的请求。磁铁链接标识这些资源,并且以这样的方式构建:它们是资源的“签名”,并确保它们在所有对等方之间唯一地标识所请求的内容。然后,连接的对等方将向其周围的对等方发送对磁链/资源的发现请求。DHT的构建方式可以帮助确定首先向哪个同级请求资源(有关详细信息,请参阅Wikipedia的Kademlia)。如果所请求的对等方不拥有所请求的资源,则通常会将查询“传递”给从其自己的DHT提取的其他对等方。

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

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

P2P网络中的资源/服务直接附加到网络地址:它们是分布式的,这就是这些高度可扩展的网络的优点。


我认为这是没有很多技术术语的最简洁的答案。谢谢。
desaivv 2014年

26

我自己也对同样的问题感到好奇。读取传输代码后,我发现libtrnasmission/tr-dht.c

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

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

因此,看来客户端具有一个内置的引导节点。当然,一旦它进入网络,就不再需要该引导节点。


9

我终于找到了规格。谷歌第一次没有帮助。(链接到主要网站bittorrent.com的Wiki。我单击了开发人员链接,注意到右侧的bittorrent.org选项卡,从那里很容易。当您不知道它们的标签是多少时,很难找到链接。点击)。

似乎所有种子都拥有同龄人网络。您可以从跟踪器中找到同伴,并在会话之间保持同伴。网络使您可以查找对等物。我还没有读过它如何与磁铁链接一起使用,但似乎尚不确定新客户如何找到对等对象。也许有些入炉,或者他们使用自己的家庭服务器或嵌入到客户端的已知跟踪器来获取网络中的第一个对等方。


嗯,我想去DHT寻找客户是正确的。“如果未指定跟踪器,则客户端应使用DHT(BEP 0005 [3])来获取对等体。”
杰夫·梅卡多

8

当我开始回答您的问题时,我没有意识到您正在询问磁铁方案的工作原理。只是以为您想知道与bittorrent协议相关的部分是如何生成的。


磁铁uri中列出的哈希是在base32中编码的torrent的信息哈希。信息哈希是洪流的本编码信息块的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")));
}

据我了解,此哈希不包含有关如何定位跟踪器的任何信息,客户端需要通过其他方式(提供的公告网址)来找到该信息。这就是在追踪器上将一个洪流与另一个洪流区分开的原因。

与bittorrent协议有关的所有内容仍然围绕着跟踪器旋转。它仍然是群体之间进行交流的主要手段。magnet uri方案并非专门为bittorrent设计的。任何P2P协议都将其用作通信的另一种形式。Bittorrent客户端适应了磁力链接,这是另一种识别torrent的方式,您无需再下载.torrent文件。磁铁uri仍需要指定tracker才能定位它,以便客户可以参与。它可以包含有关其他协议的信息,但与bittorrent协议无关。没有跟踪器,bittorrent协议最终将无法工作。


2
这没有帮助。但是,您是说它跳过了infokey块而散列了整个torrent文件吗?我的问题是关于它如何找到同龄人。

1
@ acidzombie24您可能正在考虑使用DHT定位同位体的分布式跟踪器。这与磁链无关。(en.wikipedia.org/wiki/…)–
亚历山大·萨根

2
@杰夫·M:但是什么“发送”了同行列表。链接只是一个链接,没有与之关联的跟踪器。我试图弄清楚是什么发回了同行。

1
+1。另外,相关的磁链未指定tr(acker)。只有让我感到困惑的这件事。尤其是当我使用没有洪流运行的全新安装(并且未连接到任何对等节点)并且具有磁力链接查找对等节点时。它的魔力,我不知道它是如何工作的。必须有一些可以请求对等方的家庭服务器。但这是否意味着我向对等方发送查询以查找哈希,并且客户端将消息传递给许多对等方,直到有人应答了我的电话?

1
我不确定该如何回答。我见过的所有磁铁尿素始终指定跟踪器。可能是您的客户尝试了一份它知道的公共跟踪器列表,并且碰巧有一个。相关的洪流列表将使用哪些跟踪器?如何显示?它连接到的跟踪器与磁链的来源之间是否有任何关系?也许是使用DHT的种子文件?私人种子也一样吗?同样,我不知道DHT的工作原理。我将看看是否能找到更多信息。
Jeff Mercado

3

同行列表可能是从升级客户端的洪流中填充的(例如,有一个用于utorrent的洪流会对其进行升级)。只要每个人都使用相同的客户端,那应该很好,因为您别无选择,只能共享升级。


那是搜索哈希值和其他对等点的非常合乎逻辑的地方。+1
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.