use crate::chaindef::Transaction;
#[cfg(feature = "nexa")]
use crate::nexa::hash_types::TxIdem;
use bitcoin_hashes::Hash;
use bitcoincash::consensus::encode::MAX_VEC_SIZE;
use bitcoincash::consensus::Decodable;
use bitcoincash::consensus::Encodable;
#[cfg(not(feature = "nexa"))]
use bitcoincash::Txid;
use bitcoincash::VarInt;
use crate::chaindef::OutPoint;
use crate::chaindef::OutPointHash;
#[cfg(not(feature = "nexa"))]
pub fn compute_outpoint_hash(txid: &Txid, vout: u32) -> OutPointHash {
let mut e = OutPointHash::engine();
txid.consensus_encode(&mut e)
.expect("failed to encode input txid");
vout.consensus_encode(&mut e)
.expect("failed to encode input index");
OutPointHash::from_engine(e)
}
#[cfg(feature = "nexa")]
pub fn compute_outpoint_hash(txidem: &TxIdem, n: u32) -> OutPointHash {
let mut e = OutPointHash::engine();
txidem
.consensus_encode(&mut e)
.expect("failed to encode input txid");
n.consensus_encode(&mut e)
.expect("failed to encode input index");
OutPointHash::from_engine(e)
}
#[cfg(feature = "nexa")]
pub fn compute_outpoint_hash_from_tx(tx: &Transaction, out_n: u32) -> OutPointHash {
compute_outpoint_hash(&tx.txidem(), out_n)
}
#[cfg(not(feature = "nexa"))]
pub fn compute_outpoint_hash_from_tx(tx: &Transaction, out_n: u32) -> OutPointHash {
compute_outpoint_hash(&tx.txid(), out_n)
}
#[cfg(feature = "nexa")]
pub fn outpoint_hash(previous_outpoint: &OutPoint) -> OutPointHash {
previous_outpoint.hash
}
#[cfg(not(feature = "nexa"))]
pub fn outpoint_hash(previous_output: &OutPoint) -> OutPointHash {
compute_outpoint_hash(&previous_output.txid, previous_output.vout)
}
pub fn decode_vector<R: std::io::Read + ?Sized, V: Decodable>(
r: &mut R,
) -> Result<Vec<V>, bitcoincash::consensus::encode::Error> {
let vector_len = VarInt::consensus_decode(r)?.0;
let vector_bytes = (vector_len as usize)
.checked_mul(std::mem::size_of::<V>())
.ok_or(bitcoincash::consensus::encode::Error::ParseFailed(
"Invalid length",
))?;
if vector_bytes > MAX_VEC_SIZE {
return Err(
bitcoincash::consensus::encode::Error::OversizedVectorAllocation {
requested: vector_bytes,
max: MAX_VEC_SIZE,
},
);
}
let mut vector: Vec<V> = Vec::with_capacity(vector_len as usize);
for _ in 0..vector_len {
vector.push(Decodable::consensus_decode(r)?);
}
Ok(vector)
}
pub fn encode_vector<W: std::io::Write + ?Sized, V: Encodable>(
w: &mut W,
v: &[V],
) -> Result<usize, std::io::Error> {
let mut len = 0;
len += VarInt(v.len() as u64).consensus_encode(w)?;
for i in v {
len += i.consensus_encode(w)?;
}
Ok(len)
}