use super::*;
#[cfg(feature = "private_key")]
impl<N: Network> TryFrom<PrivateKey<N>> for ComputeKey<N> {
type Error = Error;
fn try_from(private_key: PrivateKey<N>) -> Result<Self, Self::Error> {
Self::try_from(&private_key)
}
}
#[cfg(feature = "private_key")]
impl<N: Network> TryFrom<&PrivateKey<N>> for ComputeKey<N> {
type Error = Error;
fn try_from(private_key: &PrivateKey<N>) -> Result<Self, Self::Error> {
let pk_sig = N::g_scalar_multiply(&private_key.sk_sig());
let pr_sig = N::g_scalar_multiply(&private_key.r_sig());
Self::try_from((pk_sig, pr_sig))
}
}
impl<N: Network> TryFrom<(Group<N>, Group<N>)> for ComputeKey<N> {
type Error = Error;
fn try_from((pk_sig, pr_sig): (Group<N>, Group<N>)) -> Result<Self> {
let sk_prf = N::hash_to_scalar_psd4(&[pk_sig.to_x_coordinate(), pr_sig.to_x_coordinate()])?;
Ok(Self { pk_sig, pr_sig, sk_prf })
}
}
impl<N: Network> TryFrom<&(Group<N>, Group<N>)> for ComputeKey<N> {
type Error = Error;
fn try_from((pk_sig, pr_sig): &(Group<N>, Group<N>)) -> Result<Self> {
Self::try_from((*pk_sig, *pr_sig))
}
}
#[cfg(test)]
mod tests {
use super::*;
use snarkvm_console_network::MainnetV0;
type CurrentNetwork = MainnetV0;
const ITERATIONS: u64 = 1000;
#[test]
fn test_try_from() -> Result<()> {
let mut rng = TestRng::default();
for _ in 0..ITERATIONS {
let private_key = PrivateKey::<CurrentNetwork>::new(&mut rng)?;
let candidate = ComputeKey::try_from(private_key)?;
let candidate_sk_prf = CurrentNetwork::hash_to_scalar_psd4(&[
candidate.pk_sig().to_x_coordinate(),
candidate.pr_sig().to_x_coordinate(),
])?;
assert_eq!(candidate.sk_prf(), candidate_sk_prf);
assert_eq!(candidate, ComputeKey::try_from((candidate.pk_sig(), candidate.pr_sig()))?);
}
Ok(())
}
}