From 75106e6d82eb8d9be5f30f944eca91f1c4b061ca Mon Sep 17 00:00:00 2001 From: "Tobin C. Harding" Date: Thu, 12 Jun 2025 11:17:32 +1000 Subject: [PATCH] Remove checked_ prefix from fee functions The `Amount` and `FeeRate` types are not simple int wrappers, as such we do not need to mimic the stdlib too closely. Having the `checked_` prefix to the functions that do fee calcualtions adds no additional meaning. Note that I'm about to change the return type to use `NumOpResult` further justifying this change. Note we leave the 'Checked foo' in the functions docs title because the functions are still checked. --- units/src/amount/tests.rs | 26 ++++++++++++------------ units/src/amount/unsigned.rs | 10 +++++----- units/src/fee.rs | 38 ++++++++++++++++++------------------ units/src/fee_rate/mod.rs | 6 +++--- units/src/weight.rs | 4 ++-- 5 files changed, 42 insertions(+), 42 deletions(-) diff --git a/units/src/amount/tests.rs b/units/src/amount/tests.rs index 021fa13bc..853370adc 100644 --- a/units/src/amount/tests.rs +++ b/units/src/amount/tests.rs @@ -268,17 +268,17 @@ fn positive_sub() { #[test] fn amount_checked_div_by_weight_ceil() { let weight = Weight::from_kwu(1).unwrap(); - let fee_rate = sat(1).checked_div_by_weight_ceil(weight).unwrap(); + let fee_rate = sat(1).div_by_weight_ceil(weight).unwrap(); // 1 sats / 1,000 wu = 1 sats/kwu assert_eq!(fee_rate, FeeRate::from_sat_per_kwu(1).unwrap()); let weight = Weight::from_wu(381); - let fee_rate = sat(329).checked_div_by_weight_ceil(weight).unwrap(); + let fee_rate = sat(329).div_by_weight_ceil(weight).unwrap(); // 329 sats / 381 wu = 863.5 sats/kwu // round up to 864 assert_eq!(fee_rate, FeeRate::from_sat_per_kwu(864).unwrap()); - let fee_rate = Amount::ONE_SAT.checked_div_by_weight_ceil(Weight::ZERO); + let fee_rate = Amount::ONE_SAT.div_by_weight_ceil(Weight::ZERO); assert!(fee_rate.is_none()); } @@ -286,17 +286,17 @@ fn amount_checked_div_by_weight_ceil() { #[test] fn amount_checked_div_by_weight_floor() { let weight = Weight::from_kwu(1).unwrap(); - let fee_rate = sat(1).checked_div_by_weight_floor(weight).unwrap(); + let fee_rate = sat(1).div_by_weight_floor(weight).unwrap(); // 1 sats / 1,000 wu = 1 sats/kwu assert_eq!(fee_rate, FeeRate::from_sat_per_kwu(1).unwrap()); let weight = Weight::from_wu(381); - let fee_rate = sat(329).checked_div_by_weight_floor(weight).unwrap(); + let fee_rate = sat(329).div_by_weight_floor(weight).unwrap(); // 329 sats / 381 wu = 863.5 sats/kwu // round down to 863 assert_eq!(fee_rate, FeeRate::from_sat_per_kwu(863).unwrap()); - let fee_rate = Amount::ONE_SAT.checked_div_by_weight_floor(Weight::ZERO); + let fee_rate = Amount::ONE_SAT.div_by_weight_floor(Weight::ZERO); assert!(fee_rate.is_none()); } @@ -307,31 +307,31 @@ fn amount_checked_div_by_fee_rate() { let fee_rate = FeeRate::from_sat_per_kwu(2).unwrap(); // Test floor division - let weight = amount.checked_div_by_fee_rate_floor(fee_rate).unwrap(); + let weight = amount.div_by_fee_rate_floor(fee_rate).unwrap(); // 1000 sats / (2 sats/kwu) = 500,000 wu assert_eq!(weight, Weight::from_wu(500_000)); // Test ceiling division - let weight = amount.checked_div_by_fee_rate_ceil(fee_rate).unwrap(); + let weight = amount.div_by_fee_rate_ceil(fee_rate).unwrap(); assert_eq!(weight, Weight::from_wu(500_000)); // Same result for exact division // Test truncation behavior let amount = sat(1000); let fee_rate = FeeRate::from_sat_per_kwu(3).unwrap(); - let floor_weight = amount.checked_div_by_fee_rate_floor(fee_rate).unwrap(); - let ceil_weight = amount.checked_div_by_fee_rate_ceil(fee_rate).unwrap(); + let floor_weight = amount.div_by_fee_rate_floor(fee_rate).unwrap(); + let ceil_weight = amount.div_by_fee_rate_ceil(fee_rate).unwrap(); assert_eq!(floor_weight, Weight::from_wu(333_333)); assert_eq!(ceil_weight, Weight::from_wu(333_334)); // Test division by zero let zero_fee_rate = FeeRate::from_sat_per_kwu(0).unwrap(); - assert!(amount.checked_div_by_fee_rate_floor(zero_fee_rate).is_none()); - assert!(amount.checked_div_by_fee_rate_ceil(zero_fee_rate).is_none()); + assert!(amount.div_by_fee_rate_floor(zero_fee_rate).is_none()); + assert!(amount.div_by_fee_rate_ceil(zero_fee_rate).is_none()); // Test with maximum amount let max_amount = Amount::MAX; let small_fee_rate = FeeRate::from_sat_per_kwu(1).unwrap(); - let weight = max_amount.checked_div_by_fee_rate_floor(small_fee_rate).unwrap(); + let weight = max_amount.div_by_fee_rate_floor(small_fee_rate).unwrap(); // 21_000_000_0000_0000 sats / (1 sat/kwu) = 2_100_000_000_000_000_000 wu assert_eq!(weight, Weight::from_wu(2_100_000_000_000_000_000)); } diff --git a/units/src/amount/unsigned.rs b/units/src/amount/unsigned.rs index bbc126f91..2e25eda84 100644 --- a/units/src/amount/unsigned.rs +++ b/units/src/amount/unsigned.rs @@ -411,7 +411,7 @@ impl Amount { /// /// Returns [`None`] if overflow occurred. #[must_use] - pub const fn checked_div_by_weight_floor(self, weight: Weight) -> Option { + pub const fn div_by_weight_floor(self, weight: Weight) -> Option { let wu = weight.to_wu(); if wu == 0 { return None; @@ -441,12 +441,12 @@ impl Amount { /// # use bitcoin_units::{amount, Amount, FeeRate, Weight}; /// let amount = Amount::from_sat(10)?; /// let weight = Weight::from_wu(300); - /// let fee_rate = amount.checked_div_by_weight_ceil(weight); + /// let fee_rate = amount.div_by_weight_ceil(weight); /// assert_eq!(fee_rate, FeeRate::from_sat_per_kwu(34)); /// # Ok::<_, amount::OutOfRangeError>(()) /// ``` #[must_use] - pub const fn checked_div_by_weight_ceil(self, weight: Weight) -> Option { + pub const fn div_by_weight_ceil(self, weight: Weight) -> Option { let wu = weight.to_wu(); if wu == 0 { return None; @@ -471,7 +471,7 @@ impl Amount { /// /// Returns [`None`] if overflow occurred or if `fee_rate` is zero. #[must_use] - pub const fn checked_div_by_fee_rate_floor(self, fee_rate: FeeRate) -> Option { + pub const fn div_by_fee_rate_floor(self, fee_rate: FeeRate) -> Option { if let Some(msats) = self.to_sat().checked_mul(1000) { if let Some(wu) = msats.checked_div(fee_rate.to_sat_per_kwu_ceil()) { return Some(Weight::from_wu(wu)); @@ -487,7 +487,7 @@ impl Amount { /// /// Returns [`None`] if overflow occurred or if `fee_rate` is zero. #[must_use] - pub const fn checked_div_by_fee_rate_ceil(self, fee_rate: FeeRate) -> Option { + pub const fn div_by_fee_rate_ceil(self, fee_rate: FeeRate) -> Option { // Use ceil because result is used as the divisor. let rate = fee_rate.to_sat_per_kwu_ceil(); if rate == 0 { diff --git a/units/src/fee.rs b/units/src/fee.rs index 008fd920b..b156cb694 100644 --- a/units/src/fee.rs +++ b/units/src/fee.rs @@ -8,19 +8,19 @@ //! Either the weight or fee rate can be calculated if one knows the total fee and either of the //! other values. Note however that such calculations truncate (as for integer division). //! -//! We provide `fee.checked_div_by_weight_ceil(weight)` to calculate a minimum threshold fee rate +//! We provide `fee.div_by_weight_ceil(weight)` to calculate a minimum threshold fee rate //! required to pay at least `fee` for transaction with `weight`. //! //! We support various `core::ops` traits all of which return [`NumOpResult`]. //! //! For specific methods see: //! -//! * [`Amount::checked_div_by_weight_floor`] -//! * [`Amount::checked_div_by_weight_ceil`] -//! * [`Amount::checked_div_by_fee_rate_floor`] -//! * [`Amount::checked_div_by_fee_rate_ceil`] -//! * [`Weight::checked_mul_by_fee_rate`] -//! * [`FeeRate::checked_mul_by_weight`] +//! * [`Amount::div_by_weight_floor`] +//! * [`Amount::div_by_weight_ceil`] +//! * [`Amount::div_by_fee_rate_floor`] +//! * [`Amount::div_by_fee_rate_ceil`] +//! * [`Weight::mul_by_fee_rate`] +//! * [`FeeRate::mul_by_weight`] //! * [`FeeRate::to_fee`] use core::ops; @@ -33,7 +33,7 @@ crate::internal_macros::impl_op_for_references! { impl ops::Mul for Weight { type Output = NumOpResult; fn mul(self, rhs: FeeRate) -> Self::Output { - match rhs.checked_mul_by_weight(self) { + match rhs.mul_by_weight(self) { Some(amount) => R::Valid(amount), None => R::Error(E::while_doing(MathOp::Mul)), } @@ -73,7 +73,7 @@ crate::internal_macros::impl_op_for_references! { impl ops::Mul for FeeRate { type Output = NumOpResult; fn mul(self, rhs: Weight) -> Self::Output { - match self.checked_mul_by_weight(rhs) { + match self.mul_by_weight(rhs) { Some(amount) => R::Valid(amount), None => R::Error(E::while_doing(MathOp::Mul)), } @@ -114,7 +114,7 @@ crate::internal_macros::impl_op_for_references! { type Output = NumOpResult; fn div(self, rhs: Weight) -> Self::Output { - self.checked_div_by_weight_floor(rhs).valid_or_error(MathOp::Div) + self.div_by_weight_floor(rhs).valid_or_error(MathOp::Div) } } impl ops::Div for NumOpResult { @@ -155,7 +155,7 @@ crate::internal_macros::impl_op_for_references! { type Output = NumOpResult; fn div(self, rhs: FeeRate) -> Self::Output { - self.checked_div_by_fee_rate_floor(rhs).valid_or_error(MathOp::Div) + self.div_by_fee_rate_floor(rhs).valid_or_error(MathOp::Div) } } impl ops::Div for NumOpResult { @@ -211,25 +211,25 @@ mod tests { } #[test] - fn checked_weight_mul() { + fn weight_mul() { let weight = Weight::from_vb(10).unwrap(); let fee: Amount = FeeRate::from_sat_per_vb(10) .unwrap() - .checked_mul_by_weight(weight) + .mul_by_weight(weight) .expect("expected Amount"); assert_eq!(Amount::from_sat_u32(100), fee); - let fee = FeeRate::from_sat_per_kwu(10).unwrap().checked_mul_by_weight(Weight::MAX); + let fee = FeeRate::from_sat_per_kwu(10).unwrap().mul_by_weight(Weight::MAX); assert!(fee.is_none()); let weight = Weight::from_vb(3).unwrap(); let fee_rate = FeeRate::from_sat_per_vb(3).unwrap(); - let fee = fee_rate.checked_mul_by_weight(weight).unwrap(); + let fee = fee_rate.mul_by_weight(weight).unwrap(); assert_eq!(Amount::from_sat_u32(9), fee); let weight = Weight::from_wu(381); let fee_rate = FeeRate::from_sat_per_kwu(864).unwrap(); - let fee = weight.checked_mul_by_fee_rate(fee_rate).unwrap(); + let fee = weight.mul_by_fee_rate(fee_rate).unwrap(); // 381 * 0.864 yields 329.18. // The result is then rounded up to 330. assert_eq!(fee, Amount::from_sat_u32(330)); @@ -277,12 +277,12 @@ mod tests { assert_eq!(weight, Weight::from_wu(333_333)); // Verify that ceiling division gives different result - let ceil_weight = amount.checked_div_by_fee_rate_ceil(fee_rate).unwrap(); + let ceil_weight = amount.div_by_fee_rate_ceil(fee_rate).unwrap(); assert_eq!(ceil_weight, Weight::from_wu(333_334)); // Test that division by zero returns None let zero_rate = FeeRate::from_sat_per_kwu(0).unwrap(); - assert!(amount.checked_div_by_fee_rate_floor(zero_rate).is_none()); - assert!(amount.checked_div_by_fee_rate_ceil(zero_rate).is_none()); + assert!(amount.div_by_fee_rate_floor(zero_rate).is_none()); + assert!(amount.div_by_fee_rate_ceil(zero_rate).is_none()); } } diff --git a/units/src/fee_rate/mod.rs b/units/src/fee_rate/mod.rs index aec144041..70e0e371e 100644 --- a/units/src/fee_rate/mod.rs +++ b/units/src/fee_rate/mod.rs @@ -196,7 +196,7 @@ impl FeeRate { /// wrapping. pub const fn to_fee(self, weight: Weight) -> Amount { // No `unwrap_or()` in const context. - match self.checked_mul_by_weight(weight) { + match self.mul_by_weight(weight) { Some(fee) => fee, None => Amount::MAX, } @@ -208,7 +208,7 @@ impl FeeRate { /// This is equivalent to `Self::checked_mul_by_weight()`. #[must_use] #[deprecated(since = "TBD", note = "use `to_fee()` instead")] - pub fn fee_wu(self, weight: Weight) -> Option { self.checked_mul_by_weight(weight) } + pub fn fee_wu(self, weight: Weight) -> Option { self.mul_by_weight(weight) } /// Calculates the fee by multiplying this fee rate by weight, in virtual bytes, returning [`None`] /// if an overflow occurred. @@ -227,7 +227,7 @@ impl FeeRate { /// /// Returns [`None`] if overflow occurred. #[must_use] - pub const fn checked_mul_by_weight(self, weight: Weight) -> Option { + pub const fn mul_by_weight(self, weight: Weight) -> Option { let wu = weight.to_wu(); if let Some(fee_kwu) = self.to_sat_per_kwu_floor().checked_mul(wu) { // Bump by 999 to do ceil division using kwu. diff --git a/units/src/weight.rs b/units/src/weight.rs index 5bf700471..0589cb0f7 100644 --- a/units/src/weight.rs +++ b/units/src/weight.rs @@ -171,8 +171,8 @@ impl Weight { /// /// Returns [`None`] if overflow occurred. #[must_use] - pub const fn checked_mul_by_fee_rate(self, fee_rate: FeeRate) -> Option { - fee_rate.checked_mul_by_weight(self) + pub const fn mul_by_fee_rate(self, fee_rate: FeeRate) -> Option { + fee_rate.mul_by_weight(self) } }