blockdata: Improve rustdocs

Do an audit of the `blockdata` module and clean up rustdocs.
This commit is contained in:
Tobin C. Harding 2022-10-31 12:23:10 +11:00
parent fb708ca74b
commit 31740710ee
5 changed files with 77 additions and 63 deletions

View File

@ -96,7 +96,7 @@ impl Header {
}
}
/// Bitcoin block version number
/// Bitcoin block version number.
///
/// Originally used as a protocol version, but repurposed for soft-fork signaling.
///
@ -146,7 +146,7 @@ impl Version {
self.0
}
/// Check whether the version number is signalling a soft fork at the given bit.
/// Checks whether the version number is signalling a soft fork at the given bit.
///
/// A block is signalling for a soft fork under BIP-9 if the first 3 bits are `001` and
/// the version bit for the specific soft fork is toggled on.
@ -213,7 +213,7 @@ impl Block {
self.header.block_hash()
}
/// check if merkle root of header matches merkle root of the transaction list
/// Checks if merkle root of header matches merkle root of the transaction list.
pub fn check_merkle_root(&self) -> bool {
match self.compute_merkle_root() {
Some(merkle_root) => self.header.merkle_root == merkle_root,

View File

@ -26,21 +26,21 @@ use crate::network::constants::Network;
use crate::pow::CompactTarget;
use crate::internal_macros::impl_bytes_newtype;
/// How many satoshis are in "one bitcoin"
/// How many satoshis are in "one bitcoin".
pub const COIN_VALUE: u64 = 100_000_000;
/// How many seconds between blocks we expect on average
/// How many seconds between blocks we expect on average.
pub const TARGET_BLOCK_SPACING: u32 = 600;
/// How many blocks between diffchanges
/// How many blocks between diffchanges.
pub const DIFFCHANGE_INTERVAL: u32 = 2016;
/// How much time on average should occur between diffchanges
/// How much time on average should occur between diffchanges.
pub const DIFFCHANGE_TIMESPAN: u32 = 14 * 24 * 3600;
/// The maximum allowed weight for a block, see BIP 141 (network rule)
/// The maximum allowed weight for a block, see BIP 141 (network rule).
pub const MAX_BLOCK_WEIGHT: u32 = 4_000_000;
/// The minimum transaction weight for a valid serialized transaction
/// The minimum transaction weight for a valid serialized transaction.
pub const MIN_TRANSACTION_WEIGHT: u32 = 4 * 60;
/// The factor that non-witness serialization data is multiplied by during weight calculation
/// The factor that non-witness serialization data is multiplied by during weight calculation.
pub const WITNESS_SCALE_FACTOR: usize = 4;
/// The maximum allowed number of signature check operations in a block
/// The maximum allowed number of signature check operations in a block.
pub const MAX_BLOCK_SIGOPS_COST: i64 = 80_000;
/// Mainnet (bitcoin) pubkey address prefix.
pub const PUBKEY_ADDRESS_PREFIX_MAIN: u8 = 0; // 0x00
@ -62,7 +62,7 @@ pub const MAX_SCRIPTNUM_VALUE: u32 = 0x80000000; // 2^31
/// if you are doing anything remotely sane with monetary values).
pub const MAX_MONEY: u64 = 21_000_000 * COIN_VALUE;
/// Constructs and returns the coinbase (and only) transaction of the Bitcoin genesis block
/// Constructs and returns the coinbase (and only) transaction of the Bitcoin genesis block.
fn bitcoin_genesis_tx() -> Transaction {
// Base
let mut ret = Transaction {
@ -101,7 +101,7 @@ fn bitcoin_genesis_tx() -> Transaction {
ret
}
/// Constructs and returns the genesis block
/// Constructs and returns the genesis block.
pub fn genesis_block(network: Network) -> Block {
let txdata = vec![bitcoin_genesis_tx()];
let hash: sha256d::Hash = txdata[0].txid().into();

View File

@ -156,17 +156,17 @@ pub enum Error {
/// Something did a non-minimal push; for more information see
/// `https://github.com/bitcoin/bips/blob/master/bip-0062.mediawiki#Push_operators`
NonMinimalPush,
/// Some opcode expected a parameter, but it was missing or truncated
/// Some opcode expected a parameter but it was missing or truncated.
EarlyEndOfScript,
/// Tried to read an array off the stack as a number when it was more than 4 bytes
/// Tried to read an array off the stack as a number when it was more than 4 bytes.
NumericOverflow,
/// Error validating the script with bitcoinconsensus library
/// Error validating the script with bitcoinconsensus library.
#[cfg(feature = "bitcoinconsensus")]
#[cfg_attr(docsrs, doc(cfg(feature = "bitcoinconsensus")))]
BitcoinConsensus(bitcoinconsensus::Error),
/// Can not find the spent output
/// Can not find the spent output.
UnknownSpentOutput(OutPoint),
/// Can not serialize the spending transaction
/// Can not serialize the spending transaction.
Serialization
}
@ -266,7 +266,8 @@ impl From<bitcoinconsensus::Error> for Error {
}
}
/// Helper to encode an integer in script(minimal CScriptNum) format.
/// Encodes an integer in script(minimal CScriptNum) format.
///
/// Writes bytes into the buffer and returns the number of bytes written.
pub fn write_scriptint(out: &mut [u8; 8], n: i64) -> usize {
let mut len = 0;
@ -297,7 +298,8 @@ pub fn write_scriptint(out: &mut [u8; 8], n: i64) -> usize {
len
}
/// Helper to decode an integer in script(minimal CScriptNum) format
/// Decodes an integer in script(minimal CScriptNum) format.
///
/// Notice that this fails on overflow: the result is the same as in
/// bitcoind, that only 4-byte signed-magnitude values may be read as
/// numbers. They can be added or subtracted (and a long time ago,
@ -343,6 +345,8 @@ pub fn read_scriptint(v: &[u8]) -> Result<i64, Error> {
Ok(ret)
}
/// Decodes a boolean.
///
/// This is like "`read_scriptint` then map 0 to false and everything
/// else as true", except that the overflow rules don't apply.
#[inline]
@ -353,7 +357,7 @@ pub fn read_scriptbool(v: &[u8]) -> bool {
}
}
/// Read a script-encoded unsigned integer
/// Decodes a script-encoded unsigned integer.
///
/// ## Errors
///
@ -395,7 +399,7 @@ impl Script {
/// Creates a new empty script.
pub fn new() -> Script { Script(vec![].into_boxed_slice()) }
/// Creates a new script builder
/// Creates a new script builder.
pub fn builder() -> Builder {
Builder::new()
}
@ -863,15 +867,16 @@ pub struct Instructions<'a> {
}
impl<'a> Instructions<'a> {
/// Set the iterator to end so that it won't iterate any longer
/// Sets the iterator to end so that it won't iterate any longer.
fn kill(&mut self) {
let len = self.data.len();
self.data.nth(len.max(1) - 1);
}
/// takes `len` bytes long slice from iterator and returns it advancing iterator
/// if the iterator is not long enough [`Error::EarlyEndOfScript`] is returned and the iterator is killed
/// to avoid returning an infinite stream of errors.
/// Takes a `len` bytes long slice from iterator and returns it, advancing the iterator.
///
/// If the iterator is not long enough [`Error::EarlyEndOfScript`] is returned and the iterator
/// is killed to avoid returning an infinite stream of errors.
fn take_slice_or_kill(&mut self, len: usize) -> Result<&'a [u8], Error> {
if self.data.len() >= len {
let slice = &self.data.as_slice()[..len];
@ -968,9 +973,10 @@ impl Builder {
/// Checks whether the script is the empty script.
pub fn is_empty(&self) -> bool { self.0.is_empty() }
/// Adds instructions to push an integer onto the stack. Integers are
/// encoded as little-endian signed-magnitude numbers, but there are
/// dedicated opcodes to push some small integers.
/// Adds instructions to push an integer onto the stack.
///
/// Integers are encoded as little-endian signed-magnitude numbers, but there are dedicated
/// opcodes to push some small integers.
pub fn push_int(self, data: i64) -> Builder {
// We can special-case -1, 1-16
if data == -1 || (1..=16).contains(&data) {

View File

@ -146,6 +146,7 @@ impl std::error::Error for ParseOutPointError {
}
/// Parses a string-encoded transaction index (vout).
///
/// Does not permit leading zeroes or non-digit characters.
fn parse_vout(s: &str) -> Result<u32, ParseOutPointError> {
if s.len() > 1 {
@ -319,13 +320,13 @@ impl Sequence {
self.is_relative_lock_time() & (self.0 & Sequence::LOCK_TYPE_MASK > 0)
}
/// Create a relative lock-time using block height.
/// Creates a relative lock-time using block height.
#[inline]
pub fn from_height(height: u16) -> Self {
Sequence(u32::from(height))
}
/// Create a relative lock-time using time intervals where each interval is equivalent
/// Creates a relative lock-time using time intervals where each interval is equivalent
/// to 512 seconds.
///
/// Encoding finer granularity of time for relative lock-times is not supported in Bitcoin
@ -334,7 +335,7 @@ impl Sequence {
Sequence(u32::from(intervals) | Sequence::LOCK_TYPE_MASK)
}
/// Create a relative lock-time from seconds, converting the seconds into 512 second
/// Creates a relative lock-time from seconds, converting the seconds into 512 second
/// interval with floor division.
///
/// Will return an error if the input cannot be encoded in 16 bits.
@ -347,7 +348,7 @@ impl Sequence {
}
}
/// Create a relative lock-time from seconds, converting the seconds into 512 second
/// Creates a relative lock-time from seconds, converting the seconds into 512 second
/// interval with ceiling division.
///
/// Will return an error if the input cannot be encoded in 16 bits.
@ -366,7 +367,7 @@ impl Sequence {
!self.is_final()
}
/// Create a sequence from a u32 value.
/// Creates a sequence from a u32 value.
#[inline]
pub fn from_consensus(n: u32) -> Self {
Sequence(n)
@ -590,6 +591,7 @@ pub struct Transaction {
impl Transaction {
/// Computes a "normalized TXID" which does not include any signatures.
///
/// This gives a way to identify a transaction that is "the same" as
/// another in the sense of having same inputs and outputs.
pub fn ntxid(&self) -> sha256d::Hash {
@ -602,9 +604,10 @@ impl Transaction {
cloned_tx.txid().into()
}
/// Computes the txid. For non-segwit transactions this will be identical
/// to the output of `wtxid()`, but for segwit transactions,
/// this will give the correct txid (not including witnesses) while `wtxid`
/// Computes the txid.
///
/// For non-segwit transactions this will be identical to the output of `wtxid()`, but for
/// segwit transactions, this will give the correct txid (not including witnesses) while `wtxid`
/// will also hash witnesses.
pub fn txid(&self) -> Txid {
let mut enc = Txid::engine();
@ -615,9 +618,10 @@ impl Transaction {
Txid::from_engine(enc)
}
/// Computes SegWit-version of the transaction id (wtxid). For transaction with the witness
/// data this hash includes witness, for pre-witness transaction it is equal to the normal
/// value returned by txid() function.
/// Computes SegWit-version of the transaction id (wtxid).
///
/// For transaction with the witness data this hash includes witness, for pre-witness
/// transaction it is equal to the normal value returned by txid() function.
pub fn wtxid(&self) -> Wtxid {
let mut enc = Wtxid::engine();
self.consensus_encode(&mut enc).expect("engines don't error");
@ -642,7 +646,7 @@ impl Transaction {
/// have the information to determine.
/// - Does NOT handle the sighash single bug (see "Return type" section)
///
/// # Return type
/// # Returns
///
/// This function can't handle the SIGHASH_SINGLE bug internally, so it returns [`EncodeSigningDataResult`]
/// that must be handled by the caller (see [`EncodeSigningDataResult::is_sighash_single_bug`]).
@ -826,6 +830,7 @@ impl Transaction {
}
/// Verify that this transaction is able to spend its inputs.
///
/// The `spent` closure should not return the same [`TxOut`] twice!
#[cfg(feature="bitcoinconsensus")]
#[cfg_attr(docsrs, doc(cfg(feature = "bitcoinconsensus")))]
@ -846,14 +851,15 @@ impl Transaction {
Ok(())
}
/// Is this a coin base transaction?
/// Checks if this is a coin base transaction.
pub fn is_coin_base(&self) -> bool {
self.input.len() == 1 && self.input[0].previous_output.is_null()
}
/// Returns `true` if the transaction itself opted in to be BIP-125-replaceable (RBF). This
/// **does not** cover the case where a transaction becomes replaceable due to ancestors being
/// RBF.
/// Returns `true` if the transaction itself opted in to be BIP-125-replaceable (RBF).
///
/// This **does not** cover the case where a transaction becomes replaceable due to ancestors
/// being RBF.
pub fn is_explicitly_rbf(&self) -> bool {
self.input.iter().any(|input| input.sequence.is_rbf())
}

View File

@ -18,7 +18,7 @@ use crate::prelude::*;
use crate::VarInt;
use crate::taproot::TAPROOT_ANNEX_PREFIX;
/// The Witness is the data used to unlock bitcoins since the [segwit upgrade](https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki)
/// The Witness is the data used to unlock bitcoin since the [segwit upgrade].
///
/// Can be logically seen as an array of bytestrings, i.e. `Vec<Vec<u8>>`, and it is serialized on the wire
/// in that format. You can convert between this type and `Vec<Vec<u8>>` by using [`Witness::from_slice`]
@ -27,23 +27,25 @@ use crate::taproot::TAPROOT_ANNEX_PREFIX;
/// For serialization and deserialization performance it is stored internally as a single `Vec`,
/// saving some allocations.
///
/// [segwit upgrade]: <https://github.com/bitcoin/bips/blob/master/bip-0143.mediawiki>
#[derive(Clone, Default, PartialEq, Eq, PartialOrd, Ord, Debug, Hash)]
pub struct Witness {
/// Contains the witness `Vec<Vec<u8>>` serialization without the initial varint indicating the
/// number of elements (which is stored in `witness_elements`)
/// number of elements (which is stored in `witness_elements`).
content: Vec<u8>,
/// Number of elements in the witness.
/// It is stored separately (instead of as VarInt in the initial part of content) so that method
/// like [`Witness::push`] doesn't have case requiring to shift the entire array
/// The number of elements in the witness.
///
/// Stored separately (instead of as a VarInt in the initial part of content) so that methods
/// like [`Witness::push`] don't have to shift the entire array.
witness_elements: usize,
/// This is the valid index pointing to the beginning of the index area. This area is 4 * stack_size bytes
/// at the end of the content vector which stores the indices of each item.
/// This is the valid index pointing to the beginning of the index area. This area is 4 *
/// stack_size bytes at the end of the content vector which stores the indices of each item.
indices_start: usize,
}
/// Support structure to allow efficient and convenient iteration over the Witness elements
/// Support structure to allow efficient and convenient iteration over the Witness elements.
pub struct Iter<'a> {
inner: &'a [u8],
indices_start: usize,
@ -162,7 +164,7 @@ impl Encodable for Witness {
}
impl Witness {
/// Create a new empty [`Witness`]
/// Creates a new empty [`Witness`].
pub fn new() -> Self {
Witness::default()
}
@ -202,17 +204,17 @@ impl Witness {
}
}
/// Convenience method to create an array of byte-arrays from this witness
/// Convenience method to create an array of byte-arrays from this witness.
pub fn to_vec(&self) -> Vec<Vec<u8>> {
self.iter().map(|s| s.to_vec()).collect()
}
/// Returns `true` if the witness contains no element
/// Returns `true` if the witness contains no element.
pub fn is_empty(&self) -> bool {
self.witness_elements == 0
}
/// Returns a struct implementing [`Iterator`]
/// Returns a struct implementing [`Iterator`].
pub fn iter(&self) -> Iter {
Iter {
inner: self.content.as_slice(),
@ -221,12 +223,12 @@ impl Witness {
}
}
/// Returns the number of elements this witness holds
/// Returns the number of elements this witness holds.
pub fn len(&self) -> usize {
self.witness_elements
}
/// Returns the bytes required when this Witness is consensus encoded
/// Returns the bytes required when this Witness is consensus encoded.
pub fn serialized_len(&self) -> usize {
self.iter()
.map(|el| VarInt(el.len() as u64).len() + el.len())
@ -234,14 +236,14 @@ impl Witness {
+ VarInt(self.witness_elements as u64).len()
}
/// Clear the witness
/// Clear the witness.
pub fn clear(&mut self) {
self.content.clear();
self.witness_elements = 0;
self.indices_start = 0;
}
/// Push a new element on the witness, requires an allocation
/// Push a new element on the witness, requires an allocation.
pub fn push<T: AsRef<[u8]>>(&mut self, new_element: T) {
self.push_slice(new_element.as_ref());
}
@ -284,7 +286,7 @@ impl Witness {
Some(&self.content[start..start + varint.0 as usize])
}
/// Return the last element in the witness, if any
/// Returns the last element in the witness, if any.
pub fn last(&self) -> Option<&[u8]> {
if self.witness_elements == 0 {
None
@ -293,7 +295,7 @@ impl Witness {
}
}
/// Return the second-to-last element in the witness, if any
/// Returns the second-to-last element in the witness, if any.
pub fn second_to_last(&self) -> Option<&[u8]> {
if self.witness_elements <= 1 {
None