sl_oblivious/
lib.rs

1// Copyright (c) Silence Laboratories Pte. Ltd. All Rights Reserved.
2// This software is licensed under the Silence Laboratories License Agreement.
3
4/// Domain labels
5pub mod constants;
6
7/// Soft spoken Oblivious Transfer
8pub mod soft_spoken;
9
10/// zkproofs
11pub mod zkproofs;
12
13/// Endemic 1 out of 2 Oblivious Transfer
14pub mod endemic_ot;
15
16/// Random Vector OLE
17pub mod rvole;
18
19/// Utility functions
20pub mod utils {
21    use std::ops::Index;
22
23    use elliptic_curve::{
24        ff::PrimeField,
25        ops::Reduce,
26        sec1::{ModulusSize, ToEncodedPoint},
27        CurveArithmetic, FieldBytes,
28    };
29    use merlin::Transcript;
30
31    /// Custom extension trait for the merlin transcript.
32    pub trait TranscriptProtocol<C: CurveArithmetic> {
33        /// Append a point to the transcript.
34        fn append_point(
35            &mut self,
36            label: &'static [u8],
37            point: &C::ProjectivePoint,
38        );
39
40        /// Append a scalar to the transcript.
41        fn append_scalar(&mut self, label: &'static [u8], scalar: &C::Scalar);
42
43        /// Get challenge as scalar from the transcript.
44        fn challenge_scalar(&mut self, label: &'static [u8]) -> C::Scalar;
45
46        /// New transcript for DLOG proof
47        fn new_dlog_proof(
48            session_id: &[u8],
49            party_id: usize,
50            action: &[u8],
51            label: &'static [u8],
52        ) -> Transcript;
53    }
54
55    impl<C> TranscriptProtocol<C> for Transcript
56    where
57        C: CurveArithmetic,
58        C::FieldBytesSize: ModulusSize,
59        C::ProjectivePoint: ToEncodedPoint<C>,
60    {
61        fn append_point(
62            &mut self,
63            label: &'static [u8],
64            point: &C::ProjectivePoint,
65        ) {
66            self.append_message(label, point.to_encoded_point(true).as_ref())
67        }
68
69        fn append_scalar(
70            &mut self,
71            label: &'static [u8],
72            scalar: &C::Scalar,
73        ) {
74            let bytes = scalar.to_repr();
75            self.append_message(label, bytes.as_ref())
76        }
77
78        fn new_dlog_proof(
79            session_id: &[u8],
80            party_id: usize,
81            action: &[u8],
82            label: &'static [u8],
83        ) -> Self {
84            let mut transcript = Transcript::new(label);
85            transcript.append_message(b"session_id", session_id.as_ref());
86            transcript.append_u64(b"party_id", party_id as u64);
87            transcript.append_message(b"action", action);
88
89            transcript
90        }
91
92        fn challenge_scalar(&mut self, label: &'static [u8]) -> C::Scalar {
93            let mut buf = FieldBytes::<C>::default();
94            self.challenge_bytes(label, &mut buf);
95            C::Scalar::reduce_bytes(&buf)
96        }
97    }
98
99    /// Simple trait to extract a bit from a byte array.
100    pub trait ExtractBit: Index<usize, Output = u8> {
101        /// Extract a bit at given index (in little endian order) from a byte array.
102        fn extract_bit(&self, idx: usize) -> bool {
103            let byte_idx = idx >> 3;
104            let bit_idx = idx & 0x7;
105            let byte = self[byte_idx];
106            let mask = 1 << bit_idx;
107            (byte & mask) != 0
108        }
109    }
110
111    impl ExtractBit for Vec<u8> {}
112    impl<const T: usize> ExtractBit for [u8; T] {}
113
114    pub fn bit_to_bit_mask(bit: u8) -> u8 {
115        // constant time
116        // outputs 0x00 if `bit == 0` and 0xFF if `bit == 1`
117        -(bit as i8) as u8
118    }
119}
120
121pub mod params;
122
123pub mod label;
124
125/// Random Vector OLE (base OT variant)
126pub mod rvole_ot_variant;