use super::super::{MpcEngineError, MpcEngineResult, MpcExponentGroup};
use super::core::MpcEngine;
use crate::net::client_store::{
ClientInputHydrationCount, ClientInputStore, ClientOutputShareCount,
};
use crate::net::reservation::ReservationGrant;
use crate::storage::preproc::PreprocStore;
use std::sync::Arc;
use stoffel_vm_types::core_types::{ShareData, ShareType};
use stoffelnet::network_utils::ClientId;
pub trait MpcEngineMultiplication: MpcEngine {
fn multiply_share(
&self,
ty: ShareType,
left: &[u8],
right: &[u8],
) -> MpcEngineResult<ShareData>;
fn divide_fixed_by_constant(
&self,
ty: ShareType,
share_bytes: &[u8],
divisor_scaled: i64,
) -> MpcEngineResult<ShareData> {
let _ = (ty, share_bytes, divisor_scaled);
Err(MpcEngineError::operation_failed(
"divide_fixed_by_constant",
"this MPC backend does not support fixed-point division",
))
}
}
pub trait MpcEngineClientOps: MpcEngine {
fn get_client_ids_sync(&self) -> Vec<ClientId>;
fn has_client_input(&self, client_id: ClientId) -> bool {
self.get_client_ids_sync().contains(&client_id)
}
fn hydrate_client_inputs_sync(
&self,
store: &ClientInputStore,
) -> MpcEngineResult<ClientInputHydrationCount>;
fn hydrate_client_inputs_for_sync(
&self,
store: &ClientInputStore,
client_ids: &[ClientId],
) -> MpcEngineResult<ClientInputHydrationCount>;
}
pub trait MpcEngineOpenInExponent: MpcEngine {
fn open_share_in_exp(
&self,
ty: ShareType,
share_bytes: &[u8],
generator_bytes: &[u8],
) -> MpcEngineResult<Vec<u8>>;
fn native_exponent_group(&self) -> MpcExponentGroup {
MpcExponentGroup::native_for_curve(self.curve_config())
}
fn supports_exponent_group(&self, group: MpcExponentGroup) -> bool {
self.native_exponent_group() == group
}
fn open_share_in_exp_group(
&self,
group: MpcExponentGroup,
ty: ShareType,
share_bytes: &[u8],
generator_bytes: &[u8],
) -> MpcEngineResult<Vec<u8>> {
if !self.supports_exponent_group(group) {
return Err(MpcEngineError::operation_failed(
"open_share_in_exp_group",
group.unsupported_error(self.protocol_name()),
));
}
self.open_share_in_exp(ty, share_bytes, generator_bytes)
}
}
pub trait MpcEngineRandomness: MpcEngine {
fn random_share(&self, ty: ShareType) -> MpcEngineResult<ShareData>;
fn random_integer_share(&self, ty: ShareType) -> MpcEngineResult<ShareData> {
self.random_share(ty)
}
}
pub trait MpcEngineFieldOpen: MpcEngine {
fn open_share_as_field(&self, ty: ShareType, share_bytes: &[u8]) -> MpcEngineResult<Vec<u8>>;
}
pub trait MpcEnginePreprocPersistence: MpcEngine {
fn set_preproc_store(
&self,
store: Arc<dyn PreprocStore>,
program_hash: [u8; 32],
) -> MpcEngineResult<()>;
}
pub trait MpcEngineClientOutput: MpcEngine {
fn send_output_to_client(
&self,
client_id: ClientId,
shares: &[u8],
output_share_count: ClientOutputShareCount,
) -> MpcEngineResult<()>;
}
#[async_trait::async_trait]
pub trait MpcEngineReservation: MpcEngine {
async fn init_reservations(&self, program_hash: [u8; 32], capacity: u64)
-> MpcEngineResult<()>;
async fn reserve_masks(&self, client_id: ClientId, n: u64)
-> MpcEngineResult<ReservationGrant>;
async fn get_mask_share(&self, index: u64) -> MpcEngineResult<Vec<u8>>;
async fn submit_masked_input(
&self,
client_id: ClientId,
index: u64,
value: Vec<u8>,
) -> MpcEngineResult<()>;
async fn consume_masked_inputs(&self, indices: &[u64]) -> MpcEngineResult<Vec<(u64, Vec<u8>)>>;
async fn available_masks(&self) -> u64;
async fn persist_reservations(&self) -> MpcEngineResult<()>;
}