Skip to content

Commit

Permalink
Merge pull request #23 from tcharding/02-08-re-import
Browse files Browse the repository at this point in the history
Re-import PSBTv0 code from `rust-bitcoin` and `rust-miniscript`
  • Loading branch information
tcharding authored Feb 8, 2024
2 parents 225d335 + 162e8f5 commit 7ed916f
Show file tree
Hide file tree
Showing 39 changed files with 7,366 additions and 4,350 deletions.
4 changes: 3 additions & 1 deletion rustfmt.toml
Original file line number Diff line number Diff line change
@@ -1,4 +1,6 @@
ignore = []
# rust-miniscript uses a different rustfmt configuration and we want
# to preserve the code to make rebasing easier for now.
ignore = ["src/v0/miniscript"]
hard_tabs = false
tab_spaces = 4
newline_style = "Auto"
Expand Down
4 changes: 4 additions & 0 deletions src/consts.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
//! [BIP-174]: <https://github.com/bitcoin/bips/blob/master/bip-0174.mediawiki>
//! [BIP-370]: <https://github.com/bitcoin/bips/blob/master/bip-0370.mediawiki>

#![allow(dead_code)]

/// Type: Unsigned Transaction PSBT_GLOBAL_UNSIGNED_TX = 0x00
pub(crate) const PSBT_GLOBAL_UNSIGNED_TX: u8 = 0x00;
/// Type: Extended Public Key PSBT_GLOBAL_XPUB = 0x01
Expand Down Expand Up @@ -113,6 +115,7 @@ pub(crate) fn psbt_global_key_type_value_to_str(v: u8) -> &'static str {
}
}

/// Converts an input key type value consts to a string, useful for debugging.
pub(crate) fn psbt_in_key_type_value_to_str(v: u8) -> &'static str {
match v {
PSBT_IN_NON_WITNESS_UTXO => "PSBT_IN_NON_WITNESS_UTXO",
Expand Down Expand Up @@ -145,6 +148,7 @@ pub(crate) fn psbt_in_key_type_value_to_str(v: u8) -> &'static str {
}
}

