#![forbid(unsafe_op_in_unsafe_fn)]
pub mod bip112;
pub mod bip113;
pub mod bip141;
pub mod bip143;
pub mod bip30;
pub mod bip34;
pub mod bip341;
pub mod bip342;
pub mod bip65;
pub mod bip66;
pub mod bip68;
pub mod bip9;
pub mod connect_block;
pub mod kernel;
pub mod rust_path;
pub mod verify_block;
pub mod verify_tx;
pub use bip9::{DeploymentContext, DeploymentParams, DeploymentState, compute_state};
pub use connect_block::connect_block_dual_path;
pub use rust_path::{BlockState, RustValidator, TipState, UtxoView};
pub use verify_block::{
BlockRuleContext, verify_block_rules, verify_block_rules_borrowed,
verify_block_rules_borrowed_contextual, verify_block_rules_borrowed_contextual_with_txids,
verify_block_rules_borrowed_contextual_with_txids_and_witness_hint,
verify_block_rules_contextual,
};
pub use verify_tx::{
is_final_tx, verify_coinbase_script_sig_size, verify_transaction, verify_transaction_borrowed,
verify_transaction_borrowed_non_script_with_mtp, verify_transaction_borrowed_with_mtp,
verify_transaction_with_mtp,
};
use thiserror::Error;
#[derive(Debug, Error, Clone, PartialEq, Eq)]
pub enum ConsensusError {
#[error("transaction has no inputs")]
EmptyInputs,
#[error("transaction has no outputs")]
EmptyOutputs,
#[error("coinbase scriptSig length {len} outside allowed range 2..=100 bytes")]
CoinbaseScriptSigSize {
len: usize,
},
#[error("non-coinbase transaction input {input_index} spends a null outpoint")]
NullPrevout {
input_index: usize,
},
#[error("transaction contains duplicate input {input_index}")]
DuplicateInput {
input_index: usize,
},
#[error("missing prevout for input {input_index}")]
MissingPrevout {
input_index: usize,
},
#[error("transaction output value exceeds max money")]
OutputValueOverflow,
#[error("transaction spends {input_value} sats but creates {output_value} sats")]
InputsLessThanOutputs {
input_value: u64,
output_value: u64,
},
#[error("script verification failed at input {input_index}: {reason}")]
Script {
input_index: usize,
reason: String,
},
#[error("sigop cost {cost} exceeds max {max}")]
SigopsLimit {
cost: u32,
max: u32,
},
#[error("block has no transactions")]
EmptyBlock,
#[error("block first transaction is not coinbase")]
MissingCoinbase,
#[error("block transaction {tx_index} is coinbase outside position 0")]
ExtraCoinbase {
tx_index: usize,
},
#[error("block merkle tree contains a duplicate transaction mutation")]
MerkleMutation,
#[error("block merkle root mismatch")]
MerkleRoot,
#[error("block witness commitment mismatch")]
WitnessCommitment,
#[error("block weight {weight} exceeds max {max}")]
BlockWeight {
weight: u64,
max: u64,
},
#[error("{bip}: {reason}")]
Bip {
bip: &'static str,
reason: String,
},
#[error("kernel validation failed: {0}")]
Kernel(String),
#[error("consensus encoding failed: {0}")]
Encoding(String),
}
pub const MAX_MONEY: u64 = 21_000_000 * 100_000_000;
pub const MAX_BLOCK_SIGOPS_COST: u32 = 80_000;