深入浅出比特币交易 (transaction)

如果你接触比特币够久,你一定听说过比特币是个区块链,一个区块里包含很多交易,而交易都是链在一起的。那么,具体交易的细节如何?通常的技术文档都充满了术语,即使是中本聪的白皮书也难以联系实际,我最近又仔细研究了一下,这里用一种简单的比喻来解释下

比方说你的钱包里有三个地址A,B,C。你在地址A有1个币,你在钱包软件里把币发送到地址B,可以在区块链上查到这笔交易,不妨叫做交易甲。然后你又做了一笔交易乙,把币从地址B发到地址C。假设手续费是0.0001个币,每次发送你都花了0.0001个币作为手续费,那交易甲被确认后地址B就是0.9999个币,而交易乙被确认后地址C里就是0.9998个币

交易甲:地址A 1BTC -> 地址B 0.9999 BTC, 手续费 0.0001
交易乙:地址B 0.9999BTC -> 地址C 0.9998 BTC,手续费 0.0001

比特币软件具体是怎么记录的呢?

还是用账簿的比喻

账簿就是区块链,账簿的每页纸就是区块,这些纸依次装订在一起形成了一整个账簿。每页纸上贴满了一条又一条的汇款单(交易)

如果仔细观察汇款单交易乙(把0.9998个币从地址B转到地址C),会发现交易乙是由两大部分组成,前一部分可称为付款信息(input),后一部分可称为收款信息(output)

照一般在银行填汇款单的习惯,付款信息里该填支出账户(也就是地址B)和账户所有人签名(授权交易),而收款信息里应该填金额和收款方账户名(也就是地址C)。事实上,比特币交易也大致是这么写的,只有细微差别,说明中本聪在设计时是按照现有金融体系规范设计的

交易甲
付款信息: 签名 + 公钥A
(签名相当于盖章,是用地址A的私章(私钥)产生,而地址A的公钥可以用于验证这个章是否有效 (私钥公钥加密原理到处都有))

收款信息: 0.9999 (金额) + 地址B + 兑现条件
(这里的兑现条件注明了未来要花地址C的币需要满足何种条件,下面有详述)

交易乙
付款信息:签名 + 公钥B
收款信息:0.9998 + 地址C + 兑现条件

交易丙
付款信息:签名 + 公钥C
收款信息:0.9997 + 地址D + 兑现条件

有几点和银行汇款单不同的地方

第一,每个汇款单都是花前一个汇款单的收款地址里的币,这样所有交易就一个个链结在一起。如果要彻底核实某笔交易丙是否有效,就要顺着这个链一直回溯到最原始的挖矿产出交易(在交易甲之前还有别的交易),这样保证了只要用户有区块链的完整拷贝(也就是目前全节点的那60G数据),就可以独立验证任何一笔交易的有效性

第二,每次汇款只能完全将支出账户里所有的币都花掉。以交易乙为例,汇款完成后原来的地址B就空了。如果只想转一半的资金到地址C,剩下的那一半就要在收款信息里另外填一个账户地址E,也就是所谓的找零地址

第三,总汇款金额小于地址B的部分就是手续费。如果地址B里有0.9999个币,汇款到地址C的金额是0.9998个币,那中间的差额0.0001就是矿工的手续费

第四,验证交易乙是否有效,是靠上一个交易即交易甲的收款信息中的兑现规则来保证的。可以有多种规则,目前最常见的两种就是提供该收款地址的签名(P2PKH)以及提供一段程序的哈希值(P2SH)。本例说的就是P2PKH

如果你完全看懂了,那你对比特币交易的功能理解,就接近于core程序员的水平了,以后碰到很多名词如scriptSig (签名+公钥) 和scriptPubKey(兑现条件)之类就很容易知道那都是汇款单上的哪个部分了

这里还有个较为复杂的概念即签名,我另外单独发文分析,这个签名和隔离见证有密切关系

 

 

 

1

BitThink Yellow v    6 天前   via iPhone

写科普辛苦了 但是纯文字解释真的很难 结合图片动画才好些。账本比喻个人觉得对理解帮助不大。

