|
1 |
| -# The Design of CKB Bitcoin SPV |
| 1 | +# CKB Bitcoin SPV Design |
2 | 2 |
|
3 |
| -CKB Bitcoin SPV is a library, for doing Bitcoin simplified payment |
4 |
| -verification on CKB. |
| 3 | +CKB Bitcoin SPV is a library designed to facilitate Bitcoin simplified payment verification (SPV) on Nervos CKB. |
5 | 4 |
|
6 | 5 | ## Abstract
|
7 | 6 |
|
8 |
| -This document describes the design and explains the technical details of CKB |
9 |
| -Bitcoin SPV, which allows users to do on-chain verification for bitcoin |
10 |
| -transactions on CKB chain. |
| 7 | +This document provides a comprehensive overview of the design and technical details of the CKB Bitcoin SPV. Through this material, developers will acquire the knowledge needed to perform on-chain verification of Bitcoin transactions on Nervos CKB. |
11 | 8 |
|
12 | 9 | ## Background
|
13 | 10 |
|
14 |
| -For understanding this document, the knowledge of the following concepts are |
15 |
| -**required**.\ |
16 |
| -But we won't discuss them here, please learn them on their own documents. |
| 11 | +A basic knowledge of the following concepts is **required** for a better understanding of this document. |
| 12 | + |
| 13 | +Below are brief explanations of each term along with links to sources for detailed learning: |
17 | 14 |
|
18 | 15 | ### Simplified Payment Verification (SPV)
|
19 | 16 |
|
20 |
| -[Simple Payment Verification][SPV], usually abbreviated to SPV, is noted in |
21 |
| -Bitcoin whitepaper. It allows a transaction recipient to prove that the |
22 |
| -sender has control of the source funds of the payment they are offering |
23 |
| -without downloading the full Blockchain, by utilizing the properties of |
24 |
| -Merkle proofs. |
| 17 | +[Simple Payment Verification][SPV] (SPV) allows a transaction receiver to confirm that the sender has control of the source funds of the payment they are offering, without needing to download the entire blockchain. This is achieved using Merkle proofs. |
25 | 18 |
|
26 |
| -### Bitcoin Difficulty Adjustments |
| 19 | +Refer to the [Bitcoin whitepaper](https://bitcoin.org/bitcoin.pdf) for more details. |
27 | 20 |
|
28 |
| -Every 2016 blocks (which should take two weeks if this goal is kept |
29 |
| -perfectly), every Bitcoin client compares the actual time it took to |
30 |
| -generate these blocks with the 2 weeks goal and modifies the target by the |
31 |
| -percentage difference.[^1] |
| 21 | +### Bitcoin Difficulty Adjustment |
32 | 22 |
|
33 |
| -> [!Note] |
34 |
| -> The difficulty re-target being based on the time taken for the previous |
35 |
| -> 2015 blocks instead of 2016 blocks.[^2] |
| 23 | +Bitcoin adjusts the computational difficulty of mining a block every 2016 blocks, which ideally takes two weeks. Every Bitcoin client |
| 24 | +adjusts the mining difficulty by comparing the actual production time of the last 2016 blocks to the intended 2-week period, and modifies the target based on the percentage difference. [^1] |
36 | 25 |
|
37 |
| -### Bitcoin Merkle Proof |
| 26 | +> [!Note] |
| 27 | +> “The difficulty re-target [is] based on the time taken for the previous 2015 blocks instead of 2016 blocks." [^2] |
38 | 28 |
|
39 |
| -A proof that proves a transaction (in fact, just transaction hash) was |
40 |
| -included in a block. |
| 29 | +### Bitcoin Merkle Proofs |
41 | 30 |
|
42 |
| -It could be fetched through the RPC API [`gettxoutproof`], and be verified |
43 |
| -with the RPC API [`verifytxoutproof`]. |
| 31 | +A Bitcoin Merkle proof verifies that a transaction - or specifically, its hash - was included in a given block. It can be fetched |
| 32 | +through the RPC API [`gettxoutproof`] and verified with RPC API [`verifytxoutproof`]. |
44 | 33 |
|
45 | 34 | ### Merkle Mountain Range (MMR)
|
46 | 35 |
|
47 |
| -A [Merkle Mountain Range (MMR)][MMR] is a binary hash tree that allows for |
48 |
| -efficient appends of new leaves without changing the value of existing nodes. |
| 36 | +A [Merkle Mountain Range (MMR)][MMR] is a binary hash tree data structure designed to allow efficient appending of new leaves while |
| 37 | +maintaining the integrity of the existing nodes. |
49 | 38 |
|
50 |
| -An MMR proof could be used to prove whether an item is included in an MMR |
51 |
| -root or not. |
| 39 | +A MMR proof can be utilized to verify whether a specific item is included in the MMR root. |
52 | 40 |
|
53 | 41 | ## Overview
|
54 | 42 |
|
55 |
| -First, we could divide the whole problem into 2 smaller and standalone problems. |
| 43 | +Let’s break down the entire problem into two smaller, independent steps. |
56 | 44 |
|
57 |
| -### 1. On CKB, prove a header belongs to the bitcoin chain |
| 45 | +### 1. On CKB, prove if a header belongs to the bitcoin chain |
58 | 46 |
|
59 | 47 | #### 1.1. Data preparation stage
|
60 | 48 |
|
61 |
| -Since we want to do on-chain verification, so the resources are limited, for |
62 |
| -example, we couldn't afford 100 MiB storage or 30 seconds expensive |
63 |
| -computation, on CKB. |
64 |
| - |
65 |
| -So, we introduce the [Merkle Mountain Range (MMR)][MMR] to solve this |
66 |
| -problem: we only save the MMR root of bitcoin headers on CKB. |
| 49 | +Given on-chain verification comes with resource constraints, such as the inability to afford 100 MiB of storage or 30 seconds of |
| 50 | +computation on CKB, the MMR is introduced to address this issue by only saving the MMR root of Bitcoin headers on CKB. |
67 | 51 |
|
68 |
| -- First, we initialize a cell with a bitcoin header at any height. |
| 52 | +Here's how it works: |
69 | 53 |
|
70 |
| - An MMR tree will be constructed with this header only, and its root will |
71 |
| - be saved in the cell data. |
| 54 | +1. initialize a cell with a Bitcoin header at any height. |
72 | 55 |
|
73 |
| - No on-chain verification will be done for this data. |
74 |
| - Users have to check the data off-chain, then trust it. |
| 56 | + An MMR tree is constructed with the header, and its root is saved in the cell data. |
| 57 | + No on-chain verification is performed during this initialization; users need to verify the data off-chain and then trust it. |
75 | 58 |
|
76 |
| -- Also, there will be a service, which builds the same MMR tree but off-chain. |
| 59 | +3. [ckb-bitcoin-spv-service](https://github.com/ckb-cell/ckb-bitcoin-spv-service) will build the same MMR tree off-chain. |
77 | 60 |
|
78 |
| - This service will listen to the bitcoin chain and wait for the next block. |
| 61 | + This service will listen to the Bitcoin blockchain for new blocks. When a new Bitcoin block is mined, the service will update the |
| 62 | + MMR tree with the new block, calculate a new MMR root, and then send both the new MMR root and the new block header to the CKB chain. |
79 | 63 |
|
80 |
| - When the next bitcoin block is mined, this service will append this new |
81 |
| - bitcoin block into the MMR tree, calculate a new MMR root, then send the |
82 |
| - new MMR root and the new header to the CKB chain. |
| 64 | +4. an on-chain [script](https://github.com/ckb-cell/ckb-bitcoin-spv-contracts/tree/master/contracts/ckb-bitcoin-spv-type-lock) performs the following checks: |
83 | 65 |
|
84 |
| -- An on-chain script will check those new data. |
| 66 | + 1) Check the new header with two parts: |
85 | 67 |
|
86 |
| - - First, check the new header with two parts: |
87 |
| - |
88 |
| - - The field "previous block header hash" in headers[^3] should be correct. |
| 68 | + - The field "previous block header hash" in headers[^3] should be correct; |
89 | 69 |
|
90 | 70 | - The POW for the block should be valid.
|
91 | 71 |
|
92 |
| - For security, the on-chain script has to calculate the POW target for |
93 |
| - the next block by itself. |
94 |
| - |
95 |
| - So, there are two more data have to be cached on chain: |
| 72 | + For security, the on-chain script calculates the POW target for |
| 73 | + the next block, requiring the on-chain caching of: |
96 | 74 |
|
97 | 75 | - The start time of the first block after difficulty adjustment.
|
98 | 76 |
|
99 | 77 | - If the next block is one of the first blocks after difficulty
|
100 | 78 | adjustment, its target should be calculated and cached.
|
101 | 79 |
|
102 |
| - - Then, check the new MMR root: |
| 80 | + 2) Check the new MMR root: |
103 | 81 |
|
104 |
| - - The new MMR root should be constructed based on the previous MMR root, |
105 |
| - and only the new header should be appended. |
| 82 | + - The new MMR root should be based on the previous MMR root with only the new header appended. |
106 | 83 |
|
107 |
| - After the above checks passed, then save the new data into the cell. |
| 84 | + Once these checks are passed, the new data is saved into the cell. |
108 | 85 |
|
109 | 86 | > [!NOTE]
|
110 |
| -> In bitcoin headers, the height is not stored, but we have to store all |
111 |
| -> heights on CKB chain.\ |
112 |
| -> The heights are required for two reasons: calculate the index of MMR and |
113 |
| -> calculate the block confirmations. |
| 87 | +> Bitcoin headers do not store the height, |
| 88 | +> but all heights must be stored on CKB chain for two reasons: |
| 89 | +> calculating the MMR index and determining block confirmations. |
114 | 90 |
|
115 | 91 | #### 1.2. Verification stage
|
116 | 92 |
|
117 |
| -With the stored MMR root on CKB, an on-chain script can check whether a |
118 |
| -bitcoin header is contained in that MMR tree. |
| 93 | +With the stored MMR root on CKB, an on-chain script can verify whether a |
| 94 | +Bitcoin header is part of the MMR tree. |
119 | 95 |
|
120 |
| -There are 3 items required to be submitted to the CKB chain: |
121 |
| -- The MMR proof of the header which is required to be proven. |
| 96 | +The following data are required to be submitted to the CKB chain: |
| 97 | +- The MMR proof of the header to be proven. |
122 | 98 | - The full data of the header, or its hash.
|
123 | 99 | - The height of the header.
|
124 | 100 |
|
125 |
| -As the PoW of the header has been verified, if a header is contained within the |
126 |
| -MMR tree on CKB, it implies that the corresponding header is part of the Bitcoin |
127 |
| -chain. |
| 101 | +As the PoW of the header is verified and the header is within the MMR tree on CKB, it implies that the corresponding header is part of the Bitcoin chain. |
128 | 102 |
|
129 |
| -### 2. On CKB, prove a transaction is in a bitcoin block |
| 103 | +### 2. On CKB, prove if a transaction is in a Bitcoin block |
130 | 104 |
|
131 | 105 | #### 2.1. Data preparation stage
|
132 | 106 |
|
133 |
| -No more data is required to be stored in the CKB chain for transactions |
| 107 | +No additional data is required to be stored on CKB chain for transactions |
134 | 108 | verification.
|
135 | 109 |
|
136 | 110 | #### 2.2. Verification stage
|
137 | 111 |
|
138 |
| -There is a field "merkle root hash" in bitcoin headers[^3]. |
| 112 | +A Bitcoin header[^3] contains a field called "merkle root hash". |
139 | 113 |
|
140 |
| -A merkle root is derived from the hashes of all transactions included in |
| 114 | +A merkle root is derived from the hashes of all transactions in |
141 | 115 | that block, ensuring that none of those transactions can be modified without
|
142 | 116 | modifying the header.
|
143 | 117 |
|
144 |
| -So, a transaction could be verified whether it's in a header, with the |
145 |
| -merkle root hash and a merkle proof which contains it. |
| 118 | +Thus, a transaction can be verified whether it's in a header, with the merkle root hash and a merkle proof. |
146 | 119 |
|
147 | 120 | ## Optimization
|
148 | 121 |
|
149 |
| -Save any data on chain will occupy the capacity of CKBytes permanently. And, |
150 |
| -not all bitcoin headers will be used.\ |
151 |
| -So, we won't save all bitcoin headers on the chain.\ |
152 |
| -For verification, we can just put them into the witnesses. |
| 122 | +Storing data on-chain will permanently occupy the capacity of CKBytes. Since not all Bitcoin headers will be used, not all Bitcoin |
| 123 | +headers will be saved on the chain. For verification, they can be included in the `witnesses`. |
153 | 124 |
|
154 |
| -When users want to verify a bitcoin header, they should submit that header |
155 |
| -to CKB chain, or only its hash is enough. |
| 125 | +When verifying a Bitcoin header, that header or only its hash should be submitted to the CKB chain. |
156 | 126 |
|
157 |
| -But when verifies a bitcoin transaction, the full header is required to be |
158 |
| -submitted to CKB chain; because the "merkle root hash" in the header is |
159 |
| -required. \ |
160 |
| -An interesting fact is, that the merkle proof of the transaction already |
161 |
| -contains the full header.[^4] So the header doesn't have to be submitted |
162 |
| -alone. |
| 127 | +However, when verifying a Bitcoin transaction, the full header must be submitted to the CKB chain because the "merkle root hash" in the |
| 128 | +header is required. An interesting fact is that the merkle proof of the transaction already contains the full header [^4] , so the |
| 129 | +header doesn't have to be submitted separately. |
163 | 130 |
|
164 | 131 | ## Disadvantages
|
165 | 132 |
|
166 |
| -- Calculate the MMR proof is not simple for normal users. |
| 133 | +- Calculating the MMR proof is complex for average users. |
167 | 134 |
|
168 |
| - A service is required, to collect all headers which are contained in the |
169 |
| - MMR root. |
| 135 | + A service is needed to collect all headers contained in the MMR root. |
170 | 136 |
|
171 | 137 | ## References
|
172 | 138 |
|
173 |
| -- [`CalculateNextWorkRequired(..)`] |
174 |
| - |
175 |
| - The function, which is used to calculate the next target. |
176 |
| - |
177 |
| -- [`CPartialMerkleTree::ExtractMatches(..)`] |
| 139 | +- [`CalculateNextWorkRequired(..)`]: This function is used to calculate the next target. |
178 | 140 |
|
179 |
| - The function ensures that the partial Merkle tree is correctly constructed. |
| 141 | +- [`CPartialMerkleTree::ExtractMatches(..)`]: This function ensures that the partial Merkle tree is correctly constructed. |
180 | 142 | It is used to verify that a proof points to transactions.
|
181 | 143 |
|
182 | 144 | - [Merkle Mountain Ranges][MMR]
|
|
0 commit comments