Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion hintfile/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ edition = "2021"

[dependencies]
bitcoin = { workspace = true }
kernel = { package = "bitcoinkernel", git = "https://github.com/alexanderwiederin/rust-bitcoinkernel.git", rev = "31a53ebc81cf3648de2adea3ef7ee62b7a993221" }
kernel = { package = "bitcoinkernel", git = "https://github.com/alexanderwiederin/rust-bitcoinkernel.git", rev = "b7b42d65a70f2c0e5fc8d1d024549bf857211046" }

[[bin]]
name = "construct"
40 changes: 18 additions & 22 deletions hintfile/src/bin/construct.rs
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
use std::{fs::File, io::Write, sync::Arc};

use bitcoin::{consensus, OutPoint};
use hintfile::write_compact_size;
use kernel::{ChainType, ChainstateManager, ChainstateManagerOptions, ContextBuilder, KernelError};

Expand All @@ -21,35 +20,32 @@ fn main() {
let _context = Arc::new(ctx);
let chainman = ChainstateManager::new(options).unwrap();
println!("Chain state initialized");
let genesis = chainman.block_index_genesis();
// Writing the chain tip allows the client to know where to stop
let tip = chainman.block_index_tip().block_hash().hash;
file.write_all(&tip).unwrap();
file.write_all(&tip).expect("file cannot be written to");

let genesis = chainman.block_index_genesis();
let mut current = chainman.next_block_index(genesis).unwrap();
loop {
let block = chainman.read_block_data(&current).unwrap();
let bytes: Vec<u8> = block.into();
let block = consensus::deserialize::<bitcoin::Block>(&bytes).unwrap();
let (_, transactions) = block.into_parts();
println!("On block {}", current.height());
let mut delta: u64 = 0;
let mut block_offsets: Vec<u64> = Vec::new();
for tx in transactions {
let txid = tx.compute_txid();
for (index, _txout) in tx.outputs.iter().enumerate() {
let _outpoint = OutPoint {
txid,
vout: index as u32,
};
// if true
block_offsets.push(delta);
delta = 0;
println!("Block {} ...", current.height());
let mut block_unspents = Vec::new();
let mut curr = 0;
for i in 0..block.transaction_count() {
let transaction = block.transaction(i).unwrap();
for vout in 0..transaction.output_count() {
if chainman.have_coin(&transaction, vout) {
println!("Found coin at offset {curr}");
block_unspents.push(curr);
}
curr += 1;
}
}

// Overflows 32 bit machines
let len_encode = block_offsets.len() as u64;
println!("Writing block offsets");
let len_encode = block_unspents.len() as u64;
write_compact_size(len_encode, &mut file).expect("unexpected EOF");
for offset in block_offsets {
for offset in block_unspents {
write_compact_size(offset, &mut file).expect("unexpected EOF");
}
match chainman.next_block_index(current) {
Expand Down
13 changes: 11 additions & 2 deletions hintfile/src/lib.rs
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@ use std::{
io::{self, Read, Write},
};

use bitcoin::{BlockHeight, BlockHeightInterval};
use bitcoin::{consensus, BlockHash, BlockHeight, BlockHeightInterval};

pub fn write_compact_size<W: Write>(value: u64, writer: &mut W) -> Result<(), io::Error> {
match value {
Expand Down Expand Up @@ -45,6 +45,7 @@ pub fn read_compact_size<R: Read>(reader: &mut R) -> Result<u64, io::Error> {
#[derive(Debug)]
pub struct Hints {
map: BTreeMap<BlockHeight, Vec<u64>>,
assume_valid: BlockHash,
}

impl Hints {
Expand All @@ -54,6 +55,9 @@ impl Hints {
pub fn from_file<R: Read>(reader: &mut R) -> Self {
let mut map = BTreeMap::new();
let mut height = BlockHeight::from_u32(1);
let mut buf = [0; 32];
reader.read_exact(&mut buf).expect("empty file");
let assume_valid = consensus::deserialize::<BlockHash>(&buf).expect("empty file.");
while let Ok(count) = read_compact_size(reader) {
// panics on 32 bit machines
let mut offsets = Vec::with_capacity(count as usize);
Expand All @@ -65,7 +69,12 @@ impl Hints {
.checked_add(BlockHeightInterval::from_u32(1))
.expect("hintfile absurdly large.")
}
Self { map }
Self { map, assume_valid }
}

/// Get the last hash encoded in the hintfile.
pub fn stop_hash(&self) -> BlockHash {
self.assume_valid
}

/// # Panics
Expand Down