From 3730ce30e37f3017153419dca720e759b990c307 Mon Sep 17 00:00:00 2001 From: Reisen Date: Wed, 7 Jul 2021 08:48:37 +0000 Subject: [PATCH] Check the on-chain state for paid fees test Change-Id: I85def349ba9888edb8d9e4264c7eb593c0e7c766 --- solana/bridge/program/tests/integration.rs | 93 ++++++++++++++++++++-- 1 file changed, 85 insertions(+), 8 deletions(-) diff --git a/solana/bridge/program/tests/integration.rs b/solana/bridge/program/tests/integration.rs index d196e2b68..0563ec343 100644 --- a/solana/bridge/program/tests/integration.rs +++ b/solana/bridge/program/tests/integration.rs @@ -143,6 +143,7 @@ fn run_integration_tests() { test_guardian_set_change(&mut context); test_guardian_set_change_fails(&mut context); test_set_fees(&mut context); + test_set_fees_fails(&mut context); test_transfer_fees(&mut context); } @@ -486,9 +487,10 @@ fn test_guardian_set_change_fails(context: &mut Context) { fn test_set_fees(context: &mut Context) { // Initialize a wormhole bridge on Solana to test with. let (ref payer, ref client, ref program) = common::setup(); - let emitter = Keypair::from_bytes(&GOV_KEY).unwrap(); + let emitter = Keypair::from_bytes(&GOVERNANCE_KEY).unwrap(); + let sequence = context.seq.next(emitter.pubkey().to_bytes()); - let nonce = 12401; + let nonce = rand::thread_rng().gen(); let message = GovernancePayloadSetMessageFee { fee: U256::from(100), persisted_fee: U256::from(100), @@ -511,12 +513,29 @@ fn test_set_fees(context: &mut Context) { let (vaa, body, body_hash) = common::generate_vaa(&emitter, message.clone(), nonce, 1, 1); common::verify_signatures(client, program, payer, body, body_hash, &context.secret, 1).unwrap(); common::post_vaa(client, program, payer, vaa).unwrap(); - common::set_fees(client, program, payer, message_key, emitter.pubkey(), 3).unwrap(); + common::set_fees( + client, + program, + payer, + message_key, + emitter.pubkey(), + sequence, + ) + .unwrap(); + common::sync(client, payer); + + // Fetch Bridge to check on-state value. + let bridge_key = Bridge::<'_, { AccountState::Uninitialized }>::key(None, &program); + let fee_collector = FeeCollector::key(None, &program); + let bridge: BridgeData = common::get_account_data(client, &bridge_key); + assert_eq!(bridge.config.fee, 100); + assert_eq!(bridge.config.fee_persistent, 100); // Check that posting a new message fails with too small a fee. + let account_balance = client.get_account(&fee_collector).unwrap().lamports; let emitter = Keypair::new(); - let nonce = 12402; - let message = b"Fail to Pay".to_vec(); + let nonce = rand::thread_rng().gen(); + let message = [0u8; 32].to_vec(); assert!(common::post_message( client, program, @@ -528,12 +547,19 @@ fn test_set_fees(context: &mut Context) { false ) .is_err()); + common::sync(client, payer); + + assert_eq!( + client.get_account(&fee_collector).unwrap().lamports, + account_balance, + ); // And succeeds with the new. let emitter = Keypair::new(); - let nonce = 12402; - let message = b"Fail to Pay".to_vec(); - common::post_message( + let sequence = context.seq.next(emitter.pubkey().to_bytes()); + let nonce = rand::thread_rng().gen(); + let message = [0u8; 32].to_vec(); + let message_key = common::post_message( client, program, payer, @@ -544,6 +570,57 @@ fn test_set_fees(context: &mut Context) { false, ) .unwrap(); + + let (vaa, body, body_hash) = common::generate_vaa(&emitter, message.clone(), nonce, 1, 1); + common::verify_signatures(client, program, payer, body, body_hash, &context.secret, 1).unwrap(); + common::post_vaa(client, program, payer, vaa).unwrap(); + common::sync(client, payer); + + // Verify that the fee collector was paid. + assert_eq!( + client.get_account(&fee_collector).unwrap().lamports, + account_balance + 100, + ); + + // Derive where we expect created accounts to be. + let signature_set = SignatureSet::<'_, { AccountState::Uninitialized }>::key( + &SignatureSetDerivationData { hash: body_hash }, + &program, + ); + + // And that the new message is on chain. + let posted_message: PostedMessage = common::get_account_data(client, &message_key); + let signatures: SignatureSetData = common::get_account_data(client, &signature_set); + + // Verify on chain Message + assert_eq!(posted_message.0.vaa_version, 0); + assert_eq!(posted_message.0.persist, false); + assert_eq!(posted_message.0.vaa_signature_account, signature_set); + assert_eq!(posted_message.0.nonce, nonce); + assert_eq!(posted_message.0.sequence, sequence); + assert_eq!(posted_message.0.emitter_chain, 1); + assert_eq!(posted_message.0.payload, message); + assert_eq!( + posted_message.0.emitter_address, + emitter.pubkey().to_bytes() + ); + + // Verify on chain Signatures + assert_eq!(signatures.hash, body_hash); + assert_eq!(signatures.guardian_set_index, 1); + + for (signature, secret_key) in signatures.signatures.iter().zip(context.secret.iter()) { + // Sign message locally. + let (local_sig, recover_id) = secp256k1::sign(&Secp256k1Message::parse(&body_hash), &secret_key); + + // Combine recoverify with signature to match 65 byte layout. + let mut signature_bytes = [0u8; 65]; + signature_bytes[64] = recover_id.serialize(); + (&mut signature_bytes[0..64]).copy_from_slice(&local_sig.serialize()); + + // Signature stored should on chain be as expected. + assert_eq!(*signature, signature_bytes); + } } fn test_transfer_fees(context: &mut Context) {