03 BTC-协议

发布时间 2023-05-02 11:29:10作者: YangYi215

《区块链技术与应用》课程链接:https://www.bilibili.com/video/BV1Vt411X7JF/?spm_id_from=333.337.search-card.all.click


03 BTC-协议

  • 数字货币的需要解决的两个主要问题
  • 共识机制

如果央行(中心化)发行数字货币,使用央行的私钥进行签名,大家交易的时候使用央行的公钥验证数字货币是否正确,那么这样交易是否可行?

  • 央行随便分发货币,量化宽松,影响市场金融秩序;
  • 双花攻击(double spending attack):数字货币可以被多分复制。【纸币可以避免双花问题】数字货币的主要挑战之一。

那么,我们改进一下,每个数字货币上有一个编号,央行维持一个巨大的数据库,数据库记录了该数字货币的归属,交易时,收款人验证该数字货币的归属,同时修改归属权,这样是否可行?(这样可以防范double spending attack)

  • 是可行的,但这是一个中心化的方案,数字货币的发行是央行控制的,而且交易需要央行确认才能证明合法性。

那么,有没有一种方法,把央行的权利分散,职能由大家承担,这便是比特币数字货币需要解决的问题。


数字货币的两个主要问题:

  1. 谁来发行货币?发行多少?
  2. 如何防止双花攻击?证明交易的有效性?

防止双花攻击

维护一个数据结构,检查币有没有被花过?被谁花过?由所有的用户共同维护数据结构,即为区块链。【为什么是链式结构?主要为防范双花攻击

两种hash指针:

  • 构成链式结构

  • 指明币的来源【实现:每笔交易中,需要指明币的来源(交易ID),详情可看交易的数据结构】【如A—>B,交易还需存放A的签名,B的地址】

    证明币的来源

    防范double spending attack


问题:如果A要给B转账,那么如何知道B的地址?

比特币内部没有提供地址查询功能,需要通过其它的渠道去获取。比如:网站公开。


A需要知道B的地址,B需要知道A的信息吗?

B需要知道A的公钥。一是为了知道谁是转账人,更重要的一点,对交易进行验证。

不仅B需要A的公钥,所有的节点都需要知道A的公钥,用来对交易的合法性进行验证。(所有节点都得验证,因为区块链是分布式的,可能存在恶意节点,不能依赖别人的验证结果)


那么问题来了,其它节点怎么才能知道A的公钥?

A需要说明自己的公钥是什么,附在交易的输入中。


这里面是不是有个安全漏洞,怎么能让节点自己说呢?如果冒名顶替,假使B的同伙B',伪造交易,对外界说是A—>B(但其实用的是B'自己的公钥),然后用B'自己的私钥签名,其余节点收到交易,用假造的公钥验证私钥,是可以通过的。那这样岂不是把A账上的钱给偷走了?

交易的输入中必须说明币的来源,在A的币的来源的输出中,有A的公钥的哈希,也就是上一笔交易的输出,需要上一笔交易的输出的A的hash值等于A的公钥的hash(这里B'的公钥不等于A中上一笔交易的输出中A的公钥的hash),才可行。


BitCoin Script

比特币中交易的输入和输出都是使用脚本来实现的,就是使用上一笔交易的输出脚本和这一个交易的输入脚本拼在一起,看看能不能顺利执行。


比特币中区块的结构:


全节点和轻节点:

全节点进行交易的验证,轻节点没有办法做独立验证。


那么,谁来决定哪些交易应该被写入下一个区块中?按照什么样的顺序写进去?

如果每个节点自己决定行不行,比如,单个节点收到交易(合法的、非法的),进行交易验证之后,将交易打包,构建一个本地的区块链行不行?

这样,一致性得不到保证,不是一条链。【区块链,去中心化的账本,记录的数据必须一致。】

用分布式术语,账本的内容要取得分布式的共识。(distributed consensus)


分布式中有很多impossibility result,其中最著名的是FLP impossibility result。

在一个异步的系统中(asynchronous system)【网络传输时延没有上限】,即使一个成员是有问题的(faulty),那么也不可能取得共识。

还有一个比较著名的结论,叫做CAP Theorem。

  • Consistency
  • Availability
  • Partition tolerance

任何一个分布式系统中,上述三个性质中,最多只能满足两个。

分布式共识中,一个比较著名的协议,叫做Paxos。

可以达成Consistency,但是有可能一直不能共识(虽然可能性小,但是客观存在)。


比特币中的共识协议

我们假设系统中的绝大多数节点都是好的,只有一小部分是有恶意的,那么我们该如何设置共识协议?

一个简单的方法,投票的方法行不行,一个节点将交易按照顺序打包之后,发给其他节点,如果超过半数的节点投赞成票,那就把这个交易加入到区块链中,这样是否可行?

存在一个很大的问题:任何基于投票的方案,首先要确定谁有投票权。【也就是membership问题,如在联盟链hyperledger fabric中采用投票是可行的,因为其中大多数节点是好的】

投票权在比特币中行不通,因为Sybil attack存在,如果一个恶意组织,通过计算机产生超过50%的账户,那就可以控制比特币网络。

投票还有的一些小问题:

  • 有些节点可能不投票;
  • 有些节点可能恶意投票;
  • 时间复杂度过高,通讯次数过多。所以必须设置预设的规则,来达成共识,恶意节点可以不遵循,但是诚实节点都会做;

比特币中block header中有一个nBits,是target目标阈值的编码,验证区块时检查nBits设置的是不是符合比特币中规定的难度要求。

检查区块合法性,先检查区块头,后检查区块体。

区块体中的交易

  • 是不是有合法的签名
  • 以前有没有被花过

有没有一种可能,就是区块头和区块体都是合法的,但是我们仍然不愿意接收?

这个区块有什么问题?虽然下面区块中的交易都是合法的(判断有没有double spending,依据是从但当前区块出发,所在的链上有没有被双花)

这叫做forking attack,分叉攻击。通过往区块链中插入区块,来回滚某个在区块链上已经发生的交易。


如果比特币网络中,两个节点同时获得记账权,在缺省情况下(由于网络延迟),矿工会沿着最先收到的区块下往后挖(表明该矿工认可该区块)。


为什么要争夺记账权?

首先,记账节点可以决定那些交易可以被打包到下一个区块中,但是,并非主要动力。

出块奖励(block reward)

一个去中心化的数字货币需要解决两个问题

  • 谁有权发行货币
  • 怎么验证交易的合法性

谁有权发行货币

coinbase transaction:

一开始50BTC,21万个区块奖励减半。


可以通过计算hash来防止Sybil Attack。