拜占庭容错技术来源于拜占庭将军问题。拜占庭将军问题是Leslie Lamport在20世纪80年代提出的一个假象问题 [1] 。拜占庭是东罗马帝国的首都,由于当时拜占庭罗马帝国国土辽阔,每支军队的驻地分隔很远,将军们只能靠信使传递消息。发生战争时,将军们必须制订统一的行动计划。然而,这些将军中有叛徒,叛徒希望通过影响统一行动计划的制定与传播,破坏忠诚的将军们一致的行动计划。因此,将军们必须有一个预定的方法协议,使所有忠诚的将军能够达成一致,而且少数几个叛徒不能使忠诚的将军做出错误的计划。也就是说,拜占庭将军问题的实质就是要寻找一个方法,使得将军们能在一个有叛徒的非信任环境中建立对战斗计划的共识。在分布式系统中,特别是在区块链网络环境中,也和拜占庭将军的环境类似,有运行正常的服务器(类似忠诚的拜占庭将军),有故障的服务器,还有破坏者的服务器(类似叛变的拜占庭将军)。共识算法的核心是在正常的节点间形成对网络状态的共识。
求解拜占庭将军问题,隐含要满足以下两个条件:
1)每个忠诚的将军必须收到相同的命令值vi(vi是第i个将军的命令)。
2)如果第i个将军是忠诚的,那么他发送的命令和每个忠诚将军收到的vi相同。
于是,拜占庭将军问题的可以描述为:一个发送命令的将军要发送一个命令给其余n-1个将军,使得:
IC1.所有忠诚的接收命令的将军遵守相同的命令;
IC2.如果发送命令的将军是忠诚的,那么所有忠诚的接收命令的将军遵守所接收的命令。
Lamport对拜占庭将军问题的研究表明 [2] ,当n>3m时,即叛徒的个数m小于将军总数n的1/3时,通过口头同步通信(假设通信是可靠的),可以构造同时满足IC1和IC2的解决方案,即将军们可以达成一致的命令。但如果通信是可认证、防篡改伪造的(如采用PKI认证,消息签名等),则在任意多的叛徒(至少得有两个忠诚将军)的情况下都可以找到解决方案。
而在异步通信情况下,情况就没有这么乐观。Fischer-Lynch-Paterson定理证明了,只要有一个叛徒存在,拜占庭将军问题就无解 [3] 。翻译成分布式计算语言,在一个多进程异步系统中,只要有一个进程不可靠,那么就不存在一个协议,此协议能保证有限时间内使所有进程达成一致。
由此可见,拜占庭将军问题在一个分布式系统中,是一个非常有挑战性的问题。因为分布式系统不能依靠同步通信,否则性能和效率将非常低。因此寻找一种实用的解决拜占庭将军问题的算法一直是分布式计算领域中的一个重要问题。
在这里,我们先给出分布式计算中有关拜占庭缺陷和故障的两个定义:
定义1: 拜占庭缺陷(Byzantine Fault):
任何观察者从不同角度看,表现出不同症状的缺陷。
定义2: 拜占庭故障(Byzantine Failure):
在需要共识的系统中由于拜占庭缺陷导致丧失系统服务。
在分布式系统中,不是所有的缺陷或故障都能称作拜占庭缺陷或故障。像死机、丢消息等缺陷或故障不能算为拜占庭缺陷或故障。拜占庭缺陷或故障是最严重缺陷或故障,拜占庭缺陷有不可预测、任意性的缺陷,例如遭黑客破坏,中木马的服务器就是一个拜占庭服务器。
在一个有拜占庭缺陷存在的分布式系统中,所有的进程都有一个初始值。在这种情况下,共识问题(Consensus Problem),就是要寻找一个算法和协议,使得该协议满足以下三个属性。
1)一致性(Agreement):所有的非缺陷进程都必须同意同一个值。
2)正确性(Validity):如果所有的非缺陷的进程有相同的初始值,那么所有非缺陷的进程所同意的值必须是同一个初始值。
3)可结束性(Termination):每个非缺陷的进程必须最终确定一个值。
根据Fischer-Lynch-Paterson的理论,在异步通信的分布式系统中,只要有一个拜占庭缺陷的进程,就不可能找到一个共识算法,可同时满足上述要求的一致性、正确性和可结束性要求。在实际情况下,根据不同的假设条件,有很多不同的共识算法被设计出来。这些算法各有优势和局限。算法的假设条件有以下几种情况:
1)故障模型:非拜占庭故障/拜占庭故障。
2)通信类型:同步/异步。
3)通信网络连接:节点间直连数。
4)信息发送者身份:实名/匿名。
5)通信通道稳定性:通道可靠/不可靠。
6)消息认证性:认证消息/非认证消息。
在区块链网络中,由于应用场景的不同,所设计的目标各异,不同的区块链系统采用了不同的共识算法。一般来说,在私有链和联盟链情况下,对一致性、正确性有很强的要求。一般来说要采用强一致性的共识算法。而在公有链情况下,对一致性和正确性通常没法做到百分之百,通常采用最终一致性(Eventual Consistency)的共识算法。