1use curve25519_dalek_signal::ristretto::RistrettoPoint;
7use curve25519_dalek_signal::scalar::Scalar;
8use poksho::shoapi::ShoApiExt as _;
9use poksho::ShoApi;
10
11pub struct Sho {
12 internal_sho: poksho::ShoHmacSha256,
13}
14
15impl Sho {
16 pub fn new(label: &[u8], data: &[u8]) -> Self {
17 let mut sho = poksho::ShoHmacSha256::new(label);
18 sho.absorb_and_ratchet(data);
19 Sho { internal_sho: sho }
20 }
21
22 pub fn absorb_and_ratchet(&mut self, data: &[u8]) {
23 self.internal_sho.absorb_and_ratchet(data)
24 }
25
26 pub fn squeeze(&mut self, outlen: usize) -> Vec<u8> {
27 self.internal_sho.squeeze_and_ratchet(outlen)
28 }
29
30 pub fn squeeze_as_array<const N: usize>(&mut self) -> [u8; N] {
31 self.internal_sho.squeeze_and_ratchet_as_array()
32 }
33
34 pub fn get_point(&mut self) -> RistrettoPoint {
35 RistrettoPoint::from_uniform_bytes(&self.internal_sho.squeeze_and_ratchet_as_array())
36 }
37
38 pub fn get_point_single_elligator(&mut self) -> RistrettoPoint {
39 RistrettoPoint::from_uniform_bytes_single_elligator(
40 &self.internal_sho.squeeze_and_ratchet_as_array(),
41 )
42 }
43
44 pub fn get_scalar(&mut self) -> Scalar {
45 Scalar::from_bytes_mod_order_wide(&self.internal_sho.squeeze_and_ratchet_as_array())
46 }
47}
48
49impl AsMut<poksho::ShoHmacSha256> for Sho {
50 fn as_mut(&mut self) -> &mut poksho::ShoHmacSha256 {
51 &mut self.internal_sho
52 }
53}