summaryrefslogtreecommitdiffstats
path: root/third_party/rust/base64/src/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'third_party/rust/base64/src/lib.rs')
-rw-r--r--third_party/rust/base64/src/lib.rs179
1 files changed, 179 insertions, 0 deletions
diff --git a/third_party/rust/base64/src/lib.rs b/third_party/rust/base64/src/lib.rs
new file mode 100644
index 0000000000..cc9d628df6
--- /dev/null
+++ b/third_party/rust/base64/src/lib.rs
@@ -0,0 +1,179 @@
+//! # Getting started
+//!
+//! 1. Perhaps one of the preconfigured engines in [engine::general_purpose] will suit, e.g.
+//! [engine::general_purpose::STANDARD_NO_PAD].
+//! - These are re-exported in [prelude] with a `BASE64_` prefix for those who prefer to
+//! `use base64::prelude::*` or equivalent, e.g. [prelude::BASE64_STANDARD_NO_PAD]
+//! 1. If not, choose which alphabet you want. Most usage will want [alphabet::STANDARD] or [alphabet::URL_SAFE].
+//! 1. Choose which [Engine] implementation you want. For the moment there is only one: [engine::GeneralPurpose].
+//! 1. Configure the engine appropriately using the engine's `Config` type.
+//! - This is where you'll select whether to add padding (when encoding) or expect it (when
+//! decoding). If given the choice, prefer no padding.
+//! 1. Build the engine using the selected alphabet and config.
+//!
+//! For more detail, see below.
+//!
+//! ## Alphabets
+//!
+//! An [alphabet::Alphabet] defines what ASCII symbols are used to encode to or decode from.
+//!
+//! Constants in [alphabet] like [alphabet::STANDARD] or [alphabet::URL_SAFE] provide commonly used
+//! alphabets, but you can also build your own custom [alphabet::Alphabet] if needed.
+//!
+//! ## Engines
+//!
+//! Once you have an `Alphabet`, you can pick which `Engine` you want. A few parts of the public
+//! API provide a default, but otherwise the user must provide an `Engine` to use.
+//!
+//! See [Engine] for more.
+//!
+//! ## Config
+//!
+//! In addition to an `Alphabet`, constructing an `Engine` also requires an [engine::Config]. Each
+//! `Engine` has a corresponding `Config` implementation since different `Engine`s may offer different
+//! levels of configurability.
+//!
+//! # Encoding
+//!
+//! Several different encoding methods on [Engine] are available to you depending on your desire for
+//! convenience vs performance.
+//!
+//! | Method | Output | Allocates |
+//! | ------------------------ | ---------------------------- | ------------------------------ |
+//! | [Engine::encode] | Returns a new `String` | Always |
+//! | [Engine::encode_string] | Appends to provided `String` | Only if `String` needs to grow |
+//! | [Engine::encode_slice] | Writes to provided `&[u8]` | Never - fastest |
+//!
+//! All of the encoding methods will pad as per the engine's config.
+//!
+//! # Decoding
+//!
+//! Just as for encoding, there are different decoding methods available.
+//!
+//! | Method | Output | Allocates |
+//! | ------------------------ | ----------------------------- | ------------------------------ |
+//! | [Engine::decode] | Returns a new `Vec<u8>` | Always |
+//! | [Engine::decode_vec] | Appends to provided `Vec<u8>` | Only if `Vec` needs to grow |
+//! | [Engine::decode_slice] | Writes to provided `&[u8]` | Never - fastest |
+//!
+//! Unlike encoding, where all possible input is valid, decoding can fail (see [DecodeError]).
+//!
+//! Input can be invalid because it has invalid characters or invalid padding. The nature of how
+//! padding is checked depends on the engine's config.
+//! Whitespace in the input is invalid, just like any other non-base64 byte.
+//!
+//! # `Read` and `Write`
+//!
+//! To decode a [std::io::Read] of b64 bytes, wrap a reader (file, network socket, etc) with
+//! [read::DecoderReader].
+//!
+//! To write raw bytes and have them b64 encoded on the fly, wrap a [std::io::Write] with
+//! [write::EncoderWriter].
+//!
+//! There is some performance overhead (15% or so) because of the necessary buffer shuffling --
+//! still fast enough that almost nobody cares. Also, these implementations do not heap allocate.
+//!
+//! # `Display`
+//!
+//! See [display] for how to transparently base64 data via a `Display` implementation.
+//!
+//! # Examples
+//!
+//! ## Using predefined engines
+//!
+//! ```
+//! use base64::{Engine as _, engine::general_purpose};
+//!
+//! let orig = b"data";
+//! let encoded: String = general_purpose::STANDARD_NO_PAD.encode(orig);
+//! assert_eq!("ZGF0YQ", encoded);
+//! assert_eq!(orig.as_slice(), &general_purpose::STANDARD_NO_PAD.decode(encoded).unwrap());
+//!
+//! // or, URL-safe
+//! let encoded_url = general_purpose::URL_SAFE_NO_PAD.encode(orig);
+//! ```
+//!
+//! ## Custom alphabet, config, and engine
+//!
+//! ```
+//! use base64::{engine, alphabet, Engine as _};
+//!
+//! // bizarro-world base64: +/ as the first symbols instead of the last
+//! let alphabet =
+//! alphabet::Alphabet::new("+/ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789")
+//! .unwrap();
+//!
+//! // a very weird config that encodes with padding but requires no padding when decoding...?
+//! let crazy_config = engine::GeneralPurposeConfig::new()
+//! .with_decode_allow_trailing_bits(true)
+//! .with_encode_padding(true)
+//! .with_decode_padding_mode(engine::DecodePaddingMode::RequireNone);
+//!
+//! let crazy_engine = engine::GeneralPurpose::new(&alphabet, crazy_config);
+//!
+//! let encoded = crazy_engine.encode(b"abc 123");
+//!
+//! ```
+//!
+//! # Panics
+//!
+//! If length calculations result in overflowing `usize`, a panic will result.
+
+#![cfg_attr(feature = "cargo-clippy", allow(clippy::cast_lossless))]
+#![deny(
+ missing_docs,
+ trivial_casts,
+ trivial_numeric_casts,
+ unused_extern_crates,
+ unused_import_braces,
+ unused_results,
+ variant_size_differences,
+ warnings
+)]
+#![forbid(unsafe_code)]
+// Allow globally until https://github.com/rust-lang/rust-clippy/issues/8768 is resolved.
+// The desired state is to allow it only for the rstest_reuse import.
+#![allow(clippy::single_component_path_imports)]
+#![cfg_attr(not(any(feature = "std", test)), no_std)]
+
+#[cfg(all(feature = "alloc", not(any(feature = "std", test))))]
+extern crate alloc;
+#[cfg(any(feature = "std", test))]
+extern crate std as alloc;
+
+// has to be included at top level because of the way rstest_reuse defines its macros
+#[cfg(test)]
+use rstest_reuse;
+
+mod chunked_encoder;
+pub mod display;
+#[cfg(any(feature = "std", test))]
+pub mod read;
+#[cfg(any(feature = "std", test))]
+pub mod write;
+
+pub mod engine;
+pub use engine::Engine;
+
+pub mod alphabet;
+
+mod encode;
+#[allow(deprecated)]
+#[cfg(any(feature = "alloc", feature = "std", test))]
+pub use crate::encode::{encode, encode_engine, encode_engine_string};
+#[allow(deprecated)]
+pub use crate::encode::{encode_engine_slice, encoded_len, EncodeSliceError};
+
+mod decode;
+#[allow(deprecated)]
+#[cfg(any(feature = "alloc", feature = "std", test))]
+pub use crate::decode::{decode, decode_engine, decode_engine_vec};
+#[allow(deprecated)]
+pub use crate::decode::{decode_engine_slice, decoded_len_estimate, DecodeError, DecodeSliceError};
+
+pub mod prelude;
+
+#[cfg(test)]
+mod tests;
+
+const PAD_BYTE: u8 = b'=';