From f574b322818930cf87f5a739a3045dd81daa86f2 Mon Sep 17 00:00:00 2001 From: parodyBit <58690522+parodyBit@users.noreply.github.com> Date: Thu, 2 Jan 2025 10:28:18 -0700 Subject: [PATCH 1/3] Include validator pkh in authorization --- node/src/actors/json_rpc/api.rs | 10 ++++++---- src/cli/node/json_rpc_client.rs | 15 +++++++++++++-- 2 files changed, 19 insertions(+), 6 deletions(-) diff --git a/node/src/actors/json_rpc/api.rs b/node/src/actors/json_rpc/api.rs index a3ba3a632..8a3842347 100644 --- a/node/src/actors/json_rpc/api.rs +++ b/node/src/actors/json_rpc/api.rs @@ -2045,10 +2045,12 @@ pub async fn stake(params: Result) -> JsonRpcResult { // This is the actual message that gets signed as part of the authorization let msg = withdrawer.as_secp256k1_msg(); - let authorization = params - .authorization - .try_do_magic(|hex_str| KeyedSignature::from_recoverable_hex(&hex_str, &msg)) - .map_err(internal_error)?; + let authorization = params.authorization.try_do_magic(|hex_str| { + KeyedSignature::from_recoverable_hex( + &hex_str[hex_str.char_indices().nth_back(129).unwrap().0..], + &msg, + ) + }).map_err(internal_error)?; let validator = PublicKeyHash::from_public_key(&authorization.public_key); log::debug!( "[STAKE] A stake authorization was provided, and it was signed by validator {}", diff --git a/src/cli/node/json_rpc_client.rs b/src/cli/node/json_rpc_client.rs index ea4be0786..5e17f6fa0 100644 --- a/src/cli/node/json_rpc_client.rs +++ b/src/cli/node/json_rpc_client.rs @@ -1039,8 +1039,19 @@ pub fn authorize_st(addr: SocketAddr, withdrawer: Option) -> Result<(), let message = authorization.withdrawer.as_secp256k1_msg(); - let auth_bytes = authorization.signature.to_recoverable_bytes(&message)?; - let auth_string = hex::encode(auth_bytes); + let auth_string = { + let validator_bytes: [u8; 20] = authorization + .signature + .public_key + .pkh() + .as_ref() + .try_into()?; + let signature_bytes: [u8; 65] = authorization + .signature + .to_recoverable_bytes(&message) + .unwrap(); + hex::encode([&validator_bytes[..], &signature_bytes[..]].concat()) + }; let auth_qr = qrcode::QrCode::new(&auth_string)?; let auth_ascii = auth_qr From acd518e985d24e45219931edb10dbe18a7aad82a Mon Sep 17 00:00:00 2001 From: parodyBit <58690522+parodyBit@users.noreply.github.com> Date: Mon, 13 Jan 2025 06:53:34 -0700 Subject: [PATCH 2/3] chore(cli): remove validator from stake method --- node/src/actors/json_rpc/api.rs | 15 +++++++++------ src/cli/node/json_rpc_client.rs | 12 +++++++----- src/cli/node/with_node.rs | 7 +------ 3 files changed, 17 insertions(+), 17 deletions(-) diff --git a/node/src/actors/json_rpc/api.rs b/node/src/actors/json_rpc/api.rs index 8a3842347..2e68947e8 100644 --- a/node/src/actors/json_rpc/api.rs +++ b/node/src/actors/json_rpc/api.rs @@ -2045,12 +2045,15 @@ pub async fn stake(params: Result) -> JsonRpcResult { // This is the actual message that gets signed as part of the authorization let msg = withdrawer.as_secp256k1_msg(); - let authorization = params.authorization.try_do_magic(|hex_str| { - KeyedSignature::from_recoverable_hex( - &hex_str[hex_str.char_indices().nth_back(129).unwrap().0..], - &msg, - ) - }).map_err(internal_error)?; + let authorization = params + .authorization + .try_do_magic(|hex_str| { + KeyedSignature::from_recoverable_hex( + &hex_str[hex_str.char_indices().nth_back(129).unwrap().0..], + &msg, + ) + }) + .map_err(internal_error)?; let validator = PublicKeyHash::from_public_key(&authorization.public_key); log::debug!( "[STAKE] A stake authorization was provided, and it was signed by validator {}", diff --git a/src/cli/node/json_rpc_client.rs b/src/cli/node/json_rpc_client.rs index 5e17f6fa0..4e3c9032f 100644 --- a/src/cli/node/json_rpc_client.rs +++ b/src/cli/node/json_rpc_client.rs @@ -873,8 +873,7 @@ pub fn send_dr( pub fn send_st( addr: SocketAddr, value: u64, - authorization: MagicEither, - validator: MagicEither, + authorization: String, withdrawer: MagicEither, fee: Option, sorted_bigger: Option, @@ -894,7 +893,7 @@ pub fn send_st( }; let mut build_stake_params = BuildStakeParams { - authorization, + authorization: MagicEither::Left(authorization.clone()), withdrawer, value, fee, @@ -978,8 +977,11 @@ pub fn send_st( let (dry, _): (BuildStakeResponse, _) = issue_method("stake", Some(params), &mut stream, id.next())?; - let validator_address = validator - .try_do_magic(|hex_str| PublicKeyHash::from_bech32(get_environment(), &hex_str))?; + let validator_address = { + let pkh_bytes = + hex::decode(authorization.clone().chars().take(40).collect::()).unwrap(); + PublicKeyHash::from_bytes(pkh_bytes.as_slice())? + }; if validator_address != dry.validator { bail!( "The specified validator ({}) does not match the validator recovered from the authorization string ({}), please double check all arguments.", diff --git a/src/cli/node/with_node.rs b/src/cli/node/with_node.rs index b69be3f6e..26a4c8ee7 100644 --- a/src/cli/node/with_node.rs +++ b/src/cli/node/with_node.rs @@ -274,7 +274,6 @@ pub fn exec_cmd( node, value, authorization, - validator, withdrawer, fee, require_confirmation, @@ -282,8 +281,7 @@ pub fn exec_cmd( } => rpc::send_st( node.unwrap_or(default_jsonrpc), value, - MagicEither::Left(authorization), - MagicEither::Left(validator), + authorization, MagicEither::Left(withdrawer), fee.map(Fee::absolute_from_nanowits), None, @@ -794,9 +792,6 @@ pub enum Command { /// Stake authorization code (the withdrawer address, signed by the validator node) #[structopt(long = "authorization")] authorization: String, - /// Validator - #[structopt(long = "validator")] - validator: String, /// Withdrawer #[structopt(long = "withdrawer")] withdrawer: String, From 566635f46a0095d6e51a4315e927eab772330585 Mon Sep 17 00:00:00 2001 From: parodyBit <58690522+parodyBit@users.noreply.github.com> Date: Tue, 14 Jan 2025 04:21:58 -0700 Subject: [PATCH 3/3] fix(error-handling): clarify validator mismatch error message --- src/cli/node/json_rpc_client.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/cli/node/json_rpc_client.rs b/src/cli/node/json_rpc_client.rs index 4e3c9032f..85f240531 100644 --- a/src/cli/node/json_rpc_client.rs +++ b/src/cli/node/json_rpc_client.rs @@ -984,7 +984,10 @@ pub fn send_st( }; if validator_address != dry.validator { bail!( - "The specified validator ({}) does not match the validator recovered from the authorization string ({}), please double check all arguments.", + "The validator derived from the authorization string ({}) \ + does not match the validator calculated using the specified withdrawer ({}). \ + Please verify that you are using the same withdrawer address that was used \ + to generate the authorization string.", validator_address, dry.validator.to_string(), );