data_encoding_v3/
lib.rs

1//! Efficient and customizable data-encoding functions like base64, base32, and hex
2#![doc = include_str!("../README.md")]
3#![no_std]
4#![cfg_attr(docsrs, feature(doc_auto_cfg))]
5
6#[cfg(feature = "alloc")]
7extern crate alloc;
8#[cfg(feature = "std")]
9extern crate std;
10
11#[cfg(feature = "alloc")]
12use alloc::borrow::{Cow, ToOwned};
13#[cfg(feature = "alloc")]
14use alloc::string::String;
15#[cfg(feature = "alloc")]
16use alloc::vec;
17#[cfg(feature = "alloc")]
18use alloc::vec::Vec;
19use core::convert::TryInto;
20use core::marker::PhantomData;
21use core::mem::MaybeUninit;
22
23macro_rules! check {
24    ($e: expr, $c: expr) => {
25        if !$c {
26            return Err($e);
27        }
28    };
29}
30
31/// Type-level bit-width of an encoding.
32pub trait BitWidth: sealed::BitWidth {}
33
34/// Type-level bool.
35pub trait Bool: sealed::Bool {}
36
37mod sealed {
38    pub trait BitWidth {
39        const VAL: usize;
40    }
41
42    pub trait Bool {
43        type If<Then: Copy, Else: Copy>: Copy;
44        const VAL: bool;
45        fn open<Then: Copy, Else: Copy>(cond: Self::If<Then, Else>) -> If<Then, Else>;
46        fn make<Then: Copy, Else: Copy>(
47            then: impl FnOnce() -> Then, else_: impl FnOnce() -> Else,
48        ) -> Self::If<Then, Else>;
49    }
50
51    #[derive(Debug, Copy, Clone)]
52    pub enum If<Then, Else> {
53        Then(Then),
54        Else(Else),
55    }
56}
57use sealed::If;
58
59macro_rules! new_bit_width {
60    ($(($N:ident, $v:expr, $b:literal),)*) => {
61        $(
62            #[doc = concat!(" Bit-width of ", $b, " encodings.")]
63            #[derive(Debug)]
64            pub enum $N {}
65            impl BitWidth for $N {}
66            impl sealed::BitWidth for $N { const VAL: usize = $v; }
67        )*
68    };
69}
70new_bit_width![
71    (Bit1, 1, "base2"),
72    (Bit2, 2, "base4"),
73    (Bit3, 3, "base8"),
74    (Bit4, 4, "base16"),
75    (Bit5, 5, "base32"),
76    (Bit6, 6, "base64"),
77];
78
79/// Type-level false.
80#[derive(Debug)]
81pub enum False {}
82impl Bool for False {}
83impl sealed::Bool for False {
84    type If<Then: Copy, Else: Copy> = Else;
85    const VAL: bool = false;
86    fn open<Then: Copy, Else: Copy>(cond: Self::If<Then, Else>) -> If<Then, Else> {
87        If::Else(cond)
88    }
89    fn make<Then: Copy, Else: Copy>(
90        _then: impl FnOnce() -> Then, else_: impl FnOnce() -> Else,
91    ) -> Self::If<Then, Else> {
92        else_()
93    }
94}
95
96/// Type-level true.
97#[derive(Debug, Copy, Clone)]
98pub enum True {}
99impl Bool for True {}
100impl sealed::Bool for True {
101    type If<Then: Copy, Else: Copy> = Then;
102    const VAL: bool = true;
103    fn open<Then: Copy, Else: Copy>(cond: Self::If<Then, Else>) -> If<Then, Else> {
104        If::Then(cond)
105    }
106    fn make<Then: Copy, Else: Copy>(
107        then: impl FnOnce() -> Then, _else: impl FnOnce() -> Else,
108    ) -> Self::If<Then, Else> {
109        then()
110    }
111}
112
113unsafe fn cast<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool>(
114    base: &DynEncoding,
115) -> &Encoding<Bit, Msb, Pad, Wrap, Ignore> {
116    let ptr = core::ptr::from_ref(base).cast::<Encoding<Bit, Msb, Pad, Wrap, Ignore>>();
117    unsafe { &*ptr }
118}
119
120macro_rules! dispatch {
121    ($dyn:ident $($body: tt)*) => {
122        dispatch!([] Bit $dyn $($body)*)
123    };
124    ([] Bit $dyn:ident $($body:tt)*) => {
125        match $dyn.bit() {
126            1 => dispatch!([Bit1] Msb $dyn $($body)*),
127            2 => dispatch!([Bit2] Msb $dyn $($body)*),
128            3 => dispatch!([Bit3] Msb $dyn $($body)*),
129            4 => dispatch!([Bit4] Msb $dyn $($body)*),
130            5 => dispatch!([Bit5] Msb $dyn $($body)*),
131            6 => dispatch!([Bit6] Msb $dyn $($body)*),
132            _ => unreachable!(),
133        }
134    };
135    ([$($gen:ty),*] Msb $dyn:ident $($body:tt)*) => {
136        match $dyn.msb() {
137            false => dispatch!([$($gen),*, False] Pad $dyn $($body)*),
138            true => dispatch!([$($gen),*, True] Pad $dyn $($body)*),
139        }
140    };
141    ([$($gen:ty),*] Pad $dyn:ident $($body:tt)*) => {
142        match $dyn.pad().is_some() {
143            false => dispatch!([$($gen),*, False] Wrap $dyn $($body)*),
144            true => dispatch!([$($gen),*, True] Wrap $dyn $($body)*),
145        }
146    };
147    ([$($gen:ty),*] Wrap $dyn:ident $($body:tt)*) => {
148        match $dyn.wrap().is_some() {
149            false => dispatch!([$($gen),*, False] Ignore $dyn $($body)*),
150            true => dispatch!([$($gen),*, True] Ignore $dyn $($body)*),
151        }
152    };
153    ([$($gen:ty),*] Ignore $dyn:ident $($body:tt)*) => {
154        match $dyn.has_ignore() {
155            false => dispatch!({ $($gen),*, False } $dyn $($body)*),
156            true => dispatch!({ $($gen),*, True } $dyn $($body)*),
157        }
158    };
159    ({ $($gen:ty),* } $dyn:ident $($body:tt)*) => {
160        unsafe { cast::<$($gen),*>($dyn) } $($body)*
161    };
162}
163
164unsafe fn chunk_unchecked<T>(x: &[T], n: usize, i: usize) -> &[T] {
165    debug_assert!((i + 1) * n <= x.len());
166    unsafe { core::slice::from_raw_parts(x.as_ptr().add(n * i), n) }
167}
168
169unsafe fn chunk_mut_unchecked<T>(x: &mut [T], n: usize, i: usize) -> &mut [T] {
170    debug_assert!((i + 1) * n <= x.len());
171    unsafe { core::slice::from_raw_parts_mut(x.as_mut_ptr().add(n * i), n) }
172}
173
174// TODO(https://github.com/rust-lang/rust/issues/79995): Use write_slice() instead.
175unsafe fn copy_from_slice(dst: &mut [MaybeUninit<u8>], src: &[u8]) {
176    dst.copy_from_slice(unsafe { &*(core::ptr::from_ref(src) as *const [MaybeUninit<u8>]) });
177}
178
179// TODO(https://github.com/rust-lang/rust/issues/63569): Use slice_assume_init_mut() instead.
180unsafe fn slice_assume_init_mut(xs: &mut [MaybeUninit<u8>]) -> &mut [u8] {
181    unsafe { &mut *(core::ptr::from_mut(xs) as *mut [u8]) }
182}
183
184unsafe fn slice_uninit_mut(xs: &mut [u8]) -> &mut [MaybeUninit<u8>] {
185    unsafe { &mut *(core::ptr::from_mut(xs) as *mut [MaybeUninit<u8>]) }
186}
187
188#[cfg(feature = "alloc")]
189fn reserve_spare(xs: &mut Vec<u8>, n: usize) -> &mut [MaybeUninit<u8>] {
190    xs.reserve(n);
191    &mut xs.spare_capacity_mut()[.. n]
192}
193
194fn floor(x: usize, m: usize) -> usize {
195    x / m * m
196}
197
198#[inline]
199fn vectorize<F: FnMut(usize)>(n: usize, bs: usize, mut f: F) {
200    for k in 0 .. n / bs {
201        for i in k * bs .. (k + 1) * bs {
202            f(i);
203        }
204    }
205    for i in floor(n, bs) .. n {
206        f(i);
207    }
208}
209
210/// Decoding error kind
211#[derive(Debug, Copy, Clone, PartialEq, Eq)]
212pub enum DecodeKind {
213    /// Invalid length
214    Length,
215
216    /// Invalid symbol
217    Symbol,
218
219    /// Non-zero trailing bits
220    Trailing,
221
222    /// Invalid padding length
223    Padding,
224}
225
226impl core::fmt::Display for DecodeKind {
227    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
228        let description = match self {
229            DecodeKind::Length => "invalid length",
230            DecodeKind::Symbol => "invalid symbol",
231            DecodeKind::Trailing => "non-zero trailing bits",
232            DecodeKind::Padding => "invalid padding length",
233        };
234        write!(f, "{description}")
235    }
236}
237
238/// Decoding error
239#[derive(Debug, Copy, Clone, PartialEq, Eq)]
240pub struct DecodeError {
241    /// Error position
242    ///
243    /// This position is always a valid input position and represents the first encountered error.
244    pub position: usize,
245
246    /// Error kind
247    pub kind: DecodeKind,
248}
249
250#[cfg(feature = "std")]
251impl std::error::Error for DecodeError {}
252
253impl core::fmt::Display for DecodeError {
254    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
255        write!(f, "{} at {}", self.kind, self.position)
256    }
257}
258
259/// Decoding error with partial result
260#[derive(Debug, Copy, Clone, PartialEq, Eq)]
261pub struct DecodePartial {
262    /// Number of bytes read from input
263    ///
264    /// This number does not exceed the error position: `read <= error.position`.
265    pub read: usize,
266
267    /// Number of bytes written to output
268    ///
269    /// This number does not exceed the decoded length: `written <= decode_len(read)`.
270    pub written: usize,
271
272    /// Decoding error
273    pub error: DecodeError,
274}
275
276const INVALID: u8 = 128;
277const IGNORE: u8 = 129;
278const PADDING: u8 = 130;
279
280fn order(msb: bool, n: usize, i: usize) -> usize {
281    if msb { n - 1 - i } else { i }
282}
283
284#[inline]
285fn enc(bit: usize) -> usize {
286    match bit {
287        1 | 2 | 4 => 1,
288        3 | 6 => 3,
289        5 => 5,
290        _ => unreachable!(),
291    }
292}
293
294#[inline]
295fn dec(bit: usize) -> usize {
296    enc(bit) * 8 / bit
297}
298
299fn encode_len<Bit: BitWidth>(len: usize) -> usize {
300    (8 * len).div_ceil(Bit::VAL)
301}
302
303fn encode_block<Bit: BitWidth, Msb: Bool>(
304    symbols: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
305) {
306    debug_assert!(input.len() <= enc(Bit::VAL));
307    debug_assert_eq!(output.len(), encode_len::<Bit>(input.len()));
308    let bit = Bit::VAL;
309    let msb = Msb::VAL;
310    let mut x = 0u64;
311    for (i, input) in input.iter().enumerate() {
312        x |= u64::from(*input) << (8 * order(msb, enc(bit), i));
313    }
314    for (i, output) in output.iter_mut().enumerate() {
315        let y = x >> (bit * order(msb, dec(bit), i));
316        let _ = output.write(symbols[(y & 0xff) as usize]);
317    }
318}
319
320fn encode_mut<Bit: BitWidth, Msb: Bool>(
321    symbols: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
322) {
323    debug_assert_eq!(output.len(), encode_len::<Bit>(input.len()));
324    let bit = Bit::VAL;
325    let enc = enc(bit);
326    let dec = dec(bit);
327    let n = input.len() / enc;
328    let bs = match bit {
329        5 => 2,
330        6 => 4,
331        _ => 1,
332    };
333    vectorize(n, bs, |i| {
334        let input = unsafe { chunk_unchecked(input, enc, i) };
335        let output = unsafe { chunk_mut_unchecked(output, dec, i) };
336        encode_block::<Bit, Msb>(symbols, input, output);
337    });
338    encode_block::<Bit, Msb>(symbols, &input[enc * n ..], &mut output[dec * n ..]);
339}
340
341// Fails if an input character does not translate to a symbol. The error is the
342// lowest index of such character. The output is not written to.
343fn decode_block<Bit: BitWidth, Msb: Bool>(
344    values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
345) -> Result<(), usize> {
346    debug_assert!(output.len() <= enc(Bit::VAL));
347    debug_assert_eq!(input.len(), encode_len::<Bit>(output.len()));
348    let bit = Bit::VAL;
349    let msb = Msb::VAL;
350    let mut x = 0u64;
351    for j in 0 .. input.len() {
352        let y = values[input[j] as usize];
353        check!(j, y < 1 << bit);
354        x |= u64::from(y) << (bit * order(msb, dec(bit), j));
355    }
356    for (j, output) in output.iter_mut().enumerate() {
357        let _ = output.write((x >> (8 * order(msb, enc(bit), j)) & 0xff) as u8);
358    }
359    Ok(())
360}
361
362// Fails if an input character does not translate to a symbol. The error `pos`
363// is the lowest index of such character. The output is valid up to `pos / dec *
364// enc` excluded.
365fn decode_mut<Bit: BitWidth, Msb: Bool>(
366    values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
367) -> Result<(), usize> {
368    debug_assert_eq!(input.len(), encode_len::<Bit>(output.len()));
369    let bit = Bit::VAL;
370    let enc = enc(bit);
371    let dec = dec(bit);
372    let n = input.len() / dec;
373    for i in 0 .. n {
374        let input = unsafe { chunk_unchecked(input, dec, i) };
375        let output = unsafe { chunk_mut_unchecked(output, enc, i) };
376        decode_block::<Bit, Msb>(values, input, output).map_err(|e| dec * i + e)?;
377    }
378    decode_block::<Bit, Msb>(values, &input[dec * n ..], &mut output[enc * n ..])
379        .map_err(|e| dec * n + e)
380}
381
382// Fails if there are non-zero trailing bits.
383fn check_trail<Bit: BitWidth, Msb: Bool>(
384    ctb: bool, values: &[u8; 256], input: &[u8],
385) -> Result<(), ()> {
386    if 8 % Bit::VAL == 0 || !ctb {
387        return Ok(());
388    }
389    let trail = Bit::VAL * input.len() % 8;
390    if trail == 0 {
391        return Ok(());
392    }
393    let mut mask = (1 << trail) - 1;
394    if !Msb::VAL {
395        mask <<= Bit::VAL - trail;
396    }
397    check!((), values[input[input.len() - 1] as usize] & mask == 0);
398    Ok(())
399}
400
401// Fails if the padding length is invalid. The error is the index of the first
402// padding character.
403fn check_pad<Bit: BitWidth>(values: &[u8; 256], input: &[u8]) -> Result<usize, usize> {
404    let bit = Bit::VAL;
405    debug_assert_eq!(input.len(), dec(bit));
406    let is_pad = |x: &&u8| values[**x as usize] == PADDING;
407    let count = input.iter().rev().take_while(is_pad).count();
408    let len = input.len() - count;
409    check!(len, len > 0 && bit * len % 8 < bit);
410    Ok(len)
411}
412
413fn encode_base_len<Bit: BitWidth>(len: usize) -> usize {
414    encode_len::<Bit>(len)
415}
416
417fn encode_base<Bit: BitWidth, Msb: Bool>(
418    symbols: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
419) {
420    debug_assert_eq!(output.len(), encode_base_len::<Bit>(input.len()));
421    encode_mut::<Bit, Msb>(symbols, input, output);
422}
423
424fn encode_pad_len<Bit: BitWidth, Pad: Bool>(len: usize) -> usize {
425    match Pad::VAL {
426        false => encode_base_len::<Bit>(len),
427        true => len.div_ceil(enc(Bit::VAL)) * dec(Bit::VAL),
428    }
429}
430
431fn encode_pad<Bit: BitWidth, Msb: Bool, Pad: Bool>(
432    symbols: &[u8; 256], pad: Pad::If<u8, ()>, input: &[u8], output: &mut [MaybeUninit<u8>],
433) {
434    let pad = match Pad::open(pad) {
435        If::Then(x) => x,
436        If::Else(()) => return encode_base::<Bit, Msb>(symbols, input, output),
437    };
438    debug_assert_eq!(output.len(), encode_pad_len::<Bit, Pad>(input.len()));
439    let olen = encode_base_len::<Bit>(input.len());
440    encode_base::<Bit, Msb>(symbols, input, &mut output[.. olen]);
441    for output in output.iter_mut().skip(olen) {
442        let _ = output.write(pad);
443    }
444}
445
446fn encode_wrap_len<Bit: BitWidth, Pad: Bool, Wrap: Bool>(
447    wrap: Wrap::If<(usize, &[u8]), ()>, ilen: usize,
448) -> usize {
449    let olen = encode_pad_len::<Bit, Pad>(ilen);
450    match Wrap::open(wrap) {
451        If::Then((col, end)) => olen + end.len() * olen.div_ceil(col),
452        If::Else(()) => olen,
453    }
454}
455
456fn encode_wrap_mut<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool>(
457    symbols: &[u8; 256], pad: Pad::If<u8, ()>, wrap: Wrap::If<(usize, &[u8]), ()>, input: &[u8],
458    output: &mut [MaybeUninit<u8>],
459) {
460    let (col, end) = match Wrap::open(wrap) {
461        If::Then((col, end)) => (col, end),
462        If::Else(()) => return encode_pad::<Bit, Msb, Pad>(symbols, pad, input, output),
463    };
464    debug_assert_eq!(output.len(), encode_wrap_len::<Bit, Pad, Wrap>(wrap, input.len()));
465    debug_assert_eq!(col % dec(Bit::VAL), 0);
466    let bit = Bit::VAL;
467    let col = col / dec(bit);
468    let enc = col * enc(bit);
469    let dec = col * dec(bit) + end.len();
470    let olen = dec - end.len();
471    let n = input.len() / enc;
472    for i in 0 .. n {
473        let input = unsafe { chunk_unchecked(input, enc, i) };
474        let output = unsafe { chunk_mut_unchecked(output, dec, i) };
475        encode_base::<Bit, Msb>(symbols, input, &mut output[.. olen]);
476        unsafe { copy_from_slice(&mut output[olen ..], end) };
477    }
478    if input.len() > enc * n {
479        let olen = dec * n + encode_pad_len::<Bit, Pad>(input.len() - enc * n);
480        encode_pad::<Bit, Msb, Pad>(symbols, pad, &input[enc * n ..], &mut output[dec * n .. olen]);
481        unsafe { copy_from_slice(&mut output[olen ..], end) };
482    }
483}
484
485// Returns the longest valid input length and associated output length.
486fn decode_wrap_len<Bit: BitWidth, Pad: Bool>(len: usize) -> (usize, usize) {
487    let bit = Bit::VAL;
488    if Pad::VAL {
489        (floor(len, dec(bit)), len / dec(bit) * enc(bit))
490    } else {
491        let trail = bit * len % 8;
492        (len - trail / bit, bit * len / 8)
493    }
494}
495
496// Fails with Length if length is invalid. The error is the largest valid
497// length.
498fn decode_pad_len<Bit: BitWidth, Pad: Bool>(len: usize) -> Result<usize, DecodeError> {
499    let (ilen, olen) = decode_wrap_len::<Bit, Pad>(len);
500    check!(DecodeError { position: ilen, kind: DecodeKind::Length }, ilen == len);
501    Ok(olen)
502}
503
504// Fails with Length if length is invalid. The error is the largest valid
505// length.
506fn decode_base_len<Bit: BitWidth>(len: usize) -> Result<usize, DecodeError> {
507    decode_pad_len::<Bit, False>(len)
508}
509
510// Fails with Symbol if an input character does not translate to a symbol. The
511// error is the lowest index of such character.
512// Fails with Trailing if there are non-zero trailing bits.
513fn decode_base_mut<Bit: BitWidth, Msb: Bool>(
514    ctb: bool, values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
515) -> Result<usize, DecodePartial> {
516    debug_assert_eq!(Ok(output.len()), decode_base_len::<Bit>(input.len()));
517    let bit = Bit::VAL;
518    let fail = |pos, kind| DecodePartial {
519        read: pos / dec(bit) * dec(bit),
520        written: pos / dec(bit) * enc(bit),
521        error: DecodeError { position: pos, kind },
522    };
523    decode_mut::<Bit, Msb>(values, input, output).map_err(|pos| fail(pos, DecodeKind::Symbol))?;
524    check_trail::<Bit, Msb>(ctb, values, input)
525        .map_err(|()| fail(input.len() - 1, DecodeKind::Trailing))?;
526    Ok(output.len())
527}
528
529// Fails with Symbol if an input character does not translate to a symbol. The
530// error is the lowest index of such character.
531// Fails with Padding if some padding length is invalid. The error is the index
532// of the first padding character of the invalid padding.
533// Fails with Trailing if there are non-zero trailing bits.
534fn decode_pad_mut<Bit: BitWidth, Msb: Bool, Pad: Bool>(
535    ctb: bool, values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
536) -> Result<usize, DecodePartial> {
537    if !Pad::VAL {
538        return decode_base_mut::<Bit, Msb>(ctb, values, input, output);
539    }
540    debug_assert_eq!(Ok(output.len()), decode_pad_len::<Bit, Pad>(input.len()));
541    let bit = Bit::VAL;
542    let enc = enc(bit);
543    let dec = dec(bit);
544    let mut inpos = 0;
545    let mut outpos = 0;
546    let mut outend = output.len();
547    while inpos < input.len() {
548        match decode_base_mut::<Bit, Msb>(
549            ctb,
550            values,
551            &input[inpos ..],
552            &mut output[outpos .. outend],
553        ) {
554            Ok(written) => {
555                if cfg!(debug_assertions) {
556                    inpos = input.len();
557                }
558                outpos += written;
559                break;
560            }
561            Err(partial) => {
562                inpos += partial.read;
563                outpos += partial.written;
564            }
565        }
566        let inlen = check_pad::<Bit>(values, &input[inpos .. inpos + dec]).map_err(|pos| {
567            DecodePartial {
568                read: inpos,
569                written: outpos,
570                error: DecodeError { position: inpos + pos, kind: DecodeKind::Padding },
571            }
572        })?;
573        let outlen = decode_base_len::<Bit>(inlen).unwrap();
574        let written = decode_base_mut::<Bit, Msb>(
575            ctb,
576            values,
577            &input[inpos .. inpos + inlen],
578            &mut output[outpos .. outpos + outlen],
579        )
580        .map_err(|partial| {
581            debug_assert_eq!(partial.read, 0);
582            debug_assert_eq!(partial.written, 0);
583            DecodePartial {
584                read: inpos,
585                written: outpos,
586                error: DecodeError {
587                    position: inpos + partial.error.position,
588                    kind: partial.error.kind,
589                },
590            }
591        })?;
592        debug_assert_eq!(written, outlen);
593        inpos += dec;
594        outpos += outlen;
595        outend -= enc - outlen;
596    }
597    debug_assert_eq!(inpos, input.len());
598    debug_assert_eq!(outpos, outend);
599    Ok(outend)
600}
601
602fn skip_ignore(values: &[u8; 256], input: &[u8], mut inpos: usize) -> usize {
603    while inpos < input.len() && values[input[inpos] as usize] == IGNORE {
604        inpos += 1;
605    }
606    inpos
607}
608
609// Returns next input and output position.
610// Fails with Symbol if an input character does not translate to a symbol. The
611// error is the lowest index of such character.
612// Fails with Padding if some padding length is invalid. The error is the index
613// of the first padding character of the invalid padding.
614// Fails with Trailing if there are non-zero trailing bits.
615fn decode_wrap_block<Bit: BitWidth, Msb: Bool, Pad: Bool>(
616    ctb: bool, values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
617) -> Result<(usize, usize), DecodeError> {
618    let bit = Bit::VAL;
619    let dec = dec(bit);
620    let mut buf = [0u8; 8];
621    let mut shift = [0usize; 8];
622    let mut bufpos = 0;
623    let mut inpos = 0;
624    while bufpos < dec {
625        inpos = skip_ignore(values, input, inpos);
626        if inpos == input.len() {
627            break;
628        }
629        shift[bufpos] = inpos;
630        buf[bufpos] = input[inpos];
631        bufpos += 1;
632        inpos += 1;
633    }
634    let olen = decode_pad_len::<Bit, Pad>(bufpos).map_err(|mut e| {
635        e.position = shift[e.position];
636        e
637    })?;
638    let written =
639        decode_pad_mut::<Bit, Msb, Pad>(ctb, values, &buf[.. bufpos], &mut output[.. olen])
640            .map_err(|partial| {
641                debug_assert_eq!(partial.read, 0);
642                debug_assert_eq!(partial.written, 0);
643                DecodeError { position: shift[partial.error.position], kind: partial.error.kind }
644            })?;
645    Ok((inpos, written))
646}
647
648// Fails with Symbol if an input character does not translate to a symbol. The
649// error is the lowest index of such character.
650// Fails with Padding if some padding length is invalid. The error is the index
651// of the first padding character of the invalid padding.
652// Fails with Trailing if there are non-zero trailing bits.
653// Fails with Length if input length (without ignored characters) is invalid.
654fn decode_wrap_mut<Bit: BitWidth, Msb: Bool, Pad: Bool, Ignore: Bool>(
655    ctb: bool, values: &[u8; 256], input: &[u8], output: &mut [MaybeUninit<u8>],
656) -> Result<usize, DecodePartial> {
657    if !Ignore::VAL {
658        return decode_pad_mut::<Bit, Msb, Pad>(ctb, values, input, output);
659    }
660    debug_assert_eq!(output.len(), decode_wrap_len::<Bit, Pad>(input.len()).1);
661    let mut inpos = 0;
662    let mut outpos = 0;
663    while inpos < input.len() {
664        let (inlen, outlen) = decode_wrap_len::<Bit, Pad>(input.len() - inpos);
665        match decode_pad_mut::<Bit, Msb, Pad>(
666            ctb,
667            values,
668            &input[inpos .. inpos + inlen],
669            &mut output[outpos .. outpos + outlen],
670        ) {
671            Ok(written) => {
672                inpos += inlen;
673                outpos += written;
674                break;
675            }
676            Err(partial) => {
677                inpos += partial.read;
678                outpos += partial.written;
679            }
680        }
681        let (ipos, opos) = decode_wrap_block::<Bit, Msb, Pad>(
682            ctb,
683            values,
684            &input[inpos ..],
685            &mut output[outpos ..],
686        )
687        .map_err(|mut error| {
688            error.position += inpos;
689            DecodePartial { read: inpos, written: outpos, error }
690        })?;
691        inpos += ipos;
692        outpos += opos;
693    }
694    let inpos = skip_ignore(values, input, inpos);
695    if inpos == input.len() {
696        Ok(outpos)
697    } else {
698        Err(DecodePartial {
699            read: inpos,
700            written: outpos,
701            error: DecodeError { position: inpos, kind: DecodeKind::Length },
702        })
703    }
704}
705
706/// Error converting from a dynamic encoding to a static one.
707#[derive(Debug, Copy, Clone, PartialEq, Eq)]
708pub enum ConvertError {
709    /// Different bit-width.
710    BitWidth,
711
712    /// Different bit-order.
713    BitOrder,
714
715    /// Different padding.
716    Padding,
717
718    /// Different wrap.
719    Wrap,
720
721    /// Different ignore.
722    Ignore,
723}
724
725/// Base-conversion encoding.
726///
727/// See [`Specification`] for technical details or how to define a new one.
728#[derive(Debug, Clone, PartialEq, Eq)]
729#[repr(transparent)]
730pub struct Encoding<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool> {
731    // The config match the fields in data. In particular, we have the following properties:
732    // - If Bit is Bit1, Bit2, or Bit4 then Pad is False.
733    // - If Wrap is True, then Ignore is True.
734    data: InternalEncoding,
735    _type: PhantomData<(Bit, Msb, Pad, Wrap, Ignore)>,
736}
737
738/// Base-conversion encoding
739///
740/// See [`Specification`] for technical details or how to define a new one.
741// Required fields:
742//   0 - 256 (256) symbols
743// 256 - 512 (256) values
744// 512 - 513 (  1) padding
745// 513 - 514 (  1) reserved(3),ctb(1),msb(1),bit(3)
746// Optional fields:
747// 514 - 515 (  1) width
748// 515 -   * (  N) separator
749// Invariants:
750// - symbols is 2^bit unique characters repeated 2^(8-bit) times
751// - values[128 ..] are INVALID
752// - values[0 .. 128] are either INVALID, IGNORE, PADDING, or < 2^bit
753// - padding is either < 128 or INVALID
754// - values[padding] is PADDING if padding < 128
755// - values and symbols are inverse
756// - ctb is true if 8 % bit == 0
757// - width is present if there is x such that values[x] is IGNORE
758// - width % dec(bit) == 0
759// - for all x in separator values[x] is IGNORE
760#[derive(Debug, Clone, PartialEq, Eq)]
761#[repr(transparent)]
762pub struct DynEncoding(InternalEncoding);
763
764#[cfg(feature = "alloc")]
765type InternalEncoding = Cow<'static, [u8]>;
766
767#[cfg(not(feature = "alloc"))]
768type InternalEncoding = &'static [u8];
769
770impl<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool>
771    Encoding<Bit, Msb, Pad, Wrap, Ignore>
772{
773    fn sym(&self) -> &[u8; 256] {
774        self.data[0 .. 256].try_into().unwrap()
775    }
776
777    fn val(&self) -> &[u8; 256] {
778        self.data[256 .. 512].try_into().unwrap()
779    }
780
781    fn pad(&self) -> Pad::If<u8, ()> {
782        Pad::make(|| self.data[512], || ())
783    }
784
785    fn ctb(&self) -> bool {
786        self.data[513] & 0x10 != 0
787    }
788
789    fn wrap(&self) -> Wrap::If<(usize, &[u8]), ()> {
790        Wrap::make(|| (self.data[514] as usize, &self.data[515 ..]), || ())
791    }
792
793    fn has_ignore(&self) -> bool {
794        self.data.len() >= 515
795    }
796
797    /// Minimum number of input and output blocks when encoding.
798    fn block_len(&self) -> (usize, usize) {
799        let bit = Bit::VAL;
800        match Wrap::open(self.wrap()) {
801            If::Then((col, end)) => (col / dec(bit) * enc(bit), col + end.len()),
802            If::Else(()) => (enc(bit), dec(bit)),
803        }
804    }
805
806    /// Returns the encoded length of an input of length `len`.
807    ///
808    /// See [`Self::encode_mut()`] for when to use it.
809    #[must_use]
810    pub fn encode_len(&self, len: usize) -> usize {
811        encode_wrap_len::<Bit, Pad, Wrap>(self.wrap(), len)
812    }
813
814    /// Encodes `input` in `output`.
815    ///
816    /// # Panics
817    ///
818    /// Panics if the `output` length does not match the result of [`Self::encode_len()`] for the
819    /// `input` length.
820    pub fn encode_mut_uninit<'a>(
821        &self, input: &[u8], output: &'a mut [MaybeUninit<u8>],
822    ) -> &'a mut [u8] {
823        assert_eq!(output.len(), self.encode_len(input.len()));
824        encode_wrap_mut::<Bit, Msb, Pad, Wrap>(self.sym(), self.pad(), self.wrap(), input, output);
825        unsafe { slice_assume_init_mut(output) }
826    }
827
828    /// Encodes `input` in `output`.
829    ///
830    /// # Panics
831    ///
832    /// Panics if the `output` length does not match the result of [`Self::encode_len()`] for the
833    /// `input` length.
834    pub fn encode_mut(&self, input: &[u8], output: &mut [u8]) {
835        let _ = self.encode_mut_uninit(input, unsafe { slice_uninit_mut(output) });
836    }
837
838    /// Appends the encoding of `input` to `output`.
839    #[cfg(feature = "alloc")]
840    pub fn encode_append(&self, input: &[u8], output: &mut String) {
841        let output = unsafe { output.as_mut_vec() };
842        let output_len = output.len();
843        let len = self.encode_len(input.len());
844        let actual_len = self.encode_mut_uninit(input, reserve_spare(output, len)).len();
845        debug_assert_eq!(actual_len, len);
846        unsafe { output.set_len(output_len + len) };
847    }
848
849    // /// Returns an object to encode a fragmented input and append it to `output`.
850    // ///
851    // /// See the documentation of [`Encoder`] for more details and examples.
852    // #[cfg(feature = "alloc")]
853    // pub fn new_encoder<'a>(
854    //     &'a self, output: &'a mut String,
855    // ) -> Encoder<'a, Bit, Msb, Pad, Wrap, Ignore> {
856    //     Encoder::new(self, output)
857    // }
858
859    /// Writes the encoding of `input` to `output` using a temporary `buffer`.
860    ///
861    /// # Panics
862    ///
863    /// Panics if the buffer is shorter than 510 bytes.
864    ///
865    /// # Errors
866    ///
867    /// Returns an error when writing to the output fails.
868    pub fn encode_write_buffer_uninit(
869        &self, input: &[u8], output: &mut impl core::fmt::Write, buffer: &mut [MaybeUninit<u8>],
870    ) -> core::fmt::Result {
871        assert!(510 <= buffer.len());
872        let (enc, dec) = self.block_len();
873        for input in input.chunks(buffer.len() / dec * enc) {
874            let buffer = &mut buffer[.. self.encode_len(input.len())];
875            let buffer = self.encode_mut_uninit(input, buffer);
876            output.write_str(unsafe { core::str::from_utf8_unchecked(buffer) })?;
877        }
878        Ok(())
879    }
880
881    /// Writes the encoding of `input` to `output` using a temporary `buffer`.
882    ///
883    /// # Panics
884    ///
885    /// Panics if the buffer is shorter than 510 bytes.
886    ///
887    /// # Errors
888    ///
889    /// Returns an error when writing to the output fails.
890    pub fn encode_write_buffer(
891        &self, input: &[u8], output: &mut impl core::fmt::Write, buffer: &mut [u8],
892    ) -> core::fmt::Result {
893        self.encode_write_buffer_uninit(input, output, unsafe { slice_uninit_mut(buffer) })
894    }
895
896    /// Writes the encoding of `input` to `output`.
897    ///
898    /// This allocates a buffer of 1024 bytes on the stack. If you want to control the buffer size
899    /// and location, use [`Self::encode_write_buffer()`] instead.
900    ///
901    /// # Errors
902    ///
903    /// Returns an error when writing to the output fails.
904    pub fn encode_write(
905        &self, input: &[u8], output: &mut impl core::fmt::Write,
906    ) -> core::fmt::Result {
907        self.encode_write_buffer(input, output, &mut [0; 1024])
908    }
909
910    /// Returns encoded `input`.
911    #[cfg(feature = "alloc")]
912    #[must_use]
913    pub fn encode(&self, input: &[u8]) -> String {
914        let mut output = Vec::new();
915        let len = self.encode_len(input.len());
916        let actual_len = self.encode_mut_uninit(input, reserve_spare(&mut output, len)).len();
917        debug_assert_eq!(actual_len, len);
918        unsafe { output.set_len(len) };
919        unsafe { String::from_utf8_unchecked(output) }
920    }
921
922    /// Returns the decoded length of an input of length `len`.
923    ///
924    /// See [`Self::decode_mut()`] for when to use it.
925    ///
926    /// # Errors
927    ///
928    /// Returns an error if `len` is invalid. The error [kind][DecodeError::kind] is
929    /// [`DecodeKind::Length`] and the error [position][DecodeError::position] is the greatest valid
930    /// input length.
931    pub fn decode_len(&self, len: usize) -> Result<usize, DecodeError> {
932        let (ilen, olen) = decode_wrap_len::<Bit, Pad>(len);
933        check!(
934            DecodeError { position: ilen, kind: DecodeKind::Length },
935            self.has_ignore() || len == ilen
936        );
937        Ok(olen)
938    }
939
940    /// Decodes `input` in `output`.
941    ///
942    /// Returns the decoded output. Its length may be smaller than the output length if the input
943    /// contained padding or ignored characters. The output bytes after the returned length are not
944    /// initialized and should not be read.
945    ///
946    /// # Panics
947    ///
948    /// Panics if the `output` length does not match the result of [`Self::decode_len()`] for the
949    /// `input` length. Also panics if `decode_len` fails for the `input` length.
950    ///
951    /// # Errors
952    ///
953    /// Returns an error if `input` is invalid. See [`Self::decode_mut()`] for more details.
954    pub fn decode_mut_uninit<'a>(
955        &self, input: &[u8], output: &'a mut [MaybeUninit<u8>],
956    ) -> Result<&'a mut [u8], DecodePartial> {
957        assert_eq!(Ok(output.len()), self.decode_len(input.len()));
958        let len = decode_wrap_mut::<Bit, Msb, Pad, Ignore>(self.ctb(), self.val(), input, output)?;
959        Ok(unsafe { slice_assume_init_mut(&mut output[.. len]) })
960    }
961
962    /// Decodes `input` in `output`.
963    ///
964    /// Returns the length of the decoded output. This length may be smaller than the output length
965    /// if the input contained padding or ignored characters. The output bytes after the returned
966    /// length are not initialized and should not be read.
967    ///
968    /// # Panics
969    ///
970    /// Panics if the `output` length does not match the result of [`Self::decode_len()`] for the
971    /// `input` length. Also panics if `decode_len` fails for the `input` length.
972    ///
973    /// # Errors
974    ///
975    /// Returns an error if `input` is invalid. See [`Self::decode()`] for more details. The are two
976    /// differences though:
977    ///
978    /// - [`DecodeKind::Length`] may be returned only if the encoding allows ignored characters,
979    ///   because otherwise this is already checked by [`Self::decode_len()`].
980    /// - The [`DecodePartial::read`] first bytes of the input have been successfully decoded to the
981    ///   [`DecodePartial::written`] first bytes of the output.
982    pub fn decode_mut(&self, input: &[u8], output: &mut [u8]) -> Result<usize, DecodePartial> {
983        Ok(self.decode_mut_uninit(input, unsafe { slice_uninit_mut(output) })?.len())
984    }
985
986    /// Returns decoded `input`.
987    ///
988    /// # Errors
989    ///
990    /// Returns an error if `input` is invalid. The error kind can be:
991    ///
992    /// - [`DecodeKind::Length`] if the input length is invalid. The [position] is the greatest
993    ///   valid input length.
994    /// - [`DecodeKind::Symbol`] if the input contains an invalid character. The [position] is the
995    ///   first invalid character.
996    /// - [`DecodeKind::Trailing`] if the input has non-zero trailing bits. This is only possible if
997    ///   the encoding checks trailing bits. The [position] is the first character containing
998    ///   non-zero trailing bits.
999    /// - [`DecodeKind::Padding`] if the input has an invalid padding length. This is only possible
1000    ///   if the encoding uses padding. The [position] is the first padding character of the first
1001    ///   padding of invalid length.
1002    ///
1003    /// [position]: DecodeError::position
1004    #[cfg(feature = "alloc")]
1005    pub fn decode(&self, input: &[u8]) -> Result<Vec<u8>, DecodeError> {
1006        let max_len = self.decode_len(input.len())?;
1007        let mut output = Vec::new();
1008        let len = self
1009            .decode_mut_uninit(input, reserve_spare(&mut output, max_len))
1010            .map_err(|partial| partial.error)?
1011            .len();
1012        unsafe { output.set_len(len) };
1013        Ok(output)
1014    }
1015
1016    /// TODO
1017    #[cfg(feature = "alloc")]
1018    #[must_use]
1019    pub fn specification(&self) -> Specification {
1020        DynEncoding::specification(self.into())
1021    }
1022
1023    /// TODO
1024    #[must_use]
1025    pub fn as_dyn(&self) -> &DynEncoding {
1026        self.into()
1027    }
1028
1029    #[doc(hidden)]
1030    #[must_use]
1031    pub const unsafe fn new_unchecked(data: &'static [u8]) -> Self {
1032        #[cfg(feature = "alloc")]
1033        let data = Cow::Borrowed(data);
1034        Encoding { data, _type: PhantomData }
1035    }
1036
1037    fn check_compatible(base: &DynEncoding) -> Result<(), ConvertError> {
1038        check!(ConvertError::BitWidth, base.bit() == Bit::VAL);
1039        check!(ConvertError::BitOrder, base.msb() == Msb::VAL);
1040        check!(ConvertError::Padding, base.pad().is_some() == Pad::VAL);
1041        check!(ConvertError::Wrap, base.wrap().is_some() == Wrap::VAL);
1042        check!(ConvertError::Ignore, base.has_ignore() == Ignore::VAL);
1043        Ok(())
1044    }
1045}
1046
1047impl DynEncoding {
1048    fn sym(&self) -> &[u8; 256] {
1049        self.0[0 .. 256].try_into().unwrap()
1050    }
1051
1052    fn val(&self) -> &[u8; 256] {
1053        self.0[256 .. 512].try_into().unwrap()
1054    }
1055
1056    fn pad(&self) -> Option<u8> {
1057        if self.0[512] < 128 { Some(self.0[512]) } else { None }
1058    }
1059
1060    fn ctb(&self) -> bool {
1061        self.0[513] & 0x10 != 0
1062    }
1063
1064    fn msb(&self) -> bool {
1065        self.0[513] & 0x8 != 0
1066    }
1067
1068    fn bit(&self) -> usize {
1069        (self.0[513] & 0x7) as usize
1070    }
1071
1072    /// Minimum number of input and output blocks when encoding
1073    fn block_len(&self) -> (usize, usize) {
1074        let bit = self.bit();
1075        match self.wrap() {
1076            Some((col, end)) => (col / dec(bit) * enc(bit), col + end.len()),
1077            None => (enc(bit), dec(bit)),
1078        }
1079    }
1080
1081    fn wrap(&self) -> Option<(usize, &[u8])> {
1082        if self.0.len() <= 515 {
1083            return None;
1084        }
1085        Some((self.0[514] as usize, &self.0[515 ..]))
1086    }
1087
1088    fn has_ignore(&self) -> bool {
1089        self.0.len() >= 515
1090    }
1091
1092    /// Returns the encoded length of an input of length `len`
1093    ///
1094    /// See [`encode_mut`] for when to use it.
1095    ///
1096    /// [`encode_mut`]: struct.Encoding.html#method.encode_mut
1097    #[must_use]
1098    pub fn encode_len(&self, len: usize) -> usize {
1099        dispatch!(self.encode_len(len))
1100    }
1101
1102    /// Encodes `input` in `output`
1103    ///
1104    /// # Panics
1105    ///
1106    /// Panics if the `output` length does not match the result of [`encode_len`] for the `input`
1107    /// length.
1108    ///
1109    /// # Examples
1110    ///
1111    /// ```rust
1112    /// use data_encoding_v3::BASE64;
1113    /// # let mut buffer = vec![0; 100];
1114    /// let input = b"Hello world";
1115    /// let output = &mut buffer[0 .. BASE64.encode_len(input.len())];
1116    /// BASE64.encode_mut(input, output);
1117    /// assert_eq!(output, b"SGVsbG8gd29ybGQ=");
1118    /// ```
1119    ///
1120    /// [`encode_len`]: struct.Encoding.html#method.encode_len
1121    #[allow(clippy::cognitive_complexity)]
1122    pub fn encode_mut(&self, input: &[u8], output: &mut [u8]) {
1123        dispatch!(self.encode_mut(input, output))
1124    }
1125
1126    /// Appends the encoding of `input` to `output`
1127    ///
1128    /// # Examples
1129    ///
1130    /// ```rust
1131    /// use data_encoding_v3::BASE64;
1132    /// # let mut buffer = vec![0; 100];
1133    /// let input = b"Hello world";
1134    /// let mut output = "Result: ".to_string();
1135    /// BASE64.encode_append(input, &mut output);
1136    /// assert_eq!(output, "Result: SGVsbG8gd29ybGQ=");
1137    /// ```
1138    #[cfg(feature = "alloc")]
1139    pub fn encode_append(&self, input: &[u8], output: &mut String) {
1140        let output = unsafe { output.as_mut_vec() };
1141        let output_len = output.len();
1142        output.resize(output_len + self.encode_len(input.len()), 0u8);
1143        self.encode_mut(input, &mut output[output_len ..]);
1144    }
1145
1146    /// Writes the encoding of `input` to `output`
1147    ///
1148    /// This allocates a buffer of 1024 bytes on the stack. If you want to control the buffer size
1149    /// and location, use [`Encoding::encode_write_buffer()`] instead.
1150    ///
1151    /// # Errors
1152    ///
1153    /// Returns an error when writing to the output fails.
1154    pub fn encode_write(
1155        &self, input: &[u8], output: &mut impl core::fmt::Write,
1156    ) -> core::fmt::Result {
1157        self.encode_write_buffer(input, output, &mut [0; 1024])
1158    }
1159
1160    /// Writes the encoding of `input` to `output` using a temporary `buffer`
1161    ///
1162    /// # Panics
1163    ///
1164    /// Panics if the buffer is shorter than 510 bytes.
1165    ///
1166    /// # Errors
1167    ///
1168    /// Returns an error when writing to the output fails.
1169    pub fn encode_write_buffer(
1170        &self, input: &[u8], output: &mut impl core::fmt::Write, buffer: &mut [u8],
1171    ) -> core::fmt::Result {
1172        assert!(510 <= buffer.len());
1173        let (enc, dec) = self.block_len();
1174        for input in input.chunks(buffer.len() / dec * enc) {
1175            let buffer = &mut buffer[.. self.encode_len(input.len())];
1176            self.encode_mut(input, buffer);
1177            output.write_str(unsafe { core::str::from_utf8_unchecked(buffer) })?;
1178        }
1179        Ok(())
1180    }
1181
1182    /// Returns encoded `input`
1183    ///
1184    /// # Examples
1185    ///
1186    /// ```rust
1187    /// use data_encoding_v3::BASE64;
1188    /// assert_eq!(BASE64.encode(b"Hello world"), "SGVsbG8gd29ybGQ=");
1189    /// ```
1190    #[cfg(feature = "alloc")]
1191    #[must_use]
1192    pub fn encode(&self, input: &[u8]) -> String {
1193        let mut output = vec![0u8; self.encode_len(input.len())];
1194        self.encode_mut(input, &mut output);
1195        unsafe { String::from_utf8_unchecked(output) }
1196    }
1197
1198    /// Returns the maximum decoded length of an input of length `len`
1199    ///
1200    /// See [`decode_mut`] for when to use it. In particular, the actual decoded length might be
1201    /// smaller if the actual input contains padding or ignored characters.
1202    ///
1203    /// # Errors
1204    ///
1205    /// Returns an error if `len` is invalid. The error kind is [`Length`] and the [position] is the
1206    /// greatest valid input length.
1207    ///
1208    /// [`decode_mut`]: struct.Encoding.html#method.decode_mut
1209    /// [`Length`]: enum.DecodeKind.html#variant.Length
1210    /// [position]: struct.DecodeError.html#structfield.position
1211    pub fn decode_len(&self, len: usize) -> Result<usize, DecodeError> {
1212        dispatch!(self.decode_len(len))
1213    }
1214
1215    /// Decodes `input` in `output`
1216    ///
1217    /// Returns the length of the decoded output. This length may be smaller than the output length
1218    /// if the input contained padding or ignored characters. The output bytes after the returned
1219    /// length are not initialized and should not be read.
1220    ///
1221    /// # Panics
1222    ///
1223    /// Panics if the `output` length does not match the result of [`decode_len`] for the `input`
1224    /// length. Also panics if `decode_len` fails for the `input` length.
1225    ///
1226    /// # Errors
1227    ///
1228    /// Returns an error if `input` is invalid. See [`decode`] for more details. The are two
1229    /// differences though:
1230    ///
1231    /// - [`Length`] may be returned only if the encoding allows ignored characters, because
1232    ///   otherwise this is already checked by [`decode_len`].
1233    /// - The [`read`] first bytes of the input have been successfully decoded to the [`written`]
1234    ///   first bytes of the output.
1235    ///
1236    /// # Examples
1237    ///
1238    /// ```rust
1239    /// use data_encoding_v3::BASE64;
1240    /// # let mut buffer = vec![0; 100];
1241    /// let input = b"SGVsbA==byB3b3JsZA==";
1242    /// let output = &mut buffer[0 .. BASE64.decode_len(input.len()).unwrap()];
1243    /// let len = BASE64.decode_mut(input, output).unwrap();
1244    /// assert_eq!(&output[0 .. len], b"Hello world");
1245    /// ```
1246    ///
1247    /// [`decode_len`]: struct.Encoding.html#method.decode_len
1248    /// [`decode`]: struct.Encoding.html#method.decode
1249    /// [`Length`]: enum.DecodeKind.html#variant.Length
1250    /// [`read`]: struct.DecodePartial.html#structfield.read
1251    /// [`written`]: struct.DecodePartial.html#structfield.written
1252    #[allow(clippy::cognitive_complexity)]
1253    pub fn decode_mut(&self, input: &[u8], output: &mut [u8]) -> Result<usize, DecodePartial> {
1254        dispatch!(self.decode_mut(input, output))
1255    }
1256
1257    /// Returns decoded `input`
1258    ///
1259    /// # Errors
1260    ///
1261    /// Returns an error if `input` is invalid. The error kind can be:
1262    ///
1263    /// - [`Length`] if the input length is invalid. The [position] is the greatest valid input
1264    ///   length.
1265    /// - [`Symbol`] if the input contains an invalid character. The [position] is the first invalid
1266    ///   character.
1267    /// - [`Trailing`] if the input has non-zero trailing bits. This is only possible if the
1268    ///   encoding checks trailing bits. The [position] is the first character containing non-zero
1269    ///   trailing bits.
1270    /// - [`Padding`] if the input has an invalid padding length. This is only possible if the
1271    ///   encoding uses padding. The [position] is the first padding character of the first padding
1272    ///   of invalid length.
1273    ///
1274    /// # Examples
1275    ///
1276    /// ```rust
1277    /// use data_encoding_v3::BASE64;
1278    /// assert_eq!(BASE64.decode(b"SGVsbA==byB3b3JsZA==").unwrap(), b"Hello world");
1279    /// ```
1280    ///
1281    /// [`Length`]: enum.DecodeKind.html#variant.Length
1282    /// [`Symbol`]: enum.DecodeKind.html#variant.Symbol
1283    /// [`Trailing`]: enum.DecodeKind.html#variant.Trailing
1284    /// [`Padding`]: enum.DecodeKind.html#variant.Padding
1285    /// [position]: struct.DecodeError.html#structfield.position
1286    #[cfg(feature = "alloc")]
1287    pub fn decode(&self, input: &[u8]) -> Result<Vec<u8>, DecodeError> {
1288        let mut output = vec![0u8; self.decode_len(input.len())?];
1289        let len = self.decode_mut(input, &mut output).map_err(|partial| partial.error)?;
1290        output.truncate(len);
1291        Ok(output)
1292    }
1293
1294    /// Returns the bit-width
1295    #[must_use]
1296    pub fn bit_width(&self) -> usize {
1297        self.bit()
1298    }
1299
1300    /// Returns whether the encoding is canonical
1301    ///
1302    /// An encoding is not canonical if one of the following conditions holds:
1303    ///
1304    /// - trailing bits are not checked
1305    /// - padding is used
1306    /// - characters are ignored
1307    /// - characters are translated
1308    #[must_use]
1309    pub fn is_canonical(&self) -> bool {
1310        if !self.ctb() {
1311            return false;
1312        }
1313        let bit = self.bit();
1314        let sym = self.sym();
1315        let val = self.val();
1316        for i in 0 .. 256 {
1317            if val[i] == INVALID {
1318                continue;
1319            }
1320            if val[i] >= 1 << bit {
1321                return false;
1322            }
1323            if sym[val[i] as usize] as usize != i {
1324                return false;
1325            }
1326        }
1327        true
1328    }
1329
1330    /// Returns the encoding specification
1331    #[allow(clippy::missing_panics_doc)] // no panic
1332    #[cfg(feature = "alloc")]
1333    #[must_use]
1334    pub fn specification(&self) -> Specification {
1335        let mut specification = Specification::new();
1336        specification
1337            .symbols
1338            .push_str(core::str::from_utf8(&self.sym()[0 .. 1 << self.bit()]).unwrap());
1339        specification.bit_order =
1340            if self.msb() { MostSignificantFirst } else { LeastSignificantFirst };
1341        specification.check_trailing_bits = self.ctb();
1342        if let Some(pad) = self.pad() {
1343            specification.padding = Some(pad as char);
1344        }
1345        for i in 0 .. 128u8 {
1346            if self.val()[i as usize] != IGNORE {
1347                continue;
1348            }
1349            specification.ignore.push(i as char);
1350        }
1351        if let Some((col, end)) = self.wrap() {
1352            specification.wrap.width = col;
1353            specification.wrap.separator = core::str::from_utf8(end).unwrap().to_owned();
1354        }
1355        for i in 0 .. 128u8 {
1356            let canonical = if self.val()[i as usize] < 1 << self.bit() {
1357                self.sym()[self.val()[i as usize] as usize]
1358            } else if self.val()[i as usize] == PADDING {
1359                self.pad().unwrap()
1360            } else {
1361                continue;
1362            };
1363            if i == canonical {
1364                continue;
1365            }
1366            specification.translate.from.push(i as char);
1367            specification.translate.to.push(canonical as char);
1368        }
1369        specification
1370    }
1371
1372    #[doc(hidden)]
1373    #[must_use]
1374    pub const unsafe fn internal_new(implementation: &'static [u8]) -> DynEncoding {
1375        #[cfg(feature = "alloc")]
1376        let encoding = DynEncoding(Cow::Borrowed(implementation));
1377        #[cfg(not(feature = "alloc"))]
1378        let encoding = DynEncoding(implementation);
1379        encoding
1380    }
1381
1382    #[doc(hidden)]
1383    #[must_use]
1384    pub fn internal_implementation(&self) -> &[u8] {
1385        &self.0
1386    }
1387}
1388
1389impl<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool> TryFrom<DynEncoding>
1390    for Encoding<Bit, Msb, Pad, Wrap, Ignore>
1391{
1392    type Error = ConvertError;
1393
1394    fn try_from(base: DynEncoding) -> Result<Self, Self::Error> {
1395        Encoding::<Bit, Msb, Pad, Wrap, Ignore>::check_compatible(&base)?;
1396        Ok(Encoding { data: base.0, _type: PhantomData })
1397    }
1398}
1399
1400impl<Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool>
1401    From<Encoding<Bit, Msb, Pad, Wrap, Ignore>> for DynEncoding
1402{
1403    fn from(base: Encoding<Bit, Msb, Pad, Wrap, Ignore>) -> Self {
1404        DynEncoding(base.data)
1405    }
1406}
1407
1408impl<'a, Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool> TryFrom<&'a DynEncoding>
1409    for &'a Encoding<Bit, Msb, Pad, Wrap, Ignore>
1410{
1411    type Error = ConvertError;
1412
1413    fn try_from(base: &'a DynEncoding) -> Result<Self, Self::Error> {
1414        Encoding::<Bit, Msb, Pad, Wrap, Ignore>::check_compatible(base)?;
1415        Ok(unsafe { cast(base) })
1416    }
1417}
1418
1419impl<'a, Bit: BitWidth, Msb: Bool, Pad: Bool, Wrap: Bool, Ignore: Bool>
1420    From<&'a Encoding<Bit, Msb, Pad, Wrap, Ignore>> for &'a DynEncoding
1421{
1422    fn from(base: &'a Encoding<Bit, Msb, Pad, Wrap, Ignore>) -> Self {
1423        unsafe { &*core::ptr::from_ref(base).cast::<DynEncoding>() }
1424    }
1425}
1426
1427/// Order in which bits are read from a byte
1428///
1429/// The base-conversion encoding is always little-endian. This means that the least significant
1430/// **byte** is always first. However, we can still choose whether, within a byte, this is the most
1431/// significant or the least significant **bit** that is first. If the terminology is confusing,
1432/// testing on an asymmetrical example should be enough to choose the correct value.
1433///
1434/// # Examples
1435///
1436/// In the following example, we can see that a base with the `MostSignificantFirst` bit-order has
1437/// the most significant bit first in the encoded output. In particular, the output is in the same
1438/// order as the bits in the byte. The opposite happens with the `LeastSignificantFirst` bit-order.
1439/// The least significant bit is first and the output is in the reverse order.
1440///
1441/// ```rust
1442/// use data_encoding_v3::{BitOrder, Specification};
1443/// let mut spec = Specification::new();
1444/// spec.symbols.push_str("01");
1445/// spec.bit_order = BitOrder::MostSignificantFirst;  // default
1446/// let msb = spec.encoding().unwrap();
1447/// spec.bit_order = BitOrder::LeastSignificantFirst;
1448/// let lsb = spec.encoding().unwrap();
1449/// assert_eq!(msb.encode(&[0b01010011]), "01010011");
1450/// assert_eq!(lsb.encode(&[0b01010011]), "11001010");
1451/// ```
1452#[derive(Debug, Copy, Clone, PartialEq, Eq)]
1453#[cfg(feature = "alloc")]
1454pub enum BitOrder {
1455    /// Most significant bit first
1456    ///
1457    /// This is the most common and most intuitive bit-order. In particular, this is the bit-order
1458    /// used by [RFC4648] and thus the usual hexadecimal, base64, base32, base64url, and base32hex
1459    /// encodings. This is the default bit-order when [specifying](struct.Specification.html) a
1460    /// base.
1461    ///
1462    /// [RFC4648]: https://tools.ietf.org/html/rfc4648
1463    MostSignificantFirst,
1464
1465    /// Least significant bit first
1466    ///
1467    /// # Examples
1468    ///
1469    /// DNSCurve [base32] uses least significant bit first:
1470    ///
1471    /// ```rust
1472    /// use data_encoding_v3::BASE32_DNSCURVE;
1473    /// assert_eq!(BASE32_DNSCURVE.encode(&[0x64, 0x88]), "4321");
1474    /// assert_eq!(BASE32_DNSCURVE.decode(b"4321").unwrap(), vec![0x64, 0x88]);
1475    /// ```
1476    ///
1477    /// [base32]: constant.BASE32_DNSCURVE.html
1478    LeastSignificantFirst,
1479}
1480#[cfg(feature = "alloc")]
1481use crate::BitOrder::*;
1482
1483/// How to translate characters when decoding
1484///
1485/// The order matters. The first character of the `from` field is translated to the first character
1486/// of the `to` field. The second to the second. Etc.
1487///
1488/// See [Specification](struct.Specification.html) for more information.
1489#[derive(Debug, Clone)]
1490#[cfg(feature = "alloc")]
1491pub struct Translate {
1492    /// Characters to translate from
1493    pub from: String,
1494
1495    /// Characters to translate to
1496    pub to: String,
1497}
1498
1499/// How to wrap the output when encoding
1500///
1501/// See [Specification](struct.Specification.html) for more information.
1502#[derive(Debug, Clone)]
1503#[cfg(feature = "alloc")]
1504pub struct Wrap {
1505    /// Wrapping width
1506    ///
1507    /// Must be a multiple of:
1508    ///
1509    /// - 8 for a bit-width of 1 (binary), 3 (octal), and 5 (base32)
1510    /// - 4 for a bit-width of 2 (base4) and 6 (base64)
1511    /// - 2 for a bit-width of 4 (hexadecimal)
1512    ///
1513    /// Wrapping is disabled if null.
1514    pub width: usize,
1515
1516    /// Wrapping characters
1517    ///
1518    /// Wrapping is disabled if empty.
1519    pub separator: String,
1520}
1521
1522/// Base-conversion specification
1523///
1524/// It is possible to define custom encodings given a specification. To do so, it is important to
1525/// understand the theory first.
1526///
1527/// # Theory
1528///
1529/// Each subsection has an equivalent subsection in the [Practice](#practice) section.
1530///
1531/// ## Basics
1532///
1533/// The main idea of a [base-conversion] encoding is to see `[u8]` as numbers written in
1534/// little-endian base256 and convert them in another little-endian base. For performance reasons,
1535/// this crate restricts this other base to be of size 2 (binary), 4 (base4), 8 (octal), 16
1536/// (hexadecimal), 32 (base32), or 64 (base64). The converted number is written as `[u8]` although
1537/// it doesn't use all the 256 possible values of `u8`. This crate encodes to ASCII, so only values
1538/// smaller than 128 are allowed.
1539///
1540/// More precisely, we need the following elements:
1541///
1542/// - The bit-width N: 1 for binary, 2 for base4, 3 for octal, 4 for hexadecimal, 5 for base32, and
1543///   6 for base64
1544/// - The [bit-order](enum.BitOrder.html): most or least significant bit first
1545/// - The symbols function S from [0, 2<sup>N</sup>) (called values and written `uN`) to symbols
1546///   (represented as `u8` although only ASCII symbols are allowed, i.e. smaller than 128)
1547/// - The values partial function V from ASCII to [0, 2<sup>N</sup>), i.e. from `u8` to `uN`
1548/// - Whether trailing bits are checked: trailing bits are leading zeros in theory, but since
1549///   numbers are little-endian they come last
1550///
1551/// For the encoding to be correct (i.e. encoding then decoding gives back the initial input),
1552/// V(S(i)) must be defined and equal to i for all i in [0, 2<sup>N</sup>). For the encoding to be
1553/// [canonical][canonical] (i.e. different inputs decode to different outputs, or equivalently,
1554/// decoding then encoding gives back the initial input), trailing bits must be checked and if V(i)
1555/// is defined then S(V(i)) is equal to i for all i.
1556///
1557/// Encoding and decoding are given by the following pipeline:
1558///
1559/// ```text
1560/// [u8] <--1--> [[bit; 8]] <--2--> [[bit; N]] <--3--> [uN] <--4--> [u8]
1561/// 1: Map bit-order between each u8 and [bit; 8]
1562/// 2: Base conversion between base 2^8 and base 2^N (check trailing bits)
1563/// 3: Map bit-order between each [bit; N] and uN
1564/// 4: Map symbols/values between each uN and u8 (values must be defined)
1565/// ```
1566///
1567/// ## Extensions
1568///
1569/// All these extensions make the encoding not canonical.
1570///
1571/// ### Padding
1572///
1573/// Padding is useful if the following conditions are met:
1574///
1575/// - the bit-width is 3 (octal), 5 (base32), or 6 (base64)
1576/// - the length of the data to encode is not known in advance
1577/// - the data must be sent without buffering
1578///
1579/// Bases for which the bit-width N does not divide 8 may not concatenate encoded data. This comes
1580/// from the fact that it is not possible to make the difference between trailing bits and encoding
1581/// bits. Padding solves this issue by adding a new character to discriminate between trailing bits
1582/// and encoding bits. The idea is to work by blocks of lcm(8, N) bits, where lcm(8, N) is the least
1583/// common multiple of 8 and N. When such block is not complete, it is padded.
1584///
1585/// To preserve correctness, the padding character must not be a symbol.
1586///
1587/// ### Ignore characters when decoding
1588///
1589/// Ignoring characters when decoding is useful if after encoding some characters are added for
1590/// convenience or any other reason (like wrapping). In that case we want to first ignore those
1591/// characters before decoding.
1592///
1593/// To preserve correctness, ignored characters must not contain symbols or the padding character.
1594///
1595/// ### Wrap output when encoding
1596///
1597/// Wrapping output when encoding is useful if the output is meant to be printed in a document where
1598/// width is limited (typically 80-columns documents). In that case, the wrapping width and the
1599/// wrapping separator have to be defined.
1600///
1601/// To preserve correctness, the wrapping separator characters must be ignored (see previous
1602/// subsection). As such, wrapping separator characters must also not contain symbols or the padding
1603/// character.
1604///
1605/// ### Translate characters when decoding
1606///
1607/// Translating characters when decoding is useful when encoded data may be copied by a humain
1608/// instead of a machine. Humans tend to confuse some characters for others. In that case we want to
1609/// translate those characters before decoding.
1610///
1611/// To preserve correctness, the characters we translate _from_ must not contain symbols or the
1612/// padding character, and the characters we translate _to_ must only contain symbols or the padding
1613/// character.
1614///
1615/// # Practice
1616///
1617/// ## Basics
1618///
1619/// ```rust
1620/// use data_encoding_v3::{DynEncoding, Specification};
1621/// fn make_encoding(symbols: &str) -> DynEncoding {
1622///     let mut spec = Specification::new();
1623///     spec.symbols.push_str(symbols);
1624///     spec.encoding().unwrap()
1625/// }
1626/// let binary = make_encoding("01");
1627/// let octal = make_encoding("01234567");
1628/// let hexadecimal = make_encoding("0123456789abcdef");
1629/// assert_eq!(binary.encode(b"Bit"), "010000100110100101110100");
1630/// assert_eq!(octal.encode(b"Bit"), "20464564");
1631/// assert_eq!(hexadecimal.encode(b"Bit"), "426974");
1632/// ```
1633///
1634/// The `binary` base has 2 symbols `0` and `1` with value 0 and 1 respectively. The `octal` base
1635/// has 8 symbols `0` to `7` with value 0 to 7. The `hexadecimal` base has 16 symbols `0` to `9` and
1636/// `a` to `f` with value 0 to 15. The following diagram gives the idea of how encoding works in the
1637/// previous example (note that we can actually write such diagram only because the bit-order is
1638/// most significant first):
1639///
1640/// ```text
1641/// [      octal] |  2  :  0  :  4  :  6  :  4  :  5  :  6  :  4  |
1642/// [     binary] |0 1 0 0 0 0 1 0|0 1 1 0 1 0 0 1|0 1 1 1 0 1 0 0|
1643/// [hexadecimal] |   4   :   2   |   6   :   9   |   7   :   4   |
1644///                ^-- LSB                                       ^-- MSB
1645/// ```
1646///
1647/// Note that in theory, these little-endian numbers are read from right to left (the most
1648/// significant bit is at the right). Since leading zeros are meaningless (in our usual decimal
1649/// notation 0123 is the same as 123), it explains why trailing bits must be zero. Trailing bits may
1650/// occur when the bit-width of a base does not divide 8. Only binary, base4, and hexadecimal don't
1651/// have trailing bits issues. So let's consider octal and base64, which have trailing bits in
1652/// similar circumstances:
1653///
1654/// ```rust
1655/// use data_encoding_v3::{Specification, BASE64_NOPAD};
1656/// let octal = {
1657///     let mut spec = Specification::new();
1658///     spec.symbols.push_str("01234567");
1659///     spec.encoding().unwrap()
1660/// };
1661/// assert_eq!(BASE64_NOPAD.encode(b"B"), "Qg");
1662/// assert_eq!(octal.encode(b"B"), "204");
1663/// ```
1664///
1665/// We have the following diagram, where the base64 values are written between parentheses:
1666///
1667/// ```text
1668/// [base64] |   Q(16)   :   g(32)   : [has 4 zero trailing bits]
1669/// [ octal] |  2  :  0  :  4  :       [has 1 zero trailing bit ]
1670///          |0 1 0 0 0 0 1 0|0 0 0 0
1671/// [ ascii] |       B       |
1672///                           ^-^-^-^-- leading zeros / trailing bits
1673/// ```
1674///
1675/// ## Extensions
1676///
1677/// ### Padding
1678///
1679/// For octal and base64, lcm(8, 3) == lcm(8, 6) == 24 bits or 3 bytes. For base32, lcm(8, 5) is 40
1680/// bits or 5 bytes. Let's consider octal and base64:
1681///
1682/// ```rust
1683/// use data_encoding_v3::{Specification, BASE64};
1684/// let octal = {
1685///     let mut spec = Specification::new();
1686///     spec.symbols.push_str("01234567");
1687///     spec.padding = Some('=');
1688///     spec.encoding().unwrap()
1689/// };
1690/// // We start encoding but we only have "B" for now.
1691/// assert_eq!(BASE64.encode(b"B"), "Qg==");
1692/// assert_eq!(octal.encode(b"B"), "204=====");
1693/// // Now we have "it".
1694/// assert_eq!(BASE64.encode(b"it"), "aXQ=");
1695/// assert_eq!(octal.encode(b"it"), "322720==");
1696/// // By concatenating everything, we may decode the original data.
1697/// assert_eq!(BASE64.decode(b"Qg==aXQ=").unwrap(), b"Bit");
1698/// assert_eq!(octal.decode(b"204=====322720==").unwrap(), b"Bit");
1699/// ```
1700///
1701/// We have the following diagrams:
1702///
1703/// ```text
1704/// [base64] |   Q(16)   :   g(32)   :     =     :     =     |
1705/// [ octal] |  2  :  0  :  4  :  =  :  =  :  =  :  =  :  =  |
1706///          |0 1 0 0 0 0 1 0|. . . . . . . .|. . . . . . . .|
1707/// [ ascii] |       B       |        end of block aligned --^
1708///          ^-- beginning of block aligned
1709///
1710/// [base64] |   a(26)   :   X(23)   :   Q(16)   :     =     |
1711/// [ octal] |  3  :  2  :  2  :  7  :  2  :  0  :  =  :  =  |
1712///          |0 1 1 0 1 0 0 1|0 1 1 1 0 1 0 0|. . . . . . . .|
1713/// [ ascii] |       i       |       t       |
1714/// ```
1715///
1716/// ### Ignore characters when decoding
1717///
1718/// The typical use-case is to ignore newlines (`\r` and `\n`). But to keep the example small, we
1719/// will ignore spaces.
1720///
1721/// ```rust
1722/// let mut spec = data_encoding_v3::HEXLOWER.specification();
1723/// spec.ignore.push_str(" \t");
1724/// let base = spec.encoding().unwrap();
1725/// assert_eq!(base.decode(b"42 69 74"), base.decode(b"426974"));
1726/// ```
1727///
1728/// ### Wrap output when encoding
1729///
1730/// The typical use-case is to wrap after 64 or 76 characters with a newline (`\r\n` or `\n`). But
1731/// to keep the example small, we will wrap after 8 characters with a space.
1732///
1733/// ```rust
1734/// let mut spec = data_encoding_v3::BASE64.specification();
1735/// spec.wrap.width = 8;
1736/// spec.wrap.separator.push_str(" ");
1737/// let base64 = spec.encoding().unwrap();
1738/// assert_eq!(base64.encode(b"Hey you"), "SGV5IHlv dQ== ");
1739/// ```
1740///
1741/// Note that the output always ends with the separator.
1742///
1743/// ### Translate characters when decoding
1744///
1745/// The typical use-case is to translate lowercase to uppercase or reciprocally, but it is also used
1746/// for letters that look alike, like `O0` or `Il1`. Let's illustrate both examples.
1747///
1748/// ```rust
1749/// let mut spec = data_encoding_v3::HEXLOWER.specification();
1750/// spec.translate.from.push_str("ABCDEFOIl");
1751/// spec.translate.to.push_str("abcdef011");
1752/// let base = spec.encoding().unwrap();
1753/// assert_eq!(base.decode(b"BOIl"), base.decode(b"b011"));
1754/// ```
1755///
1756/// [base-conversion]: https://en.wikipedia.org/wiki/Positional_notation#Base_conversion
1757/// [canonical]: https://tools.ietf.org/html/rfc4648#section-3.5
1758#[derive(Debug, Clone)]
1759#[cfg(feature = "alloc")]
1760pub struct Specification {
1761    /// Symbols
1762    ///
1763    /// The number of symbols must be 2, 4, 8, 16, 32, or 64. Symbols must be ASCII characters
1764    /// (smaller than 128) and they must be unique.
1765    pub symbols: String,
1766
1767    /// Bit-order
1768    ///
1769    /// The default is to use most significant bit first since it is the most common.
1770    pub bit_order: BitOrder,
1771
1772    /// Check trailing bits
1773    ///
1774    /// The default is to check trailing bits. This field is ignored when unnecessary (i.e. for
1775    /// base2, base4, and base16).
1776    pub check_trailing_bits: bool,
1777
1778    /// Padding
1779    ///
1780    /// The default is to not use padding. The padding character must be ASCII and must not be a
1781    /// symbol.
1782    pub padding: Option<char>,
1783
1784    /// Characters to ignore when decoding
1785    ///
1786    /// The default is to not ignore characters when decoding. The characters to ignore must be
1787    /// ASCII and must not be symbols or the padding character.
1788    pub ignore: String,
1789
1790    /// How to wrap the output when encoding
1791    ///
1792    /// The default is to not wrap the output when encoding. The wrapping characters must be ASCII
1793    /// and must not be symbols or the padding character.
1794    pub wrap: Wrap,
1795
1796    /// How to translate characters when decoding
1797    ///
1798    /// The default is to not translate characters when decoding. The characters to translate from
1799    /// must be ASCII and must not have already been assigned a semantics. The characters to
1800    /// translate to must be ASCII and must have been assigned a semantics (symbol, padding
1801    /// character, or ignored character).
1802    pub translate: Translate,
1803}
1804
1805#[cfg(feature = "alloc")]
1806impl Default for Specification {
1807    fn default() -> Self {
1808        Self::new()
1809    }
1810}
1811
1812#[derive(Debug, Copy, Clone)]
1813#[cfg(feature = "alloc")]
1814enum SpecificationErrorImpl {
1815    BadSize,
1816    NotAscii,
1817    Duplicate(u8),
1818    ExtraPadding,
1819    WrapLength,
1820    WrapWidth(u8),
1821    FromTo,
1822    Undefined(u8),
1823}
1824#[cfg(feature = "alloc")]
1825use crate::SpecificationErrorImpl::*;
1826
1827/// Specification error
1828#[derive(Debug, Copy, Clone)]
1829#[cfg(feature = "alloc")]
1830pub struct SpecificationError(SpecificationErrorImpl);
1831
1832#[cfg(feature = "alloc")]
1833impl core::fmt::Display for SpecificationError {
1834    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
1835        match self.0 {
1836            BadSize => write!(f, "invalid number of symbols"),
1837            NotAscii => write!(f, "non-ascii character"),
1838            Duplicate(c) => write!(f, "{:?} has conflicting definitions", c as char),
1839            ExtraPadding => write!(f, "unnecessary padding"),
1840            WrapLength => write!(f, "invalid wrap width or separator length"),
1841            WrapWidth(x) => write!(f, "wrap width not a multiple of {x}"),
1842            FromTo => write!(f, "translate from/to length mismatch"),
1843            Undefined(c) => write!(f, "{:?} is undefined", c as char),
1844        }
1845    }
1846}
1847
1848#[cfg(feature = "std")]
1849impl std::error::Error for SpecificationError {
1850    fn description(&self) -> &str {
1851        match self.0 {
1852            BadSize => "invalid number of symbols",
1853            NotAscii => "non-ascii character",
1854            Duplicate(_) => "conflicting definitions",
1855            ExtraPadding => "unnecessary padding",
1856            WrapLength => "invalid wrap width or separator length",
1857            WrapWidth(_) => "wrap width not a multiple",
1858            FromTo => "translate from/to length mismatch",
1859            Undefined(_) => "undefined character",
1860        }
1861    }
1862}
1863
1864#[cfg(feature = "alloc")]
1865impl Specification {
1866    /// Returns a default specification
1867    #[must_use]
1868    pub fn new() -> Specification {
1869        Specification {
1870            symbols: String::new(),
1871            bit_order: MostSignificantFirst,
1872            check_trailing_bits: true,
1873            padding: None,
1874            ignore: String::new(),
1875            wrap: Wrap { width: 0, separator: String::new() },
1876            translate: Translate { from: String::new(), to: String::new() },
1877        }
1878    }
1879
1880    /// Returns the specified encoding
1881    ///
1882    /// # Errors
1883    ///
1884    /// Returns an error if the specification is invalid.
1885    pub fn encoding(&self) -> Result<DynEncoding, SpecificationError> {
1886        let symbols = self.symbols.as_bytes();
1887        let bit: u8 = match symbols.len() {
1888            2 => 1,
1889            4 => 2,
1890            8 => 3,
1891            16 => 4,
1892            32 => 5,
1893            64 => 6,
1894            _ => return Err(SpecificationError(BadSize)),
1895        };
1896        let mut values = [INVALID; 128];
1897        let set = |v: &mut [u8; 128], i: u8, x: u8| {
1898            check!(SpecificationError(NotAscii), i < 128);
1899            if v[i as usize] == x {
1900                return Ok(());
1901            }
1902            check!(SpecificationError(Duplicate(i)), v[i as usize] == INVALID);
1903            v[i as usize] = x;
1904            Ok(())
1905        };
1906        for (v, symbols) in symbols.iter().enumerate() {
1907            #[allow(clippy::cast_possible_truncation)] // no truncation
1908            set(&mut values, *symbols, v as u8)?;
1909        }
1910        let msb = self.bit_order == MostSignificantFirst;
1911        let ctb = self.check_trailing_bits || 8 % bit == 0;
1912        let pad = match self.padding {
1913            None => None,
1914            Some(pad) => {
1915                check!(SpecificationError(ExtraPadding), 8 % bit != 0);
1916                check!(SpecificationError(NotAscii), pad.len_utf8() == 1);
1917                set(&mut values, pad as u8, PADDING)?;
1918                Some(pad as u8)
1919            }
1920        };
1921        for i in self.ignore.bytes() {
1922            set(&mut values, i, IGNORE)?;
1923        }
1924        let wrap = if self.wrap.separator.is_empty() || self.wrap.width == 0 {
1925            None
1926        } else {
1927            let col = self.wrap.width;
1928            let end = self.wrap.separator.as_bytes();
1929            check!(SpecificationError(WrapLength), col < 256 && end.len() < 256);
1930            #[allow(clippy::cast_possible_truncation)] // no truncation
1931            let col = col as u8;
1932            #[allow(clippy::cast_possible_truncation)] // no truncation
1933            let dec = dec(bit as usize) as u8;
1934            check!(SpecificationError(WrapWidth(dec)), col % dec == 0);
1935            for &i in end {
1936                set(&mut values, i, IGNORE)?;
1937            }
1938            Some((col, end))
1939        };
1940        let from = self.translate.from.as_bytes();
1941        let to = self.translate.to.as_bytes();
1942        check!(SpecificationError(FromTo), from.len() == to.len());
1943        for i in 0 .. from.len() {
1944            check!(SpecificationError(NotAscii), to[i] < 128);
1945            let v = values[to[i] as usize];
1946            check!(SpecificationError(Undefined(to[i])), v != INVALID);
1947            set(&mut values, from[i], v)?;
1948        }
1949        let mut encoding = Vec::new();
1950        for _ in 0 .. 256 / symbols.len() {
1951            encoding.extend_from_slice(symbols);
1952        }
1953        encoding.extend_from_slice(&values);
1954        encoding.extend_from_slice(&[INVALID; 128]);
1955        match pad {
1956            None => encoding.push(INVALID),
1957            Some(pad) => encoding.push(pad),
1958        }
1959        encoding.push(bit);
1960        if msb {
1961            encoding[513] |= 0x08;
1962        }
1963        if ctb {
1964            encoding[513] |= 0x10;
1965        }
1966        if let Some((col, end)) = wrap {
1967            encoding.push(col);
1968            encoding.extend_from_slice(end);
1969        } else if values.contains(&IGNORE) {
1970            encoding.push(0);
1971        }
1972        Ok(DynEncoding(Cow::Owned(encoding)))
1973    }
1974}
1975
1976/// Hexadecimal encoding.
1977pub type Hex = Encoding<Bit4, True, False, False, False>;
1978
1979/// Base32 encoding.
1980pub type Base32 = Encoding<Bit5, True, True, False, False>;
1981
1982/// Base32 encoding (no padding).
1983pub type Base32NoPad = Encoding<Bit5, True, False, False, False>;
1984
1985/// Base32 encoding (LSB first, no padding).
1986pub type Base32LsbNoPad = Encoding<Bit5, False, False, False, False>;
1987
1988/// Base64 encoding.
1989pub type Base64 = Encoding<Bit6, True, True, False, False>;
1990
1991/// Base64 encoding (no padding).
1992pub type Base64NoPad = Encoding<Bit6, True, False, False, False>;
1993
1994/// Base64 encoding (wrap).
1995pub type Base64Wrap = Encoding<Bit6, True, True, True, True>;
1996
1997/// Lowercase hexadecimal encoding
1998///
1999/// This encoding is a static version of:
2000///
2001/// ```rust
2002/// # use data_encoding_v3::{Specification, HEXLOWER};
2003/// let mut spec = Specification::new();
2004/// spec.symbols.push_str("0123456789abcdef");
2005/// assert_eq!(HEXLOWER.as_dyn(), &spec.encoding().unwrap());
2006/// ```
2007///
2008/// # Examples
2009///
2010/// ```rust
2011/// use data_encoding_v3::HEXLOWER;
2012/// let deadbeef = vec![0xde, 0xad, 0xbe, 0xef];
2013/// assert_eq!(HEXLOWER.decode(b"deadbeef").unwrap(), deadbeef);
2014/// assert_eq!(HEXLOWER.encode(&deadbeef), "deadbeef");
2015/// ```
2016pub static HEXLOWER: Hex = unsafe { Hex::new_unchecked(HEXLOWER_IMPL) };
2017const HEXLOWER_IMPL: &[u8] = &[
2018    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54,
2019    55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100,
2020    101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51,
2021    52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97,
2022    98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48,
2023    49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55,
2024    56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100,
2025    101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51,
2026    52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97,
2027    98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48,
2028    49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55,
2029    56, 57, 97, 98, 99, 100, 101, 102, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2030    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2031    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 0, 1, 2,
2032    3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2033    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2034    128, 128, 128, 128, 128, 10, 11, 12, 13, 14, 15, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2035    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2036    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2037    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2038    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2039    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2040    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2041    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2042    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 28,
2043];
2044
2045/// Lowercase hexadecimal encoding with case-insensitive decoding
2046///
2047/// This encoding is a static version of:
2048///
2049/// ```rust
2050/// # use data_encoding_v3::{Specification, HEXLOWER_PERMISSIVE};
2051/// let mut spec = Specification::new();
2052/// spec.symbols.push_str("0123456789abcdef");
2053/// spec.translate.from.push_str("ABCDEF");
2054/// spec.translate.to.push_str("abcdef");
2055/// assert_eq!(HEXLOWER_PERMISSIVE.as_dyn(), &spec.encoding().unwrap());
2056/// ```
2057///
2058/// # Examples
2059///
2060/// ```rust
2061/// use data_encoding_v3::HEXLOWER_PERMISSIVE;
2062/// let deadbeef = vec![0xde, 0xad, 0xbe, 0xef];
2063/// assert_eq!(HEXLOWER_PERMISSIVE.decode(b"DeadBeef").unwrap(), deadbeef);
2064/// assert_eq!(HEXLOWER_PERMISSIVE.encode(&deadbeef), "deadbeef");
2065/// ```
2066///
2067/// You can also define a shorter name:
2068///
2069/// ```rust
2070/// pub use data_encoding_v3::HEXLOWER_PERMISSIVE as HEX;
2071/// ```
2072pub static HEXLOWER_PERMISSIVE: Hex = unsafe { Hex::new_unchecked(HEXLOWER_PERMISSIVE_IMPL) };
2073const HEXLOWER_PERMISSIVE_IMPL: &[u8] = &[
2074    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54,
2075    55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100,
2076    101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51,
2077    52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97,
2078    98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48,
2079    49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55,
2080    56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100,
2081    101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51,
2082    52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97,
2083    98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48,
2084    49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 48, 49, 50, 51, 52, 53, 54, 55,
2085    56, 57, 97, 98, 99, 100, 101, 102, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2086    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2087    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 0, 1, 2,
2088    3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 10, 11, 12, 13, 14, 15, 128, 128, 128,
2089    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2090    128, 128, 128, 128, 10, 11, 12, 13, 14, 15, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2091    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2092    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2093    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2094    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2095    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2096    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2097    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2098    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 28,
2099];
2100
2101/// Uppercase hexadecimal encoding
2102///
2103/// This encoding is a static version of:
2104///
2105/// ```rust
2106/// # use data_encoding_v3::{Specification, HEXUPPER};
2107/// let mut spec = Specification::new();
2108/// spec.symbols.push_str("0123456789ABCDEF");
2109/// assert_eq!(HEXUPPER.as_dyn(), &spec.encoding().unwrap());
2110/// ```
2111///
2112/// It is compliant with [RFC4648] and known as "base16" or "hex".
2113///
2114/// # Examples
2115///
2116/// ```rust
2117/// use data_encoding_v3::HEXUPPER;
2118/// let deadbeef = vec![0xde, 0xad, 0xbe, 0xef];
2119/// assert_eq!(HEXUPPER.decode(b"DEADBEEF").unwrap(), deadbeef);
2120/// assert_eq!(HEXUPPER.encode(&deadbeef), "DEADBEEF");
2121/// ```
2122///
2123/// [RFC4648]: https://tools.ietf.org/html/rfc4648#section-8
2124pub static HEXUPPER: Hex = unsafe { Hex::new_unchecked(HEXUPPER_IMPL) };
2125const HEXUPPER_IMPL: &[u8] = &[
2126    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2127    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2128    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2129    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2130    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2131    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2132    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2133    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2134    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2135    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2136    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 128, 128, 128, 128, 128, 128,
2137    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2138    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2139    128, 128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 10, 11,
2140    12, 13, 14, 15, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2141    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2142    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2143    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2144    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2145    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2146    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2147    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2148    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2149    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 28,
2150];
2151
2152/// Uppercase hexadecimal encoding with case-insensitive decoding
2153///
2154/// This encoding is a static version of:
2155///
2156/// ```rust
2157/// # use data_encoding_v3::{Specification, HEXUPPER_PERMISSIVE};
2158/// let mut spec = Specification::new();
2159/// spec.symbols.push_str("0123456789ABCDEF");
2160/// spec.translate.from.push_str("abcdef");
2161/// spec.translate.to.push_str("ABCDEF");
2162/// assert_eq!(HEXUPPER_PERMISSIVE.as_dyn(), &spec.encoding().unwrap());
2163/// ```
2164///
2165/// # Examples
2166///
2167/// ```rust
2168/// use data_encoding_v3::HEXUPPER_PERMISSIVE;
2169/// let deadbeef = vec![0xde, 0xad, 0xbe, 0xef];
2170/// assert_eq!(HEXUPPER_PERMISSIVE.decode(b"DeadBeef").unwrap(), deadbeef);
2171/// assert_eq!(HEXUPPER_PERMISSIVE.encode(&deadbeef), "DEADBEEF");
2172/// ```
2173pub static HEXUPPER_PERMISSIVE: Hex = unsafe { Hex::new_unchecked(HEXUPPER_PERMISSIVE_IMPL) };
2174const HEXUPPER_PERMISSIVE_IMPL: &[u8] = &[
2175    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2176    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2177    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2178    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2179    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2180    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2181    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2182    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2183    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55,
2184    56, 57, 65, 66, 67, 68, 69, 70, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2185    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 128, 128, 128, 128, 128, 128,
2186    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2187    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2188    128, 128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 10, 11,
2189    12, 13, 14, 15, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2190    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 10, 11, 12, 13, 14, 15, 128, 128, 128, 128,
2191    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2192    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2193    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2194    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2195    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2196    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2197    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2198    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 28,
2199];
2200
2201/// Padded base32 encoding
2202///
2203/// This encoding is a static version of:
2204///
2205/// ```rust
2206/// # use data_encoding_v3::{Specification, BASE32};
2207/// let mut spec = Specification::new();
2208/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZ234567");
2209/// spec.padding = Some('=');
2210/// assert_eq!(BASE32.as_dyn(), &spec.encoding().unwrap());
2211/// ```
2212///
2213/// It conforms to [RFC4648].
2214///
2215/// [RFC4648]: https://tools.ietf.org/html/rfc4648#section-6
2216pub static BASE32: Base32 = unsafe { Base32::new_unchecked(BASE32_IMPL) };
2217const BASE32_IMPL: &[u8] = &[
2218    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2219    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2220    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72,
2221    73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55,
2222    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2223    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2224    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72,
2225    73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55,
2226    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2227    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2228    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 128, 128, 128, 128, 128, 128,
2229    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2230    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2231    128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 128, 128, 128, 128, 128, 130, 128, 128,
2232    128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
2233    25, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2234    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2235    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2236    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2237    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2238    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2239    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2240    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2241    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 29,
2242];
2243
2244/// Unpadded base32 encoding
2245///
2246/// This encoding is a static version of:
2247///
2248/// ```rust
2249/// # use data_encoding_v3::{Specification, BASE32_NOPAD};
2250/// let mut spec = Specification::new();
2251/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZ234567");
2252/// assert_eq!(BASE32_NOPAD.as_dyn(), &spec.encoding().unwrap());
2253/// ```
2254pub static BASE32_NOPAD: Base32NoPad = unsafe { Base32NoPad::new_unchecked(BASE32_NOPAD_IMPL) };
2255const BASE32_NOPAD_IMPL: &[u8] = &[
2256    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2257    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2258    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72,
2259    73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55,
2260    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2261    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2262    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72,
2263    73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55,
2264    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2265    89, 90, 50, 51, 52, 53, 54, 55, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80,
2266    81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 50, 51, 52, 53, 54, 55, 128, 128, 128, 128, 128, 128,
2267    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2268    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2269    128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 128, 128, 128, 128, 128, 128, 128, 128,
2270    128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24,
2271    25, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2272    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2273    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2274    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2275    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2276    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2277    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2278    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2279    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 29,
2280];
2281
2282/// Padded base32hex encoding
2283///
2284/// This encoding is a static version of:
2285///
2286/// ```rust
2287/// # use data_encoding_v3::{Specification, BASE32HEX};
2288/// let mut spec = Specification::new();
2289/// spec.symbols.push_str("0123456789ABCDEFGHIJKLMNOPQRSTUV");
2290/// spec.padding = Some('=');
2291/// assert_eq!(BASE32HEX.as_dyn(), &spec.encoding().unwrap());
2292/// ```
2293///
2294/// It conforms to [RFC4648].
2295///
2296/// [RFC4648]: https://tools.ietf.org/html/rfc4648#section-7
2297pub static BASE32HEX: Base32 = unsafe { Base32::new_unchecked(BASE32HEX_IMPL) };
2298const BASE32HEX_IMPL: &[u8] = &[
2299    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2300    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2301    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55,
2302    56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86,
2303    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2304    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2305    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55,
2306    56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86,
2307    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2308    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2309    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 128, 128, 128, 128, 128, 128,
2310    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2311    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2312    128, 128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 130, 128, 128, 128, 10, 11,
2313    12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 128, 128, 128,
2314    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2315    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2316    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2317    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2318    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2319    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2320    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2321    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2322    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 29,
2323];
2324
2325/// Unpadded base32hex encoding
2326///
2327/// This encoding is a static version of:
2328///
2329/// ```rust
2330/// # use data_encoding_v3::{Specification, BASE32HEX_NOPAD};
2331/// let mut spec = Specification::new();
2332/// spec.symbols.push_str("0123456789ABCDEFGHIJKLMNOPQRSTUV");
2333/// assert_eq!(BASE32HEX_NOPAD.as_dyn(), &spec.encoding().unwrap());
2334/// ```
2335pub static BASE32HEX_NOPAD: Base32NoPad =
2336    unsafe { Base32NoPad::new_unchecked(BASE32HEX_NOPAD_IMPL) };
2337const BASE32HEX_NOPAD_IMPL: &[u8] = &[
2338    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2339    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2340    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55,
2341    56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86,
2342    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2343    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2344    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55,
2345    56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86,
2346    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
2347    79, 80, 81, 82, 83, 84, 85, 86, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 65, 66, 67, 68, 69, 70,
2348    71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 128, 128, 128, 128, 128, 128,
2349    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2350    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2351    128, 128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 10, 11,
2352    12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 128, 128, 128,
2353    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2354    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2355    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2356    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2357    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2358    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2359    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2360    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2361    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 29,
2362];
2363
2364/// DNSSEC base32 encoding
2365///
2366/// This encoding is a static version of:
2367///
2368/// ```rust
2369/// # use data_encoding_v3::{Specification, BASE32_DNSSEC};
2370/// let mut spec = Specification::new();
2371/// spec.symbols.push_str("0123456789abcdefghijklmnopqrstuv");
2372/// spec.translate.from.push_str("ABCDEFGHIJKLMNOPQRSTUV");
2373/// spec.translate.to.push_str("abcdefghijklmnopqrstuv");
2374/// assert_eq!(BASE32_DNSSEC.as_dyn(), &spec.encoding().unwrap());
2375/// ```
2376///
2377/// It conforms to [RFC5155]:
2378///
2379/// - It uses a base32 extended hex alphabet.
2380/// - It is case-insensitive when decoding and uses lowercase when encoding.
2381/// - It does not use padding.
2382///
2383/// [RFC5155]: https://tools.ietf.org/html/rfc5155
2384pub static BASE32_DNSSEC: Base32NoPad = unsafe { Base32NoPad::new_unchecked(BASE32_DNSSEC_IMPL) };
2385const BASE32_DNSSEC_IMPL: &[u8] = &[
2386    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107,
2387    108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57,
2388    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2389    116, 117, 118, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 103, 104,
2390    105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 48, 49, 50, 51, 52, 53,
2391    54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112,
2392    113, 114, 115, 116, 117, 118, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101,
2393    102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 48, 49,
2394    50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109,
2395    110, 111, 112, 113, 114, 115, 116, 117, 118, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98,
2396    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2397    118, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106,
2398    107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117, 118, 128, 128, 128, 128, 128, 128, 128,
2399    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2400    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2401    128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 10, 11, 12, 13,
2402    14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 128, 128, 128, 128,
2403    128, 128, 128, 128, 128, 128, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25,
2404    26, 27, 28, 29, 30, 31, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2405    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2406    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2407    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2408    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2409    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2410    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2411    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 29,
2412];
2413
2414#[allow(clippy::doc_markdown)]
2415/// DNSCurve base32 encoding
2416///
2417/// This encoding is a static version of:
2418///
2419/// ```rust
2420/// # use data_encoding_v3::{BitOrder, Specification, BASE32_DNSCURVE};
2421/// let mut spec = Specification::new();
2422/// spec.symbols.push_str("0123456789bcdfghjklmnpqrstuvwxyz");
2423/// spec.bit_order = BitOrder::LeastSignificantFirst;
2424/// spec.translate.from.push_str("BCDFGHJKLMNPQRSTUVWXYZ");
2425/// spec.translate.to.push_str("bcdfghjklmnpqrstuvwxyz");
2426/// assert_eq!(BASE32_DNSCURVE.as_dyn(), &spec.encoding().unwrap());
2427/// ```
2428///
2429/// It conforms to [DNSCurve].
2430///
2431/// [DNSCurve]: https://dnscurve.org/in-implement.html
2432pub static BASE32_DNSCURVE: Base32LsbNoPad =
2433    unsafe { Base32LsbNoPad::new_unchecked(BASE32_DNSCURVE_IMPL) };
2434const BASE32_DNSCURVE_IMPL: &[u8] = &[
2435    48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 98, 99, 100, 102, 103, 104, 106, 107, 108, 109, 110,
2436    112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57,
2437    98, 99, 100, 102, 103, 104, 106, 107, 108, 109, 110, 112, 113, 114, 115, 116, 117, 118, 119,
2438    120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 98, 99, 100, 102, 103, 104, 106, 107,
2439    108, 109, 110, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53,
2440    54, 55, 56, 57, 98, 99, 100, 102, 103, 104, 106, 107, 108, 109, 110, 112, 113, 114, 115, 116,
2441    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 98, 99, 100, 102, 103,
2442    104, 106, 107, 108, 109, 110, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 48, 49,
2443    50, 51, 52, 53, 54, 55, 56, 57, 98, 99, 100, 102, 103, 104, 106, 107, 108, 109, 110, 112, 113,
2444    114, 115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 98, 99,
2445    100, 102, 103, 104, 106, 107, 108, 109, 110, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121,
2446    122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 98, 99, 100, 102, 103, 104, 106, 107, 108, 109,
2447    110, 112, 113, 114, 115, 116, 117, 118, 119, 120, 121, 122, 128, 128, 128, 128, 128, 128, 128,
2448    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2449    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2450    128, 128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 128, 128, 128, 128, 128, 128, 128, 128, 10, 11,
2451    12, 128, 13, 14, 15, 128, 16, 17, 18, 19, 20, 128, 21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31,
2452    128, 128, 128, 128, 128, 128, 128, 10, 11, 12, 128, 13, 14, 15, 128, 16, 17, 18, 19, 20, 128,
2453    21, 22, 23, 24, 25, 26, 27, 28, 29, 30, 31, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2454    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2455    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2456    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2457    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2458    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2459    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2460    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 21,
2461];
2462
2463/// Padded base64 encoding
2464///
2465/// This encoding is a static version of:
2466///
2467/// ```rust
2468/// # use data_encoding_v3::{Specification, BASE64};
2469/// let mut spec = Specification::new();
2470/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/");
2471/// spec.padding = Some('=');
2472/// assert_eq!(BASE64.as_dyn(), &spec.encoding().unwrap());
2473/// ```
2474///
2475/// It conforms to [RFC4648].
2476///
2477/// [RFC4648]: https://tools.ietf.org/html/rfc4648#section-4
2478pub static BASE64: Base64 = unsafe { Base64::new_unchecked(BASE64_IMPL) };
2479const BASE64_IMPL: &[u8] = &[
2480    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2481    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2482    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66,
2483    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2484    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2485    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67,
2486    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2487    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2488    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67, 68,
2489    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2490    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2491    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 128, 128, 128, 128,
2492    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2493    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2494    128, 62, 128, 128, 128, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 130, 128,
2495    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2496    24, 25, 128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2497    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2498    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2499    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2500    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2501    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2502    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2503    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2504    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 30,
2505];
2506
2507/// Unpadded base64 encoding
2508///
2509/// This encoding is a static version of:
2510///
2511/// ```rust
2512/// # use data_encoding_v3::{Specification, BASE64_NOPAD};
2513/// let mut spec = Specification::new();
2514/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/");
2515/// assert_eq!(BASE64_NOPAD.as_dyn(), &spec.encoding().unwrap());
2516/// ```
2517pub static BASE64_NOPAD: Base64NoPad = unsafe { Base64NoPad::new_unchecked(BASE64_NOPAD_IMPL) };
2518const BASE64_NOPAD_IMPL: &[u8] = &[
2519    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2520    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2521    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66,
2522    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2523    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2524    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67,
2525    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2526    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2527    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67, 68,
2528    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2529    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2530    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 128, 128, 128, 128,
2531    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2532    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2533    128, 62, 128, 128, 128, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 128, 128,
2534    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2535    24, 25, 128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2536    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2537    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2538    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2539    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2540    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2541    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2542    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2543    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 30,
2544];
2545
2546/// MIME base64 encoding
2547///
2548/// This encoding is a static version of:
2549///
2550/// ```rust
2551/// # use data_encoding_v3::{Specification, BASE64_MIME};
2552/// let mut spec = Specification::new();
2553/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/");
2554/// spec.padding = Some('=');
2555/// spec.wrap.width = 76;
2556/// spec.wrap.separator.push_str("\r\n");
2557/// assert_eq!(BASE64_MIME.as_dyn(), &spec.encoding().unwrap());
2558/// ```
2559///
2560/// It does not exactly conform to [RFC2045] because it does not print the header
2561/// and does not ignore all characters.
2562///
2563/// [RFC2045]: https://tools.ietf.org/html/rfc2045
2564pub static BASE64_MIME: Base64Wrap = unsafe { Base64Wrap::new_unchecked(BASE64_MIME_IMPL) };
2565const BASE64_MIME_IMPL: &[u8] = &[
2566    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2567    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2568    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66,
2569    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2570    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2571    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67,
2572    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2573    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2574    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67, 68,
2575    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2576    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2577    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 128, 128, 128, 128,
2578    128, 128, 128, 128, 128, 128, 129, 128, 128, 129, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2579    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2580    128, 62, 128, 128, 128, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 130, 128,
2581    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2582    24, 25, 128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2583    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2584    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2585    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2586    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2587    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2588    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2589    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2590    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 30, 76, 13, 10,
2591];
2592
2593/// MIME base64 encoding without trailing bits check
2594///
2595/// This encoding is a static version of:
2596///
2597/// ```rust
2598/// # use data_encoding_v3::{Specification, BASE64_MIME_PERMISSIVE};
2599/// let mut spec = Specification::new();
2600/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/");
2601/// spec.padding = Some('=');
2602/// spec.wrap.width = 76;
2603/// spec.wrap.separator.push_str("\r\n");
2604/// spec.check_trailing_bits = false;
2605/// assert_eq!(BASE64_MIME_PERMISSIVE.as_dyn(), &spec.encoding().unwrap());
2606/// ```
2607///
2608/// It does not exactly conform to [RFC2045] because it does not print the header
2609/// and does not ignore all characters.
2610///
2611/// [RFC2045]: https://tools.ietf.org/html/rfc2045
2612pub static BASE64_MIME_PERMISSIVE: Base64Wrap =
2613    unsafe { Base64Wrap::new_unchecked(BASE64_MIME_PERMISSIVE_IMPL) };
2614const BASE64_MIME_PERMISSIVE_IMPL: &[u8] = &[
2615    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2616    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2617    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66,
2618    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2619    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2620    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67,
2621    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2622    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2623    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 65, 66, 67, 68,
2624    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2625    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2626    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 43, 47, 128, 128, 128, 128,
2627    128, 128, 128, 128, 128, 128, 129, 128, 128, 129, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2628    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2629    128, 62, 128, 128, 128, 63, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 130, 128,
2630    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2631    24, 25, 128, 128, 128, 128, 128, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2632    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2633    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2634    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2635    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2636    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2637    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2638    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2639    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 14, 76, 13, 10,
2640];
2641
2642/// Padded base64url encoding
2643///
2644/// This encoding is a static version of:
2645///
2646/// ```rust
2647/// # use data_encoding_v3::{Specification, BASE64URL};
2648/// let mut spec = Specification::new();
2649/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_");
2650/// spec.padding = Some('=');
2651/// assert_eq!(BASE64URL.as_dyn(), &spec.encoding().unwrap());
2652/// ```
2653///
2654/// It conforms to [RFC4648].
2655///
2656/// [RFC4648]: https://tools.ietf.org/html/rfc4648#section-5
2657pub static BASE64URL: Base64 = unsafe { Base64::new_unchecked(BASE64URL_IMPL) };
2658const BASE64URL_IMPL: &[u8] = &[
2659    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2660    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2661    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66,
2662    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2663    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2664    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66, 67,
2665    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2666    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2667    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66, 67, 68,
2668    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2669    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2670    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 128, 128, 128, 128,
2671    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2672    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2673    128, 128, 128, 62, 128, 128, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 130, 128,
2674    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2675    24, 25, 128, 128, 128, 128, 63, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2676    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2677    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2678    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2679    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2680    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2681    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2682    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2683    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 61, 30,
2684];
2685
2686/// Unpadded base64url encoding
2687///
2688/// This encoding is a static version of:
2689///
2690/// ```rust
2691/// # use data_encoding_v3::{Specification, BASE64URL_NOPAD};
2692/// let mut spec = Specification::new();
2693/// spec.symbols.push_str("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789-_");
2694/// assert_eq!(BASE64URL_NOPAD.as_dyn(), &spec.encoding().unwrap());
2695/// ```
2696pub static BASE64URL_NOPAD: Base64NoPad =
2697    unsafe { Base64NoPad::new_unchecked(BASE64URL_NOPAD_IMPL) };
2698const BASE64URL_NOPAD_IMPL: &[u8] = &[
2699    65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88,
2700    89, 90, 97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114,
2701    115, 116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66,
2702    67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90,
2703    97, 98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115,
2704    116, 117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66, 67,
2705    68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97,
2706    98, 99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116,
2707    117, 118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 65, 66, 67, 68,
2708    69, 70, 71, 72, 73, 74, 75, 76, 77, 78, 79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89, 90, 97, 98,
2709    99, 100, 101, 102, 103, 104, 105, 106, 107, 108, 109, 110, 111, 112, 113, 114, 115, 116, 117,
2710    118, 119, 120, 121, 122, 48, 49, 50, 51, 52, 53, 54, 55, 56, 57, 45, 95, 128, 128, 128, 128,
2711    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2712    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2713    128, 128, 128, 62, 128, 128, 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, 128, 128, 128, 128, 128,
2714    128, 128, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19, 20, 21, 22, 23,
2715    24, 25, 128, 128, 128, 128, 63, 128, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39,
2716    40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2717    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2718    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2719    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2720    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2721    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2722    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128,
2723    128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 128, 30,
2724];