Commit Graph

52 Commits

Author SHA1 Message Date
Tobin C. Harding 5973dce9db
blockdata: Run the formatter
Run `cargo +nightly fmt`, no other manual changes.
2023-03-21 08:33:24 +11:00
Martin Habovstiak 00b46d6d9d Indent functions
This fixes indentatiion that was intentionally "messed up" to make code
review easier.
2023-03-17 08:16:21 +01:00
Martin Habovstiak d56d202aeb Support weight prediction in `const` context
Some smart contracts or simplified wallets statically know the sizes of
transactions or inputs. The possible approaches to handling them so far
were re-computing the values (and hoping the optimizer will const fold
them) or using a simple constant which may be harder to understand and
get right. It's much nicer to just use a `const` but our code didn't
support it until now.

This change adds methods that can compute the prediction in `const`
context for Rust versions >= 1.46.0 which allow use of loops (and
conditions but those could be workaround anyway).

As a side effect of this, the change also adds `const` to `VarInt::len`
in Rust 1.46+. While this one could be made unconditional using array
trick it's probably not worth it because of the planned MSRV bump.

Note: this commit is intentionally unformatted to make diff easier to
understand. Formatting will be done in future commit.
2023-03-17 08:16:17 +01:00
Martin Habovstiak 3eb648df01 Add constants to `InputWeightPrediction`
There are several common spends in Bitcoin that have known input weight
predictions. It can be useful to have these as constants, so this change
adds them. However, this only adds native segwit ones as the others are
slowly fading away and might clutter the API.
2023-03-07 09:50:13 +01:00
Tobin C. Harding 42b07586ac
Improve the public API
We created the `crypto` crate as a container for cryptography modules
with the idea that it may be split out into a separate crate. There is
no reason for users of the lib to know about this module. Also, we have
two `taproot` modules, one in `crypto` and one at the crate root, this
makes for un-ergonomic usage of the lib.

Improve the public API by doing:

- Make the `crypto` module private (`pub(crate)`).
- Re-export `crypto::taproot::Signature` (and `Error`) from
  `crate::taproot`
2023-03-01 09:28:42 +11:00
Andrew Poelstra 5a867821aa
Merge rust-bitcoin/rust-bitcoin#1623: Improve string parsing
090dad770f Improve string parsing (Tobin C. Harding)

Pull request description:

  Currently we implement string parsing for height/time from the `absolute` module but not the `relative` module.

  Improve the macros used to implement string parsing and use the new versions to implement string parsing for the height and time types in `relative`.

  Done while reviewing data structures in relation to `serde`.

ACKs for top commit:
  apoelstra:
    ACK 090dad770f
  Kixunil:
    ACK 090dad770f

Tree-SHA512: bfa88efbaf5dc35755eb46df373a08e223f112860e8a65f58db9fdd77e2c01dc9377da735b33ef58940004fe5fe11690ac09be19591fded2c9fd04cd7d2bdf73
2023-02-25 21:16:38 +00:00
Harshil Jani f62885890d Accept borrowed values in InputWeightPrediction::new()
Signed-off-by: Harshil Jani <harshiljani2002@gmail.com>
2023-02-25 17:20:40 +05:30
Tobin C. Harding 438ee45691
Show cache construction in rustdoc
To make it more clear what the cache is show the cache construction line
in rustdoc.
2023-02-21 08:12:32 +11:00
Tobin C. Harding 9f39e872bc
Rename SchnorrSighashType to TapSighashType
As we did for `SchnorrSighash`, rename the `SchnorrSighashType` to
`TapSighashType`.
2023-02-20 12:58:09 +11:00
Tobin C. Harding 40c246743b
Split Sighash into LegacySighash and SegwitV0Sighash
Currently we have `TapSighash` that is used for taproot sighashes but
for non-taproot sighashes we use `hash_types::Sighash`. We can improve
the API by creating a `LegacySighash`, and `SegwitV0Sighash`.

Copy the original `Sighash` macro calls to create the two new types in
the `sighash` module.

While we are at it, put the `TapSighash` and `TapSighashTag` into the
`sighash` module also.
2023-02-20 12:58:09 +11:00
Tobin C. Harding e38d843536
Do not use deprecated function in rustdoc example
Currently we are use the deprecated signing method on `Transaction`, we
should use the new method on the sighash cache.
2023-02-20 12:58:08 +11:00
Andrew Poelstra f00b6362a0
Merge rust-bitcoin/rust-bitcoin#1636: Weight prediction
ae2aaaa436 Add `script_pubkey_lens` method (Martin Habovstiak)
cf068d16b0 Implement transaction weight prediction (Martin Habovstiak)

