Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rm usdc oracle dependancy #216

Merged
merged 2 commits into from
Mar 27, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 1 addition & 4 deletions pool/src/auctions/auction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -130,10 +130,7 @@ pub fn delete_liquidation(e: &Env, user: &Address) {
storage::del_auction(e, &(AuctionType::UserLiquidation as u32), user);
}

/// Fills the auction from the invoker. The filler is expected to maintain allowances to both
/// the pool and the backstop module.
///
/// TODO: Use auth-next to avoid required allowances
/// Fills the auction from the invoker.
///
/// ### Arguments
/// * `pool` - The pool
Expand Down
136 changes: 131 additions & 5 deletions pool/src/auctions/backstop_interest_auction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ pub fn create_interest_auction_data(
}

let mut pool = Pool::load(e);
let oracle_scalar = 10i128.pow(pool.load_price_decimals(e));
let mut auction_data = AuctionData {
lot: map![e],
bid: map![e],
Expand Down Expand Up @@ -48,13 +49,15 @@ pub fn create_interest_auction_data(
panic_with_error!(e, PoolError::BadRequest);
}

let usdc_token = storage::get_usdc_token(e);
let usdc_to_base = pool.load_price(e, &usdc_token);
let backstop_client = BackstopClient::new(&e, &storage::get_backstop(e));
let pool_backstop_data = backstop_client.pool_data(&e.current_contract_address());
let backstop_token_value_base = (pool_backstop_data.usdc * 5)
.fixed_div_floor(pool_backstop_data.tokens, usdc_to_base)
.unwrap_optimized();
let backstop_token_value_base = (pool_backstop_data
.usdc
.fixed_mul_floor(oracle_scalar, SCALAR_7)
.unwrap_optimized()
* 5)
.fixed_div_floor(pool_backstop_data.tokens, SCALAR_7)
.unwrap_optimized();
let bid_amount = interest_value
.fixed_mul_floor(1_4000000, SCALAR_7)
.unwrap_optimized()
Expand Down Expand Up @@ -396,6 +399,129 @@ mod tests {
});
}

#[test]
fn test_create_interest_auction_14_decimal_oracle() {
let e = Env::default();
e.mock_all_auths();
e.budget().reset_unlimited(); // setup exhausts budget

e.ledger().set(LedgerInfo {
timestamp: 12345,
protocol_version: 20,
sequence_number: 50,
network_id: Default::default(),
base_reserve: 10,
min_temp_entry_ttl: 10,
min_persistent_entry_ttl: 10,
max_entry_ttl: 2000000,
});

let bombadil = Address::generate(&e);

let pool_address = create_pool(&e);
let (usdc_id, _) = testutils::create_usdc_token(&e, &pool_address, &bombadil);
let (blnd_id, _) = testutils::create_blnd_token(&e, &pool_address, &bombadil);

let (backstop_token_id, _) = create_comet_lp_pool(&e, &bombadil, &blnd_id, &usdc_id);
let (backstop_address, backstop_client) = testutils::create_backstop(&e);
testutils::setup_backstop(
&e,
&pool_address,
&backstop_address,
&backstop_token_id,
&usdc_id,
&blnd_id,
);
backstop_client.deposit(&bombadil, &pool_address, &(50 * SCALAR_7));
backstop_client.update_tkn_val();
let (oracle_id, oracle_client) = testutils::create_mock_oracle(&e);

let (underlying_0, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_0, mut reserve_data_0) = testutils::default_reserve_meta();
reserve_data_0.last_time = 12345;
reserve_data_0.backstop_credit = 100_0000000;
reserve_data_0.b_supply = 1000_0000000;
reserve_data_0.d_supply = 750_0000000;
reserve_config_0.index = 0;
testutils::create_reserve(
&e,
&pool_address,
&underlying_0,
&reserve_config_0,
&reserve_data_0,
);

let (underlying_1, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_1, mut reserve_data_1) = testutils::default_reserve_meta();
reserve_data_1.last_time = 12345;
reserve_data_1.backstop_credit = 25_0000000;
reserve_data_1.b_supply = 250_0000000;
reserve_data_1.d_supply = 187_5000000;
reserve_config_1.index = 1;
testutils::create_reserve(
&e,
&pool_address,
&underlying_1,
&reserve_config_1,
&reserve_data_1,
);

let (underlying_2, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_2, mut reserve_data_2) = testutils::default_reserve_meta();
reserve_data_2.last_time = 12345;
reserve_config_2.index = 1;
testutils::create_reserve(
&e,
&pool_address,
&underlying_2,
&reserve_config_2,
&reserve_data_2,
);

oracle_client.set_data(
&bombadil,
&Asset::Other(Symbol::new(&e, "USD")),
&vec![
&e,
Asset::Stellar(underlying_0.clone()),
Asset::Stellar(underlying_1.clone()),
Asset::Stellar(underlying_2),
Asset::Stellar(usdc_id.clone()),
],
&14,
&300,
);
oracle_client.set_price_stable(&vec![
&e,
2_0000000_0000000,
4_0000000_0000000,
100_0000000_0000000,
1_0000000_0000000,
]);

let pool_config = PoolConfig {
oracle: oracle_id,
bstop_rate: 0_1000000,
status: 0,
max_positions: 4,
};
e.as_contract(&pool_address, || {
storage::set_pool_config(&e, &pool_config);

let result = create_interest_auction_data(
&e,
&backstop_address,
&vec![&e, underlying_0.clone(), underlying_1.clone()],
);
assert_eq!(result.block, 51);
assert_eq!(result.bid.get_unchecked(backstop_token_id), 336_0000000);
assert_eq!(result.bid.len(), 1);
assert_eq!(result.lot.get_unchecked(underlying_0), 100_0000000);
assert_eq!(result.lot.get_unchecked(underlying_1), 25_0000000);
assert_eq!(result.lot.len(), 2);
});
}

