mls_rs/
lib.rs

1// Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2// Copyright by contributors to this project.
3// SPDX-License-Identifier: (Apache-2.0 OR MIT)
4
5//! An implementation of the [IETF Messaging Layer Security](https://messaginglayersecurity.rocks)
6//! end-to-end encryption (E2EE) protocol.
7//!
8//! ## What is MLS?
9//!
10//! MLS is a new IETF end-to-end encryption standard that is designed to
11//! provide transport agnostic, asynchronous, and highly performant
12//! communication between a group of clients.
13//!
14//! ## MLS Protocol Features
15//!
16//! - Multi-party E2EE [group evolution](https://www.rfc-editor.org/rfc/rfc9420.html#name-cryptographic-state-and-evo)
17//!   via a propose-then-commit mechanism.
18//! - Asynchronous by design with pre-computed [key packages](https://www.rfc-editor.org/rfc/rfc9420.html#name-key-packages),
19//!   allowing members to be added to a group while offline.
20//! - Customizable credential system with built in support for X.509 certificates.
21//! - [Extension system](https://www.rfc-editor.org/rfc/rfc9420.html#name-extensions)
22//!   allowing for application specific data to be negotiated via the protocol.
23//! - Strong forward secrecy and post compromise security.
24//! - Crypto agility via support for multiple [cipher suites](https://www.rfc-editor.org/rfc/rfc9420.html#name-cipher-suites).
25//! - Pre-shared key support.
26//! - Subgroup branching.
27//! - Group reinitialization for breaking changes such as protocol upgrades.
28//!
29//! ## Features
30//!
31//! - Easy to use client interface that can manage multiple MLS identities and groups.
32//! - 100% RFC 9420 conformance with support for all default credential, proposal,
33//!   and extension types.
34//! - Support for WASM builds.
35//! - Configurable storage for key packages, secrets and group state
36//!   via traits along with provided "in memory" and SQLite implementations.
37//! - Support for custom user proposal and extension types.
38//! - Ability to create user defined credentials with custom validation
39//!   routines that can bridge to existing credential schemes.
40//! - OpenSSL and Rust Crypto based cipher suite implementations.
41//! - Crypto agility with support for user defined cipher suite.
42//! - Extensive test suite including security and interop focused tests against
43//!   pre-computed test vectors.
44//!
45//! ## Crypto Providers
46//!
47//! For cipher suite descriptions see the RFC documentation [here](https://www.rfc-editor.org/rfc/rfc9420.html#name-mls-cipher-suites)
48//!
49//! | Name | Cipher Suites | X509 Support |
50//! |------|---------------|--------------|
51//! | OpenSSL | 1-7 | Stable |
52//! | AWS-LC | 1,2,3,5,7 | Stable |
53//! | Rust Crypto | 1,2,3 | ⚠️ Experimental |
54//!
55//! ## Security Notice
56//!
57//! This library has been validated for conformance to the RFC 9420 specification but has not yet received a full security audit by a 3rd party.
58
59#![allow(clippy::enum_variant_names)]
60#![allow(clippy::result_large_err)]
61#![allow(clippy::nonstandard_macro_braces)]
62#![cfg_attr(not(feature = "std"), no_std)]
63#![cfg_attr(docsrs, feature(doc_cfg))]
64#![cfg_attr(coverage_nightly, feature(coverage_attribute))]
65extern crate alloc;
66
67#[cfg(all(test, target_arch = "wasm32"))]
68wasm_bindgen_test::wasm_bindgen_test_configure!(run_in_browser);
69
70#[cfg(all(test, target_arch = "wasm32"))]
71use wasm_bindgen_test::wasm_bindgen_test as futures_test;
72
73#[cfg(all(test, mls_build_async, not(target_arch = "wasm32")))]
74use futures_test::test as futures_test;
75
76#[cfg(test)]
77macro_rules! hex {
78    ($input:literal) => {
79        hex::decode($input).expect("invalid hex value")
80    };
81}
82
83#[cfg(test)]
84macro_rules! load_test_case_json {
85    ($name:ident, $generate:expr) => {
86        load_test_case_json!($name, $generate, to_vec_pretty)
87    };
88    ($name:ident, $generate:expr, $to_json:ident) => {{
89        #[cfg(any(target_arch = "wasm32", not(feature = "std")))]
90        {
91            // Do not remove `async`! (The goal of this line is to remove warnings
92            // about `$generate` not being used. Actually calling it will make tests fail.)
93            let _ = async { $generate };
94            serde_json::from_slice(include_bytes!(concat!(
95                env!("CARGO_MANIFEST_DIR"),
96                "/test_data/",
97                stringify!($name),
98                ".json"
99            )))
100            .unwrap()
101        }
102
103        #[cfg(all(not(target_arch = "wasm32"), feature = "std"))]
104        {
105            let path = concat!(
106                env!("CARGO_MANIFEST_DIR"),
107                "/test_data/",
108                stringify!($name),
109                ".json"
110            );
111            if !std::path::Path::new(path).exists() {
112                std::fs::write(path, serde_json::$to_json(&$generate).unwrap()).unwrap();
113            }
114            serde_json::from_slice(&std::fs::read(path).unwrap()).unwrap()
115        }
116    }};
117}
118
119mod cipher_suite {
120    pub use mls_rs_core::crypto::CipherSuite;
121}
122
123pub use cipher_suite::CipherSuite;
124
125mod protocol_version {
126    pub use mls_rs_core::protocol_version::ProtocolVersion;
127}
128
129pub use protocol_version::ProtocolVersion;
130
131pub mod client;
132pub mod client_builder;
133mod client_config;
134/// Dependencies of [`CryptoProvider`] and [`CipherSuiteProvider`]
135pub mod crypto;
136/// Extension utilities and built-in extension types.
137pub mod extension;
138/// Tools to observe groups without being a member, useful
139/// for server implementations.
140#[cfg(feature = "external_client")]
141#[cfg_attr(docsrs, doc(cfg(feature = "external_client")))]
142pub mod external_client;
143mod grease;
144/// E2EE group created by a [`Client`].
145pub mod group;
146mod hash_reference;
147/// Identity providers to use with [`ClientBuilder`](client_builder::ClientBuilder).
148pub mod identity;
149mod iter;
150mod key_package;
151pub(crate) mod map;
152/// Pre-shared key support.
153pub mod psk;
154mod signer;
155/// Storage providers to use with
156/// [`ClientBuilder`](client_builder::ClientBuilder).
157pub mod storage_provider;
158
159pub use mls_rs_core::{
160    crypto::{CipherSuiteProvider, CryptoProvider},
161    group::GroupStateStorage,
162    identity::IdentityProvider,
163    key_package::KeyPackageStorage,
164    psk::PreSharedKeyStorage,
165};
166
167/// Dependencies of [`MlsRules`].
168pub mod mls_rules {
169    pub use crate::group::{
170        mls_rules::{
171            CommitDirection, CommitOptions, CommitSource, DefaultMlsRules, EncryptionOptions,
172        },
173        proposal_filter::{ProposalBundle, ProposalInfo, ProposalSource},
174    };
175
176    #[cfg(feature = "by_ref_proposal")]
177    pub use crate::group::proposal_ref::ProposalRef;
178}
179
180pub use mls_rs_core::extension::{Extension, ExtensionList};
181
182pub use crate::{
183    client::Client,
184    group::{
185        framing::{MlsMessage, MlsMessageDescription, WireFormat},
186        mls_rules::MlsRules,
187        Group,
188    },
189    key_package::{KeyPackage, KeyPackageRef},
190};
191
192/// Error types.
193pub mod error {
194    pub use crate::client::MlsError;
195    pub use mls_rs_core::error::{AnyError, IntoAnyError};
196    pub use mls_rs_core::extension::ExtensionError;
197}
198
199/// WASM compatible timestamp.
200pub mod time {
201    pub use mls_rs_core::time::*;
202}
203
204mod tree_kem;
205
206pub use mls_rs_codec;
207
208mod private {
209    pub trait Sealed {}
210}
211
212use private::Sealed;
213
214#[cfg(any(test, feature = "test_util"))]
215#[doc(hidden)]
216pub mod test_utils;
217
218#[cfg(feature = "ffi")]
219pub use safer_ffi_gen;