/// Converts an output key type value consts to a string, useful for debugging.
pub(crate) fn psbt_out_key_type_value_to_str(v: u8) -> &'static str {
match v {
PSBT_OUT_REDEEM_SCRIPT => "PSBT_OUT_REDEEM_SCRIPT",
Expand Down
28 changes: 14 additions & 14 deletions src/macros.rs
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@
///
/// Sets `self.thing` to be `Some(other.thing)` iff `self.thing` is `None`.
/// If `self.thing` already contains a value then this macro does nothing.
macro_rules! combine_option {
macro_rules! v2_combine_option {
($thing:ident, $slf:ident, $other:ident) => {
if let (&None, Some($thing)) = (&$slf.$thing, $other.$thing) {
$slf.$thing = Some($thing);
Expand All @@ -13,21 +13,21 @@ macro_rules! combine_option {
}

/// Combines to `BTreeMap` fields by extending the map in `self.thing`.
macro_rules! combine_map {
macro_rules! v2_combine_map {
($thing:ident, $slf:ident, $other:ident) => {
$slf.$thing.extend($other.$thing)
};
}

// Implements our Serialize/Deserialize traits using bitcoin consensus serialization.
macro_rules! impl_psbt_de_serialize {
macro_rules! v2_impl_psbt_de_serialize {
($thing:ty) => {
impl_psbt_serialize!($thing);
impl_psbt_deserialize!($thing);
v2_impl_psbt_serialize!($thing);
v2_impl_psbt_deserialize!($thing);
};
}

macro_rules! impl_psbt_deserialize {
macro_rules! v2_impl_psbt_deserialize {
($thing:ty) => {
impl $crate::serialize::Deserialize for $thing {
fn deserialize(bytes: &[u8]) -> Result<Self, $crate::serialize::Error> {
Expand All @@ -38,7 +38,7 @@ macro_rules! impl_psbt_deserialize {
};
}

macro_rules! impl_psbt_serialize {
macro_rules! v2_impl_psbt_serialize {
($thing:ty) => {
impl $crate::serialize::Serialize for $thing {
fn serialize(&self) -> $crate::prelude::Vec<u8> { bitcoin::consensus::serialize(self) }
Expand All @@ -48,7 +48,7 @@ macro_rules! impl_psbt_serialize {

// Note we purposefully do not use the fully qualified path for `InsertPairError`.
#[rustfmt::skip]
macro_rules! impl_psbt_insert_pair {
macro_rules! v2_impl_psbt_insert_pair {
($slf:ident.$unkeyed_name:ident <= <$raw_key:ident: _>|<$raw_value:ident: $unkeyed_value_type:ty>) => {
if $raw_key.key.is_empty() {
if $slf.$unkeyed_name.is_none() {
Expand Down Expand Up @@ -78,7 +78,7 @@ macro_rules! impl_psbt_insert_pair {
}

#[rustfmt::skip]
macro_rules! impl_psbt_get_pair {
macro_rules! v2_impl_psbt_get_pair {
($rv:ident.push($slf:ident.$unkeyed_name:ident, $unkeyed_typeval:ident)) => {
if let Some(ref $unkeyed_name) = $slf.$unkeyed_name {
$rv.push($crate::raw::Pair {
Expand All @@ -104,14 +104,14 @@ macro_rules! impl_psbt_get_pair {
}

// macros for serde of hashes
macro_rules! impl_psbt_hash_de_serialize {
macro_rules! v2_impl_psbt_hash_de_serialize {
($hash_type:ty) => {
impl_psbt_hash_serialize!($hash_type);
impl_psbt_hash_deserialize!($hash_type);
v2_impl_psbt_hash_serialize!($hash_type);
v2_impl_psbt_hash_deserialize!($hash_type);
};
}

macro_rules! impl_psbt_hash_deserialize {
macro_rules! v2_impl_psbt_hash_deserialize {
($hash_type:ty) => {
impl $crate::serialize::Deserialize for $hash_type {
fn deserialize(bytes: &[u8]) -> Result<Self, $crate::serialize::Error> {
Expand All @@ -121,7 +121,7 @@ macro_rules! impl_psbt_hash_deserialize {
};
}

macro_rules! impl_psbt_hash_serialize {
macro_rules! v2_impl_psbt_hash_serialize {
($hash_type:ty) => {
impl $crate::serialize::Serialize for $hash_type {
fn serialize(&self) -> $crate::prelude::Vec<u8> { self.as_byte_array().to_vec() }
Expand Down
37 changes: 37 additions & 0 deletions src/miniscript.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
// SPDX-License-Identifier: CC0-1.0

//! Private scoped stuff copied from `rust-miniscript`.

pub(crate) trait ItemSize {
fn size(&self) -> usize;
}

impl<Pk: MiniscriptKey> ItemSize for Placeholder<Pk> {
fn size(&self) -> usize {
match self {
Placeholder::Pubkey(_, size) => *size,
Placeholder::PubkeyHash(_, size) => *size,
Placeholder::EcdsaSigPk(_) | Placeholder::EcdsaSigPkHash(_) => 73,
Placeholder::SchnorrSigPk(_, _, size) | Placeholder::SchnorrSigPkHash(_, _, size) =>
size + 1, // +1 for the OP_PUSH
Placeholder::HashDissatisfaction
| Placeholder::Sha256Preimage(_)
| Placeholder::Hash256Preimage(_)
| Placeholder::Ripemd160Preimage(_)
| Placeholder::Hash160Preimage(_) => 33,
Placeholder::PushOne => 2, // On legacy this should be 1 ?
Placeholder::PushZero => 1,
Placeholder::TapScript(s) => s.len(),
Placeholder::TapControlBlock(cb) => cb.serialize().len(),
}
}
}

impl ItemSize for Vec<u8> {
fn size(&self) -> usize { self.len() }
}

// Helper function to calculate witness size
pub(crate) fn witness_size<T: ItemSize>(wit: &[T]) -> usize {
wit.iter().map(T::size).sum::<usize>() + varint_len(wit.len())
}
33 changes: 18 additions & 15 deletions src/serialize.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,23 +39,26 @@ pub(crate) trait Deserialize: Sized {
fn deserialize(bytes: &[u8]) -> Result<Self, Error>;
}

impl_psbt_de_serialize!(absolute::LockTime);
impl_psbt_de_serialize!(Amount);
impl_psbt_de_serialize!(Transaction);
impl_psbt_de_serialize!(transaction::Version);
impl_psbt_de_serialize!(TxOut);
impl_psbt_de_serialize!(Witness);
impl_psbt_de_serialize!(VarInt);
impl_psbt_hash_de_serialize!(ripemd160::Hash);
impl_psbt_hash_de_serialize!(sha256::Hash);
impl_psbt_hash_de_serialize!(TapLeafHash);
impl_psbt_hash_de_serialize!(TapNodeHash);
impl_psbt_hash_de_serialize!(Txid);
impl_psbt_hash_de_serialize!(hash160::Hash);
impl_psbt_hash_de_serialize!(sha256d::Hash);
// Strictly speaking these do not need the prefix because the v0 versions are
// unused but we want to leave thoes in the code so the the files are close as
// possible to the original from bitcoin/miniscript repos.
v2_impl_psbt_de_serialize!(absolute::LockTime);
v2_impl_psbt_de_serialize!(Amount);
v2_impl_psbt_de_serialize!(Transaction);
v2_impl_psbt_de_serialize!(transaction::Version);
v2_impl_psbt_de_serialize!(TxOut);
v2_impl_psbt_de_serialize!(Witness);
v2_impl_psbt_de_serialize!(VarInt);
v2_impl_psbt_hash_de_serialize!(ripemd160::Hash);
v2_impl_psbt_hash_de_serialize!(sha256::Hash);
v2_impl_psbt_hash_de_serialize!(TapLeafHash);
v2_impl_psbt_hash_de_serialize!(TapNodeHash);
v2_impl_psbt_hash_de_serialize!(Txid);
v2_impl_psbt_hash_de_serialize!(hash160::Hash);
v2_impl_psbt_hash_de_serialize!(sha256d::Hash);

// taproot
impl_psbt_de_serialize!(Vec<TapLeafHash>);
v2_impl_psbt_de_serialize!(Vec<TapLeafHash>);

impl Serialize for ScriptBuf {
fn serialize(&self) -> Vec<u8> { self.to_bytes() }
Expand Down
Loading

0 comments on commit 7ed916f

Please sign in to comment.