p_ot.rs 5.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184
  1. use crate::field::FromPrf;
  2. use crate::permutation::Permutation;
  3. use core::marker::PhantomData;
  4. use ff::Field;
  5. pub struct POTKeyParty<F: FromPrf, Perm> {
  6. /// log of the database size
  7. log_domain_size: u32,
  8. /// if init was run
  9. is_initialized: bool,
  10. /// PRF key of the Index Party
  11. prf_key_i: Option<<F as FromPrf>::PrfKey>,
  12. /// PRF key of the Receiver Party
  13. prf_key_r: Option<<F as FromPrf>::PrfKey>,
  14. /// Permutation
  15. permutation: Option<Perm>,
  16. _phantom: PhantomData<F>,
  17. }
  18. impl<F: Field + FromPrf, Perm: Permutation> POTKeyParty<F, Perm> {
  19. pub fn new(log_domain_size: u32) -> Self {
  20. Self {
  21. log_domain_size,
  22. is_initialized: false,
  23. prf_key_i: None,
  24. prf_key_r: None,
  25. permutation: None,
  26. _phantom: PhantomData,
  27. }
  28. }
  29. pub fn is_initialized(&self) -> bool {
  30. self.is_initialized
  31. }
  32. pub fn init(&mut self) -> ((F::PrfKey, Perm::Key), F::PrfKey) {
  33. assert!(!self.is_initialized);
  34. self.prf_key_i = Some(F::prf_key_gen());
  35. self.prf_key_r = Some(F::prf_key_gen());
  36. let permutation_key = Perm::sample(self.log_domain_size);
  37. self.permutation = Some(Perm::from_key(permutation_key));
  38. self.is_initialized = true;
  39. (
  40. (self.prf_key_i.unwrap(), permutation_key),
  41. self.prf_key_r.unwrap(),
  42. )
  43. }
  44. pub fn expand(&self) -> Vec<F> {
  45. assert!(self.is_initialized);
  46. let n = 1 << self.log_domain_size;
  47. (0..n)
  48. .map(|x| {
  49. let pi_x = self.permutation.as_ref().unwrap().permute(x) as u64;
  50. F::prf(&self.prf_key_i.unwrap(), pi_x) + F::prf(&self.prf_key_r.unwrap(), pi_x)
  51. })
  52. .collect()
  53. }
  54. }
  55. pub struct POTIndexParty<F: FromPrf, Perm> {
  56. /// log of the database size
  57. log_domain_size: u32,
  58. /// if init was run
  59. is_initialized: bool,
  60. /// PRF key of the Index Party
  61. prf_key_i: Option<<F as FromPrf>::PrfKey>,
  62. /// Permutation
  63. permutation: Option<Perm>,
  64. _phantom: PhantomData<F>,
  65. }
  66. impl<F: Field + FromPrf, Perm: Permutation> POTIndexParty<F, Perm> {
  67. pub fn new(log_domain_size: u32) -> Self {
  68. Self {
  69. log_domain_size,
  70. is_initialized: false,
  71. prf_key_i: None,
  72. permutation: None,
  73. _phantom: PhantomData,
  74. }
  75. }
  76. pub fn is_initialized(&self) -> bool {
  77. self.is_initialized
  78. }
  79. pub fn init(&mut self, prf_key_i: F::PrfKey, permutation_key: Perm::Key) {
  80. assert!(!self.is_initialized);
  81. self.prf_key_i = Some(prf_key_i);
  82. self.permutation = Some(Perm::from_key(permutation_key));
  83. self.is_initialized = true;
  84. }
  85. pub fn access(&self, index: u64) -> (u64, F) {
  86. assert!(index < (1 << self.log_domain_size));
  87. let pi_x = self.permutation.as_ref().unwrap().permute(index as usize) as u64;
  88. (pi_x, F::prf(&self.prf_key_i.unwrap(), pi_x))
  89. }
  90. }
  91. pub struct POTReceiverParty<F: FromPrf> {
  92. /// log of the database size
  93. log_domain_size: u32,
  94. /// if init was run
  95. is_initialized: bool,
  96. /// PRF key of the Receiver Party
  97. prf_key_r: Option<<F as FromPrf>::PrfKey>,
  98. _phantom: PhantomData<F>,
  99. }
  100. impl<F: Field + FromPrf> POTReceiverParty<F> {
  101. pub fn new(log_domain_size: u32) -> Self {
  102. Self {
  103. log_domain_size,
  104. is_initialized: false,
  105. prf_key_r: None,
  106. _phantom: PhantomData,
  107. }
  108. }
  109. pub fn is_initialized(&self) -> bool {
  110. self.is_initialized
  111. }
  112. pub fn init(&mut self, prf_key_r: F::PrfKey) {
  113. assert!(!self.is_initialized);
  114. self.prf_key_r = Some(prf_key_r);
  115. self.is_initialized = true;
  116. }
  117. pub fn access(&self, permuted_index: u64, output_share: F) -> F {
  118. assert!(permuted_index < (1 << self.log_domain_size));
  119. F::prf(&self.prf_key_r.unwrap(), permuted_index) + output_share
  120. }
  121. }
  122. #[cfg(test)]
  123. mod tests {
  124. use super::*;
  125. use crate::field::Fp;
  126. use crate::permutation::FisherYatesPermutation;
  127. fn test_pot<F, Perm>(log_domain_size: u32)
  128. where
  129. F: Field + FromPrf,
  130. Perm: Permutation,
  131. {
  132. let n = 1 << log_domain_size;
  133. // creation
  134. let mut key_party = POTKeyParty::<F, Perm>::new(log_domain_size);
  135. let mut index_party = POTIndexParty::<F, Perm>::new(log_domain_size);
  136. let mut receiver_party = POTReceiverParty::<F>::new(log_domain_size);
  137. assert!(!key_party.is_initialized());
  138. assert!(!index_party.is_initialized());
  139. assert!(!receiver_party.is_initialized());
  140. // init
  141. let (msg_to_index_party, msg_to_receiver_party) = key_party.init();
  142. index_party.init(msg_to_index_party.0, msg_to_index_party.1);
  143. receiver_party.init(msg_to_receiver_party);
  144. assert!(key_party.is_initialized());
  145. assert!(index_party.is_initialized());
  146. assert!(receiver_party.is_initialized());
  147. // expand to the key party's output
  148. let output_k = key_party.expand();
  149. assert_eq!(output_k.len(), n);
  150. // access each index and verify consistency with key party's output
  151. for i in 0..(n as u64) {
  152. let msg_to_receiver_party = index_party.access(i);
  153. let output = receiver_party.access(msg_to_receiver_party.0, msg_to_receiver_party.1);
  154. assert_eq!(output, output_k[i as usize]);
  155. }
  156. }
  157. #[test]
  158. fn test_all_pot() {
  159. let log_domain_size = 10;
  160. test_pot::<Fp, FisherYatesPermutation>(log_domain_size);
  161. }
  162. }