分布式系统入门 | 拜占庭将军问题

关于拜占庭帝国的将军,请见分类:拜占庭将军

拜占庭故障(也叫做交互一致性源一致性错误雪崩拜占庭协议问题拜占庭将领问题拜占庭故障)是一个计算机系统的状态,特别是「分布式计算」系统中,其中的组件可能会故障,并且在组件故障时可能发生故障信息。

“拜占庭将军问题”这个名字来自于一个寓言,用于描述一种情况——在这种情况下,为了避免系统发生灾难性故障,系统的参与者达成协调一致的策略,但其中一些参与者是不可信的。

简单理解,就是一个系统内可能存在故障、恶意的节点前提下,需要对一些决策达成一致。

在拜占庭故障中,像服务器之类的组件在故障检测系统中可能会反反复复地出现故障和正常运行状态之间切换,从而向不同的观察者表现不同的症状。其他组件很难宣布它发生故障并将其关闭在网络之外,因为他们首先需要针对哪个组件发生故障达成共识。

拜占庭容错( BFT ) 就是这种状态下可靠的「容错计算机系统」

特征

拜占庭式故障对于不同的观者者呈现出不同的表现。拜占庭故障是一个系统服务的损失,因为系统中需要对拜占庭故障达成共识。

拜占庭容错的目标是能够预防系统组件的故障,无论系统的其他组件是否有阻止它们之间达成一致的症状,这种情况下,系统的正常运转需要达成这样的一致。

假设有足够数量的精确运行的组件来维护服务,拜占庭容错系统的其他正常运行的组件将能够继续按最初的预期提供系统服务。

即使有部分节点故障或者是恶意节点,也可以保证分布式系统正常运行。

拜占庭故障被认为是故障模式中最普遍和最困难的故障类别。所谓的「失败停止故障模式」占据了故障范围内的最简单的一部分。失败停止故障模式只意味着唯一的故障方式是节点崩溃,被其他节点检测到。拜占庭故障意味着没有限制,即故障节点可以生成任意数据,包括使其看起来像一个正常运行的节点数据。

因此,拜占庭故障会混淆故障检测系统,这使得容错变得困难。尽管进行了类比,但拜占庭故障不一定是涉及敌对人为干扰的安全问题:它可能纯粹是由电子或软件故障引起的。

这里使用的术语故障和失败是根据标准定义,最初由IEEE计算机协会可靠计算和容错技术委员会和IFIP工作组 10.4组成的“基本概念和术语”联合委员会创建的可靠的计算和容错。

注意事项

拜占庭容错只关心广播的正确性,即当一个组件向其他组件广播一个一致的值(即向其他组件发送相同的值)时,它们都收到完全相同的值。或者在如果广播的值不一致,其他组件就共同的值达成一致。

⚠️这里我想强调一点:这种容错不包括值本身的正确性。例如,一个恶意的组件故意发送错误值,但向所有组件发送一致的相同值(其实这是错误值),这种情况不会被拜占庭容错方案捕获。

正式定义

设定:

给定一个包含 n 个组件的系统,其中 t 个组件是不可靠的,同时假设所有组件之间只有点对点通道(用于通信)。

每当组件 A 尝试广播值 x 时,允许其他组件相互讨论并验证 A 广播的一致性,最终确定一个共同的值 y(达成共识的值)。

属性:

如果组件 A 可以广播值 x,则系统被称为抵制拜占庭故障,然后:

  1. 如果A是诚实的,则所有诚实的组件都同意值 x
  2. 在任何情况下,所有诚实组件都同意相同的值 y

变化形式:

这个问题在同步和异步通信的情况下都已经被研究过。

上面的通信图假设是完整的图(即每个组件可以相互讨论),但通信图页可以是受限制的。

也可以在更“现实”的问题中放宽要求,即故障组件不会串通在一起来试图哄骗其他组件出错。正是在这种情况下,设计了实用的算法。

比如在公司的内网,可以假定不存在恶意节点,只存在故障节点。

历史

拜占庭共识问题是由Robert Shostak构想和正式化的,他将其称为「交互一致性」问题。这项工作是在 1978 年在 NASA 赞助的SRI International计算机科学实验室的 SIFT 项目的背景下完成的。

「SIFT(for Software Implemented Fault Tolerance,即软件实现容错)」是 John Wensley 的核心,它基于使用多台通用计算机的想法,这些计算机将通过成对消息进行通信来达成共识,即使某些计算机出现了故障。