Pull request description:

  When creating a transaction one must know the the fee beforehand to set
  appropriate amounts for outputs and to know the fee, weight is required.
  So far we only had a method on an already-constructed transaction. This
  method clearly wasn't helpful when constructing the transaction except
  for hacks like temporarily adding an all-zeroes signature.

  This change adds a function that can compute the transaction weight
  without knowing individual bytes of the scripts, witnesses and other
  elements. It only needs to know their sizes.

  To make the API less error-prone a special, trivial, type is also added
  for computing the lengths of witnesses.

  Based on #1627

ACKs for top commit:
  apoelstra:
    ACK ae2aaaa436
  tcharding:
    ACK ae2aaaa436

Tree-SHA512: 55376601c2c2826bb0909cc25ff5b65816f0b1a2d57fb2cd8831f3db5382de0f4a364d518b312f0528bb5f44c30f3f74f8d254145eed2bfd65e2332b7c4d7c8b
2023-02-13 22:40:42 +00:00
Martin Habovstiak ae2aaaa436 Add `script_pubkey_lens` method
In some cases people construct the transaction with a dummy fee output
value before calculating the weight. A method to create the iterator
over `script_pubkey` lengths is useful in such cases.
2023-02-13 11:16:31 +01:00
Martin Habovstiak 6be89bf94f Add `minimal_non_dust` to `TxOut`
In some scenarios it's useful to create outputs with minimal relayable
value. E.g. outputs designated for fee bumping using CPFP. A method for
this is useful.

This implements a constructor of `TxOut` that computes the minimal
non-dust value from the passed script.

Closes #1459
2023-02-11 17:14:48 +01:00
Martin Habovstiak cf068d16b0 Implement transaction weight prediction
When creating a transaction one must know the the fee beforehand to set
appropriate amounts for outputs and to know the fee, weight is required.
So far we only had a method on an already-constructed transaction. This
method clearly wasn't helpful when constructing the transaction except
for hacks like temporarily adding an all-zeroes signature.

This change adds a function that can compute the transaction weight
without knowing individual bytes of the scripts, witnesses and other
elements. It only needs to know their sizes.

To make the API less error-prone a special, trivial, type is also added
for computing the lengths of witnesses.
2023-02-11 12:57:37 +01:00
Tobin C. Harding 090dad770f
Improve string parsing
Currently we implement string parsing for height/time from the
`absolute` module but not the `relative` module.

Improve the macros used to implement string parsing and use the new
versions to implement string parsing for the height and time types in
`relative`.
2023-02-10 12:28:25 +11:00
Martin Habovstiak 70cf4515db Add `Weight` and `FeeRate` newtypes
Use of general-purpose integers is often error-prone and annoying. We're
working towards improving it by introducing newtypes.

This adds newtypes for weight and fee rate to make fee computation
easier and more readable. Note however that this dosn't change the type
for individual parts of the transaction since computing the total weight
is not as simple as summing them up and we want to avoid such confusion.

Part of #630
2023-02-08 23:17:30 +01:00
Tobin C. Harding aae03999a5
Do not export unusual hash types at crate root
Currently we use a wildcard to export all the hash types in
`hash_types`. We are moving to a world were we only export
normal/standard types from the crate root.

Remove the reexport of the following hash types:

- `FilterHash`
- `FilterHeader`
- `TxMerkleNode`
- `WitnessCommitment`
- `WitnessMerkleNode`
- `XpubIdentifier`
- `Sighash`

Fix: #1541
2023-02-04 13:34:20 +11:00
Tobin C. Harding a308e1e2ea
Remove FromHex for all types except Vec and array
Remove `FromHex` from hash and script types

- Remove the `FromHex` implementation from hash types and `ScriptBuf`
- Remove the `FromStr` implementation from `ScriptBuf` because it does not
  roundtrip with `Display`.
- Implement a method `from_hex` on `ScriptBuf`.
- Implement `FromStr` on hash types using a fixed size array.

This leaves `FromHex` implementations only on `Vec` and fixed size arrays.
2023-02-01 08:26:46 +11:00
Tobin C. Harding 7dde3b3b22 Make max/min_value functions const
The `max_value` and `min_value` functions only exist to be
compatible/uniform with Rust 1.41.1 they will never change and they just
return a constant value. They can therefore be made const functions.
2023-01-31 08:35:32 +11:00
Tobin C. Harding 3c0598b399
Add standard constants to lock times
Some of the lock time structs (`Height`, `Time` ect.) are missing
standard constants for min, max ect.

