use crate::{Error, Result};
use crate::crypto::asymmetric::{Decryptor, KeyPair, Signer};
use crate::crypto::backend::interface::Asymmetric;
use crate::crypto::mpi;
use crate::crypto::mpi::{ProtectedMPI, MPI};
use crate::crypto::mem::Protected;
use crate::crypto::SessionKey;
use crate::packet::key::{Key4, SecretParts};
use crate::packet::{key, Key};
use crate::types::{Curve, HashAlgorithm, PublicKeyAlgorithm};
use std::convert::{TryFrom, TryInto};
use std::time::SystemTime;
use openssl::bn::{BigNum, BigNumRef, BigNumContext};
use openssl::derive::Deriver;
use openssl::ec::{EcGroup, EcKey, EcPoint, PointConversionForm};
use openssl::ecdsa::EcdsaSig;
use openssl::nid::Nid;
use openssl::pkey::PKey;
use openssl::pkey_ctx::PkeyCtx;
use openssl::rsa::{Padding, Rsa, RsaPrivateKeyBuilder};
use openssl::sign::Signer as OpenSslSigner;
use openssl::sign::Verifier;
impl Asymmetric for super::Backend {
fn x25519_generate_key() -> Result<(Protected, [u8; 32])> {
let pair = openssl::pkey::PKey::generate_x25519()?;
Ok((pair.raw_private_key()?.into(),
pair.raw_public_key()?.as_slice().try_into()?))
}
fn x25519_derive_public(secret: &Protected) -> Result<[u8; 32]> {
let key = PKey::private_key_from_raw_bytes(
secret, openssl::pkey::Id::X25519)?;
Ok(key.raw_public_key()?.as_slice().try_into()?)
}
fn x25519_shared_point(secret: &Protected, public: &[u8; 32])
-> Result<Protected> {
let public = PKey::public_key_from_raw_bytes(
public, openssl::pkey::Id::X25519)?;
let secret = PKey::private_key_from_raw_bytes(
secret, openssl::pkey::Id::X25519)?;
let mut deriver = Deriver::new(&secret)?;
deriver.set_peer(&public)?;
Ok(deriver.derive_to_vec()?.into())
}
fn ed25519_generate_key() -> Result<(Protected, [u8; 32])> {
let pair = openssl::pkey::PKey::generate_ed25519()?;
Ok((pair.raw_private_key()?.into(),
pair.raw_public_key()?.as_slice().try_into()?))
}
fn ed25519_derive_public(secret: &Protected) -> Result<[u8; 32]> {
let key = PKey::private_key_from_raw_bytes(
secret, openssl::pkey::Id::ED25519)?;
Ok(key.raw_public_key()?.as_slice().try_into()?)
}
fn ed25519_sign(secret: &Protected, _public: &[u8; 32], digest: &[u8])
-> Result<[u8; 64]> {
let key = PKey::private_key_from_raw_bytes(
secret, openssl::pkey::Id::ED25519)?;
let mut signer = OpenSslSigner::new_without_digest(&key)?;
Ok(signer.sign_oneshot_to_vec(digest)?.as_slice().try_into()?)
}
fn ed25519_verify(public: &[u8; 32], digest: &[u8], signature: &[u8; 64])
-> Result<bool> {
let key = PKey::public_key_from_raw_bytes(
public, openssl::pkey::Id::ED25519)?;
let mut verifier = Verifier::new_without_digest(&key)?;
Ok(verifier.verify_oneshot(signature, digest)?)
}
}
impl TryFrom<&ProtectedMPI> for BigNum {
type Error = anyhow::Error;
fn try_from