diff --git a/applications/tari_console_wallet/src/automation/commands.rs b/applications/tari_console_wallet/src/automation/commands.rs index a8e3f28f2c..b6e0da7bbb 100644 --- a/applications/tari_console_wallet/src/automation/commands.rs +++ b/applications/tari_console_wallet/src/automation/commands.rs @@ -34,6 +34,7 @@ use chrono::{DateTime, Utc}; use digest::Digest; use futures::FutureExt; use log::*; +use rand::rngs::OsRng; use serde::{de::DeserializeOwned, Serialize}; use sha2::Sha256; use strum_macros::{Display, EnumIter, EnumString}; @@ -41,7 +42,7 @@ use tari_app_grpc::authentication::salted_password::create_salted_hashed_passwor use tari_common_types::{ emoji::EmojiId, transaction::TxId, - types::{CommitmentFactory, FixedHash, PublicKey}, + types::{CommitmentFactory, FixedHash, PrivateKey, PublicKey, Signature}, }; use tari_comms::{ connectivity::{ConnectivityEvent, ConnectivityRequester}, @@ -53,6 +54,7 @@ use tari_core::transactions::{ tari_amount::{uT, MicroTari, Tari}, transaction_components::{OutputFeatures, TransactionOutput, UnblindedOutput}, }; +use tari_crypto::keys::{PublicKey as TraitPublicKey, SecretKey}; use tari_utilities::{hex::Hex, ByteArray}; use tari_wallet::{ connectivity_service::WalletConnectivityInterface, @@ -87,6 +89,7 @@ pub enum WalletCommand { SendOneSided, CreateKeyPair, CreateAggregateSignatureUtxo, + SignMessage, MakeItRain, CoinSplit, DiscoverPeer, @@ -272,6 +275,17 @@ pub async fn coin_split( Ok(tx_id) } +pub fn sign_message(private_key: String, challenge: String) -> Result { + let private_key = + PrivateKey::from_hex(private_key.as_str()).map_err(|e| CommandError::InvalidArgument(e.to_string()))?; + let challenge = challenge.as_bytes(); + + let nonce = PrivateKey::random(&mut OsRng); + let signature = Signature::sign(private_key, nonce.clone(), challenge).map_err(CommandError::FailedSignature)?; + + Ok(signature) +} + async fn wait_for_comms(connectivity_requester: &ConnectivityRequester) -> Result<(), CommandError> { let mut connectivity = connectivity_requester.get_event_subscription(); print!("Waiting for connectivity... "); @@ -697,6 +711,18 @@ pub async fn command_runner( }, Err(e) => eprintln!("CreateAggregateSignatureUtxo error! {}", e), }, + SignMessage(args) => match sign_message(args.private_key, args.challenge) { + Ok(sgn) => { + println!( + "Sign message: + 1. signature: {}, + 2. public key: {}", + sgn.get_signature().to_hex(), + sgn.get_public_nonce().to_hex(), + ) + }, + Err(e) => eprintln!("SignMessage error! {}", e), + }, SendTari(args) => { match send_tari( transaction_service.clone(), diff --git a/applications/tari_console_wallet/src/automation/error.rs b/applications/tari_console_wallet/src/automation/error.rs index 06ab26f57b..79f15842af 100644 --- a/applications/tari_console_wallet/src/automation/error.rs +++ b/applications/tari_console_wallet/src/automation/error.rs @@ -29,6 +29,7 @@ use log::*; use tari_common::exit_codes::{ExitCode, ExitError}; use tari_common_types::types::FixedHashSizeError; use tari_core::transactions::{tari_amount::MicroTariError, transaction_components::TransactionError}; +use tari_crypto::signatures::SchnorrSignatureError; use tari_utilities::hex::HexError; use tari_wallet::{ error::{WalletError, WalletStorageError}, @@ -82,6 +83,8 @@ pub enum CommandError { General(String), #[error("FixedHash size error `{0}`")] FixedHashSizeError(#[from] FixedHashSizeError), + #[error("Invalid signature: `{0}`")] + FailedSignature(#[from] SchnorrSignatureError), } impl From for ExitError { diff --git a/applications/tari_console_wallet/src/cli.rs b/applications/tari_console_wallet/src/cli.rs index c7f5a2e7d0..3f03f52cd8 100644 --- a/applications/tari_console_wallet/src/cli.rs +++ b/applications/tari_console_wallet/src/cli.rs @@ -118,6 +118,7 @@ pub enum CliCommands { BurnTari(BurnTariArgs), CreateKeyPair(CreateKeyPairArgs), CreateAggregateSignatureUtxo(CreateAggregateSignatureUtxoArgs), + SignMessage(SignMessageArgs), SendOneSided(SendTariArgs), SendOneSidedToStealthAddress(SendTariArgs), MakeItRain(MakeItRainArgs), @@ -173,6 +174,12 @@ pub struct CreateAggregateSignatureUtxoArgs { pub public_keys: Vec, } +#[derive(Debug, Args, Clone)] +pub struct SignMessageArgs { + pub private_key: String, + pub challenge: String, +} + #[derive(Debug, Args, Clone)] pub struct MakeItRainArgs { pub destination: UniPublicKey, diff --git a/applications/tari_console_wallet/src/wallet_modes.rs b/applications/tari_console_wallet/src/wallet_modes.rs index 1315d33a9d..313ecfe513 100644 --- a/applications/tari_console_wallet/src/wallet_modes.rs +++ b/applications/tari_console_wallet/src/wallet_modes.rs @@ -433,6 +433,8 @@ mod test { --public-keys=5c4f2a4b3f3f84e047333218a84fd24f581a9d7e4f23b78e3714e9d174427d61 \ --public-keys=f6b2ca781342a3ebe30ee1643655c96f1d7c14f4d49f077695395de98ae73665 + sign-message 5c4f2a4b3f3f84e047333218a84fd24f581a9d7e4f23b78e3714e9d174427d61 my_challenge! + coin-split --message Make_many_dust_UTXOs! --fee-per-gram 2 0.001T 499 make-it-rain --duration 100 --transactions-per-second 10 --start-amount 0.009200T --increase-amount 0T \ @@ -450,6 +452,7 @@ mod test { let mut burn_tari = false; let mut create_key_pair = false; let mut create_aggregate_signature_utxo = false; + let mut sign_message = false; let mut make_it_rain = false; let mut coin_split = false; let mut discover_peer = false; @@ -461,6 +464,7 @@ mod test { CliCommands::BurnTari(_) => burn_tari = true, CliCommands::CreateKeyPair(_) => create_key_pair = true, CliCommands::CreateAggregateSignatureUtxo(_) => create_aggregate_signature_utxo = true, + CliCommands::SignMessage(_) => sign_message = true, CliCommands::SendOneSided(_) => {}, CliCommands::SendOneSidedToStealthAddress(_) => {}, CliCommands::MakeItRain(_) => make_it_rain = true, @@ -486,6 +490,7 @@ mod test { burn_tari && create_key_pair && create_aggregate_signature_utxo && + sign_message && make_it_rain && coin_split && discover_peer && diff --git a/infrastructure/tari_script/src/op_codes.rs b/infrastructure/tari_script/src/op_codes.rs index 745f3a0eeb..16faa5b913 100644 --- a/infrastructure/tari_script/src/op_codes.rs +++ b/infrastructure/tari_script/src/op_codes.rs @@ -556,10 +556,10 @@ impl fmt::Display for Opcode { (*msg).to_hex() )) }, - Return => fmt.write_str("Return"), - IfThen => fmt.write_str("IfThen"), - Else => fmt.write_str("Else"), - EndIf => fmt.write_str("EndIf"), + Return => write!(fmt, "Return"), + IfThen => write!(fmt, "IfThen"), + Else => write!(fmt, "Else"), + EndIf => write!(fmt, "EndIf"), } } }