proper counting block fees and rewards
This commit is contained in:
parent
9fc5583fa3
commit
91206defc1
|
@ -5,7 +5,7 @@ use work::block_reward_satoshi;
|
||||||
use duplex_store::DuplexTransactionOutputProvider;
|
use duplex_store::DuplexTransactionOutputProvider;
|
||||||
use canon::CanonBlock;
|
use canon::CanonBlock;
|
||||||
use constants::MAX_BLOCK_SIGOPS;
|
use constants::MAX_BLOCK_SIGOPS;
|
||||||
use error::Error;
|
use error::{Error, TransactionError};
|
||||||
|
|
||||||
/// Flexible verification of ordered block
|
/// Flexible verification of ordered block
|
||||||
pub struct BlockAcceptor<'a> {
|
pub struct BlockAcceptor<'a> {
|
||||||
|
@ -115,11 +115,12 @@ impl<'a> BlockRule for BlockCoinbaseClaim<'a> {
|
||||||
fn check(&self) -> Result<(), Error> {
|
fn check(&self) -> Result<(), Error> {
|
||||||
let store = DuplexTransactionOutputProvider::new(self.store, &*self.block);
|
let store = DuplexTransactionOutputProvider::new(self.store, &*self.block);
|
||||||
|
|
||||||
let mut fee: u64 = 0;
|
let mut fees: u64 = 0;
|
||||||
|
|
||||||
for tx in self.block.transactions.iter().skip(1) {
|
for tx in self.block.transactions.iter().skip(1) {
|
||||||
|
// (1) Total sum of all referenced outputs
|
||||||
let mut incoming: u64 = 0;
|
let mut incoming: u64 = 0;
|
||||||
for input in tx.inputs.iter() {
|
for input in tx.raw.inputs.iter() {
|
||||||
let (sum, overflow) = incoming.overflowing_add(
|
let (sum, overflow) = incoming.overflowing_add(
|
||||||
store.previous_transaction_output(&input.previous_output).map(|o| o.value).unwrap_or(0));
|
store.previous_transaction_output(&input.previous_output).map(|o| o.value).unwrap_or(0));
|
||||||
if overflow {
|
if overflow {
|
||||||
|
@ -128,31 +129,25 @@ impl<'a> BlockRule for BlockCoinbaseClaim<'a> {
|
||||||
incoming = sum;
|
incoming = sum;
|
||||||
}
|
}
|
||||||
|
|
||||||
let spends = tx.total_spends();
|
// (2) Total sum of all outputs
|
||||||
|
let spends = tx.raw.total_spends();
|
||||||
|
|
||||||
let (sum, overflow) = fee.overflowing_add(incoming);
|
// Difference between (1) and (2)
|
||||||
|
let (difference, overflow) = incoming.overflowing_sub(spends);
|
||||||
if overflow {
|
if overflow {
|
||||||
return Err(Error::
|
return Err(Error::Transaction(2, TransactionError::Overspend))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Adding to total fees (with possible overflow)
|
||||||
|
let (sum, overflow) = fees.overflowing_add(difference);
|
||||||
|
if overflow {
|
||||||
|
return Err(Error::TransactionFeesOverflow)
|
||||||
|
}
|
||||||
|
|
||||||
|
fees = sum;
|
||||||
}
|
}
|
||||||
|
|
||||||
let available = self.block.transactions.iter()
|
|
||||||
.skip(1)
|
|
||||||
.flat_map(|tx| tx.raw.inputs.iter())
|
|
||||||
.map(|input| store.previous_transaction_output(&input.previous_output).map(|o| o.value).unwrap_or(0))
|
|
||||||
.sum::<u64>();
|
|
||||||
|
|
||||||
let spends = self.block.transactions.iter()
|
|
||||||
.skip(1)
|
|
||||||
.map(|tx| tx.raw.total_spends())
|
|
||||||
.sum::<u64>();
|
|
||||||
|
|
||||||
let claim = self.block.transactions[0].raw.total_spends();
|
let claim = self.block.transactions[0].raw.total_spends();
|
||||||
let (fees, overflow) = available.overflowing_sub(spends);
|
|
||||||
if overflow {
|
|
||||||
return Err(Error::TransactionFeesOverflow);
|
|
||||||
}
|
|
||||||
|
|
||||||
let (reward, overflow) = fees.overflowing_add(block_reward_satoshi(self.height));
|
let (reward, overflow) = fees.overflowing_add(block_reward_satoshi(self.height));
|
||||||
if overflow {
|
if overflow {
|
||||||
|
|
|
@ -40,6 +40,8 @@ pub enum Error {
|
||||||
TransactionFeeAndRewardOverflow,
|
TransactionFeeAndRewardOverflow,
|
||||||
/// Sum of the transaction fees in block exceeds u64::max
|
/// Sum of the transaction fees in block exceeds u64::max
|
||||||
TransactionFeesOverflow,
|
TransactionFeesOverflow,
|
||||||
|
/// Sum of all referenced outputs in block transactions resulted in the overflow
|
||||||
|
ReferencedInputsSumOverflow
|
||||||
}
|
}
|
||||||
|
|
||||||
#[derive(Debug, PartialEq)]
|
#[derive(Debug, PartialEq)]
|
||||||
|
|
Loading…
Reference in New Issue