canceling all transactions on all markets for a market maker before e… (#14)

* canceling all transactions on all markets for a market maker before each run

---------

Co-authored-by: Maximilian Schneider <max@mango.markets>
This commit is contained in:
galactus 2023-04-15 12:17:15 +02:00 committed by GitHub
parent 378d41485c
commit 1ffd1e344a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 102 additions and 5 deletions

View File

@ -137,13 +137,14 @@ async fn get_blocks_with_retry(
) -> Result<Vec<Slot>, ()> {
const N_TRY_REQUEST_BLOCKS: u64 = 4;
for _ in 0..N_TRY_REQUEST_BLOCKS {
let block_slots = client.get_blocks_with_commitment(start_block, None, commitment_confirmation)
let block_slots = client
.get_blocks_with_commitment(start_block, None, commitment_confirmation)
.await;
match block_slots {
Ok(slots) => {
return Ok(slots);
},
}
Err(error) => {
warn!("Failed to download blocks: {}, retry", error);
}
@ -268,7 +269,9 @@ pub fn confirmations_by_blocks(
}
start_instant = tokio::time::Instant::now();
let block_slots = get_blocks_with_retry(client.clone(), start_block, commitment_confirmation).await;
let block_slots =
get_blocks_with_retry(client.clone(), start_block, commitment_confirmation)
.await;
if block_slots.is_err() {
break;
}
@ -277,7 +280,7 @@ pub fn confirmations_by_blocks(
if block_slots.is_empty() {
continue;
}
start_block = *block_slots.last().unwrap();
start_block = *block_slots.last().unwrap() + 1;
let blocks = block_slots.iter().map(|slot| {
client.get_block_with_config(

View File

@ -10,7 +10,7 @@ use {
},
keeper::start_keepers,
mango::{AccountKeys, MangoConfig},
market_markers::start_market_making_threads,
market_markers::{clean_market_makers, start_market_making_threads},
result_writer::initialize_result_writers,
states::PerpMarketCache,
stats::MangoSimulationStats,
@ -147,6 +147,15 @@ pub async fn main() -> anyhow::Result<()> {
.iter()
.map(|x| Pubkey::from_str(x.as_str()).unwrap())
.collect();
clean_market_makers(
nb_rpc_client.clone(),
&account_keys_parsed,
&perp_market_caches,
blockhash.clone(),
)
.await;
// start keeper if keeper authority is present
let keepers_jl = if let Some(keeper_authority) = keeper_authority {
let jl = start_keepers(

View File

@ -15,6 +15,7 @@ use mango::{
matching::Side,
};
use rand::{distributions::Uniform, prelude::Distribution, seq::SliceRandom};
use solana_client::nonblocking::rpc_client::RpcClient;
use solana_program::pubkey::Pubkey;
use solana_sdk::{
compute_budget, hash::Hash, instruction::Instruction, message::Message, signature::Keypair,
@ -269,3 +270,87 @@ pub fn start_market_making_threads(
})
.collect()
}
fn create_cancel_all_orders(
perp_market: &PerpMarketCache,
mango_account_pk: Pubkey,
mango_account_signer: &Keypair,
) -> Transaction {
let mango_account_signer_pk = to_sp_pk(&mango_account_signer.pubkey());
let cb_instruction = compute_budget::ComputeBudgetInstruction::set_compute_unit_limit(1000000);
let pf_instruction = compute_budget::ComputeBudgetInstruction::set_compute_unit_price(1000);
let instruction: Instruction = to_sdk_instruction(
cancel_all_perp_orders(
&perp_market.mango_program_pk,
&perp_market.mango_group_pk,
&mango_account_pk,
&mango_account_signer_pk,
&perp_market.perp_market_pk,
&perp_market.bids,
&perp_market.asks,
255,
)
.unwrap(),
);
Transaction::new_unsigned(Message::new(
&[cb_instruction, pf_instruction, instruction],
Some(&mango_account_signer.pubkey()),
))
}
pub async fn clean_market_makers(
rpc_client: Arc<RpcClient>,
account_keys_parsed: &Vec<AccountKeys>,
perp_market_caches: &Vec<PerpMarketCache>,
blockhash: Arc<RwLock<Hash>>,
) {
info!("Cleaning previous transactions by market makers");
let mut tasks = vec![];
for market_maker in account_keys_parsed {
let mango_account_pk =
Pubkey::from_str(market_maker.mango_account_pks[0].as_str()).unwrap();
for perp_market in perp_market_caches {
let market_maker = market_maker.clone();
let perp_market = perp_market.clone();
let rpc_client = rpc_client.clone();
let mango_account_pk = mango_account_pk.clone();
let blockhash = blockhash.clone();
let task = tokio::spawn(async move {
let mango_account_signer =
Keypair::from_bytes(market_maker.secret_key.as_slice()).unwrap();
for _ in 0..10 {
let mut tx = create_cancel_all_orders(
&perp_market,
mango_account_pk,
&mango_account_signer,
);
let recent_blockhash = *blockhash.read().await;
tx.sign(&[&mango_account_signer], recent_blockhash);
// send and confirm the transaction with an RPC
if let Ok(res) = tokio::time::timeout(
Duration::from_secs(10),
rpc_client.send_and_confirm_transaction(&tx),
)
.await
{
match res {
Ok(_) => break,
Err(e) => info!("Error occured while doing cancel all for ma : {} and perp market : {} error : {}", mango_account_pk, perp_market.perp_market_pk, e),
}
}
}
});
tasks.push(task);
}
}
futures::future::join_all(tasks).await;
info!("finished cleaning market makers");
}