Add standard constants taking into consideration the various locktime
corner cases.

Add `max_value` and `min_value` to be consistent with Rust 1.41.1 (incl.
`Sequence`).

Fix: #1451
2023-01-25 07:43:48 +11:00
Tobin C. Harding a762a89b48
Add documentation to Sequence::is_final
The term "final" is an archaic Bitcoin term however it is well used, it
exists in Bitcoin Core code as well as in various bips. To help folks
new to Bitcoin add documentation to the `is_final` method including
historical notes.
2023-01-23 09:18:23 +11:00
Tobin C. Harding b1490a26ea
Move enables_absolute_lock_time method
In preparation for deprecating the `is_final` method; move the
`enables_absolute_lock_time` method to be directly above the `is_final`
method.

Refactor only, no logic changes.
2023-01-22 17:04:58 +11:00
Martin Habovstiak 089a1e452d Replace `Vec::from_hex` with `hex!`
This makes the code less noisy and is a preparation for changing it to
`const`-based literal. Because of the preparation, places that used
variables to store the hex string were changed to constants.

There are still some instances of `Vec::from_hex` left - where they
won't be changeable to `const` and where `hex!` is unavailable
(integration tests). These may be dealt with later.

See also #1189
2022-12-31 21:10:19 +01:00
Daniela Brozzoni 4a6a12011d
Fix typos in docs
See #828
2022-12-19 09:32:52 +01:00
Andrew Poelstra 0203107360
Merge rust-bitcoin/rust-bitcoin#1475: add some documentation clarifying the locktime ordering shenanigans in #1330
02c1cd6291 add some documentation clarifying the locktime ordering shenanigans in #1330 (Andrew Poelstra)

Pull request description:

  Updates the CHANGELOG and also the doccomment on `Transaction`.

ACKs for top commit:
  tcharding:
    ACK 02c1cd6291
  Kixunil:
    ACK 02c1cd6291
  sanket1729:
    ACK 02c1cd6291

Tree-SHA512: e2d23a90fb1e53758449fe49a3db7ae1497a260ce7efcade4b50265fa70840db273609019590d9d0a69e1272607a6bcf37924b805b4f09909487eb0c3b91a3cd
2022-12-16 14:41:00 +00:00
Andrew Poelstra 02c1cd6291
add some documentation clarifying the locktime ordering shenanigans in #1330 2022-12-15 23:12:03 +00:00
Andrew Poelstra c657a1be3c
Merge rust-bitcoin/rust-bitcoin#1467: Add weight utilities to `TxIn` and `TxOut`
6d51e9255b Add weight utilities to `TxIn` and `TxOut` (Daniela Brozzoni)

Pull request description:

  - Add `segwit_weight` and `legacy_weight` methods to `TxIn`
  - Add `weight` method to `TxOut`

ACKs for top commit:
  danielabrozzoni:
    > ACK [6d51e92](6d51e9255b)
  apoelstra:
    ACK 6d51e9255b
  Kixunil:
    ACK 6d51e9255b