比特币感谢地址: 1Aug9NQPT1Hotn6BGhc14YeRHszMduhU79
kcb medium avatar
2

kcb Yellow v    6 天前

支持!看了一半,明天接着看

比特币感谢地址: 1CWdUWWgdVuLi7aBHNALqijXm1aecZxCuC
vatten medium avatar
3

vatten Yellow v    6 天前

我觉得账簿的例子很不错了,因为中本聪在创建比特币的时候,只能从传统金融体系的交易处理中借鉴,所以设计上肯定是类似的。找了张建行的汇款单,可对比这张单子看一下比特币的交易乙是怎么写的。可以看到绝大多数栏目都被省略了,只剩下付款信息和收款信息两部分(实际上有6个栏目,但这两部分最重要)

chehw medium avatar
4

chehw Yellow v    5 天前

@vatten
你上面那个“比特币交易单”的填写格式有点小问题。

如果与银行汇款单相对应,格式应该是:

注:
(1). “全称”一栏不用填写,因为比特币是“伪匿名性的”,账户不需要与真实姓名绑定。
(2). 比特币系统的“签名”,对应的是:银行工作人员验证你的身份证和你本人是否相符、银行卡密码是否输入正确等。备案信息(比如复印身份证)并不需要显示在汇款单上。

由(2)可以看出,“签名”信息在经过矿工验证后,实际上是可以单独存放的,交易提交时,需要提供签名信息,由矿工确认是否有支配权。当交易收录后,由于已经有POW工作量证明确认了,实际上就没必要把“签名”附加在交易记录本身,因为只有重新同步区块链的完全节点才需要签名信息。

vatten medium avatar
5

vatten Yellow v    5 天前

@chehw

你这是在说理想的比特币交易单应该是什么格式了,我这里给出的是目前的实现方式,具体就是这个表,我能把它翻译成汇款单形式也是花了一些心思的,因为要忠于原来的格式又便于理解。签名很复杂,所以我另外发文再说

vatten medium avatar
6

vatten Yellow v    5 天前

汇款单上每一栏都有中文说明,好让用户知道该填什么内容,但对计算机来说是不需要的,因为每个客户端都有对交易格式的标准定义和理解,所以只要按顺序发送这一串从010000到000000的数计算机就会识别了,以下就是这个完整的数串,可以看到是由付款信息(input)和收款信息(output)两大部分组成的,其中scriptSig部分包含了最多的数据,也就是签名和公钥

vatten medium avatar
7

vatten Yellow v    5 天前

@chehw

(1). “全称”一栏不用填写,因为比特币是“伪匿名性的”,账户不需要与真实姓名绑定。

没错,我那个图里已经没有全称一栏,只有一栏叫做付款信息,格式略有不同,但和比特币的格式接近

(2). 比特币系统的“签名”,对应的是:银行工作人员验证你的身份证和你本人是否相符、银行卡密码是否输入正确等。备案信息(比如复印身份证)并不需要显示在汇款单上。

这个签名就相当于你的私章。不过计算机实现起来比较不同,因为在人人都可接收的P2P网络上发送这个汇款单,没有银行之类的可信任的权威机构,就有两个难点:
1. 没有签名,其他人无法认证这张汇款单是否有效
2. 你还得保证这张汇款单不被恶意用户篡改

所以在比特币里,这张汇款单本身是包含在签名里的,这是整个比特币交易最复杂的地方,但也是安全最重要的保证,我另外写个贴分析

chehw medium avatar
8

chehw Yellow v    4 天前

@vatten

P2P网络上发送这个汇款单,没有银行之类的可信任的权威机构,就有两个难点:
1. 没有签名,其他人无法认证这张汇款单是否有效
2. 你还得保证这张汇款单不被恶意用户篡改

还有第3个难点:
3、 即使签名有效,在没有可信第三方确认的情况下,收款方无法确定是否存在双花————即自己是唯一的收款方。因为支付者可以签署多个有效签名,把同一笔钱同时转给若干人(例如:A把某一房产同时卖给B和C,在入住前,B无法知道C也买了同一处房产)。

