use std::sync::Arc;
use crate::{
AeadAlgorithm, BlockCipherAlgorithm, CbcAlgorithm, CryptoAlgorithm, CryptoError, HashAlgorithm,
HmacAlgorithm, KeyExchangeAlgorithm, PublicKey, SecretVec, SignatureScheme,
StreamCipherAlgorithm,
};
pub trait RTCCryptoProvider: Send + Sync {
fn name(&self) -> &'static str;
fn crypto(&self) -> &dyn RTCCrypto;
fn random(&self) -> &dyn RTCRandom;
}
pub trait RTCRandom: Send + Sync {
fn fill(&self, output: &mut [u8]) -> Result<(), CryptoError>;
}
pub trait RTCCrypto: Send + Sync {
fn supports(&self, algorithm: CryptoAlgorithm) -> bool;
fn hash(&self, algorithm: HashAlgorithm, _data: &[u8]) -> Result<Vec<u8>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(CryptoAlgorithm::Hash(
algorithm,
)))
}
fn block_encrypt(
&self,
algorithm: BlockCipherAlgorithm,
_key: &[u8],
_block: &mut [u8],
) -> Result<(), CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::BlockCipher(algorithm),
))
}
fn new_hmac(&self, algorithm: HmacAlgorithm, _key: &[u8]) -> Result<Box<dyn Mac>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(CryptoAlgorithm::Hmac(
algorithm,
)))
}
fn new_stream_cipher(
&self,
algorithm: StreamCipherAlgorithm,
_key: &[u8],
) -> Result<Box<dyn StreamCipher>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::StreamCipher(algorithm),
))
}
fn new_aead(
&self,
algorithm: AeadAlgorithm,
_key: &[u8],
) -> Result<Box<dyn AeadCipher>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(CryptoAlgorithm::Aead(
algorithm,
)))
}
fn new_cbc(
&self,
algorithm: CbcAlgorithm,
_key: &[u8],
) -> Result<Box<dyn CbcCipher>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(CryptoAlgorithm::Cbc(
algorithm,
)))
}
fn start_key_exchange(
&self,
algorithm: KeyExchangeAlgorithm,
) -> Result<Box<dyn ActiveKeyExchange>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::KeyExchange(algorithm),
))
}
fn generate_signing_key(
&self,
scheme: SignatureScheme,
) -> Result<Arc<dyn SigningKey>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::SigningKeyGeneration(scheme),
))
}
fn import_signing_key(
&self,
scheme: SignatureScheme,
_pkcs8_der: &[u8],
) -> Result<Arc<dyn SigningKey>, CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::SigningKeyImport(scheme),
))
}
fn verify_signature(
&self,
scheme: SignatureScheme,
_public_key: PublicKey<'_>,
_message: &[u8],
_signature: &[u8],
) -> Result<(), CryptoError> {
Err(CryptoError::UnsupportedAlgorithm(
CryptoAlgorithm::Signature(scheme),
))
}
}
pub trait Mac: Send {
fn output_len(&self) -> usize;
fn sign(&mut self, input: &[&[u8]], output: &mut [u8]) -> Result<(), CryptoError>;
fn verify(&mut self, input: &[&[u8]], expected: &[u8]) -> Result<(), CryptoError>;
}
pub trait StreamCipher: Send {
fn apply_keystream(&mut self, iv: &[u8], data: &mut [u8]) -> Result<(), CryptoError>;
}
pub trait AeadCipher: Send {
fn tag_len(&self) -> usize;
fn seal_in_place(
&mut self,
nonce: &[u8],
aad: &[u8],
plaintext_and_ciphertext: &mut [u8],
tag_out: &mut [u8],
) -> Result<(), CryptoError>;
fn open_in_place(
&mut self,
nonce: &[u8],
aad: &[u8],
ciphertext_and_plaintext: &mut [u8],
tag: &[u8],
) -> Result<(), CryptoError>;
}
pub trait CbcCipher: Send {
fn block_len(&self) -> usize;
fn encrypt_blocks(&mut self, iv: &[u8], blocks: &mut [u8]) -> Result<(), CryptoError>;
fn decrypt_blocks(&mut self, iv: &[u8], blocks: &mut [u8]) -> Result<(), CryptoError>;
}
pub trait ActiveKeyExchange: Send {
fn algorithm(&self) -> KeyExchangeAlgorithm;
fn public_key(&self) -> &[u8];
fn complete(self: Box<Self>, peer_public_key: &[u8]) -> Result<SecretVec, CryptoError>;
}
pub trait SigningKey: Send + Sync {
fn supports(&self, scheme: SignatureScheme) -> bool;
fn public_key(&self) -> PublicKey<'_>;
fn sign(&self, scheme: SignatureScheme, message: &[u8]) -> Result<Vec<u8>, CryptoError>;
fn to_pkcs8_der(&self) -> Result<Option<SecretVec>, CryptoError> {
Ok(None)
}
}