Skip to content

Commit

Permalink
CU-1yykjpw Fix calc_utilization_ratio() and add proptest for it.
Browse files Browse the repository at this point in the history
  • Loading branch information
vivekvpandya committed Jan 18, 2022
1 parent 19c1a53 commit 718e790
Show file tree
Hide file tree
Showing 3 changed files with 18 additions and 28 deletions.
8 changes: 2 additions & 6 deletions frame/composable-traits/src/lending/math.rs
Original file line number Diff line number Diff line change
Expand Up @@ -39,15 +39,11 @@ pub fn calc_utilization_ratio(
}

let total = cash.safe_add(&borrows)?;
// also max value is 1.00000000000000000, it still fails with u8, so mul by u16 and cast to u8
// safely
let utilization_ratio = borrows
.checked_div(&total)
.expect("above checks prove it cannot error")
.checked_mul_int(100_u16)
.ok_or(ArithmeticError::Overflow)?
.try_into()
.map_err(|_| ArithmeticError::Overflow)?;
.checked_mul_int(100_u8)
.ok_or(ArithmeticError::Overflow)?;
Ok(Percent::from_percent(utilization_ratio))
}

Expand Down
22 changes: 0 additions & 22 deletions frame/composable-traits/src/rate_model.rs
Original file line number Diff line number Diff line change
Expand Up @@ -47,28 +47,6 @@ pub type Ratio = FixedU128;
/// accounts to length of year)
pub const SECONDS_PER_YEAR: DurationSeconds = 365 * 24 * ONE_HOUR;

/// utilization_ratio = total_borrows / (total_cash + total_borrows)
pub fn calc_utilization_ratio(
cash: LiftedFixedBalance,
borrows: LiftedFixedBalance,
) -> Result<Percent, ArithmeticError> {
if borrows.is_zero() {
return Ok(Percent::zero())
}

let total = cash.safe_add(&borrows)?;
// also max value is 1.00000000000000000, it still fails with u8, so mul by u16 and cast to u8
// safely
let utilization_ratio = borrows
.checked_div(&total)
.expect("above checks prove it cannot error")
.checked_mul_int(100_u16)
.ok_or(ArithmeticError::Overflow)?
.try_into()
.map_err(|_| ArithmeticError::Overflow)?;
Ok(Percent::from_percent(utilization_ratio))
}

pub trait InterestRate {
fn get_borrow_rate(&mut self, utilization: Percent) -> Option<Rate>;
}
Expand Down
16 changes: 16 additions & 0 deletions frame/lending/src/tests.rs
Original file line number Diff line number Diff line change
Expand Up @@ -331,6 +331,7 @@ fn new_jump_model() -> (Percent, InterestRateModel) {
fn test_calc_utilization_ratio() {
// 50% borrow
assert_eq!(Lending::calc_utilization_ratio(&1, &1).unwrap(), Percent::from_percent(50));
assert_eq!(Lending::calc_utilization_ratio(&1, &1).unwrap(), Percent::from_float(0.50));
assert_eq!(Lending::calc_utilization_ratio(&100, &100).unwrap(), Percent::from_percent(50));
// no borrow
assert_eq!(Lending::calc_utilization_ratio(&1, &0).unwrap(), Percent::zero());
Expand Down Expand Up @@ -705,6 +706,13 @@ prop_compose! {
}
}

prop_compose! {
fn valid_cash_borrow()(cash in 1..u32::MAX)(borrow in 0..cash, cash in Just(cash))
-> (u32, u32) {
(cash, borrow)
}
}

prop_compose! {
fn valid_amounts_without_overflow_2()
(x in MINIMUM_BALANCE..u64::MAX as Balance / 2,
Expand Down Expand Up @@ -831,6 +839,14 @@ proptest! {
})?;
}

#[test]
fn calc_utilization_ratio_proptest((cash, borrow) in valid_cash_borrow()) {
new_test_ext().execute_with(|| {
prop_assert_eq!(Lending::calc_utilization_ratio(&cash.into(), &borrow.into()).unwrap(), Percent::from_float(borrow as f64 / (cash as f64 + borrow as f64)));
Ok(())
})?;
}

#[test]
fn market_creation_with_multi_level_priceable_lp(depth in 0..20) {
new_test_ext().execute_with(|| {
Expand Down

0 comments on commit 718e790

Please sign in to comment.