项目开始时,并不清楚总共需要多少台计算机才能保证 n 台故障计算机的阴谋不会“阻挠”正确运行的计算机达成共识。Shostak 表明至少需要 3 n+ 1,并设计了一个两轮 3 n+ 1 消息传递协议,该协议适用于 n = 1。他的同事 Marshall Pease 将算法推广到任何 n > 0,证明 3 n+ 1 是充分必要的。这些结果,连同Leslie Lamport后来使用数字签名证明 3n 的充分性,发表在开创性的论文—— 《Reaching Agreement in the Presence of Faults》(在存在故障的情况下达成共识)。

作者因这篇论文获得了 2005 年 Edsger W. Dijkstra 奖

为了让交互一致性问题更容易理解,Lamport 设计了一个精彩的寓言,其中一群陆军将领制定了进攻城市的计划。在原始版本中,故事将将军们塑造为阿尔巴尼亚军队的指挥官。在杰克·戈德堡(Jack Goldberg)的建议下,名称被更改,最终确定为“拜占庭”,以防止存在潜在的冒犯。同一作者在 1982 年的论文“拜占庭将军问题”中提出了这个问题的表述以及一些额外的结果。

类比

在最简形式下,将军们只需决定是进攻还是撤退。一些将军可能更喜欢进攻,而另一些将军则更喜欢撤退。重要的是,每个将军都同意一个共同的决定,因为几个将军三心二意的进攻导致军队溃败,这比协同进攻或协同撤退要糟糕得多。

因为存在奸诈的将军,他们不仅可能投票支持次优策略,而且可能有选择地投票,使问题变得复杂。

例如,如果九位将军投票,其中四位支持进攻,另外四位支持撤退,第九位将军可以向这些将军投票赞成撤退,其余投反对票。那些从第九位将军那里得到撤退投票的将撤退,而其余的将进攻(这可能对进攻方不利)。由于将军们在物理上分开并且不得不通过可能无法投递选票或可能伪造虚假选票的信使发送他们的选票,这个问题变得更加复杂。

正式决定

如果大多数忠诚的(非故障的)将军能对他们的策略达成一致,就可以实现拜占庭容错。可以为丢失的消息提供默认投票值

例如,可以为丢失的消息赋予值 。此外,如果同意 票占多数,则可以使用预先分配的默认策略(例如,撤退)。

这个故事在计算机系统上的典型映射是,计算机是将军,它们的数字通信系统连接是信使。虽然这个问题在类比中被表述为决策和安全问题,但在电子学中,它不能简单地通过「加密」、「数字签名」来解决,因为错误电压等故障可以通过加密过程传播。

因此,一个组件可能对一个组件显示为正常工作而对另一个组件出现故障,这阻止就组件是否有故障形成共识。

比如出现一个叛徒将军,给一部分忠诚将军发送进攻,另一部分忠诚将军发送失败。

例子

两篇期刊论文中给出了几个拜占庭失败的例子。这些和其他示例在 NASA DASHlink 网页上进行了描述。[12]这些网页还描述了一些可能导致拜占庭故障的现象。

例子参考1参考2

拜占庭错误在新建造的 弗吉尼亚级潜艇的耐久性测试期间很少被观察到,并且在不规则的点上被观察到,至少在 2005 年(当问题被公开报告时)。

早期解决方案

Lamport、Shostak 和 Pease 在 1982 年描述了几种解决方案。

他们首先指出,将军问题可以简化为解决“指挥官和中尉”问题,其中忠诚的中尉必须一致行动,并且他们的行动在指挥官忠诚的情况下,必须符合指挥官的命令:

  • 一种解决方案考虑了消息可能被伪造的场景,但只要不忠诚的将军数量少于将军的三分之一,就会是拜占庭容错「口型型拜占庭将军问题」)。

    无法对付三分之一或更多的叛徒,最终只能证明一个指挥官和两个中尉的问题无法解决,如果指挥官是叛徒的话。看到这一点,假设我们有一个叛逆的指挥官 A,和两个中尉 B 和 C:当 A 告诉 B 进攻 C 撤退时,B 和 C 相互发送消息,转发 A 的消息,B 和 C 都不能找出谁是叛徒,因为它不一定是 A——另一个中尉可能已经伪造了据称来自 A 的消息。

    可以证明,如果n是将军的总数,并且tn 中的叛徒数量,那么只有当n > 3 t 并且通信是同步的(「有界延迟」)时,问题才有解决方案。

  • 第二种解决方案需要不可伪造的消息签名「签名式拜占庭将军问题」)。

    对于「安全关键系统」「数字签名」(在现代计算机系统中,可以在实践中使用「公钥密码术实现」)可以在任意数量的叛徒将军面前提供拜占庭容错能力。

    然而,对于「安全关键系统」(其中“安全”解决智能威胁,而“安全”解决活动或任务的固有危险),简单的错误检测代码,例如CRC,能以低得多的成本提供较弱但足够的覆盖。这对于拜占庭和非拜占庭故障都是如此。此外,有时安全措施会削弱安全性,反之亦然。因此,加密数字签名方法不是安全关键系统的好选择,除非存在特定的安全威胁。

    虽然「错误检测代码」(例如 CRC)比加密技术更好,但两者都不能为安全关键系统中的电子设备提供足够的覆盖范围。Schrödinger CRC场景说明了这一点,其中具有单个拜占庭错误位的 CRC 保护消息向不同的观察者呈现不同的数据,并且每个观察者看到一个有效的 CRC。

  • 还介绍了前两种解决方案的变体,在某些情况下,并非所有将军都可以直接相互通信,从而允许拜占庭容错行为。