#[test]
fn test_create_interest_auction_applies_interest() {
let e = Env::default();
Expand Down
150 changes: 145 additions & 5 deletions pool/src/auctions/bad_debt_auction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ pub fn create_bad_debt_auction_data(e: &Env, backstop: &Address) -> AuctionData
};

let mut pool = Pool::load(e);
let oracle_scalar = 10i128.pow(pool.load_price_decimals(e));
let backstop_positions = storage::get_user_positions(e, backstop);
let reserve_list = storage::get_res_list(e);
let mut debt_value = 0;
Expand All @@ -47,11 +48,10 @@ pub fn create_bad_debt_auction_data(e: &Env, backstop: &Address) -> AuctionData
// TODO: Remove backstop_token getter call if WASM cache is not implemented
mootz12 marked this conversation as resolved.
Show resolved Hide resolved
let backstop_token = backstop_client.backstop_token();
let pool_backstop_data = backstop_client.pool_data(&e.current_contract_address());
let usdc_token = storage::get_usdc_token(e);
let usdc_to_base = pool.load_price(e, &usdc_token);
let backstop_value_base = usdc_to_base
.fixed_mul_floor(pool_backstop_data.usdc, SCALAR_7)
.unwrap_optimized()
let backstop_value_base = pool_backstop_data
.usdc
.fixed_mul_floor(oracle_scalar, SCALAR_7)
.unwrap_optimized() // adjust for oracle scalar
* 5; // Since the backstop LP token is an 80/20 split of USDC/BLND, we multiply by 5 to get the value of the BLND portion
let backstop_token_to_base = backstop_value_base
.fixed_div_floor(pool_backstop_data.tokens, SCALAR_7)
Expand Down Expand Up @@ -338,6 +338,146 @@ mod tests {
});
}

