1use darkfi_sdk::{
20 crypto::{
21 schnorr::{SchnorrSecret, Signature},
22 MerkleTree, SecretKey,
23 },
24 pasta::{group::ff::FromUniformBytes, pallas},
25 tx::TransactionHash,
26};
27#[cfg(feature = "async-serial")]
28use darkfi_serial::async_trait;
29use darkfi_serial::{deserialize, serialize, SerialDecodable, SerialEncodable};
30use num_bigint::BigUint;
31use sled_overlay::{sled, SledDbOverlayStateDiff};
32
33use crate::{tx::Transaction, util::time::Timestamp, Error, Result};
34
35use super::{parse_record, parse_u32_key_record, Header, HeaderHash, SledDbOverlayPtr};
36
37#[derive(Debug, Clone, SerialEncodable, SerialDecodable)]
43pub struct Block {
44 pub header: HeaderHash,
46 pub txs: Vec<TransactionHash>,
48 pub signature: Signature,
50}
51
52impl Block {
53 pub fn new(header: HeaderHash, txs: Vec<TransactionHash>, signature: Signature) -> Self {
54 Self { header, txs, signature }
55 }
56
57 pub fn hash(&self) -> HeaderHash {
59 self.header
60 }
61
62 pub fn from_block_info(block_info: &BlockInfo) -> Self {
64 let header = block_info.header.hash();
65 let txs = block_info.txs.iter().map(|tx| tx.hash()).collect();
66 let signature = block_info.signature;
67 Self { header, txs, signature }
68 }
69}
70
71#[derive(Debug, Clone, SerialEncodable, SerialDecodable)]
77pub struct BlockInfo {
79 pub header: Header,
81 pub txs: Vec<Transaction>,
83 pub signature: Signature,
85}
86impl Default for BlockInfo {
89 fn default() -> Self {
91 Self {
92 header: Header::default(),
93 txs: vec![Transaction::default()],
94 signature: Signature::dummy(),
95 }
96 }
97}
98
99impl BlockInfo {
100 pub fn new(header: Header, txs: Vec<Transaction>, signature: Signature) -> Self {
101 Self { header, txs, signature }
102 }
103
104 pub fn new_empty(header: Header) -> Self {
107 let txs = vec![];
108 let signature = Signature::dummy();
109 Self { header, txs, signature }
110 }
111
112 pub fn hash(&self) -> HeaderHash {
114 self.header.hash()
115 }
116
117 pub fn append_tx(&mut self, tx: Transaction) {
121 let mut tree = MerkleTree::new(1);
122 for block_tx in &self.txs {
124 append_tx_to_merkle_tree(&mut tree, block_tx);
125 }
126 append_tx_to_merkle_tree(&mut tree, &tx);
128 self.txs.push(tx);
129 self.header.transactions_root = tree.root(0).unwrap();
131 }
132
133 pub fn append_txs(&mut self, txs: Vec<Transaction>) {
138 let mut tree = MerkleTree::new(1);
139 for block_tx in &self.txs {
141 append_tx_to_merkle_tree(&mut tree, block_tx);
142 }
143 for tx in txs {
145 append_tx_to_merkle_tree(&mut tree, &tx);
146 self.txs.push(tx);
147 }
148 self.header.transactions_root = tree.root(0).unwrap();
150 }
151
152 pub fn sign(&mut self, secret_key: &SecretKey) {
154 self.signature = secret_key.sign(self.hash().inner());
155 }
156}
157
158#[derive(Debug, SerialEncodable, SerialDecodable)]
160pub struct BlockOrder {
161 pub height: u32,
163 pub block: HeaderHash,
165}
166
167#[derive(Clone, Debug, SerialEncodable, SerialDecodable)]
173pub struct BlockRanks {
174 pub target_rank: BigUint,
176 pub targets_rank: BigUint,
178 pub hash_rank: BigUint,
180 pub hashes_rank: BigUint,
182}
183
184impl BlockRanks {
185 pub fn new(
186 target_rank: BigUint,
187 targets_rank: BigUint,
188 hash_rank: BigUint,
189 hashes_rank: BigUint,
190 ) -> Self {
191 Self { target_rank, targets_rank, hash_rank, hashes_rank }
192 }
193}
194
195#[derive(Clone, Debug, SerialEncodable, SerialDecodable)]
201pub struct BlockDifficulty {
202 pub height: u32,
204 pub timestamp: Timestamp,
206 pub difficulty: BigUint,
208 pub cumulative_difficulty: BigUint,
210 pub ranks: BlockRanks,
212}
213
214impl BlockDifficulty {
215 pub fn new(
216 height: u32,
217 timestamp: Timestamp,
218 difficulty: BigUint,
219 cumulative_difficulty: BigUint,
220 ranks: BlockRanks,
221 ) -> Self {
222 Self { height, timestamp, difficulty, cumulative_difficulty, ranks }
223 }
224
225 pub fn genesis(timestamp: Timestamp) -> Self {
227 let ranks = BlockRanks::new(
228 BigUint::from(0u64),
229 BigUint::from(0u64),
230 BigUint::from(0u64),
231 BigUint::from(0u64),
232 );
233 BlockDifficulty::new(0u32, timestamp, BigUint::from(0u64), BigUint::from(0u64), ranks)
234 }
235}
236
237pub const SLED_BLOCK_TREE: &[u8] = b"_blocks";
238pub const SLED_BLOCK_ORDER_TREE: &[u8] = b"_block_order";
239pub const SLED_BLOCK_DIFFICULTY_TREE: &[u8] = b"_block_difficulty";
240pub const SLED_BLOCK_STATE_INVERSE_DIFF_TREE: &[u8] = b"_block_state_inverse_diff";
241
242#[derive(Clone)]
245pub struct BlockStore {
246 pub main: sled::Tree,
249 pub order: sled::Tree,
253 pub difficulty: sled::Tree,
257 pub state_inverse_diff: sled::Tree,
261}
262
263impl BlockStore {
264 pub fn new(db: &sled::Db) -> Result<Self> {
266 let main = db.open_tree(SLED_BLOCK_TREE)?;
267 let order = db.open_tree(SLED_BLOCK_ORDER_TREE)?;
268 let difficulty = db.open_tree(SLED_BLOCK_DIFFICULTY_TREE)?;
269 let state_inverse_diff = db.open_tree(SLED_BLOCK_STATE_INVERSE_DIFF_TREE)?;
270 Ok(Self { main, order, difficulty, state_inverse_diff })
271 }
272
273 pub fn insert(&self, blocks: &[Block]) -> Result<Vec<HeaderHash>> {
275 let (batch, ret) = self.insert_batch(blocks);
276 self.main.apply_batch(batch)?;
277 Ok(ret)
278 }
279
280 pub fn insert_order(&self, heights: &[u32], hashes: &[HeaderHash]) -> Result<()> {
283 let batch = self.insert_batch_order(heights, hashes);
284 self.order.apply_batch(batch)?;
285 Ok(())
286 }
287
288 pub fn insert_difficulty(&self, block_difficulties: &[BlockDifficulty]) -> Result<()> {
291 let batch = self.insert_batch_difficulty(block_difficulties);
292 self.difficulty.apply_batch(batch)?;
293 Ok(())
294 }
295
296 pub fn insert_state_inverse_diff(
299 &self,
300 heights: &[u32],
301 diffs: &[SledDbOverlayStateDiff],
302 ) -> Result<()> {
303 let batch = self.insert_batch_state_inverse_diff(heights, diffs);
304 self.state_inverse_diff.apply_batch(batch)?;
305 Ok(())
306 }
307
308 pub fn insert_batch(&self, blocks: &[Block]) -> (sled::Batch, Vec<HeaderHash>) {
314 let mut ret = Vec::with_capacity(blocks.len());
315 let mut batch = sled::Batch::default();
316
317 for block in blocks {
318 let blockhash = block.hash();
319 batch.insert(blockhash.inner(), serialize(block));
320 ret.push(blockhash);
321 }
322
323 (batch, ret)
324 }
325
326 pub fn insert_batch_order(&self, heights: &[u32], hashes: &[HeaderHash]) -> sled::Batch {
330 let mut batch = sled::Batch::default();
331
332 for (i, height) in heights.iter().enumerate() {
333 batch.insert(&height.to_be_bytes(), hashes[i].inner());
334 }
335
336 batch
337 }
338
339 pub fn insert_batch_difficulty(&self, block_difficulties: &[BlockDifficulty]) -> sled::Batch {
344 let mut batch = sled::Batch::default();
345
346 for block_difficulty in block_difficulties {
347 batch.insert(&block_difficulty.height.to_be_bytes(), serialize(block_difficulty));
348 }
349
350 batch
351 }
352
353 pub fn insert_batch_state_inverse_diff(
358 &self,
359 heights: &[u32],
360 diffs: &[SledDbOverlayStateDiff],
361 ) -> sled::Batch {
362 let mut batch = sled::Batch::default();
363
364 for (i, height) in heights.iter().enumerate() {
365 batch.insert(&height.to_be_bytes(), serialize(&diffs[i]));
366 }
367
368 batch
369 }
370
371 pub fn contains(&self, blockhash: &HeaderHash) -> Result<bool> {
373 Ok(self.main.contains_key(blockhash.inner())?)
374 }
375
376 pub fn contains_order(&self, height: u32) -> Result<bool> {
378 Ok(self.order.contains_key(height.to_be_bytes())?)
379 }
380
381 pub fn get(&self, block_hashes: &[HeaderHash], strict: bool) -> Result<Vec<Option<Block>>> {
387 let mut ret = Vec::with_capacity(block_hashes.len());
388
389 for hash in block_hashes {
390 if let Some(found) = self.main.get(hash.inner())? {
391 let block = deserialize(&found)?;
392 ret.push(Some(block));
393 continue
394 }
395 if strict {
396 return Err(Error::BlockNotFound(hash.as_string()))
397 }
398 ret.push(None);
399 }
400
401 Ok(ret)
402 }
403
404 pub fn get_order(&self, heights: &[u32], strict: bool) -> Result<Vec<Option<HeaderHash>>> {
410 let mut ret = Vec::with_capacity(heights.len());
411
412 for height in heights {
413 if let Some(found) = self.order.get(height.to_be_bytes())? {
414 let block_hash = deserialize(&found)?;
415 ret.push(Some(block_hash));
416 continue
417 }
418 if strict {
419 return Err(Error::BlockHeightNotFound(*height))
420 }
421 ret.push(None);
422 }
423
424 Ok(ret)
425 }
426
427 pub fn get_difficulty(
434 &self,
435 heights: &[u32],
436 strict: bool,
437 ) -> Result<Vec<Option<BlockDifficulty>>> {
438 let mut ret = Vec::with_capacity(heights.len());
439
440 for height in heights {
441 if let Some(found) = self.difficulty.get(height.to_be_bytes())? {
442 let block_difficulty = deserialize(&found)?;
443 ret.push(Some(block_difficulty));
444 continue
445 }
446 if strict {
447 return Err(Error::BlockDifficultyNotFound(*height))
448 }
449 ret.push(None);
450 }
451
452 Ok(ret)
453 }
454
455 pub fn get_state_inverse_diff(
462 &self,
463 heights: &[u32],
464 strict: bool,
465 ) -> Result<Vec<Option<SledDbOverlayStateDiff>>> {
466 let mut ret = Vec::with_capacity(heights.len());
467
468 for height in heights {
469 if let Some(found) = self.state_inverse_diff.get(height.to_be_bytes())? {
470 let state_inverse_diff = deserialize(&found)?;
471 ret.push(Some(state_inverse_diff));
472 continue
473 }
474 if strict {
475 return Err(Error::BlockStateInverseDiffNotFound(*height))
476 }
477 ret.push(None);
478 }
479
480 Ok(ret)
481 }
482
483 pub fn get_all(&self) -> Result<Vec<(HeaderHash, Block)>> {
487 let mut blocks = vec![];
488
489 for block in self.main.iter() {
490 blocks.push(parse_record(block.unwrap())?);
491 }
492
493 Ok(blocks)
494 }
495
496 pub fn get_all_order(&self) -> Result<Vec<(u32, HeaderHash)>> {
500 let mut order = vec![];
501
502 for record in self.order.iter() {
503 order.push(parse_u32_key_record(record.unwrap())?);
504 }
505
506 Ok(order)
507 }
508
509 pub fn get_order_by_range(&self, start: u32, end: u32) -> Result<Vec<(u32, HeaderHash)>> {
512 if start >= end {
513 return Err(Error::DatabaseError(format!("Heights range is invalid: {start}..{end}")))
514 }
515
516 let mut blocks = vec![];
517
518 let start_key = start.to_be_bytes();
519 let end_key = end.to_be_bytes();
520
521 for block in self.order.range(start_key..=end_key) {
522 blocks.push(parse_u32_key_record(block.unwrap())?);
523 }
524
525 Ok(blocks)
526 }
527
528 pub fn get_all_difficulty(&self) -> Result<Vec<(u32, BlockDifficulty)>> {
532 let mut block_difficulties = vec![];
533
534 for record in self.difficulty.iter() {
535 block_difficulties.push(parse_u32_key_record(record.unwrap())?);
536 }
537
538 Ok(block_difficulties)
539 }
540
541 pub fn get_before(&self, height: u32, n: usize) -> Result<Vec<HeaderHash>> {
545 let mut ret = vec![];
546
547 let mut key = height;
548 let mut counter = 0;
549 while counter < n {
550 let record = self.order.get_lt(key.to_be_bytes())?;
551 if record.is_none() {
552 break
553 }
554 let (height, hash) = parse_u32_key_record(record.unwrap())?;
557 key = height;
558 ret.insert(0, hash);
559 counter += 1;
560 }
561
562 Ok(ret)
563 }
564
565 pub fn get_all_after(&self, height: u32) -> Result<Vec<HeaderHash>> {
569 let mut ret = vec![];
570
571 let mut key = height;
572 while let Some(found) = self.order.get_gt(key.to_be_bytes())? {
573 let (height, hash) = parse_u32_key_record(found)?;
574 key = height;
575 ret.push(hash);
576 }
577
578 Ok(ret)
579 }
580
581 pub fn get_first(&self) -> Result<(u32, HeaderHash)> {
584 let Some(found) = self.order.first()? else { return Err(Error::BlockHeightNotFound(0u32)) };
585 let (height, hash) = parse_u32_key_record(found)?;
586
587 Ok((height, hash))
588 }
589
590 pub fn get_last(&self) -> Result<(u32, HeaderHash)> {
593 let found = self.order.last()?.unwrap();
594 let (height, hash) = parse_u32_key_record(found)?;
595
596 Ok((height, hash))
597 }
598
599 pub fn get_last_n_orders(&self, n: usize) -> Result<Vec<(u32, HeaderHash)>> {
601 let records = self.order.iter().rev().take(n);
603
604 let mut last_n = vec![];
607 for record in records {
608 let record = record?;
609 let parsed_record = parse_u32_key_record(record)?;
610 last_n.insert(0, parsed_record);
611 }
612 Ok(last_n)
613 }
614
615 pub fn get_last_difficulty(&self) -> Result<Option<BlockDifficulty>> {
619 let Some(found) = self.difficulty.last()? else { return Ok(None) };
620 let block_difficulty = deserialize(&found.1)?;
621 Ok(Some(block_difficulty))
622 }
623
624 pub fn get_last_n_difficulties(&self, n: usize) -> Result<Vec<BlockDifficulty>> {
626 let records = self.difficulty.iter().rev().take(n);
628 let mut last_n = vec![];
631 for record in records {
632 last_n.insert(0, deserialize(&record?.1)?);
633 }
634
635 Ok(last_n)
636 }
637
638 pub fn get_difficulties_before(&self, height: u32, n: usize) -> Result<Vec<BlockDifficulty>> {
642 let mut ret = vec![];
643
644 let mut key = height;
645 let mut counter = 0;
646 while counter < n {
647 let record = self.difficulty.get_lt(key.to_be_bytes())?;
648 if record.is_none() {
649 break
650 }
651 let (height, difficulty) = parse_u32_key_record(record.unwrap())?;
654 key = height;
655 ret.insert(0, difficulty);
656 counter += 1;
657 }
658
659 Ok(ret)
660 }
661
662 pub fn get_state_inverse_diffs_after(
667 &self,
668 height: u32,
669 ) -> Result<Vec<SledDbOverlayStateDiff>> {
670 let mut ret = vec![];
671
672 let mut key = height;
673 while let Some(found) = self.state_inverse_diff.get_gt(key.to_be_bytes())? {
674 let (height, state_inverse_diff) = parse_u32_key_record(found)?;
675 key = height;
676 ret.push(state_inverse_diff);
677 }
678
679 Ok(ret)
680 }
681
682 pub fn len(&self) -> usize {
684 self.order.len()
685 }
686
687 pub fn is_empty(&self) -> bool {
689 self.order.is_empty()
690 }
691}
692
693pub struct BlockStoreOverlay(SledDbOverlayPtr);
695
696impl BlockStoreOverlay {
697 pub fn new(overlay: &SledDbOverlayPtr) -> Result<Self> {
698 overlay.lock().unwrap().open_tree(SLED_BLOCK_TREE, true)?;
699 overlay.lock().unwrap().open_tree(SLED_BLOCK_ORDER_TREE, true)?;
700 overlay.lock().unwrap().open_tree(SLED_BLOCK_DIFFICULTY_TREE, true)?;
701 overlay.lock().unwrap().open_tree(SLED_BLOCK_STATE_INVERSE_DIFF_TREE, true)?;
702 Ok(Self(overlay.clone()))
703 }
704
705 pub fn insert(&self, blocks: &[Block]) -> Result<Vec<HeaderHash>> {
710 let mut ret = Vec::with_capacity(blocks.len());
711 let mut lock = self.0.lock().unwrap();
712
713 for block in blocks {
714 let blockhash = block.hash();
715 lock.insert(SLED_BLOCK_TREE, blockhash.inner(), &serialize(block))?;
716 ret.push(blockhash);
717 }
718
719 Ok(ret)
720 }
721
722 pub fn insert_order(&self, heights: &[u32], hashes: &[HeaderHash]) -> Result<()> {
725 if heights.len() != hashes.len() {
726 return Err(Error::InvalidInputLengths)
727 }
728
729 let mut lock = self.0.lock().unwrap();
730
731 for (i, height) in heights.iter().enumerate() {
732 lock.insert(SLED_BLOCK_ORDER_TREE, &height.to_be_bytes(), hashes[i].inner())?;
733 }
734
735 Ok(())
736 }
737
738 pub fn insert_difficulty(&self, block_difficulties: &[BlockDifficulty]) -> Result<()> {
740 let mut lock = self.0.lock().unwrap();
741
742 for block_difficulty in block_difficulties {
743 lock.insert(
744 SLED_BLOCK_DIFFICULTY_TREE,
745 &block_difficulty.height.to_be_bytes(),
746 &serialize(block_difficulty),
747 )?;
748 }
749
750 Ok(())
751 }
752
753 pub fn get(&self, block_hashes: &[HeaderHash], strict: bool) -> Result<Vec<Option<Block>>> {
759 let mut ret = Vec::with_capacity(block_hashes.len());
760 let lock = self.0.lock().unwrap();
761
762 for hash in block_hashes {
763 if let Some(found) = lock.get(SLED_BLOCK_TREE, hash.inner())? {
764 let block = deserialize(&found)?;
765 ret.push(Some(block));
766 continue
767 }
768 if strict {
769 return Err(Error::BlockNotFound(hash.as_string()))
770 }
771 ret.push(None);
772 }
773
774 Ok(ret)
775 }
776
777 pub fn get_order(&self, heights: &[u32], strict: bool) -> Result<Vec<Option<HeaderHash>>> {
783 let mut ret = Vec::with_capacity(heights.len());
784 let lock = self.0.lock().unwrap();
785
786 for height in heights {
787 if let Some(found) = lock.get(SLED_BLOCK_ORDER_TREE, &height.to_be_bytes())? {
788 let block_hash = deserialize(&found)?;
789 ret.push(Some(block_hash));
790 continue
791 }
792 if strict {
793 return Err(Error::BlockHeightNotFound(*height))
794 }
795 ret.push(None);
796 }
797
798 Ok(ret)
799 }
800
801 pub fn get_last(&self) -> Result<(u32, HeaderHash)> {
804 let found = match self.0.lock().unwrap().last(SLED_BLOCK_ORDER_TREE)? {
805 Some(b) => b,
806 None => return Err(Error::BlockHeightNotFound(0u32)),
807 };
808 let (height, hash) = parse_u32_key_record(found)?;
809
810 Ok((height, hash))
811 }
812
813 pub fn is_empty(&self) -> Result<bool> {
815 Ok(self.0.lock().unwrap().is_empty(SLED_BLOCK_ORDER_TREE)?)
816 }
817}
818
819pub fn append_tx_to_merkle_tree(tree: &mut MerkleTree, tx: &Transaction) {
821 let mut buf = [0u8; 64];
822 buf[..32].copy_from_slice(tx.hash().inner());
823 let leaf = pallas::Base::from_uniform_bytes(&buf);
824 tree.append(leaf.into());
825}