• 区块链 1.0


    北京大学肖臻老师《区块链技术与应用》公开课 笔记

    比特币中的密码学原理

    哈希函数性质

    1. Collision Resistance:
      • 碰撞:x≠y,但H(x) = H(y)
      • 含义:对于输入x,没有特定的方法(除了遍历x)能找到y(≠x),使得H(x) = H(y).
      • 输入空间应足够大且分布均匀
    2. Hiding:
      • 无法由哈希函数输出H(y), 反推输入x(除非遍历x)
      • 输入空间应足够大,且分布均匀
    3. Puzzle friendly:
      • 无法找到特定方法x,可以构造特定的输出H(y)。→ 这也是为什么nonce可以作为工作量证明PoW

    目前区块链采用的哈希函数SHA-256 (Secure Hash Algorithm),256位

    非对称加密

    1. 私钥对交易(tx)签名,公钥用于验证
    2. 具备好的随机元的情况下,生成相同公私钥对的概率几乎为0

    数据结构

    1. 哈希指针(Hash Pointer):包含所指向的结构体的哈希值(指针只是形象的说法,其实只有哈希,没有指针)
    2. 区块链:使用哈希指针构成的链表,每个哈希指针保存的哈希值为前一个区块(包含哈希指针)的哈希值。只要保存根哈希指针,即可判断整条链的block是否被篡改
    3. 区块:Block Header(包含Block Data的Merkel Tree的根哈希值) + Block Body
      • Block Header包含:
        • Version -- 区块链版本
        • 前一个区块block header的哈希指针
        • Merkel tree的根哈希
        • nBits -- 挖矿目标阈值(r字节,target简略版)
        • nonce(4bytes) -- 挖矿所求随机数
    4. Merkel Tree: 叶节点为所有交易,父节点包含两个指向子节点的哈希指针。 Block Body中的交易由Merkel Tree组成,用于验证某项交易存在。任意交易被篡改,则根哈希值改变
    5. 全节点和轻节点:
      • 全节点(full node):保存区块链所有信息,验证每个交易
      • 轻节点(light node):只包含block header,无法独立验证交易,只是利用区块链的信息
      • Merkel proof:轻节点验证与自己相关的某个交易合法性时,只需向临近的全节点请求该交易Merkel Tree路径上相对的哈希值即可验证
    6. 交易: 输入为比特币来源,输出为接收者的公钥,交易通过发送者的私钥签名。发送者需提供自身公钥做验证

    共识协议

    1. 联盟链中多数节点是诚实的,可以采用投票。公链中账户可以随意创建,如果仍采用投票,则会出现女巫攻击(即一个节点创建多于半数的公私钥对,赢取投票)
    2. 求解computational puzzle,获得nonce(工作量证明PoW)的节点获得记账权
    3. 其他节点接收到新的区块后,先验证nonce合法性,再验证每条交易的合法性
    4. 即使nonce和每条交易合法,如果哈希指针指向的不是最长合法链,则区块不会被节点接受
    5. 若两个节点几乎同时获得记账权,区块均合法,则其他节点接受先收到的区块。进行算力竞赛,直达一条链胜出,成为最长合法链。而另一区块作废
    6. 矿工的区块被接受,则获得出块奖励block reward(称为铸币交易coinbase transaction),该交易位于block body中,称作coinbase transaction 。每21万个区块(约4年),奖励减半。50→25→12.5,现在为12.5BTC
    7. 这种情况下女巫攻击无效,因为创建多个账户并不会增加算力(记账权)

    比特币具体实现

    UTXO

    1. transaction-based ledger 基于交易的账本,没有记录每个账户中有多少余额。所以交易的输入中需要包含交易的来源。比特币系统中每个全节点内存中需要维护一个UTXO,记录为被花掉的交易(没有写入区块链里)。(更安全,但需要查询以往的交易。而以太坊是基于账户的账本account-based ledger)
    2. Unspent Transaction Output
    3. total input = total output,但有的时候output略小(包含traction fee给矿工,否则矿工没有动力将别人的交易打包成区块)
    4. Bitcoin is secured by mining.

    出块概率

    1. 多次伯努利实验,近似于泊松分布
    2. Memoryless -- 过去的工作量不会影响后续出块的概率
    3. 当区块链节点中,诚实的节点占大多数(指算力,不是账户数)时,恶意节点篡改数据的概率是很小的(恶意节点算力必须占大多数)
    4. 挖矿时除了修改nonce外,由于难度加大,可能穷尽所有取值也得不到合法值。还可以尝试修改merkel tree的根hash(通过修改coinbase域 -- extra nonce)

    比特币网络

    1. 应用层:区块链协议
    2. 网络层:P2P overlay 网络
    3. overflooding,对带宽消耗很大,带宽是瓶颈。默认每个区块1M字节(每个区块包含大概4k个交易)
    4. best effort
    5. 比特币设计原则:简单、鲁棒而不是高效

    挖矿

    1. difficult to solve, but easy to verify

    2. 挖矿难度difficulty x target = difficulty_1_target(难度为1时的target,为常数),即成反比

    3. 默认每2016个block调整一次出块难度,即14天。new target = current target x (actual time / expected time),调整倍数限制在(4分之1到4倍)

    4. 之所以要控制出块时间,是为了避免分叉攻击。如果target固定,难度越来越小,出块时间越来越短。同一时间出现的分叉数可能会很大,导致诚实节点的算力被分散。恶意节点只需用较小的算力就能把自己的链挖成最长合法链。出块时间没有最优值,但需要稳定在某个范围。

    5. 全节点&轻节点:

      全节点 轻节点
      一直在线 不是一直在线
      在本地硬盘上维护完整区块链信息 不用保存整个区块链,只要保存每个区块块头
      在内存里维护UTXO集合,以便快速检验交易正确性 不用保存全部交易,只保存与自己相关的交易
      监听比特币网络上的交易信息,验证每个交易合法性 无法检验大多数交易合法性,只能检验于自己相关交易的合法性
      决定哪些交易会被打包到区块里 无法检测网上发布的区块正确性
      挖矿:
      决定沿哪条链挖下去
      当出现等长分叉时,选择哪一个分叉
      可以验证挖矿难度
      只能检测哪个是最长链,不知道哪个是最长合法链
    6. 比特币安全性保证:

      • 密码学上公私钥签名
      • 共识机制
    7. 挖矿历史演进:CPU→GPU→ASIC芯片(Application Specific Integrated Circuit)→ 矿池

      • 由通用到专业化
      • 矿池的出现:
        • 由一个矿主pool manager管理多个矿工miner,miner只计算哈希值,由矿主负责全节点事务
        • 通过工作量证明进行收益分配。矿主通过降低挖矿难度,让每个miner提交almost valid block,以此作为PoW
        • 优点:相比miner单干,收益更稳定(miner单干要么挖到中大奖,要么打水漂)
        • 缺点:单个矿池算力达到50%更为可能。矿主不需要实际拥有那么多miner,只要发动攻击时号召就够了
    8. 算力大于51%时的攻击形式

      • 分叉攻击(Forking Attack):某笔待回滚交易后面连接6个区块确认后,矿池开始从该交易的分叉开始挖,追赶最长合法链。因为算力足够大,总能追上的
      • 抵制攻击(Boycott Attack):只要链上出现包含某笔A交易的区块,就从另一分叉开始挖,直到挖成最长合法链,使A交易作废
      • 盗币❌: 因为没有对方私钥,所以无法盗币。即使强行加到链上,诚实的节点也只会从另一条合法链去延伸

    比特币脚本

    验证形式

    1. Input Script 接上输入来源交易的Output Script
    2. 一开始是拼接后验证,现在input和output一般分开验证
    3. 只利用堆栈stack

    脚本形式

    1. P2PK(Pay to Public Key)
      • input: PUSHDATA(Sig)
      • output:PUSHDATA(PubKey) + CHECKSIG
    2. P2PKH(Pay to Public Key Hash)
      • input: PUSHDATA(Sig) + PUSHDATA(PubKey)
      • output:DUP + Hash160 + PUSHDATA(PubKeyHash) + EqualVerify + CHECKSIG
    3. P2SH(Pay to Script Hash)
      • input: PUSHDATA(Sig) + PUSHDATA(SeriRS)
      • output: PUSHDATA(RSH) + Equal
      • 第二阶段:执行反序列化的赎回脚本,验证签名
      • 用处:主要用于多重签名,将签名的复杂性转移到输入端
    4. Proof of Burn
      • output:RETURN + ...
      • 销毁比特币证明。由于比特币不可篡改性质,可在输出脚本RETURN后加任意内容,如专利hash作为证明。也用于作为PoW,换取某些小币种

    分叉形式

    1. State Fork:因出块时间接近而导致的分叉。恶意节点故意延伸的分叉也算state fork(又叫delibrate fork)
    2. Protocol Fork:因协议更新导致
      • Hard Fork: 只要部分节点不更新协议,分叉会一直存在。e.g. 大部分算力修改出块大小上限1M → 4M,新旧节点将沿各自认可的合法链延伸(新节点认旧节点,但新节点链更长,将沿新链延伸)
      • Soft Fork:分叉是临时性的,不会一直存在。e.g. 大部分算力出块大小上限1M → 4M,将主要沿新节点链延伸(因为旧节点也认新节点,且新节点链更长)

    比特币的匿名性

    1. 由于比特币的公开性,匿名性是比较差的(或者说,pseudonomity较好,但无法防范linkability)
    2. 获取BTC用户信息方式
      • 关联账户:一个交易中的多个input关联。输出中若存在一个output小于所有input(input个数 ≥ 2,商家只有一个),则该output为零钱账户
      • 交易:买入卖出BTC、用BTC进行现实世界的交易
    3. 比特币保护匿名性措施:
      • Mixing服务
      • 某些比特币钱包也能实现mixing服务
      • 比特币交易所其实也实现了mixing的功能
    4. 零知识证明
      • 含义:证明者A向验证者B证明一个陈述是正确的,过程中不需要透露出除该陈述是正确的之外的任何信息
      • 同态隐藏
        • 若x ≠ y,则其加密函数值E(x) ≠ E(y) → 逆否命题:若E(x) = E(y),则x = y
        • 隐匿性:很难由E(x)反推出x
        • 同态运算:
          • 同态加法:E(x) + E(y) = E(x + y)
          • 同态乘法:E(x) * E(y) = E(x * y)
          • 多项式运算类推
      • 例子
        • Alice向Bob证明自己知道一组x、y满足x + y = 7,但不想向Bob透露x和y值。→通过E(x)和E(y)
        • 盲签方法:用户A自己生成serialNum,银行在不知道serialNum的情况下为序列号签名生成Token。交易后用户B向银行提交SerialNum和Token验证货币真实性
        • 零币(zerocoin)和零钞(zerocash):相比BTC实现更好的匿名性,但用户较少。原因是性能损耗、用户需求不大、未解决与现实世界交易时的匿名性

    比特币思考

    1. 哈希指针:只包含哈希,不包含指针。区块是存储在key-value数据库中的,key为hash,value为区块(比特币和以太坊为levelDB)
    2. 私钥截断分开保存的做法存在安全风险(且死账残留在UTXO中,对矿工不友好),更好的做法是采用多重签名
    3. 分布式共识理论上是不可能的,但实践上区块链将其变成可能
    4. 不要被学术界的思维限制了头脑,不要被程序员的思维限制了想象力
    5. 量子计算:离真正可用还很遥远,而且最先受到冲击的会是传统金融业;比特币中output中的公钥哈希本身丢失了部分数据,是不可逆的(所以公钥也不要随意泄露,每次交易后就应更换账号)
  • 相关阅读:
    个人管理:提高你的搜商
    敏捷个人:提供更多文档下载,并转载一篇敏捷个人读书笔记
    个人管理: 激励你的一句话
    敏捷个人 从Scrum实践来思考如何导入价值观
    信息系统开发平台OpenExpressApp 如何解决ComboBox.TextProperty绑定带来问题的来龙去脉
    敏捷个人 敏捷个人价值观,欢迎提出你的意见和你的价值观
    使用VS2010的CodedUI来做自己的自动化测试框架
    .Net4下的MEF(Managed Extensibility Framework) 架构简介
    IronRuby - 快速在半小时学习Ruby基础知识
    敏捷个人 项目网站文档页签增加blog链接
  • 原文地址:https://www.cnblogs.com/DreamEagle/p/15900406.html
Copyright © 2020-2023  润新知