Skip to main content

hpke_dispatch/
config.rs

1use hpke::HpkeError;
2
3use crate::{
4    base_mode_open, base_mode_seal, Aead, EncappedKeyAndCiphertext, IdLookupError, Kdf, Kem,
5};
6
7/// Configuration for crate interfaces.
8///
9/// Contains an ([`Aead`], [`Kdf`], [`Kem`]) algorithmic triple. This can be used with
10/// [`Config::base_mode_seal`], [`Config::base_mode_open`], [`base_mode_seal`], or
11/// [`base_mode_open`].
12#[derive(Copy, Clone, Debug, PartialEq, Eq)]
13#[cfg_attr(
14    feature = "serde",
15    derive(serde_crate::Serialize, serde_crate::Deserialize)
16)]
17#[cfg_attr(feature = "serde", serde(crate = "serde_crate"))]
18pub struct Config {
19    /// the [authenticated encryption with additional data encryption function](crate::Aead) to be
20    /// used
21    pub aead: Aead,
22    /// the [key derivation function](crate::Kdf) to be used
23    pub kdf: Kdf,
24    /// the [asymmetric key encapsulation mechanism](crate::Kem) to be used
25    pub kem: Kem,
26}
27
28impl Config {
29    /// Single-shot HPKE ciphertext sealing.
30    ///
31    /// `base_mode_seal` provides an interface to [`hpke::single_shot_seal`] that does not require
32    /// compile time selection of an algorithm. Instead, the selected algorithm is provided through
33    /// the receiver.
34    ///
35    /// # Errors
36    ///
37    /// This will return a `Result::Err` variant if:
38    ///
39    /// * we are unable to deserialize the recipient public key
40    /// * there is an error in key encapsultion
41    /// * there is an error in encryption
42    pub fn base_mode_seal(
43        &self,
44        recipient_public_key: &[u8],
45        info: &[u8],
46        plaintext: &[u8],
47        aad: &[u8],
48    ) -> Result<EncappedKeyAndCiphertext, HpkeError> {
49        base_mode_seal(self, recipient_public_key, info, plaintext, aad)
50    }
51
52    /// Single-shot HPKE ciphertext opening.
53    ///
54    /// `base_mode_open` provides an interface to [`hpke::single_shot_open`] that does not require
55    /// compile time selection of an algorithm. Instead, the selected algorithm is provided through
56    /// the receiver
57    ///
58    /// # Errors
59    ///
60    /// This will return a `Result::Err` variant if:
61    ///
62    /// * we are unable to deserialize the private key or encapsulated key
63    /// * there is an error in key decapsulation
64    /// * there is an error in decryption
65    pub fn base_mode_open(
66        &self,
67        private_key: &[u8],
68        encapped_key: &[u8],
69        info: &[u8],
70        ciphertext: &[u8],
71        aad: &[u8],
72    ) -> Result<Vec<u8>, HpkeError> {
73        base_mode_open(self, private_key, encapped_key, info, ciphertext, aad)
74    }
75
76    /// Attempt to convert three u16 ids into a valid [`Config`].
77    ///
78    /// The ID mappings are defined in the [IANA HPKE registries][1].
79    ///
80    /// [1]: https://www.iana.org/assignments/hpke/hpke.xhtml
81    pub fn try_from_ids(aead_id: u16, kdf_id: u16, kem_id: u16) -> Result<Config, IdLookupError> {
82        Ok(Self {
83            aead: aead_id.try_into().map_err(|_| IdLookupError("aead"))?,
84            kdf: kdf_id.try_into().map_err(|_| IdLookupError("kdf"))?,
85            kem: kem_id.try_into().map_err(|_| IdLookupError("kem"))?,
86        })
87    }
88}