#[test]
fn test_create_bad_debt_auction_oracle_14_decimals() {
let e = Env::default();
e.mock_all_auths_allowing_non_root_auth();
e.budget().reset_unlimited(); // setup exhausts budget

e.ledger().set(LedgerInfo {
timestamp: 12345,
protocol_version: 20,
sequence_number: 50,
network_id: Default::default(),
base_reserve: 10,
min_temp_entry_ttl: 10,
min_persistent_entry_ttl: 10,
max_entry_ttl: 2000000,
});

let bombadil = Address::generate(&e);
let samwise = Address::generate(&e);
let pool_address = create_pool(&e);

let (blnd, blnd_client) = testutils::create_blnd_token(&e, &pool_address, &bombadil);
let (usdc, usdc_client) = testutils::create_usdc_token(&e, &pool_address, &bombadil);
let (lp_token, lp_token_client) =
testutils::create_comet_lp_pool(&e, &bombadil, &blnd, &usdc);
let (backstop_address, backstop_client) = testutils::create_backstop(&e);
testutils::setup_backstop(
&e,
&pool_address,
&backstop_address,
&lp_token,
&usdc,
&blnd,
);
// mint lp tokens
blnd_client.mint(&samwise, &500_001_0000000);
blnd_client.approve(&samwise, &lp_token, &i128::MAX, &99999);
usdc_client.mint(&samwise, &12_501_0000000);
usdc_client.approve(&samwise, &lp_token, &i128::MAX, &99999);
lp_token_client.join_pool(
&50_000_0000000,
&vec![&e, 500_001_0000000, 12_501_0000000],
&samwise,
);
backstop_client.deposit(&samwise, &pool_address, &50_000_0000000);
backstop_client.update_tkn_val();

let (oracle_id, oracle_client) = testutils::create_mock_oracle(&e);

let (underlying_0, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_0, mut reserve_data_0) = testutils::default_reserve_meta();
reserve_data_0.d_rate = 1_100_000_000;
reserve_data_0.last_time = 12345;
reserve_config_0.index = 0;
testutils::create_reserve(
&e,
&pool_address,
&underlying_0,
&reserve_config_0,
&reserve_data_0,
);

let (underlying_1, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_1, mut reserve_data_1) = testutils::default_reserve_meta();
reserve_data_1.d_rate = 1_200_000_000;
reserve_data_1.last_time = 12345;
reserve_config_1.index = 1;
testutils::create_reserve(
&e,
&pool_address,
&underlying_1,
&reserve_config_1,
&reserve_data_1,
);

let (underlying_2, _) = testutils::create_token_contract(&e, &bombadil);
let (mut reserve_config_2, mut reserve_data_2) = testutils::default_reserve_meta();
reserve_data_2.b_rate = 1_100_000_000;
reserve_data_2.last_time = 12345;
reserve_config_2.index = 1;
testutils::create_reserve(
&e,
&pool_address,
&underlying_2,
&reserve_config_2,
&reserve_data_2,
);

oracle_client.set_data(
&bombadil,
&Asset::Other(Symbol::new(&e, "USD")),
&vec![
&e,
Asset::Stellar(underlying_0.clone()),
Asset::Stellar(underlying_1.clone()),
Asset::Stellar(underlying_2),
Asset::Stellar(usdc),
],
&14,
&300,
);
oracle_client.set_price_stable(&vec![
&e,
2_0000000_0000000,
4_0000000_0000000,
100_0000000_0000000,
1_0000000_0000000,
]);

let positions: Positions = Positions {
collateral: map![&e],
liabilities: map![
&e,
(reserve_config_0.index, 10_0000000),
(reserve_config_1.index, 2_5000000)
],
supply: map![&e],
};

let pool_config = PoolConfig {
oracle: oracle_id,
bstop_rate: 0_1000000,
status: 0,
max_positions: 4,
};
e.as_contract(&pool_address, || {
storage::set_pool_config(&e, &pool_config);
storage::set_user_positions(&e, &backstop_address, &positions);

let result = create_bad_debt_auction_data(&e, &backstop_address);

assert_eq!(result.block, 51);
assert_eq!(result.bid.get_unchecked(underlying_0), 10_0000000);
assert_eq!(result.bid.get_unchecked(underlying_1), 2_5000000);
assert_eq!(result.bid.len(), 2);
assert_eq!(result.lot.get_unchecked(lp_token), 38_0800000);
assert_eq!(result.lot.len(), 1);
});
}

#[test]
fn test_create_bad_debt_auction_max_balance() {
let e = Env::default();
Expand Down
1 change: 0 additions & 1 deletion pool/src/auctions/user_liquidation_auction.rs
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ use crate::{errors::PoolError, storage};

use super::AuctionType;

// TODO: Revalidate math with alternative decimal reserve
pub fn create_user_liq_auction_data(
e: &Env,
user: &Address,
Expand Down
2 changes: 1 addition & 1 deletion test-suites/src/test_fixture.rs
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ impl TestFixture<'_> {
let (blnd_id, blnd_client) = create_stellar_token(&e, &bombadil);
let (eth_id, eth_client) = create_token(&e, &bombadil, 9, "wETH");
let (usdc_id, usdc_client) = create_stellar_token(&e, &bombadil);
let (xlm_id, xlm_client) = create_stellar_token(&e, &bombadil); // TODO: make native
let (xlm_id, xlm_client) = create_stellar_token(&e, &bombadil);
let (stable_id, stable_client) = create_token(&e, &bombadil, 6, "STABLE");

// deploy Blend Protocol contracts
Expand Down
2 changes: 1 addition & 1 deletion test-suites/tests/test_liquidation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -313,7 +313,7 @@ fn test_liquidations() {
frodo_stable_balance - usdc_bid_amount
+ stable_interest_lot_amount
.fixed_div_floor(2 * 10i128.pow(6), 10i128.pow(6))
.unwrap(), // - usdc_donate_bid_amount TODO: add donate diff when donating is implemented
.unwrap(),
10i128.pow(6),
);
assert_approx_eq_abs(
Expand Down
Loading