phantom_zone/
lib.rs

1use num_traits::Zero;
2
3mod backend;
4mod bool;
5mod decomposer;
6mod lwe;
7mod multi_party;
8mod ntt;
9mod pbs;
10mod random;
11mod rgsw;
12#[cfg(any(feature = "interactive_mp", feature = "non_interactive_mp"))]
13mod shortint;
14mod utils;
15
16pub use backend::{
17    ArithmeticLazyOps, ArithmeticOps, ModInit, ModularOpsU64, ShoupMatrixFMA, VectorOps,
18};
19
20pub use bool::*;
21pub use ntt::{Ntt, NttBackendU64, NttInit};
22#[cfg(any(feature = "interactive_mp", feature = "non_interactive_mp"))]
23pub use shortint::{div_zero_error_flag, reset_error_flags, FheUint8};
24
25pub use decomposer::{Decomposer, DecomposerIter, DefaultDecomposer};
26
27pub trait Matrix: AsRef<[Self::R]> {
28    type MatElement;
29    type R: Row<Element = Self::MatElement>;
30
31    fn dimension(&self) -> (usize, usize);
32
33    fn get_row(&self, row_idx: usize) -> impl Iterator<Item = &Self::MatElement> {
34        self.as_ref()[row_idx].as_ref().iter().map(move |r| r)
35    }
36
37    fn get_row_slice(&self, row_idx: usize) -> &[Self::MatElement] {
38        self.as_ref()[row_idx].as_ref()
39    }
40
41    fn iter_rows(&self) -> impl Iterator<Item = &Self::R> {
42        self.as_ref().iter().map(move |r| r)
43    }
44
45    fn get(&self, row_idx: usize, column_idx: usize) -> &Self::MatElement {
46        &self.as_ref()[row_idx].as_ref()[column_idx]
47    }
48
49    fn split_at_row(&self, idx: usize) -> (&[<Self as Matrix>::R], &[<Self as Matrix>::R]) {
50        self.as_ref().split_at(idx)
51    }
52
53    /// Does the matrix fit sub-matrix of dimension row x col
54    fn fits(&self, row: usize, col: usize) -> bool;
55}
56
57pub trait MatrixMut: Matrix + AsMut<[<Self as Matrix>::R]>
58where
59    <Self as Matrix>::R: RowMut,
60{
61    fn get_row_mut(&mut self, row_index: usize) -> &mut [Self::MatElement] {
62        self.as_mut()[row_index].as_mut()
63    }
64
65    fn iter_rows_mut(&mut self) -> impl Iterator<Item = &mut Self::R> {
66        self.as_mut().iter_mut().map(move |r| r)
67    }
68
69    fn set(&mut self, row_idx: usize, column_idx: usize, val: <Self as Matrix>::MatElement) {
70        self.as_mut()[row_idx].as_mut()[column_idx] = val;
71    }
72
73    fn split_at_row_mut(
74        &mut self,
75        idx: usize,
76    ) -> (&mut [<Self as Matrix>::R], &mut [<Self as Matrix>::R]) {
77        self.as_mut().split_at_mut(idx)
78    }
79}
80
81pub trait MatrixEntity: Matrix // where
82// <Self as Matrix>::MatElement: Zero,
83{
84    fn zeros(row: usize, col: usize) -> Self;
85}
86
87pub trait Row: AsRef<[Self::Element]> {
88    type Element;
89}
90
91pub trait RowMut: Row + AsMut<[<Self as Row>::Element]> {}
92
93pub trait RowEntity: Row {
94    fn zeros(col: usize) -> Self;
95}
96
97impl<T> Matrix for Vec<Vec<T>> {
98    type MatElement = T;
99    type R = Vec<T>;
100
101    fn dimension(&self) -> (usize, usize) {
102        (self.len(), self[0].len())
103    }
104
105    fn fits(&self, row: usize, col: usize) -> bool {
106        self.len() >= row && self[0].len() >= col
107    }
108}
109
110impl<T> Matrix for &[Vec<T>] {
111    type MatElement = T;
112    type R = Vec<T>;
113
114    fn dimension(&self) -> (usize, usize) {
115        (self.len(), self[0].len())
116    }
117
118    fn fits(&self, row: usize, col: usize) -> bool {
119        self.len() >= row && self[0].len() >= col
120    }
121}
122
123impl<T> Matrix for &mut [Vec<T>] {
124    type MatElement = T;
125    type R = Vec<T>;
126
127    fn dimension(&self) -> (usize, usize) {
128        (self.len(), self[0].len())
129    }
130
131    fn fits(&self, row: usize, col: usize) -> bool {
132        self.len() >= row && self[0].len() >= col
133    }
134}
135
136impl<T> MatrixMut for Vec<Vec<T>> {}
137impl<T> MatrixMut for &mut [Vec<T>] {}
138
139impl<T: Zero + Clone> MatrixEntity for Vec<Vec<T>> {
140    fn zeros(row: usize, col: usize) -> Self {
141        vec![vec![T::zero(); col]; row]
142    }
143}
144
145impl<T> Row for Vec<T> {
146    type Element = T;
147}
148
149impl<T> Row for [T] {
150    type Element = T;
151}
152
153impl<T> RowMut for Vec<T> {}
154
155impl<T: Zero + Clone> RowEntity for Vec<T> {
156    fn zeros(col: usize) -> Self {
157        vec![T::zero(); col]
158    }
159}
160
161pub trait Encryptor<M: ?Sized, C> {
162    fn encrypt(&self, m: &M) -> C;
163}
164
165pub trait Decryptor<M, C> {
166    fn decrypt(&self, c: &C) -> M;
167}
168
169pub trait MultiPartyDecryptor<M, C> {
170    type DecryptionShare;
171
172    fn gen_decryption_share(&self, c: &C) -> Self::DecryptionShare;
173    fn aggregate_decryption_shares(&self, c: &C, shares: &[Self::DecryptionShare]) -> M;
174}
175
176pub trait KeySwitchWithId<C> {
177    fn key_switch(&self, user_id: usize) -> C;
178}
179
180pub trait SampleExtractor<R> {
181    /// Extract ciphertext at `index`
182    fn extract_at(&self, index: usize) -> R;
183    /// Extract all ciphertexts
184    fn extract_all(&self) -> Vec<R>;
185    /// Extract first `how_many` ciphertexts
186    fn extract_many(&self, how_many: usize) -> Vec<R>;
187}
188
189trait Encoder<F, T> {
190    fn encode(&self, v: F) -> T;
191}
192
193trait SizeInBitsWithLogModulus {
194    /// Returns size of `Self` containing several elements mod Q where
195    /// 2^{log_modulus-1} < Q <= `2^log_modulus`
196    fn size(&self, log_modulus: usize) -> usize;
197}
198
199impl SizeInBitsWithLogModulus for Vec<Vec<u64>> {
200    fn size(&self, log_modulus: usize) -> usize {
201        let mut total = 0;
202        self.iter().for_each(|r| total += log_modulus * r.len());
203        total
204    }
205}
206
207impl SizeInBitsWithLogModulus for Vec<u64> {
208    fn size(&self, log_modulus: usize) -> usize {
209        self.len() * log_modulus
210    }
211}