# Chia BLS 密钥架构

By [moonfunjohn](https://paragraph.com/@verashang) · 2022-02-11

---

引言
==

在这篇文章里面，我会阐述在Chia区块链网络中不同类型私钥的生成，存储，以及使用。这个私钥系统被设计得足够灵活来支持多种不同的配置和矿池设置，也能够抵御各种攻击。

BLS 私钥
======

所有 Chia 私钥都是 BLS-12-381 私钥，遵循 IETF 规范、用于私钥派生的 EIP-2333 规范和 BIP 44 注册。私钥是32字节，公钥是48字节，签名是96字节（公钥是G1中的点，签名是G2中的点。）。BLS签名允许许多功能和优化，如非交互式 m/n 阈值、在一个区块中聚合所有签名，以及将两个硬币合并到同一笔交易中的 chialisp 技巧。可以使用24个单词的助记词来生成私钥。用户可以只备份这24个单词，并在任何其它地方使用它们。

![Chia Keys架构图](https://storage.googleapis.com/papyrus_images/1ecfc71465811ff93aad87cc11cb23731085b4f7d18a4d373f48825e018346d4.png)

Chia Keys架构图

这24个单词的助记词可以与BLS主私钥相互转换。BLS主私钥存储在操作系统的钥匙串中，通常需要密码验证并进行加密。

主私钥可用于派生子私钥，子私钥还可用于派生孙私钥，级别数可以是无限的。多个BLS公钥可以聚合成一个新的公钥，用于验证聚合签名。

每次钱包生成一个新地址来接收资金时，它都会生成一个新的BLS私钥。农场主和矿池仅使用当前代码库中的第一个私钥，但可以更新它们以在每次赢得区块时生成新密钥，以增加隐私。pk代表公钥，sk代表私钥（密钥）。当钱包获得支付时，会创建一个使用钱包BLS公钥的chialisp程序，这个程序被称为拼图，经过哈希处理以生成拼图哈希(Puzzle Hash)。然后将拼图哈希转换为 bech32m 格式的地址。地址格式更方便纠错和使用。因此，一个地址相当于钱包的一个子BLS公钥，其私钥是从主私钥派生。

农田ID
====

农田ID是一个32字节的值，作为确定性种子来创建整个农田。具有相同农田ID的两个农田将创建两个字节相同的农田文件。农田ID是能被公开读取的，可以放入空间对象的证明中。

可以通过两种方式来生成农田ID，具体取决于农田所需的耕作方法。

![农田ID](https://storage.googleapis.com/papyrus_images/03dedd81e37c7b991fa43925cde5f12586f761801f06d02912031bc5e5ef6fa9.png)

农田ID

1.  向矿池公钥耕种。这种耕种方法适合单独耕种（无矿池）或开始在没有任何XCH的情况下耕种。为了耕种这样的农田，我们将农田公钥和矿池公钥散列在一起。当成功耕种一个区块时，矿池私钥必须对奖励地址进行签名。这种方法的缺点是如果使用矿池，矿池不能改变，农田永远和矿池绑定在一起。
    
2.  向矿池的智能合约地址耕种。这种耕作方式适合想要使用矿池耕种，但也可以在以后更改自己农田所属矿池的用户。奖励直接进入拼图哈希（智能合约地址），而不是需要矿池的签名，它被编码到农田中。这个地址是一个由用户控制的智能合约地址，这个智能合约指定了用户当前的矿池。用户可以切换矿池，这会有一定的延迟(约24小时)。新奖励将会重新路由到新矿池。这种方法的缺点是它需要在耕种之前创建区块链交易。因此，用户在开始耕种之前必须先拥有XCH。
    

农田公钥
====

那么，上图中显示的农田公钥是什么？农田公钥是一个2/2 BLS聚合公钥，由农夫公钥和本地公钥结合生成。本地公钥是收割机为每个农田创建的完全随机的私钥生成的公钥，并放入该农田中。它们不是任何BLS私钥的子项，因此不同的农田之间是完全独立。农夫私钥是在农夫机器存储的私钥。

每个区块都需要来自农田私钥的签名。这意味着我们需要聚合两个签名：一个来自本地私钥，由收割机生成，另一个来自农夫私钥，由农夫生成。农夫将两个签名聚合起来生成农田签名。

农田格式
====

农田格式取决于使用的是农场向矿池公钥耕种还是农场向智能合约地址耕种。如果耕种到智能合约地址，则拼图哈希（智能合约地址）会直接编码到农田中。否则，矿池公钥将直接编码到农田中。请注意，这不是确切的农田格式，此处省略了更多细节。

![农田格式](https://storage.googleapis.com/papyrus_images/4e2d7c23a699293fefe77e777723c9daedc7e569593f7d5f9d1e8574e48ada0b.png)

农田格式

这里重要的一点是收割机只在农田中存储他们的本地私钥，农田不需要从收割机获取其他私钥。仅凭这本地私钥是无法做任何事情的，因为它必须与农民的钥匙结合使用。因此，攻击收割机无法重定向区块奖励。

架构
==

下图设计了一个架构，农民决定将所有私钥分开。钱包私钥在钱包服务节点中，可以选择冷存储。收割机节点把本地私钥分散于各个农田。农夫节点存储农夫私钥，以及一个单独的矿池节点存储矿池私钥。请注意，在最简单的配置中，用户可以在同一台机器上运行所有服务（钱包、节点、收割机、农民、矿池），在这种情况下所有私钥使用相同的主私钥。

![架构](https://storage.googleapis.com/papyrus_images/08d78acf83bb410881b0290b10b3030765303f11f768f79b230907c1654093da.png)

架构

在此架构中，收割机仅存储农田，并在必要时向农夫提供农田本地私钥的签名。农夫机器有自己的私钥，用于创建新区块的签名，并将它们与农田本地私钥签名结合。农夫机器可以设置钱包地址来接收资产，这样用户就可以将他们的钱包私钥冷存储起来。此外，农夫和收割机之间的通信通道通过TLS证书进行身份验证，这使收割机可以知道农夫是否可信。

农夫还可以定期向矿池索要签名，用于对矿池奖励币进行签名。回想一下，每个区块都有资格创建两个coinbase奖励币：矿池奖励为 7/8，农夫奖励为 1/8 + 交易费用。

如果使用矿池智能合约拼图哈希，则矿池签名不包含在区块中。

---

*Originally published on [moonfunjohn](https://paragraph.com/@verashang/chia-bls)*