Tree-SHA512: 217eae49b5f6e8149af251fb82682aed34e0003342d19ec66aa0f66b8044d50c18d1e3e2d58068e4d2572b1af8bbc3403bfd5447662b45bc4f1e0e7f0672964f
2022-12-15 20:21:00 +00:00
Daniela Brozzoni 6d51e9255b
Add weight utilities to `TxIn` and `TxOut`
- Add `segwit_weight` and `legacy_weight` methods to `TxIn`
- Add `weight` method to `TxOut`
2022-12-15 09:20:56 +01:00
Martin Habovstiak 8e428562cb Implemented unsized `Script`
This renames `Script` to `ScriptBuf` and adds unsized `Script` modeled
after `PathBuf`/`Path`. The change cleans up the API a bit, especially
all functions that previously accepted `&Script` now accept truly
borrowed version. Some functions that perviously accepted `&[u8]` can
now accept `&Script` because constructing it is no loger costly.
2022-12-14 23:21:27 +01:00
Andrew Poelstra 1b15a13e5a
run cargo clippy and fmt 2022-12-13 14:52:43 +00:00
Andrew Poelstra 821842e1a1
drop Ord on absolute::LockTime; add Ord to Transaction 2022-12-13 14:52:36 +00:00
Andrew Poelstra 5b7d801ee6
remove PackedLockTime type
This can be replicated by deleting the `type PackedLockTime = LockTime'
line, and then running
    find . -type f | xargs sed -i 's/PackedLockTime/LockTime/g
at the root of the repo.
2022-12-11 19:08:14 +00:00
Andrew Poelstra 32afe5ae48
Merge rust-bitcoin/rust-bitcoin#1400: Add trait `FromStrHex` for tuple structs with single `u32` member
e00dfa9806 impl FromHexStr for structs with single u32 member (connormullett)

Pull request description:

  Closes: #1112

   - Adds new trait `FromStrHex` with 2 methods: `from_hex_str` and `from_hex_str_no_prefix`
   -  Impl new trait on each tuple struct with single u32 member. eg `Time(u32)`

  As stated in the issue, grep through codebase with `\(u32\)` and `\(pub u32\)` to see all implementations and verify none were missed.

  NonStandardSighashType is an error type and should never be constructed from a hex string. Therefore, it has been omitted from this change.

  Tests are somewhat redundant, but cover 4 cases each. 2 happy paths, 1 for each function. 1 case for malformed/invalid hex input, and 1 for calling no_prefix without a prefix

ACKs for top commit:
  Kixunil:
    ACK e00dfa9806
  apoelstra:
    ACK e00dfa9806

Tree-SHA512: 221faef7fc1fa8fdb4cba79cfae317a0b63984937c345c6ca2287123a078f38911cdc07db7589a88b7bc6fbecf389e9bcff47952728410510ffcfc1857e0f91f
2022-12-11 18:47:32 +00:00
connormullett e00dfa9806 impl FromHexStr for structs with single u32 member
Adds new module `string` to be later converted to its own
crate. The module currently contains the FromHexStr trait and an error
type to be used for implementing hex parsing on types. This change
also adds implementations of FromHexStr for types with a single u32
member such as `Sequence(pub u32)`. All structs that match the
following regex have been given this implementation
`\(u32\)` and `\(pub u32\)`. All implementations have associated
unit tests matching all possible cases. NonStandardSighashType has
been ommitted from this change as it is an error and should not be
constructed using the methods added in this change.

Adds parse::hex_u32 for future use to be made generic to allow
different sizes of integers to be parsed from hex strings.

The error type FromHexError implements required traits such as
Display and std::error::Error
2022-12-11 00:01:58 -05:00
Tobin C. Harding 26be9ddd27 Make RBF rustdoc more scrary
In order to really bring the security risks of RBF to peoples attention
make the docs more scary.
2022-12-06 12:25:30 +11:00
Tobin C. Harding c9a49d5be7 blockdata: Improve content of rustdocs
Recently we (tcharding) do some mechanical improvements to the rustdocs
in the `blockdata` module without considering the content. On review a
bunch of improvements were suggested.

Improve the content of various rustdoc comments in the `blockdata`
module.

Suggested content came from reviewers, all mistakes are my own :)
2022-12-06 12:25:30 +11:00
Tobin C. Harding 31740710ee blockdata: Improve rustdocs
Do an audit of the `blockdata` module and clean up rustdocs.
2022-12-06 12:25:26 +11:00
Martin Habovstiak 1a2cf2681d Implement consensus encoding adapter for serde
In some protocols it is preferred to serialize consensus-encodable types
using consensus encoding. E.g. serialize `Transaction` as hex-encoded
string in Json in Bitcoin Core RPC protocol. This change provides
adapter to make this easier.

The adapter allows providing custom byte-to-string encoder for more
exotic cases and provides a hex implementation which should be useful in
majority of the cases.

Should help with #765
2022-12-02 10:48:05 +01:00
Noah Lanson d78a996bf6 Add `Witness::from_slice()` and depreciate `Witness:from_vec()` 2022-11-15 04:50:17 +11:00
sanket1729 932aaaa88a
Merge rust-bitcoin/rust-bitcoin#1367: Do clippy improvements
1050fe9cae Remove unnecessary borrow (Tobin C. Harding)
3966709336 Use is_none() (Tobin C. Harding)
d192052519 Remove unnecessary dereference (Tobin C. Harding)
624cda07b3 Remove unnecessary casts (Tobin C. Harding)

Pull request description:

  Clippy has been updated and new warnings are being triggered in our codebase. This PR does all warnings using nightly since they all looked like reasonable things to fix.

  Needed for CI to pass in other open PRs.

ACKs for top commit:
  Kixunil:
    ACK 1050fe9cae
  sanket1729:
    ACK 1050fe9cae.

Tree-SHA512: 7dcfb6a72a0aae51b49b417bb94cbe1becb1095d1bf0011921b1834a10f792cfcdeee37993ab9b103bd2dfcc9cd3c26cd7f1bb80b06b0d1aa4aaa454bfb0b3f0
2022-11-04 03:17:49 -07:00
Tobin C. Harding 3966709336 Use is_none()
Clippy emits:

 warning: binary comparison to literal `Option::None`

As suggested, use `find.is_none()` instead of comparison with `None`.
2022-11-04 11:47:34 +11:00
Martin Habovstiak d6ca7e4b9f Add a test parsing transaction with a huge witness
This transaction broke past versions of `rust-bitcoin` and LND so this
adds a test to avoid reintroducing the problem in the future.

See also https://github.com/romanz/electrs/issues/783
2022-11-01 14:27:38 +01:00
Tobin C. Harding fd7f8daeff Move sighash module to crate root
Done as part of the effort to flatten the `util` module.

The `sighash` module can stand alone in the crate root, it provides a
discreet set of functionality - the `SighashCache` and associated types.
2022-10-25 09:14:01 +11:00
Andrew Poelstra 01d5129d79
Merge rust-bitcoin/rust-bitcoin#1293: Move a bunch of stuff out of `internal_macros`
7d851b42ee Move serde_string_* macros to the serde_utils module (Tobin C. Harding)
53b681b838 Move const_assert to bitcoin_internals (Tobin C. Harding)
5a8a5ff6c9 Move debug_from_display to bitcoin_internals (Tobin C. Harding)
a2f08f2bc6 Improve docs on impl_array_newtype macro (Tobin C. Harding)
771cdde282 Move impl_array_newtype to bitcoin_internals (Tobin C. Harding)

Pull request description:

  Move macros out of `internal_macros`, done in an effort to work towards removing the `internal_macros` module since we have `bitcoin_internals` now.

ACKs for top commit:
  apoelstra:
    ACK 7d851b42ee
  Kixunil:
    ACK 7d851b42ee

Tree-SHA512: b31b3a5b4d18a2dbe3f358bff62ae6ca4041d432c755e9c45b0241d48903e02c95e79ec72a7478b9d2a53486ce9eef19bfe3b8905aba19036e59c0719f193ce7
2022-10-21 22:07:44 +00:00
Andrew Poelstra 17f0d29d08
add some comments to `Transaction::weight`
FIxes #1159
2022-10-20 15:24:17 +00:00
Tobin C. Harding 7d851b42ee Move serde_string_* macros to the serde_utils module
In preparation for emptying the `internal_macros` module move the
`serde_string_impl` and `serde_struct_human_string_imp` macros to the
`serde_utils` module.

Rationale: `internal_macros` stuff can go over in the `internals` crate
now that we have one. The serde macros could go over there but we have a
`serde_utils` module that holds code for implementing serde traits,
these two macros are exactly that.
2022-10-20 06:15:57 +11:00
Tobin C. Harding 2001f44e46 Try to fix up sighash export mess
Recently we moved a few types from `transaction` to `sighash`, while
doing so I erroneously annotated code with the `deprecated` attribute
hoping it would give downstream users a gentle upgrade experience. It
turns out `deprecated` only works on functions.

During that same work, we re-exported from the crate root a bunch of
types from the `sighash` module that probably should not have been
re-exported. We are currently trying to create a nice clean API surface,
in an effort to move in the right direction we should remove the
re-exports and just re-export the `sighash` module.

Try to clean up the sighash export mess by doing:

- Remove the re-exports from the `transaction` module
- Remove crate level re-exports of `sighash` module types
- Re-export `sighash` module

Note, this patch is a breaking API change, justified by the fact that
there is no good way to gently lead downstream when moving types since
types cannot be deprecated with the `deprecated` attribute.
2022-09-19 16:46:02 +10:00
Noah 96dfcdf3b7 Implement From for hash types 2022-09-16 22:29:05 +10:00
Tobin C. Harding 3f275f7f2b Remove code deprecated in v0.28.0
I believe we said we'd keep deprecated code around for two release
cycles so this code can  all be deleted now.
2022-09-15 13:29:02 +10:00