Update how signatures are handled by the Router

This commit is contained in:
Luke Parker
2024-11-02 10:47:09 -04:00
parent 6a520a7412
commit cf4123b0f8
3 changed files with 151 additions and 77 deletions

View File

@@ -309,26 +309,36 @@ impl Router {
/// Get the message to be signed in order to update the key for Serai.
pub fn update_serai_key_message(nonce: u64, key: &PublicKey) -> Vec<u8> {
("updateSeraiKey", U256::try_from(nonce).expect("couldn't convert u64 to u256"), key.eth_repr())
.abi_encode_packed()
[
abi::updateSeraiKeyCall::SELECTOR.as_slice(),
&(U256::try_from(nonce).unwrap(), U256::ZERO, key.eth_repr()).abi_encode_params(),
]
.concat()
}
/// Construct a transaction to update the key representing Serai.
pub fn update_serai_key(&self, public_key: &PublicKey, sig: &Signature) -> TxLegacy {
TxLegacy {
to: TxKind::Call(self.1),
input: abi::updateSeraiKeyCall::new((public_key.eth_repr().into(), sig.into()))
.abi_encode()
.into(),
gas_limit: 40748 * 120 / 100,
input: [
abi::updateSeraiKeyCall::SELECTOR.as_slice(),
&(abi::Signature::from(sig), public_key.eth_repr()).abi_encode_params(),
]
.concat()
.into(),
gas_limit: 40927 * 120 / 100,
..Default::default()
}
}
/// Get the message to be signed in order to execute a series of `OutInstruction`s.
pub fn execute_message(nonce: u64, coin: Coin, fee: U256, outs: OutInstructions) -> Vec<u8> {
("execute".to_string(), U256::try_from(nonce).unwrap(), coin.address(), fee, outs.0)
.abi_encode_sequence()
[
abi::executeCall::SELECTOR.as_slice(),
&(U256::try_from(nonce).unwrap(), U256::ZERO, coin.address(), fee, outs.0)
.abi_encode_params(),
]
.concat()
}
/// Construct a transaction to execute a batch of `OutInstruction`s.
@@ -336,7 +346,12 @@ impl Router {
let outs_len = outs.0.len();
TxLegacy {
to: TxKind::Call(self.1),
input: abi::executeCall::new((coin.address(), fee, outs.0, sig.into())).abi_encode().into(),
input: [
abi::executeCall::SELECTOR.as_slice(),
&(abi::Signature::from(sig), coin.address(), fee, outs.0).abi_encode_params(),
]
.concat()
.into(),
// TODO
gas_limit: 100_000 + ((200_000 + 10_000) * u128::try_from(outs_len).unwrap()),
..Default::default()

View File

@@ -10,7 +10,7 @@ use alloy_sol_types::SolCall;
use alloy_consensus::TxLegacy;
use alloy_rpc_types_eth::BlockNumberOrTag;
use alloy_rpc_types_eth::{BlockNumberOrTag, TransactionReceipt};
use alloy_simple_request_transport::SimpleRequest;
use alloy_rpc_client::ClientBuilder;
use alloy_provider::RootProvider;
@@ -154,8 +154,16 @@ async fn test_erc20_in_instruction() {
todo!("TODO")
}
async fn publish_outs(key: (Scalar, PublicKey), nonce: u64, coin: Coin, fee: U256, outs: OutInstructions) -> TransactionReceipt {
let msg = Router::execute_message(nonce, coin, fee, instructions.clone());
async fn publish_outs(
provider: &RootProvider<SimpleRequest>,
router: &Router,
key: (Scalar, PublicKey),
nonce: u64,
coin: Coin,
fee: U256,
outs: OutInstructions,
) -> TransactionReceipt {
let msg = Router::execute_message(nonce, coin, fee, outs.clone());
let nonce = Scalar::random(&mut OsRng);
let c = Signature::challenge(ProjectivePoint::GENERATOR * nonce, &key.1, &msg);
@@ -163,10 +171,10 @@ async fn publish_outs(key: (Scalar, PublicKey), nonce: u64, coin: Coin, fee: U25
let sig = Signature::new(c, s).unwrap();
let mut tx = router.execute(coin, fee, instructions, &sig);
let mut tx = router.execute(coin, fee, outs, &sig);
tx.gas_price = 100_000_000_000u128;
let tx = ethereum_primitives::deterministically_sign(&tx);
ethereum_test_primitives::publish_tx(&provider, tx).await
ethereum_test_primitives::publish_tx(provider, tx).await
}
#[tokio::test]
@@ -182,7 +190,7 @@ async fn test_eth_address_out_instruction() {
ethereum_test_primitives::fund_account(&provider, router.address(), amount).await;
let instructions = OutInstructions::from([].as_slice());
let receipt = publish_outs(key, 1, Coin::Ether, fee, instructions);
let receipt = publish_outs(&provider, &router, key, 1, Coin::Ether, fee, instructions).await;
assert!(receipt.status());
println!("empty execute used {} gas:", receipt.gas_used);