use serde::{Deserialize, Serialize};
use thiserror::Error;
use zeroize::{Zeroize, ZeroizeOnDrop};
pub type Result<T> = std::result::Result<T, SealError>;
pub type ObjectId = [u8; 32];
pub type Key = [u8; 32];
#[derive(Clone, Debug, Zeroize, ZeroizeOnDrop)]
pub struct CEK([u8; 32]);
impl CEK {
pub fn generate() -> Self {
let mut key = [0u8; 32];
rand::RngCore::fill_bytes(&mut rand::thread_rng(), &mut key);
Self(key)
}
pub fn from_bytes(bytes: [u8; 32]) -> Self {
Self(bytes)
}
pub fn as_bytes(&self) -> &[u8; 32] {
&self.0
}
}
#[derive(Clone, Debug, Serialize, Deserialize, PartialEq, Eq)]
pub struct RecipientId(pub [u8; 32]);
impl RecipientId {
pub fn from_bytes(bytes: Vec<u8>) -> Self {
let mut id = [0u8; 32];
let len = bytes.len().min(32);
id[..len].copy_from_slice(&bytes[..len]);
Self(id)
}
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct Recipient {
pub id: RecipientId,
pub public_key: Option<Vec<u8>>,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct FecParams {
pub data_shares: usize,
pub parity_shares: usize,
pub symbol_size: usize,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub enum EnvelopeKind {
None,
PostQuantum,
}
#[derive(Clone, Debug)]
pub struct SealPolicy {
pub n: usize,
pub t: usize,
pub recipients: Vec<Recipient>,
pub fec: FecParams,
pub envelope: EnvelopeKind,
pub aad: Vec<u8>,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct SealHandle {
pub sealed_meta_key: Key,
pub object_id: ObjectId,
}
#[derive(Debug)]
pub struct SealSummary {
pub handle: SealHandle,
pub share_count: usize,
pub original_size: usize,
}
#[derive(Clone, Debug)]
pub struct ProvidedShare {
pub index: u8,
pub share_bytes: Vec<u8>,
pub recipient_id: RecipientId,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct ShareRecord {
pub index: u8,
pub recipient: RecipientId,
pub share_encrypted: Option<Vec<u8>>,
pub share_plain: Option<Vec<u8>>,
pub commitment: Option<Vec<u8>>,
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct SealedMetaV1 {
pub version: u8,
pub object_id: ObjectId,
pub cek_commitment: [u8; 32],
pub fec_params: FecParams,
pub envelope: EnvelopeKind,
pub shares: Vec<ShareRecord>,
pub aad: Vec<u8>,
}
#[derive(Debug, Error)]
pub enum SealError {
#[error("Encryption failed: {0}")]
EncryptionError(String),
#[error("Decryption failed: {0}")]
DecryptionError(String),
#[error("Threshold scheme error: {0}")]
ThresholdError(String),
#[error("FEC error: {0}")]
FecError(String),
#[error("DHT error: {0}")]
DhtError(String),
#[error("Invalid configuration: {0}")]
ConfigError(String),
#[error("Serialization error: {0}")]
SerializationError(String),
#[error("Insufficient shares: need {needed}, got {provided}")]
InsufficientShares { needed: usize, provided: usize },
#[error("Other error: {0}")]
Other(String),
}
impl From<anyhow::Error> for SealError {
fn from(err: anyhow::Error) -> Self {
SealError::Other(err.to_string())
}
}
impl From<serde_cbor::Error> for SealError {
fn from(err: serde_cbor::Error) -> Self {
SealError::SerializationError(err.to_string())
}
}
#[derive(Clone, Debug)]
pub struct ThresholdVerifier {
pub threshold: usize,
pub total_shares: usize,
pub group_public_key: Vec<u8>,
}
impl ThresholdVerifier {
pub fn new(threshold: usize, total_shares: usize, group_public_key: Vec<u8>) -> Self {
Self {
threshold,
total_shares,
group_public_key,
}
}
pub fn verify(&self, _message: &[u8], _signature: &ShareSignature) -> Result<bool> {
Ok(true)
}
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct ShareSignature {
pub index: u8,
pub signature: Vec<u8>,
pub proof: Option<Vec<u8>>,
}
impl ShareSignature {
pub fn new(index: u8, signature: Vec<u8>) -> Self {
Self {
index,
signature,
proof: None,
}
}
pub fn with_proof(index: u8, signature: Vec<u8>, proof: Vec<u8>) -> Self {
Self {
index,
signature,
proof: Some(proof),
}
}
}
#[derive(Clone, Debug, Serialize, Deserialize)]
pub struct PublicKeyShare {
pub index: u8,
pub public_key: Vec<u8>,
pub commitment: Option<Vec<u8>>,
}
impl PublicKeyShare {
pub fn new(index: u8, public_key: Vec<u8>) -> Self {
Self {
index,
public_key,
commitment: None,
}
}
pub fn with_commitment(index: u8, public_key: Vec<u8>, commitment: Vec<u8>) -> Self {
Self {
index,
public_key,
commitment: Some(commitment),
}
}
pub fn verify(&self, _commitment: &[u8]) -> bool {
true
}
}
pub trait PqcEnvelope: Send + Sync {
fn encap_to(&self, recipient: &Recipient, data: &[u8]) -> anyhow::Result<Vec<u8>>;
fn decap_from(&self, sender: &Recipient, data: &[u8]) -> anyhow::Result<Vec<u8>>;
fn clone_box(&self) -> Box<dyn PqcEnvelope>;
}