1980 年设计了多种系统架构实现拜占庭容错。其中包括:Draper 的 FTMP、霍尼韦尔的 MMFCS和 SRI 的 SIFT

先进的解决方案

1999 年,Miguel Castro 和 Barbara Liskov 提出了“「实用拜占庭容错」”(PBFT)算法,提供高性能拜占庭状态机复制,每秒能处理数千个请求,延迟增加了亚毫秒。

在 PBFT 之后,引入了几种 BFT 协议以提高其鲁棒性和性能。

例如,Q/U,HQ,Zyzzyva 和 ABSTRACTs,解决了性能和成本问题;而其他协议,如 Aardvark和 RBFT,解决了其鲁棒性问题。此外,Adapt 试图利用现有的 BFT 协议,通过以自适应方式在它们之间进行切换,用在潜在条件发生变化时提高系统的鲁棒性和性能。此外,引入了利用可信组件来减少副本数量的 BFT 协议,例如 A2M-PBFT-EA和 MinBFT。

受 PBFT 的启发,Tendermint BFT 引入部分异步网络,主要用于区块链工作量证明。

BFT 实现

使用 BFT 的一个例子是比特币,一种点对点数字现金系统。比特币网络并行工作,以产生 「blockchain」工作量证明使系统能够克服拜占庭故障,达到了系统全局状态一致。

一些飞机系统,例如波音 777 飞机信息管理系统通过其ARINC 659 SAFEbus网络)、波音 777 飞行控制系统和波音 787 飞行控制系统使用拜占庭容错;因为这些是实时系统,他们的拜占庭容错解决方案必须具有非常低的延迟。

例如,SAFEbus 可以在增加的延迟一微秒的数量级内实现拜占庭容错。

一些航天器飞行系统,例如SpaceX Dragon 的飞行系统,在其设计中考虑了拜占庭容错。

可见这种思想多么巧妙!不仅仅用在分布式系统设计上,还可以用在现实生活中多个场景得到应用。

拜占庭容错机制将传入消息(或仅其签名)重复给该传入消息的其他接收者的组件。所有这些机制都假设重复消息的行为会阻止拜占庭故障的传播。对于具有高度安全性或安全关键性的系统,必须证明这些假设在可接受的故障覆盖范围内是真实的。

通过测试提供证据时,一个困难是创建具有拜占庭症状的足够广泛的信号。这种测试可能需要专门的故障注入器

软件

  • UpRight 是一个开源库,用于构建能够容忍崩溃(“up”)和拜占庭行为(“right”)的服务,其中包含了许多这些协议的创新。

  • BFT-SMaRt 库是一个用 Java 开发的高性能拜占庭容错状态机复制库。该库实现了一个与 PBFT 非常相似的协议,以及提供状态传输和主机动态重新配置的补充协议。BFT-SMaRt 是实现状态机复制的最新努力成果,仍在积极维护中。

  • Archistar利用纤薄的 BFT 层进行通信。它使用 LGPLv2 许可的 Java 构建了一个安全的多云存储系统原型。重点在于简单性和可读性,旨在成为进一步研究项目的基础。

  • Askemos 是一个并发的、垃圾收集的、持久的编程平台,它位于复制状态机之上,可以容忍拜占庭故障。它原型化了一个促进智能合约的执行环境。

References

posted @ 2021-06-18 20:38  Alan-Yin  阅读(2165)  评论(0编辑  收藏  举报