针对上面的三个问题,比特币系统的解决方案是:
(1)借助公钥密码学的数字签名技术,可以无须可信第三方确认,依靠数字签名即可证明是支付者本人进行的汇款。
(2)借助merkle tree技术,网络上的任何人只要获取了对应merkle tree的分支(最多几百字节左右),就可以确定交易内容的真实完整性。恶意者即使篡改1个二进制位(bit)的数据也会被发现。
(3)借助区块链+POW工作量证明,恶意者只有持续控制了51%以上的算力(需要高额的资金成本和时间成本,算力=时间+金钱),才能故意制造出双花。

对于(1),由于验证签名时必须调取历史账目(outpoint中的UTXO),因此只有掌握了所有历史数据的完全节点才能做到。90%以上的用户(这里假设90%以上的用户没有足够的资源或耐心去运行完全节点)实际上是无法验证签名的。对于大部分用户来说,依赖的是POW工作量证明(矿工在收录交易时必须验证交易有效,否则挖出的块不会被其他全节点接受,只会白白浪费算力),用交易的确认数来确保交易有效。

由此可以看出,签名仅在矿工挖矿和全节点同步时才需要,对于90%以上的用户来说,收到的签名数据不仅自己无法处理,还占用了网络带宽和存储资源。
交易中的签名数据只是少数(但至关重要)群体才真正需要,所以“将签名分离出来,只提供给有需求的参与者”,这至少在理论上是成立的,现实实现起来也不难。

vatten medium avatar
9

vatten Yellow v    4 天前

@chehw

没错,你说的这些都是一些很了解比特币内部工作机制的人才明白的了,而我是试图写的让任何小学文化的人都能看懂并独立做出决策,而不是仅仅接受一些结论。但看到你说的这些相关问题,又联系上区块,我真的感觉要用一个账簿的例子来让任何人理解比特币的工作机理非常具有挑战性,我只能先试试

光有结论性的东西对做决策来说是没用的,比如说我是手持10个亿的基金,面对这么个结论:“借助公钥密码学的数字签名技术,可以无须可信第三方确认,依靠数字签名即可证明是支付者本人进行的汇款。”那我要问:凭什么依靠数字签名就一定可以证明是支付者本人进行的付款?我要因此而转账5个亿,谁能担保我的资金不会给黑了?然后我就得去查资料,结果是一堆火星文,丝毫无助于我增强对这个结论的信任度,因此决策不可能因为这个结论而做出

在不理解机理的情况下,可以依靠两种方式决策,一是看大多数人长时间的使用:如果很多人甚至银行都用这个系统转账很多年了,那风险相对来说就小了。银行通常不投资没有经过时间考验的创新,时间是最好的试金石。另一种则是我通过逐渐学习和了解其工作机理自己推导出来这种安全性是必然的,那我甚至可以做到领先市场。不过,要想了解到每个细节是非常困难的,通常都是了解到功能层面的逻辑,能判断主要方向正确即可,也就是说,面对未来的某种系统变化,本来该减少的不会判断成该增加,本来会变危险的不会判断为会变安全,能做到这点就足够了

你给的这三个结论,如果都问一个为什么,恐怕没有个很长的论文,是很难回答的。所以你直接把这三个结论当成公理并在此基础之上推导出来的推论,在这三个结论无法得到完全证明之前,都是无法用来做决策的(前两天我才看到一个视频说比特币所用的SECP256K1椭圆曲线签名不是一种很安全的方式,从来没有被研究机构推荐过)。但绝大多数人都没有可能有足够知识证明这三个结论,所以很可能会盲目相信权威所说的了,这就给了权威误导群众的机会。这种情况下我宁愿简单选择不用未经时间考验的系统

Advertisements
深入浅出比特币交易 (transaction)

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out /  Change )

Google+ photo

You are commenting using your Google+ account. Log Out /  Change )

Twitter picture

You are commenting using your Twitter account. Log Out /  Change )

Facebook photo

You are commenting using your Facebook account. Log Out /  Change )

w

Connecting to %s