PaperTrader/src/libtrader/client/network/cmd/get_server_salt.rs

59 lines
1.8 KiB
Rust

use std::io;
use argon2::password_hash::SaltString;
use crate::common::message::*;
use tokio::net::TcpStream;
use tokio_rustls::client::TlsStream;
/// Issues a command to the connected TLS server to obtain a salt.
///
/// All salts returned are of size ```digest::SHA512_OUTPUT_LEN/2```, 32 bytes.
/// Should be used in contexts that return ```io::Result```.
/// Should be used in Async contexts.
///
/// Arguments:
/// socket - The TLS stream to use for the salt.
///
/// Returns: a ```io::Result<[u8; 32]>```.
///
/// Example:
/// ```rust
/// let server_salt: [u8; digest::SHA512_OUTPUT_LEN/2] = get_server_salt(tls_client)?;
/// ```
pub async fn get_server_salt(socket: &mut TlsStream<TcpStream>) -> std::io::Result<SaltString> {
/*
* request to generate a salt from the server.
* */
Message::new()
.command(Command::GenHashSalt)
.send(socket)
.await?;
let ret_msg = Message::receive(socket).await?;
/* assert received message */
if !ret_msg.assert_command(Command::Success) || !ret_msg.assert_data() {
Err(io::Error::new(
io::ErrorKind::InvalidData,
"Failed getting generated server Salt, received an invalid message.",
))
} else {
let salt_raw: String = ret_msg.get_data().map_err(|_| {
io::Error::new(
io::ErrorKind::InvalidData,
"Failed getting generated server Salt, received an invalid message.",
)
})?;
/* verify that the salt is actually valid */
SaltString::new(salt_raw.as_str()).map_err(|_| {
io::Error::new(
io::ErrorKind::InvalidData,
"Failed getting generated server Salt, received an invalid message.",
)
})
}
}