crypto_bigint/lib.rs
1#![no_std]
2#![cfg_attr(docsrs, feature(doc_auto_cfg))]
3#![doc = include_str!("../README.md")]
4#![doc(
5 html_logo_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg",
6 html_favicon_url = "https://raw.githubusercontent.com/RustCrypto/meta/master/logo.svg"
7)]
8#![deny(unsafe_code)]
9#![warn(
10 clippy::mod_module_files,
11 clippy::unwrap_used,
12 missing_docs,
13 missing_debug_implementations,
14 missing_copy_implementations,
15 rust_2018_idioms,
16 trivial_casts,
17 trivial_numeric_casts,
18 unused_qualifications
19)]
20
21//! ## Usage
22//!
23//! The core types of `crypto-bigint` are as follows:
24//!
25//! - [`Uint`]: stack-allocated big integer type, const generic around a number of [`Limb`]s.
26//! Type aliases are provided for various sizes, e.g. [`U128`], [`U384`], [`U256`], [`U2048`],
27//! [`U3072`], [`U4096`].
28//! - [`BoxedUint`]: heap-allocated big integer type. Requires the `alloc` crate feature is enabled.
29//!
30//! Big integer types in this crate use a 32-bit or 64-bit saturated representation, depending on
31//! the underlying CPU's pointer width.
32//!
33//! The following types for modular arithmetic are available under the [`modular`] submodule:
34//!
35//! - [`modular::ConstMontyForm`]: stack-allocated type-safe modular arithmetic using Montgomery
36//! form suitable for cases where the modulus is known at compile-time.
37//! - [`modular::MontyForm`]: stack-allocated modular arithmetic using Montgomery form for cases
38//! where the modulus is only known at runtime.
39//! - [`modular::BoxedMontyForm`]: heap-allocated modular arithmetic using Montgomery form.
40//! Requires the `alloc` crate feature is enabled.
41//!
42//! ### `const fn` usage
43//!
44//! The [`Uint`] type provides a number of `const fn` inherent methods which
45//! can be used for initializing and performing arithmetic on big integers in
46//! const contexts:
47//!
48//! ```
49//! use crypto_bigint::U256;
50//!
51//! // Parse a constant from a big endian hexadecimal string.
52//! pub const MODULUS: U256 =
53//! U256::from_be_hex("ffffffff00000000ffffffffffffffffbce6faada7179e84f3b9cac2fc632551");
54//!
55//! // Compute `MODULUS` shifted right by 1 at compile time
56//! pub const MODULUS_SHR1: U256 = MODULUS.shr(1);
57//! ```
58//!
59//! ### Trait-based usage
60//!
61//! The [`Uint`] type itself does not implement the standard arithmetic traits
62//! such as [`Add`], [`Sub`], [`Mul`], and [`Div`].
63//!
64//! To use these traits you must first pick a wrapper type which determines
65//! overflow behavior: [`Wrapping`] or [`Checked`].
66//!
67//! #### Wrapping arithmetic
68//!
69//! ```
70//! use crypto_bigint::{U256, Wrapping};
71//!
72//! let a = Wrapping(U256::MAX);
73//! let b = Wrapping(U256::ONE);
74//! let c = a + b;
75//!
76//! // `MAX` + 1 wraps back around to zero
77//! assert_eq!(c.0, U256::ZERO);
78//! ```
79//!
80//! #### Checked arithmetic
81//!
82//! ```
83//! use crypto_bigint::{U256, Checked};
84//!
85//! let a = Checked::new(U256::ONE);
86//! let b = Checked::new(U256::from(2u8));
87//! let c = a + b;
88//! assert_eq!(c.0.unwrap(), U256::from(3u8))
89//! ```
90//!
91//! ### Modular arithmetic
92//!
93//! This library has initial support for modular arithmetic in the form of the
94//! [`AddMod`], [`SubMod`], [`NegMod`], and [`MulMod`] traits, as well as the
95//! support for the [`Rem`] trait when used with a [`NonZero`] operand.
96//!
97//! ```
98//! use crypto_bigint::{AddMod, U256};
99//!
100//! // mod 3
101//! let modulus = U256::from(3u8);
102//!
103//! // 1 + 1 mod 3 = 2
104//! let a = U256::ONE.add_mod(&U256::ONE, &modulus);
105//! assert_eq!(a, U256::from(2u8));
106//!
107//! // 2 + 1 mod 3 = 0
108//! let b = a.add_mod(&U256::ONE, &modulus);
109//! assert_eq!(b, U256::ZERO);
110//! ```
111//!
112//! It also supports modular arithmetic over constant moduli using `ConstMontyForm`,
113//! and over moduli set at runtime using `MontyForm`.
114//! That includes modular exponentiation and multiplicative inverses.
115//! These features are described in the [`modular`] module.
116//!
117//! ### Random number generation
118//!
119//! When the `rand_core` or `rand` features of this crate are enabled, it's
120//! possible to generate random numbers using any RNG by using the
121//! [`Random`] trait:
122//!
123//! ```
124//! # #[cfg(feature = "rand")]
125//! # {
126//! use crypto_bigint::{Random, U256, rand_core::OsRng};
127//!
128//! let n = U256::random(&mut OsRng);
129//! # }
130//! ```
131//!
132//! #### Modular random number generation
133//!
134//! The [`RandomMod`] trait supports generating random numbers with a uniform
135//! distribution around a given [`NonZero`] modulus.
136//!
137//! ```
138//! # #[cfg(feature = "rand")]
139//! # {
140//! use crypto_bigint::{NonZero, RandomMod, U256, rand_core::OsRng};
141//!
142//! let modulus = NonZero::new(U256::from(3u8)).unwrap();
143//! let n = U256::random_mod(&mut OsRng, &modulus);
144//! # }
145//! ```
146//!
147//! [`Add`]: core::ops::Add
148//! [`Div`]: core::ops::Div
149//! [`Mul`]: core::ops::Mul
150//! [`Rem`]: core::ops::Rem
151//! [`Sub`]: core::ops::Sub
152
153#[cfg(feature = "alloc")]
154#[allow(unused_imports)]
155#[macro_use]
156extern crate alloc;
157
158#[cfg(feature = "rand_core")]
159pub use rand_core;
160#[cfg(feature = "rlp")]
161pub use rlp;
162pub use subtle;
163#[cfg(feature = "zeroize")]
164pub use zeroize;
165
166#[cfg(feature = "hybrid-array")]
167pub use {
168 crate::array::{ArrayDecoding, ArrayEncoding, ByteArray},
169 hybrid_array::{self, typenum::consts},
170};
171
172#[cfg(feature = "alloc")]
173pub use crate::uint::boxed::BoxedUint;
174pub use crate::{
175 checked::Checked,
176 const_choice::{ConstChoice, ConstCtOption},
177 int::types::*,
178 int::*,
179 limb::{Limb, WideWord, Word},
180 non_zero::NonZero,
181 odd::Odd,
182 traits::*,
183 uint::div_limb::Reciprocal,
184 uint::*,
185 wrapping::Wrapping,
186};
187
188#[macro_use]
189mod macros;
190
191pub mod modular;
192
193#[cfg(feature = "hybrid-array")]
194mod array;
195mod checked;
196mod const_choice;
197mod int;
198mod limb;
199mod non_zero;
200mod odd;
201mod primitives;
202mod traits;
203mod uint;
204mod wrapping;
205
206/// Import prelude for this crate: includes important traits.
207pub mod prelude {
208 #[cfg(feature = "hybrid-array")]
209 pub use crate::array::{ArrayDecoding, ArrayEncoding};
210 pub use crate::traits::*;
211}