From 369d11587339ce74f8ebc76f2607fe55545eaf7d Mon Sep 17 00:00:00 2001 From: garhve Date: Tue, 20 Dec 2022 11:04:25 +0800 Subject: Build small project following the book --- .../target/doc/src/cfg_if/lib.rs.html | 354 + .../target/doc/src/getrandom/error.rs.html | 385 + .../target/doc/src/getrandom/error_impls.rs.html | 51 + .../target/doc/src/getrandom/lib.rs.html | 585 ++ .../target/doc/src/getrandom/linux_android.rs.html | 97 + .../target/doc/src/getrandom/use_file.rs.html | 281 + .../target/doc/src/getrandom/util.rs.html | 131 + .../target/doc/src/getrandom/util_libc.rs.html | 323 + .../target/doc/src/guessing_game/main.rs.html | 76 + .../target/doc/src/libc/fixed_width_ints.rs.html | 200 + .../guessing_game/target/doc/src/libc/lib.rs.html | 316 + .../target/doc/src/libc/macros.rs.html | 688 ++ .../target/doc/src/libc/unix/align.rs.html | 14 + .../src/libc/unix/linux_like/linux/align.rs.html | 302 + .../unix/linux_like/linux/arch/generic/mod.rs.html | 576 ++ .../libc/unix/linux_like/linux/arch/mod.rs.html | 32 + .../libc/unix/linux_like/linux/gnu/align.rs.html | 28 + .../libc/unix/linux_like/linux/gnu/b64/mod.rs.html | 254 + .../linux_like/linux/gnu/b64/x86_64/align.rs.html | 50 + .../linux_like/linux/gnu/b64/x86_64/mod.rs.html | 1668 ++++ .../linux/gnu/b64/x86_64/not_x32.rs.html | 902 ++ .../src/libc/unix/linux_like/linux/gnu/mod.rs.html | 2820 ++++++ .../doc/src/libc/unix/linux_like/linux/mod.rs.html | 8986 ++++++++++++++++++++ .../unix/linux_like/linux/non_exhaustive.rs.html | 20 + .../doc/src/libc/unix/linux_like/mod.rs.html | 3660 ++++++++ .../target/doc/src/libc/unix/mod.rs.html | 3108 +++++++ .../target/doc/src/ppv_lite86/lib.rs.html | 46 + .../target/doc/src/ppv_lite86/soft.rs.html | 946 +++ .../target/doc/src/ppv_lite86/types.rs.html | 598 ++ .../target/doc/src/ppv_lite86/x86_64/mod.rs.html | 876 ++ .../target/doc/src/ppv_lite86/x86_64/sse2.rs.html | 3408 ++++++++ .../doc/src/rand/distributions/bernoulli.rs.html | 441 + .../src/rand/distributions/distribution.rs.html | 547 ++ .../doc/src/rand/distributions/float.rs.html | 627 ++ .../doc/src/rand/distributions/integer.rs.html | 551 ++ .../target/doc/src/rand/distributions/mod.rs.html | 439 + .../doc/src/rand/distributions/other.rs.html | 733 ++ .../doc/src/rand/distributions/slice.rs.html | 237 + .../doc/src/rand/distributions/uniform.rs.html | 3319 ++++++++ .../doc/src/rand/distributions/utils.rs.html | 861 ++ .../doc/src/rand/distributions/weighted.rs.html | 97 + .../src/rand/distributions/weighted_index.rs.html | 919 ++ .../guessing_game/target/doc/src/rand/lib.rs.html | 431 + .../target/doc/src/rand/prelude.rs.html | 71 + .../guessing_game/target/doc/src/rand/rng.rs.html | 1203 +++ .../target/doc/src/rand/rngs/adapter/mod.rs.html | 35 + .../target/doc/src/rand/rngs/adapter/read.rs.html | 303 + .../doc/src/rand/rngs/adapter/reseeding.rs.html | 775 ++ .../target/doc/src/rand/rngs/mock.rs.html | 177 + .../target/doc/src/rand/rngs/mod.rs.html | 241 + .../target/doc/src/rand/rngs/std.rs.html | 199 + .../target/doc/src/rand/rngs/thread.rs.html | 289 + .../target/doc/src/rand/seq/index.rs.html | 1359 +++ .../target/doc/src/rand/seq/mod.rs.html | 2715 ++++++ .../target/doc/src/rand_chacha/chacha.rs.html | 1267 +++ .../target/doc/src/rand_chacha/guts.rs.html | 549 ++ .../target/doc/src/rand_chacha/lib.rs.html | 69 + .../target/doc/src/rand_core/block.rs.html | 1081 +++ .../target/doc/src/rand_core/error.rs.html | 459 + .../target/doc/src/rand_core/impls.rs.html | 417 + .../target/doc/src/rand_core/le.rs.html | 115 + .../target/doc/src/rand_core/lib.rs.html | 1065 +++ .../target/doc/src/rand_core/os.rs.html | 173 + 63 files changed, 53545 insertions(+) create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/cfg_if/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error_impls.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/linux_android.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/use_file.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util_libc.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/guessing_game/main.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/fixed_width_ints.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/macros.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/align.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/align.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/generic/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/align.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/align.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/not_x32.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/non_exhaustive.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/soft.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/types.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/sse2.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/bernoulli.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/distribution.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/float.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/integer.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/other.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/slice.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/uniform.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/utils.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted_index.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/prelude.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rng.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/read.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/reseeding.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mock.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/std.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/thread.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/index.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/mod.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/chacha.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/guts.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/block.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/error.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/impls.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/le.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/lib.rs.html create mode 100644 rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/os.rs.html (limited to 'rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src') diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/cfg_if/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/cfg_if/lib.rs.html new file mode 100644 index 0000000..8c9fb7c --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/cfg_if/lib.rs.html @@ -0,0 +1,354 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+
//! A macro for defining `#[cfg]` if-else statements.
+//!
+//! The macro provided by this crate, `cfg_if`, is similar to the `if/elif` C
+//! preprocessor macro by allowing definition of a cascade of `#[cfg]` cases,
+//! emitting the implementation which matches first.
+//!
+//! This allows you to conveniently provide a long list `#[cfg]`'d blocks of code
+//! without having to rewrite each clause multiple times.
+//!
+//! # Example
+//!
+//! ```
+//! cfg_if::cfg_if! {
+//!     if #[cfg(unix)] {
+//!         fn foo() { /* unix specific functionality */ }
+//!     } else if #[cfg(target_pointer_width = "32")] {
+//!         fn foo() { /* non-unix, 32-bit functionality */ }
+//!     } else {
+//!         fn foo() { /* fallback implementation */ }
+//!     }
+//! }
+//!
+//! # fn main() {}
+//! ```
+
+#![no_std]
+#![doc(html_root_url = "https://docs.rs/cfg-if")]
+#![deny(missing_docs)]
+#![cfg_attr(test, deny(warnings))]
+
+/// The main macro provided by this crate. See crate documentation for more
+/// information.
+#[macro_export]
+macro_rules! cfg_if {
+    // match if/else chains with a final `else`
+    ($(
+        if #[cfg($meta:meta)] { $($tokens:tt)* }
+    ) else * else {
+        $($tokens2:tt)*
+    }) => {
+        $crate::cfg_if! {
+            @__items
+            () ;
+            $( ( ($meta) ($($tokens)*) ), )*
+            ( () ($($tokens2)*) ),
+        }
+    };
+
+    // match if/else chains lacking a final `else`
+    (
+        if #[cfg($i_met:meta)] { $($i_tokens:tt)* }
+        $(
+            else if #[cfg($e_met:meta)] { $($e_tokens:tt)* }
+        )*
+    ) => {
+        $crate::cfg_if! {
+            @__items
+            () ;
+            ( ($i_met) ($($i_tokens)*) ),
+            $( ( ($e_met) ($($e_tokens)*) ), )*
+            ( () () ),
+        }
+    };
+
+    // Internal and recursive macro to emit all the items
+    //
+    // Collects all the negated cfgs in a list at the beginning and after the
+    // semicolon is all the remaining items
+    (@__items ($($not:meta,)*) ; ) => {};
+    (@__items ($($not:meta,)*) ; ( ($($m:meta),*) ($($tokens:tt)*) ), $($rest:tt)*) => {
+        // Emit all items within one block, applying an appropriate #[cfg]. The
+        // #[cfg] will require all `$m` matchers specified and must also negate
+        // all previous matchers.
+        #[cfg(all($($m,)* not(any($($not),*))))] $crate::cfg_if! { @__identity $($tokens)* }
+
+        // Recurse to emit all other items in `$rest`, and when we do so add all
+        // our `$m` matchers to the list of `$not` matchers as future emissions
+        // will have to negate everything we just matched as well.
+        $crate::cfg_if! { @__items ($($not,)* $($m,)*) ; $($rest)* }
+    };
+
+    // Internal macro to make __apply work out right for different match types,
+    // because of how macros matching/expand stuff.
+    (@__identity $($tokens:tt)*) => {
+        $($tokens)*
+    };
+}
+
+#[cfg(test)]
+mod tests {
+    cfg_if! {
+        if #[cfg(test)] {
+            use core::option::Option as Option2;
+            fn works1() -> Option2<u32> { Some(1) }
+        } else {
+            fn works1() -> Option<u32> { None }
+        }
+    }
+
+    cfg_if! {
+        if #[cfg(foo)] {
+            fn works2() -> bool { false }
+        } else if #[cfg(test)] {
+            fn works2() -> bool { true }
+        } else {
+            fn works2() -> bool { false }
+        }
+    }
+
+    cfg_if! {
+        if #[cfg(foo)] {
+            fn works3() -> bool { false }
+        } else {
+            fn works3() -> bool { true }
+        }
+    }
+
+    cfg_if! {
+        if #[cfg(test)] {
+            use core::option::Option as Option3;
+            fn works4() -> Option3<u32> { Some(1) }
+        }
+    }
+
+    cfg_if! {
+        if #[cfg(foo)] {
+            fn works5() -> bool { false }
+        } else if #[cfg(test)] {
+            fn works5() -> bool { true }
+        }
+    }
+
+    #[test]
+    fn it_works() {
+        assert!(works1().is_some());
+        assert!(works2());
+        assert!(works3());
+        assert!(works4().is_some());
+        assert!(works5());
+    }
+
+    #[test]
+    #[allow(clippy::assertions_on_constants)]
+    fn test_usage_within_a_function() {
+        cfg_if! {if #[cfg(debug_assertions)] {
+            // we want to put more than one thing here to make sure that they
+            // all get configured properly.
+            assert!(cfg!(debug_assertions));
+            assert_eq!(4, 2+2);
+        } else {
+            assert!(works1().is_some());
+            assert_eq!(10, 5+5);
+        }}
+    }
+
+    trait Trait {
+        fn blah(&self);
+    }
+
+    #[allow(dead_code)]
+    struct Struct;
+
+    impl Trait for Struct {
+        cfg_if! {
+            if #[cfg(feature = "blah")] {
+                fn blah(&self) {
+                    unimplemented!();
+                }
+            } else {
+                fn blah(&self) {
+                    unimplemented!();
+                }
+            }
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error.rs.html new file mode 100644 index 0000000..4f73e10 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error.rs.html @@ -0,0 +1,385 @@ +error.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+use core::{fmt, num::NonZeroU32};
+
+/// A small and `no_std` compatible error type
+///
+/// The [`Error::raw_os_error()`] will indicate if the error is from the OS, and
+/// if so, which error code the OS gave the application. If such an error is
+/// encountered, please consult with your system documentation.
+///
+/// Internally this type is a NonZeroU32, with certain values reserved for
+/// certain purposes, see [`Error::INTERNAL_START`] and [`Error::CUSTOM_START`].
+///
+/// *If this crate's `"std"` Cargo feature is enabled*, then:
+/// - [`getrandom::Error`][Error] implements
+///   [`std::error::Error`](https://doc.rust-lang.org/std/error/trait.Error.html)
+/// - [`std::io::Error`](https://doc.rust-lang.org/std/io/struct.Error.html) implements
+///   [`From<getrandom::Error>`](https://doc.rust-lang.org/std/convert/trait.From.html).
+#[derive(Copy, Clone, Eq, PartialEq)]
+pub struct Error(NonZeroU32);
+
+const fn internal_error(n: u16) -> Error {
+    // SAFETY: code > 0 as INTERNAL_START > 0 and adding n won't overflow a u32.
+    let code = Error::INTERNAL_START + (n as u32);
+    Error(unsafe { NonZeroU32::new_unchecked(code) })
+}
+
+impl Error {
+    /// This target/platform is not supported by `getrandom`.
+    pub const UNSUPPORTED: Error = internal_error(0);
+    /// The platform-specific `errno` returned a non-positive value.
+    pub const ERRNO_NOT_POSITIVE: Error = internal_error(1);
+    /// Call to iOS [`SecRandomCopyBytes`](https://developer.apple.com/documentation/security/1399291-secrandomcopybytes) failed.
+    pub const IOS_SEC_RANDOM: Error = internal_error(3);
+    /// Call to Windows [`RtlGenRandom`](https://docs.microsoft.com/en-us/windows/win32/api/ntsecapi/nf-ntsecapi-rtlgenrandom) failed.
+    pub const WINDOWS_RTL_GEN_RANDOM: Error = internal_error(4);
+    /// RDRAND instruction failed due to a hardware issue.
+    pub const FAILED_RDRAND: Error = internal_error(5);
+    /// RDRAND instruction unsupported on this target.
+    pub const NO_RDRAND: Error = internal_error(6);
+    /// The environment does not support the Web Crypto API.
+    pub const WEB_CRYPTO: Error = internal_error(7);
+    /// Calling Web Crypto API `crypto.getRandomValues` failed.
+    pub const WEB_GET_RANDOM_VALUES: Error = internal_error(8);
+    /// On VxWorks, call to `randSecure` failed (random number generator is not yet initialized).
+    pub const VXWORKS_RAND_SECURE: Error = internal_error(11);
+    /// Node.js does not have the `crypto` CommonJS module.
+    pub const NODE_CRYPTO: Error = internal_error(12);
+    /// Calling Node.js function `crypto.randomFillSync` failed.
+    pub const NODE_RANDOM_FILL_SYNC: Error = internal_error(13);
+    /// Called from an ES module on Node.js. This is unsupported, see:
+    /// <https://docs.rs/getrandom#nodejs-es-module-support>.
+    pub const NODE_ES_MODULE: Error = internal_error(14);
+
+    /// Codes below this point represent OS Errors (i.e. positive i32 values).
+    /// Codes at or above this point, but below [`Error::CUSTOM_START`] are
+    /// reserved for use by the `rand` and `getrandom` crates.
+    pub const INTERNAL_START: u32 = 1 << 31;
+
+    /// Codes at or above this point can be used by users to define their own
+    /// custom errors.
+    pub const CUSTOM_START: u32 = (1 << 31) + (1 << 30);
+
+    /// Extract the raw OS error code (if this error came from the OS)
+    ///
+    /// This method is identical to [`std::io::Error::raw_os_error()`][1], except
+    /// that it works in `no_std` contexts. If this method returns `None`, the
+    /// error value can still be formatted via the `Display` implementation.
+    ///
+    /// [1]: https://doc.rust-lang.org/std/io/struct.Error.html#method.raw_os_error
+    #[inline]
+    pub fn raw_os_error(self) -> Option<i32> {
+        if self.0.get() < Self::INTERNAL_START {
+            match () {
+                #[cfg(target_os = "solid_asp3")]
+                // On SOLID, negate the error code again to obtain the original
+                // error code.
+                () => Some(-(self.0.get() as i32)),
+                #[cfg(not(target_os = "solid_asp3"))]
+                () => Some(self.0.get() as i32),
+            }
+        } else {
+            None
+        }
+    }
+
+    /// Extract the bare error code.
+    ///
+    /// This code can either come from the underlying OS, or be a custom error.
+    /// Use [`Error::raw_os_error()`] to disambiguate.
+    #[inline]
+    pub const fn code(self) -> NonZeroU32 {
+        self.0
+    }
+}
+
+cfg_if! {
+    if #[cfg(unix)] {
+        fn os_err(errno: i32, buf: &mut [u8]) -> Option<&str> {
+            let buf_ptr = buf.as_mut_ptr() as *mut libc::c_char;
+            if unsafe { libc::strerror_r(errno, buf_ptr, buf.len()) } != 0 {
+                return None;
+            }
+
+            // Take up to trailing null byte
+            let n = buf.len();
+            let idx = buf.iter().position(|&b| b == 0).unwrap_or(n);
+            core::str::from_utf8(&buf[..idx]).ok()
+        }
+    } else {
+        fn os_err(_errno: i32, _buf: &mut [u8]) -> Option<&str> {
+            None
+        }
+    }
+}
+
+impl fmt::Debug for Error {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        let mut dbg = f.debug_struct("Error");
+        if let Some(errno) = self.raw_os_error() {
+            dbg.field("os_error", &errno);
+            let mut buf = [0u8; 128];
+            if let Some(err) = os_err(errno, &mut buf) {
+                dbg.field("description", &err);
+            }
+        } else if let Some(desc) = internal_desc(*self) {
+            dbg.field("internal_code", &self.0.get());
+            dbg.field("description", &desc);
+        } else {
+            dbg.field("unknown_code", &self.0.get());
+        }
+        dbg.finish()
+    }
+}
+
+impl fmt::Display for Error {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        if let Some(errno) = self.raw_os_error() {
+            let mut buf = [0u8; 128];
+            match os_err(errno, &mut buf) {
+                Some(err) => err.fmt(f),
+                None => write!(f, "OS Error: {}", errno),
+            }
+        } else if let Some(desc) = internal_desc(*self) {
+            f.write_str(desc)
+        } else {
+            write!(f, "Unknown Error: {}", self.0.get())
+        }
+    }
+}
+
+impl From<NonZeroU32> for Error {
+    fn from(code: NonZeroU32) -> Self {
+        Self(code)
+    }
+}
+
+fn internal_desc(error: Error) -> Option<&'static str> {
+    match error {
+        Error::UNSUPPORTED => Some("getrandom: this target is not supported"),
+        Error::ERRNO_NOT_POSITIVE => Some("errno: did not return a positive value"),
+        Error::IOS_SEC_RANDOM => Some("SecRandomCopyBytes: iOS Security framework failure"),
+        Error::WINDOWS_RTL_GEN_RANDOM => Some("RtlGenRandom: Windows system function failure"),
+        Error::FAILED_RDRAND => Some("RDRAND: failed multiple times: CPU issue likely"),
+        Error::NO_RDRAND => Some("RDRAND: instruction not supported"),
+        Error::WEB_CRYPTO => Some("Web Crypto API is unavailable"),
+        Error::WEB_GET_RANDOM_VALUES => Some("Calling Web API crypto.getRandomValues failed"),
+        Error::VXWORKS_RAND_SECURE => Some("randSecure: VxWorks RNG module is not initialized"),
+        Error::NODE_CRYPTO => Some("Node.js crypto CommonJS module is unavailable"),
+        Error::NODE_RANDOM_FILL_SYNC => Some("Calling Node.js API crypto.randomFillSync failed"),
+        Error::NODE_ES_MODULE => Some("Node.js ES modules are not directly supported, see https://docs.rs/getrandom#nodejs-es-module-support"),
+        _ => None,
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use super::Error;
+    use core::mem::size_of;
+
+    #[test]
+    fn test_size() {
+        assert_eq!(size_of::<Error>(), 4);
+        assert_eq!(size_of::<Result<(), Error>>(), 4);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error_impls.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error_impls.rs.html new file mode 100644 index 0000000..8312fb2 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/error_impls.rs.html @@ -0,0 +1,51 @@ +error_impls.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+#![cfg_attr(docsrs, doc(cfg(feature = "std")))]
+extern crate std;
+
+use crate::Error;
+use core::convert::From;
+use std::io;
+
+impl From<Error> for io::Error {
+    fn from(err: Error) -> Self {
+        match err.raw_os_error() {
+            Some(errno) => io::Error::from_raw_os_error(errno),
+            None => io::Error::new(io::ErrorKind::Other, err),
+        }
+    }
+}
+
+impl std::error::Error for Error {}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/lib.rs.html new file mode 100644 index 0000000..1ee8d19 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/lib.rs.html @@ -0,0 +1,585 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+
// Copyright 2019 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Interface to the operating system's random number generator.
+//!
+//! # Supported targets
+//!
+//! | Target            | Target Triple      | Implementation
+//! | ----------------- | ------------------ | --------------
+//! | Linux, Android    | `*‑linux‑*`        | [`getrandom`][1] system call if available, otherwise [`/dev/urandom`][2] after successfully polling `/dev/random`
+//! | Windows           | `*‑windows‑*`      | [`BCryptGenRandom`]
+//! | macOS             | `*‑apple‑darwin`   | [`getentropy`][3] if available, otherwise [`/dev/random`][4] (identical to `/dev/urandom`)
+//! | iOS               | `*‑apple‑ios`      | [`SecRandomCopyBytes`]
+//! | FreeBSD           | `*‑freebsd`        | [`getrandom`][5] if available, otherwise [`kern.arandom`][6]
+//! | OpenBSD           | `*‑openbsd`        | [`getentropy`][7]
+//! | NetBSD            | `*‑netbsd`         | [`kern.arandom`][8]
+//! | Dragonfly BSD     | `*‑dragonfly`      | [`getrandom`][9] if available, otherwise [`/dev/random`][10]
+//! | Solaris, illumos  | `*‑solaris`, `*‑illumos` | [`getrandom`][11] if available, otherwise [`/dev/random`][12]
+//! | Fuchsia OS        | `*‑fuchsia`        | [`cprng_draw`]
+//! | Redox             | `*‑redox`          | `/dev/urandom`
+//! | Haiku             | `*‑haiku`          | `/dev/random` (identical to `/dev/urandom`)
+//! | Hermit            | `x86_64-*-hermit`  | [`RDRAND`]
+//! | SGX               | `x86_64‑*‑sgx`     | [`RDRAND`]
+//! | VxWorks           | `*‑wrs‑vxworks‑*`  | `randABytes` after checking entropy pool initialization with `randSecure`
+//! | ESP-IDF           | `*‑espidf`         | [`esp_fill_random`]
+//! | Emscripten        | `*‑emscripten`     | `/dev/random` (identical to `/dev/urandom`)
+//! | WASI              | `wasm32‑wasi`      | [`random_get`]
+//! | Web Browser and Node.js | `wasm32‑*‑unknown` | [`Crypto.getRandomValues`] if available, then [`crypto.randomFillSync`] if on Node.js, see [WebAssembly support]
+//! | SOLID             | `*-kmc-solid_*`    | `SOLID_RNG_SampleRandomBytes`
+//! | Nintendo 3DS      | `armv6k-nintendo-3ds` | [`getrandom`][1]
+//!
+//! There is no blanket implementation on `unix` targets that reads from
+//! `/dev/urandom`. This ensures all supported targets are using the recommended
+//! interface and respect maximum buffer sizes.
+//!
+//! Pull Requests that add support for new targets to `getrandom` are always welcome.
+//!
+//! ## Unsupported targets
+//!
+//! By default, `getrandom` will not compile on unsupported targets, but certain
+//! features allow a user to select a "fallback" implementation if no supported
+//! implementation exists.
+//!
+//! All of the below mechanisms only affect unsupported
+//! targets. Supported targets will _always_ use their supported implementations.
+//! This prevents a crate from overriding a secure source of randomness
+//! (either accidentally or intentionally).
+//!
+//! ### RDRAND on x86
+//!
+//! *If the `rdrand` Cargo feature is enabled*, `getrandom` will fallback to using
+//! the [`RDRAND`] instruction to get randomness on `no_std` `x86`/`x86_64`
+//! targets. This feature has no effect on other CPU architectures.
+//!
+//! ### WebAssembly support
+//!
+//! This crate fully supports the
+//! [`wasm32-wasi`](https://github.com/CraneStation/wasi) and
+//! [`wasm32-unknown-emscripten`](https://www.hellorust.com/setup/emscripten/)
+//! targets. However, the `wasm32-unknown-unknown` target (i.e. the target used
+//! by `wasm-pack`) is not automatically
+//! supported since, from the target name alone, we cannot deduce which
+//! JavaScript interface is in use (or if JavaScript is available at all).
+//!
+//! Instead, *if the `js` Cargo feature is enabled*, this crate will assume
+//! that you are building for an environment containing JavaScript, and will
+//! call the appropriate methods. Both web browser (main window and Web Workers)
+//! and Node.js environments are supported, invoking the methods
+//! [described above](#supported-targets) using the [`wasm-bindgen`] toolchain.
+//!
+//! To enable the `js` Cargo feature, add the following to the `dependencies`
+//! section in your `Cargo.toml` file:
+//! ```toml
+//! [dependencies]
+//! getrandom = { version = "0.2", features = ["js"] }
+//! ```
+//!
+//! This can be done even if `getrandom` is not a direct dependency. Cargo
+//! allows crates to enable features for indirect dependencies.
+//!
+//! This feature should only be enabled for binary, test, or benchmark crates.
+//! Library crates should generally not enable this feature, leaving such a
+//! decision to *users* of their library. Also, libraries should not introduce
+//! their own `js` features *just* to enable `getrandom`'s `js` feature.
+//!
+//! This feature has no effect on targets other than `wasm32-unknown-unknown`.
+//!
+//! #### Node.js ES module support
+//!
+//! Node.js supports both [CommonJS modules] and [ES modules]. Due to
+//! limitations in wasm-bindgen's [`module`] support, we cannot directly
+//! support ES Modules running on Node.js. However, on Node v15 and later, the
+//! module author can add a simple shim to support the Web Cryptography API:
+//! ```js
+//! import { webcrypto } from 'node:crypto'
+//! globalThis.crypto = webcrypto
+//! ```
+//! This crate will then use the provided `webcrypto` implementation.
+//!
+//! ### Custom implementations
+//!
+//! The [`register_custom_getrandom!`] macro allows a user to mark their own
+//! function as the backing implementation for [`getrandom`]. See the macro's
+//! documentation for more information about writing and registering your own
+//! custom implementations.
+//!
+//! Note that registering a custom implementation only has an effect on targets
+//! that would otherwise not compile. Any supported targets (including those
+//! using `rdrand` and `js` Cargo features) continue using their normal
+//! implementations even if a function is registered.
+//!
+//! ## Early boot
+//!
+//! Sometimes, early in the boot process, the OS has not collected enough
+//! entropy to securely seed its RNG. This is especially common on virtual
+//! machines, where standard "random" events are hard to come by.
+//!
+//! Some operating system interfaces always block until the RNG is securely
+//! seeded. This can take anywhere from a few seconds to more than a minute.
+//! A few (Linux, NetBSD and Solaris) offer a choice between blocking and
+//! getting an error; in these cases, we always choose to block.
+//!
+//! On Linux (when the `getrandom` system call is not available), reading from
+//! `/dev/urandom` never blocks, even when the OS hasn't collected enough
+//! entropy yet. To avoid returning low-entropy bytes, we first poll
+//! `/dev/random` and only switch to `/dev/urandom` once this has succeeded.
+//!
+//! On OpenBSD, this kind of entropy accounting isn't available, and on
+//! NetBSD, blocking on it is discouraged. On these platforms, nonblocking
+//! interfaces are used, even when reliable entropy may not be available.
+//! On the platforms where it is used, the reliability of entropy accounting
+//! itself isn't free from controversy. This library provides randomness
+//! sourced according to the platform's best practices, but each platform has
+//! its own limits on the grade of randomness it can promise in environments
+//! with few sources of entropy.
+//!
+//! ## Error handling
+//!
+//! We always choose failure over returning known insecure "random" bytes. In
+//! general, on supported platforms, failure is highly unlikely, though not
+//! impossible. If an error does occur, then it is likely that it will occur
+//! on every call to `getrandom`, hence after the first successful call one
+//! can be reasonably confident that no errors will occur.
+//!
+//! [1]: http://man7.org/linux/man-pages/man2/getrandom.2.html
+//! [2]: http://man7.org/linux/man-pages/man4/urandom.4.html
+//! [3]: https://www.unix.com/man-page/mojave/2/getentropy/
+//! [4]: https://www.unix.com/man-page/mojave/4/random/
+//! [5]: https://www.freebsd.org/cgi/man.cgi?query=getrandom&manpath=FreeBSD+12.0-stable
+//! [6]: https://www.freebsd.org/cgi/man.cgi?query=random&sektion=4
+//! [7]: https://man.openbsd.org/getentropy.2
+//! [8]: https://man.netbsd.org/sysctl.7
+//! [9]: https://leaf.dragonflybsd.org/cgi/web-man?command=getrandom
+//! [10]: https://leaf.dragonflybsd.org/cgi/web-man?command=random&section=4
+//! [11]: https://docs.oracle.com/cd/E88353_01/html/E37841/getrandom-2.html
+//! [12]: https://docs.oracle.com/cd/E86824_01/html/E54777/random-7d.html
+//!
+//! [`BCryptGenRandom`]: https://docs.microsoft.com/en-us/windows/win32/api/bcrypt/nf-bcrypt-bcryptgenrandom
+//! [`Crypto.getRandomValues`]: https://www.w3.org/TR/WebCryptoAPI/#Crypto-method-getRandomValues
+//! [`RDRAND`]: https://software.intel.com/en-us/articles/intel-digital-random-number-generator-drng-software-implementation-guide
+//! [`SecRandomCopyBytes`]: https://developer.apple.com/documentation/security/1399291-secrandomcopybytes?language=objc
+//! [`cprng_draw`]: https://fuchsia.dev/fuchsia-src/zircon/syscalls/cprng_draw
+//! [`crypto.randomFillSync`]: https://nodejs.org/api/crypto.html#cryptorandomfillsyncbuffer-offset-size
+//! [`esp_fill_random`]: https://docs.espressif.com/projects/esp-idf/en/latest/esp32/api-reference/system/random.html#_CPPv415esp_fill_randomPv6size_t
+//! [`random_get`]: https://github.com/WebAssembly/WASI/blob/main/phases/snapshot/docs.md#-random_getbuf-pointeru8-buf_len-size---errno
+//! [WebAssembly support]: #webassembly-support
+//! [`wasm-bindgen`]: https://github.com/rustwasm/wasm-bindgen
+//! [`module`]: https://rustwasm.github.io/wasm-bindgen/reference/attributes/on-js-imports/module.html
+//! [CommonJS modules]: https://nodejs.org/api/modules.html
+//! [ES modules]: https://nodejs.org/api/esm.html
+
+#![doc(
+    html_logo_url = "https://www.rust-lang.org/logos/rust-logo-128x128-blk.png",
+    html_favicon_url = "https://www.rust-lang.org/favicon.ico",
+    html_root_url = "https://docs.rs/getrandom/0.2.8"
+)]
+#![no_std]
+#![warn(rust_2018_idioms, unused_lifetimes, missing_docs)]
+#![cfg_attr(docsrs, feature(doc_cfg))]
+
+#[macro_use]
+extern crate cfg_if;
+
+mod error;
+mod util;
+// To prevent a breaking change when targets are added, we always export the
+// register_custom_getrandom macro, so old Custom RNG crates continue to build.
+#[cfg(feature = "custom")]
+mod custom;
+#[cfg(feature = "std")]
+mod error_impls;
+
+pub use crate::error::Error;
+
+// System-specific implementations.
+//
+// These should all provide getrandom_inner with the same signature as getrandom.
+cfg_if! {
+    if #[cfg(any(target_os = "emscripten", target_os = "haiku",
+                 target_os = "redox"))] {
+        mod util_libc;
+        #[path = "use_file.rs"] mod imp;
+    } else if #[cfg(any(target_os = "android", target_os = "linux"))] {
+        mod util_libc;
+        mod use_file;
+        #[path = "linux_android.rs"] mod imp;
+    } else if #[cfg(any(target_os = "illumos", target_os = "solaris"))] {
+        mod util_libc;
+        mod use_file;
+        #[path = "solaris_illumos.rs"] mod imp;
+    } else if #[cfg(any(target_os = "freebsd", target_os = "netbsd"))] {
+        mod util_libc;
+        #[path = "bsd_arandom.rs"] mod imp;
+    } else if #[cfg(target_os = "dragonfly")] {
+        mod util_libc;
+        mod use_file;
+        #[path = "dragonfly.rs"] mod imp;
+    } else if #[cfg(target_os = "fuchsia")] {
+        #[path = "fuchsia.rs"] mod imp;
+    } else if #[cfg(target_os = "ios")] {
+        #[path = "ios.rs"] mod imp;
+    } else if #[cfg(target_os = "macos")] {
+        mod util_libc;
+        mod use_file;
+        #[path = "macos.rs"] mod imp;
+    } else if #[cfg(target_os = "openbsd")] {
+        mod util_libc;
+        #[path = "openbsd.rs"] mod imp;
+    } else if #[cfg(target_os = "wasi")] {
+        #[path = "wasi.rs"] mod imp;
+    } else if #[cfg(all(target_arch = "x86_64", target_os = "hermit"))] {
+        #[path = "rdrand.rs"] mod imp;
+    } else if #[cfg(target_os = "vxworks")] {
+        mod util_libc;
+        #[path = "vxworks.rs"] mod imp;
+    } else if #[cfg(target_os = "solid_asp3")] {
+        #[path = "solid.rs"] mod imp;
+    } else if #[cfg(target_os = "espidf")] {
+        #[path = "espidf.rs"] mod imp;
+    } else if #[cfg(windows)] {
+        #[path = "windows.rs"] mod imp;
+    } else if #[cfg(all(target_arch = "x86_64", target_env = "sgx"))] {
+        #[path = "rdrand.rs"] mod imp;
+    } else if #[cfg(all(feature = "rdrand",
+                        any(target_arch = "x86_64", target_arch = "x86")))] {
+        #[path = "rdrand.rs"] mod imp;
+    } else if #[cfg(all(feature = "js",
+                        target_arch = "wasm32", target_os = "unknown"))] {
+        #[path = "js.rs"] mod imp;
+    } else if #[cfg(all(target_os = "horizon", target_arch = "arm"))] {
+        // We check for target_arch = "arm" because the Nintendo Switch also
+        // uses Horizon OS (it is aarch64).
+        mod util_libc;
+        #[path = "3ds.rs"] mod imp;
+    } else if #[cfg(feature = "custom")] {
+        use custom as imp;
+    } else if #[cfg(all(target_arch = "wasm32", target_os = "unknown"))] {
+        compile_error!("the wasm32-unknown-unknown target is not supported by \
+                        default, you may need to enable the \"js\" feature. \
+                        For more information see: \
+                        https://docs.rs/getrandom/#webassembly-support");
+    } else {
+        compile_error!("target is not supported, for more information see: \
+                        https://docs.rs/getrandom/#unsupported-targets");
+    }
+}
+
+/// Fill `dest` with random bytes from the system's preferred random number
+/// source.
+///
+/// This function returns an error on any failure, including partial reads. We
+/// make no guarantees regarding the contents of `dest` on error. If `dest` is
+/// empty, `getrandom` immediately returns success, making no calls to the
+/// underlying operating system.
+///
+/// Blocking is possible, at least during early boot; see module documentation.
+///
+/// In general, `getrandom` will be fast enough for interactive usage, though
+/// significantly slower than a user-space CSPRNG; for the latter consider
+/// [`rand::thread_rng`](https://docs.rs/rand/*/rand/fn.thread_rng.html).
+pub fn getrandom(dest: &mut [u8]) -> Result<(), Error> {
+    if dest.is_empty() {
+        return Ok(());
+    }
+    imp::getrandom_inner(dest)
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/linux_android.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/linux_android.rs.html new file mode 100644 index 0000000..19232f1 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/linux_android.rs.html @@ -0,0 +1,97 @@ +linux_android.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Implementation for Linux / Android
+use crate::{
+    util::LazyBool,
+    util_libc::{last_os_error, sys_fill_exact},
+    {use_file, Error},
+};
+
+pub fn getrandom_inner(dest: &mut [u8]) -> Result<(), Error> {
+    // getrandom(2) was introduced in Linux 3.17
+    static HAS_GETRANDOM: LazyBool = LazyBool::new();
+    if HAS_GETRANDOM.unsync_init(is_getrandom_available) {
+        sys_fill_exact(dest, |buf| unsafe {
+            getrandom(buf.as_mut_ptr() as *mut libc::c_void, buf.len(), 0)
+        })
+    } else {
+        use_file::getrandom_inner(dest)
+    }
+}
+
+fn is_getrandom_available() -> bool {
+    let res = unsafe { getrandom(core::ptr::null_mut(), 0, libc::GRND_NONBLOCK) };
+    if res < 0 {
+        match last_os_error().raw_os_error() {
+            Some(libc::ENOSYS) => false, // No kernel support
+            Some(libc::EPERM) => false,  // Blocked by seccomp
+            _ => true,
+        }
+    } else {
+        true
+    }
+}
+
+unsafe fn getrandom(
+    buf: *mut libc::c_void,
+    buflen: libc::size_t,
+    flags: libc::c_uint,
+) -> libc::ssize_t {
+    libc::syscall(libc::SYS_getrandom, buf, buflen, flags) as libc::ssize_t
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/use_file.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/use_file.rs.html new file mode 100644 index 0000000..27a1fa7 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/use_file.rs.html @@ -0,0 +1,281 @@ +use_file.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Implementations that just need to read from a file
+use crate::{
+    util::LazyUsize,
+    util_libc::{open_readonly, sys_fill_exact},
+    Error,
+};
+use core::{
+    cell::UnsafeCell,
+    sync::atomic::{AtomicUsize, Ordering::Relaxed},
+};
+
+#[cfg(any(
+    target_os = "dragonfly",
+    target_os = "emscripten",
+    target_os = "haiku",
+    target_os = "macos",
+    target_os = "solaris",
+    target_os = "illumos"
+))]
+const FILE_PATH: &str = "/dev/random\0";
+#[cfg(any(target_os = "android", target_os = "linux", target_os = "redox"))]
+const FILE_PATH: &str = "/dev/urandom\0";
+
+pub fn getrandom_inner(dest: &mut [u8]) -> Result<(), Error> {
+    let fd = get_rng_fd()?;
+    let read = |buf: &mut [u8]| unsafe { libc::read(fd, buf.as_mut_ptr() as *mut _, buf.len()) };
+
+    if cfg!(target_os = "emscripten") {
+        // `Crypto.getRandomValues` documents `dest` should be at most 65536 bytes.
+        for chunk in dest.chunks_mut(65536) {
+            sys_fill_exact(chunk, read)?;
+        }
+    } else {
+        sys_fill_exact(dest, read)?;
+    }
+    Ok(())
+}
+
+// Returns the file descriptor for the device file used to retrieve random
+// bytes. The file will be opened exactly once. All subsequent calls will
+// return the same file descriptor. This file descriptor is never closed.
+fn get_rng_fd() -> Result<libc::c_int, Error> {
+    static FD: AtomicUsize = AtomicUsize::new(LazyUsize::UNINIT);
+    fn get_fd() -> Option<libc::c_int> {
+        match FD.load(Relaxed) {
+            LazyUsize::UNINIT => None,
+            val => Some(val as libc::c_int),
+        }
+    }
+
+    // Use double-checked locking to avoid acquiring the lock if possible.
+    if let Some(fd) = get_fd() {
+        return Ok(fd);
+    }
+
+    // SAFETY: We use the mutex only in this method, and we always unlock it
+    // before returning, making sure we don't violate the pthread_mutex_t API.
+    static MUTEX: Mutex = Mutex::new();
+    unsafe { MUTEX.lock() };
+    let _guard = DropGuard(|| unsafe { MUTEX.unlock() });
+
+    if let Some(fd) = get_fd() {
+        return Ok(fd);
+    }
+
+    // On Linux, /dev/urandom might return insecure values.
+    #[cfg(any(target_os = "android", target_os = "linux"))]
+    wait_until_rng_ready()?;
+
+    let fd = unsafe { open_readonly(FILE_PATH)? };
+    // The fd always fits in a usize without conflicting with UNINIT.
+    debug_assert!(fd >= 0 && (fd as usize) < LazyUsize::UNINIT);
+    FD.store(fd as usize, Relaxed);
+
+    Ok(fd)
+}
+
+// Succeeds once /dev/urandom is safe to read from
+#[cfg(any(target_os = "android", target_os = "linux"))]
+fn wait_until_rng_ready() -> Result<(), Error> {
+    // Poll /dev/random to make sure it is ok to read from /dev/urandom.
+    let fd = unsafe { open_readonly("/dev/random\0")? };
+    let mut pfd = libc::pollfd {
+        fd,
+        events: libc::POLLIN,
+        revents: 0,
+    };
+    let _guard = DropGuard(|| unsafe {
+        libc::close(fd);
+    });
+
+    loop {
+        // A negative timeout means an infinite timeout.
+        let res = unsafe { libc::poll(&mut pfd, 1, -1) };
+        if res >= 0 {
+            debug_assert_eq!(res, 1); // We only used one fd, and cannot timeout.
+            return Ok(());
+        }
+        let err = crate::util_libc::last_os_error();
+        match err.raw_os_error() {
+            Some(libc::EINTR) | Some(libc::EAGAIN) => continue,
+            _ => return Err(err),
+        }
+    }
+}
+
+struct Mutex(UnsafeCell<libc::pthread_mutex_t>);
+
+impl Mutex {
+    const fn new() -> Self {
+        Self(UnsafeCell::new(libc::PTHREAD_MUTEX_INITIALIZER))
+    }
+    unsafe fn lock(&self) {
+        let r = libc::pthread_mutex_lock(self.0.get());
+        debug_assert_eq!(r, 0);
+    }
+    unsafe fn unlock(&self) {
+        let r = libc::pthread_mutex_unlock(self.0.get());
+        debug_assert_eq!(r, 0);
+    }
+}
+
+unsafe impl Sync for Mutex {}
+
+struct DropGuard<F: FnMut()>(F);
+
+impl<F: FnMut()> Drop for DropGuard<F> {
+    fn drop(&mut self) {
+        self.0()
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util.rs.html new file mode 100644 index 0000000..73b842f --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util.rs.html @@ -0,0 +1,131 @@ +util.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+
// Copyright 2019 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+#![allow(dead_code)]
+use core::sync::atomic::{AtomicUsize, Ordering::Relaxed};
+
+// This structure represents a lazily initialized static usize value. Useful
+// when it is preferable to just rerun initialization instead of locking.
+// Both unsync_init and sync_init will invoke an init() function until it
+// succeeds, then return the cached value for future calls.
+//
+// Both methods support init() "failing". If the init() method returns UNINIT,
+// that value will be returned as normal, but will not be cached.
+//
+// Users should only depend on the _value_ returned by init() functions.
+// Specifically, for the following init() function:
+//      fn init() -> usize {
+//          a();
+//          let v = b();
+//          c();
+//          v
+//      }
+// the effects of c() or writes to shared memory will not necessarily be
+// observed and additional synchronization methods with be needed.
+pub struct LazyUsize(AtomicUsize);
+
+impl LazyUsize {
+    pub const fn new() -> Self {
+        Self(AtomicUsize::new(Self::UNINIT))
+    }
+
+    // The initialization is not completed.
+    pub const UNINIT: usize = usize::max_value();
+
+    // Runs the init() function at least once, returning the value of some run
+    // of init(). Multiple callers can run their init() functions in parallel.
+    // init() should always return the same value, if it succeeds.
+    pub fn unsync_init(&self, init: impl FnOnce() -> usize) -> usize {
+        // Relaxed ordering is fine, as we only have a single atomic variable.
+        let mut val = self.0.load(Relaxed);
+        if val == Self::UNINIT {
+            val = init();
+            self.0.store(val, Relaxed);
+        }
+        val
+    }
+}
+
+// Identical to LazyUsize except with bool instead of usize.
+pub struct LazyBool(LazyUsize);
+
+impl LazyBool {
+    pub const fn new() -> Self {
+        Self(LazyUsize::new())
+    }
+
+    pub fn unsync_init(&self, init: impl FnOnce() -> bool) -> bool {
+        self.0.unsync_init(|| init() as usize) != 0
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util_libc.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util_libc.rs.html new file mode 100644 index 0000000..95b9e91 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/getrandom/util_libc.rs.html @@ -0,0 +1,323 @@ +util_libc.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+
// Copyright 2019 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+#![allow(dead_code)]
+use crate::Error;
+use core::{
+    num::NonZeroU32,
+    ptr::NonNull,
+    sync::atomic::{fence, AtomicPtr, Ordering},
+};
+use libc::c_void;
+
+cfg_if! {
+    if #[cfg(any(target_os = "netbsd", target_os = "openbsd", target_os = "android"))] {
+        use libc::__errno as errno_location;
+    } else if #[cfg(any(target_os = "linux", target_os = "emscripten", target_os = "redox"))] {
+        use libc::__errno_location as errno_location;
+    } else if #[cfg(any(target_os = "solaris", target_os = "illumos"))] {
+        use libc::___errno as errno_location;
+    } else if #[cfg(any(target_os = "macos", target_os = "freebsd"))] {
+        use libc::__error as errno_location;
+    } else if #[cfg(target_os = "haiku")] {
+        use libc::_errnop as errno_location;
+    } else if #[cfg(all(target_os = "horizon", target_arch = "arm"))] {
+        extern "C" {
+            // Not provided by libc: https://github.com/rust-lang/libc/issues/1995
+            fn __errno() -> *mut libc::c_int;
+        }
+        use __errno as errno_location;
+    }
+}
+
+cfg_if! {
+    if #[cfg(target_os = "vxworks")] {
+        use libc::errnoGet as get_errno;
+    } else if #[cfg(target_os = "dragonfly")] {
+        // Until rust-lang/rust#29594 is stable, we cannot get the errno value
+        // on DragonFlyBSD. So we just return an out-of-range errno.
+        unsafe fn get_errno() -> libc::c_int { -1 }
+    } else {
+        unsafe fn get_errno() -> libc::c_int { *errno_location() }
+    }
+}
+
+pub fn last_os_error() -> Error {
+    let errno = unsafe { get_errno() };
+    if errno > 0 {
+        Error::from(NonZeroU32::new(errno as u32).unwrap())
+    } else {
+        Error::ERRNO_NOT_POSITIVE
+    }
+}
+
+// Fill a buffer by repeatedly invoking a system call. The `sys_fill` function:
+//   - should return -1 and set errno on failure
+//   - should return the number of bytes written on success
+pub fn sys_fill_exact(
+    mut buf: &mut [u8],
+    sys_fill: impl Fn(&mut [u8]) -> libc::ssize_t,
+) -> Result<(), Error> {
+    while !buf.is_empty() {
+        let res = sys_fill(buf);
+        if res < 0 {
+            let err = last_os_error();
+            // We should try again if the call was interrupted.
+            if err.raw_os_error() != Some(libc::EINTR) {
+                return Err(err);
+            }
+        } else {
+            // We don't check for EOF (ret = 0) as the data we are reading
+            // should be an infinite stream of random bytes.
+            buf = &mut buf[(res as usize)..];
+        }
+    }
+    Ok(())
+}
+
+// A "weak" binding to a C function that may or may not be present at runtime.
+// Used for supporting newer OS features while still building on older systems.
+// Based off of the DlsymWeak struct in libstd:
+// https://github.com/rust-lang/rust/blob/1.61.0/library/std/src/sys/unix/weak.rs#L84
+// except that the caller must manually cast self.ptr() to a function pointer.
+pub struct Weak {
+    name: &'static str,
+    addr: AtomicPtr<c_void>,
+}
+
+impl Weak {
+    // A non-null pointer value which indicates we are uninitialized. This
+    // constant should ideally not be a valid address of a function pointer.
+    // However, if by chance libc::dlsym does return UNINIT, there will not
+    // be undefined behavior. libc::dlsym will just be called each time ptr()
+    // is called. This would be inefficient, but correct.
+    // TODO: Replace with core::ptr::invalid_mut(1) when that is stable.
+    const UNINIT: *mut c_void = 1 as *mut c_void;
+
+    // Construct a binding to a C function with a given name. This function is
+    // unsafe because `name` _must_ be null terminated.
+    pub const unsafe fn new(name: &'static str) -> Self {
+        Self {
+            name,
+            addr: AtomicPtr::new(Self::UNINIT),
+        }
+    }
+
+    // Return the address of a function if present at runtime. Otherwise,
+    // return None. Multiple callers can call ptr() concurrently. It will
+    // always return _some_ value returned by libc::dlsym. However, the
+    // dlsym function may be called multiple times.
+    pub fn ptr(&self) -> Option<NonNull<c_void>> {
+        // Despite having only a single atomic variable (self.addr), we still
+        // cannot always use Ordering::Relaxed, as we need to make sure a
+        // successful call to dlsym() is "ordered before" any data read through
+        // the returned pointer (which occurs when the function is called).
+        // Our implementation mirrors that of the one in libstd, meaning that
+        // the use of non-Relaxed operations is probably unnecessary.
+        match self.addr.load(Ordering::Relaxed) {
+            Self::UNINIT => {
+                let symbol = self.name.as_ptr() as *const _;
+                let addr = unsafe { libc::dlsym(libc::RTLD_DEFAULT, symbol) };
+                // Synchronizes with the Acquire fence below
+                self.addr.store(addr, Ordering::Release);
+                NonNull::new(addr)
+            }
+            addr => {
+                let func = NonNull::new(addr)?;
+                fence(Ordering::Acquire);
+                Some(func)
+            }
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(any(target_os = "linux", target_os = "emscripten"))] {
+        use libc::open64 as open;
+    } else {
+        use libc::open;
+    }
+}
+
+// SAFETY: path must be null terminated, FD must be manually closed.
+pub unsafe fn open_readonly(path: &str) -> Result<libc::c_int, Error> {
+    debug_assert_eq!(path.as_bytes().last(), Some(&0));
+    loop {
+        let fd = open(path.as_ptr() as *const _, libc::O_RDONLY | libc::O_CLOEXEC);
+        if fd >= 0 {
+            return Ok(fd);
+        }
+        let err = last_os_error();
+        // We should try again if open() was interrupted.
+        if err.raw_os_error() != Some(libc::EINTR) {
+            return Err(err);
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/guessing_game/main.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/guessing_game/main.rs.html new file mode 100644 index 0000000..78f078f --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/guessing_game/main.rs.html @@ -0,0 +1,76 @@ +main.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+
use std::io;
+use rand::Rng;
+use std::cmp::Ordering;
+
+fn main() {
+    println!("Guess the number!");
+
+    let secret_number = rand::thread_rng().gen_range(1..=100);
+
+    println!("The secret number is: {secret_number}");
+
+    loop {
+        println!("Please input your number.");
+
+        let mut guess = String::new();
+
+        io::stdin()
+            .read_line(&mut guess)
+            .expect("Failed to read line.");
+
+        let guess: u32 = match guess.trim().parse() {
+            Ok(num) => num,
+            Err(_) => continue,
+        };
+
+        println!("You guessed: {guess}");
+
+        match guess.cmp(&secret_number) {
+            Ordering::Less => println!("Too small!"),
+            Ordering::Greater => println!("Too big!"),
+            Ordering::Equal => {
+                println!("You win!");
+                break;
+            },
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/fixed_width_ints.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/fixed_width_ints.rs.html new file mode 100644 index 0000000..4cf37e4 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/fixed_width_ints.rs.html @@ -0,0 +1,200 @@ +fixed_width_ints.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+
//! This module contains type aliases for C's fixed-width integer types .
+//!
+//! These aliases are deprecated: use the Rust types instead.
+
+#[deprecated(since = "0.2.55", note = "Use i8 instead.")]
+pub type int8_t = i8;
+#[deprecated(since = "0.2.55", note = "Use i16 instead.")]
+pub type int16_t = i16;
+#[deprecated(since = "0.2.55", note = "Use i32 instead.")]
+pub type int32_t = i32;
+#[deprecated(since = "0.2.55", note = "Use i64 instead.")]
+pub type int64_t = i64;
+#[deprecated(since = "0.2.55", note = "Use u8 instead.")]
+pub type uint8_t = u8;
+#[deprecated(since = "0.2.55", note = "Use u16 instead.")]
+pub type uint16_t = u16;
+#[deprecated(since = "0.2.55", note = "Use u32 instead.")]
+pub type uint32_t = u32;
+#[deprecated(since = "0.2.55", note = "Use u64 instead.")]
+pub type uint64_t = u64;
+
+cfg_if! {
+    if #[cfg(all(libc_int128, target_arch = "aarch64", not(target_os = "windows")))] {
+        // This introduces partial support for FFI with __int128 and
+        // equivalent types on platforms where Rust's definition is validated
+        // to match the standard C ABI of that platform.
+        //
+        // Rust does not guarantee u128/i128 are sound for FFI, and its
+        // definitions are in fact known to be incompatible. [0]
+        //
+        // However these problems aren't fundamental, and are just platform
+        // inconsistencies. Specifically at the time of this writing:
+        //
+        // * For x64 SysV ABIs (everything but Windows), the types are underaligned.
+        // * For all Windows ABIs, Microsoft doesn't actually officially define __int128,
+        //   and as a result different implementations don't actually agree on its ABI.
+        //
+        // But on the other major aarch64 platforms (android, linux, ios, macos) we have
+        // validated that rustc has the right ABI for these types. This is important because
+        // aarch64 uses these types in some fundamental OS types like user_fpsimd_struct,
+        // which represents saved simd registers.
+        //
+        // Any API which uses these types will need to `#[ignore(improper_ctypes)]`
+        // until the upstream rust issue is resolved, but this at least lets us make
+        // progress on platforms where this type is important.
+        //
+        // The list of supported architectures and OSes is intentionally very restricted,
+        // as careful work needs to be done to verify that a particular platform
+        // has a conformant ABI.
+        //
+        // [0]: https://github.com/rust-lang/rust/issues/54341
+
+        /// C `__int128` (a GCC extension that's part of many ABIs)
+        pub type __int128 = i128;
+        /// C `unsigned __int128` (a GCC extension that's part of many ABIs)
+        pub type __uint128 = u128;
+        /// C __int128_t (alternate name for [__int128][])
+        pub type __int128_t = i128;
+        /// C __uint128_t (alternate name for [__uint128][])
+        pub type __uint128_t = u128;
+
+        cfg_if! {
+            if #[cfg(libc_underscore_const_names)] {
+                macro_rules! static_assert_eq {
+                    ($a:expr, $b:expr) => {
+                        const _: [(); $a] = [(); $b];
+                    };
+                }
+
+                // NOTE: if you add more platforms to here, you may need to cfg
+                // these consts. They should always match the platform's values
+                // for `sizeof(__int128)` and `_Alignof(__int128)`.
+                const _SIZE_128: usize = 16;
+                const _ALIGN_128: usize = 16;
+
+                // Since Rust doesn't officially guarantee that these types
+                // have compatible ABIs, we const assert that these values have the
+                // known size/align of the target platform's libc. If rustc ever
+                // tries to regress things, it will cause a compilation error.
+                //
+                // This isn't a bullet-proof solution because e.g. it doesn't
+                // catch the fact that llvm and gcc disagree on how x64 __int128
+                // is actually *passed* on the stack (clang underaligns it for
+                // the same reason that rustc *never* properly aligns it).
+                static_assert_eq!(core::mem::size_of::<__int128>(), _SIZE_128);
+                static_assert_eq!(core::mem::align_of::<__int128>(), _ALIGN_128);
+
+                static_assert_eq!(core::mem::size_of::<__uint128>(), _SIZE_128);
+                static_assert_eq!(core::mem::align_of::<__uint128>(), _ALIGN_128);
+
+                static_assert_eq!(core::mem::size_of::<__int128_t>(), _SIZE_128);
+                static_assert_eq!(core::mem::align_of::<__int128_t>(), _ALIGN_128);
+
+                static_assert_eq!(core::mem::size_of::<__uint128_t>(), _SIZE_128);
+                static_assert_eq!(core::mem::align_of::<__uint128_t>(), _ALIGN_128);
+            }
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/lib.rs.html new file mode 100644 index 0000000..b46015a --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/lib.rs.html @@ -0,0 +1,316 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+
//! libc - Raw FFI bindings to platforms' system libraries
+//!
+//! [Documentation for other platforms][pd].
+//!
+//! [pd]: https://rust-lang.github.io/libc/#platform-specific-documentation
+#![crate_name = "libc"]
+#![crate_type = "rlib"]
+#![allow(
+    renamed_and_removed_lints, // Keep this order.
+    unknown_lints, // Keep this order.
+    bad_style,
+    overflowing_literals,
+    improper_ctypes,
+    // This lint is renamed but we run CI for old stable rustc so should be here.
+    redundant_semicolon,
+    redundant_semicolons,
+    unused_macros,
+    unused_macro_rules,
+)]
+#![cfg_attr(libc_deny_warnings, deny(warnings))]
+// Attributes needed when building as part of the standard library
+#![cfg_attr(feature = "rustc-dep-of-std", feature(link_cfg, no_core))]
+#![cfg_attr(libc_thread_local, feature(thread_local))]
+// Enable extra lints:
+#![cfg_attr(feature = "extra_traits", deny(missing_debug_implementations))]
+#![deny(missing_copy_implementations, safe_packed_borrows)]
+#![cfg_attr(not(feature = "rustc-dep-of-std"), no_std)]
+#![cfg_attr(feature = "rustc-dep-of-std", no_core)]
+#![cfg_attr(libc_const_extern_fn_unstable, feature(const_extern_fn))]
+
+#[macro_use]
+mod macros;
+
+cfg_if! {
+    if #[cfg(feature = "rustc-dep-of-std")] {
+        extern crate rustc_std_workspace_core as core;
+        #[allow(unused_imports)]
+        use core::iter;
+        #[allow(unused_imports)]
+        use core::ops;
+        #[allow(unused_imports)]
+        use core::option;
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_priv_mod_use)] {
+        #[cfg(libc_core_cvoid)]
+        #[allow(unused_imports)]
+        use core::ffi;
+        #[allow(unused_imports)]
+        use core::fmt;
+        #[allow(unused_imports)]
+        use core::hash;
+        #[allow(unused_imports)]
+        use core::num;
+        #[allow(unused_imports)]
+        use core::mem;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        use core::clone::Clone;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        use core::marker::{Copy, Send, Sync};
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        use core::option::Option;
+    } else {
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::fmt;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::hash;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::num;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::mem;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::clone::Clone;
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::marker::{Copy, Send, Sync};
+        #[doc(hidden)]
+        #[allow(unused_imports)]
+        pub use core::option::Option;
+    }
+}
+
+cfg_if! {
+    if #[cfg(windows)] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod windows;
+        pub use windows::*;
+    } else if #[cfg(target_os = "fuchsia")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod fuchsia;
+        pub use fuchsia::*;
+    } else if #[cfg(target_os = "switch")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod switch;
+        pub use switch::*;
+    } else if #[cfg(target_os = "psp")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod psp;
+        pub use psp::*;
+    } else if #[cfg(target_os = "vxworks")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod vxworks;
+        pub use vxworks::*;
+    } else if #[cfg(target_os = "solid_asp3")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod solid;
+        pub use solid::*;
+    } else if #[cfg(unix)] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod unix;
+        pub use unix::*;
+    } else if #[cfg(target_os = "hermit")] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod hermit;
+        pub use hermit::*;
+    } else if #[cfg(all(target_env = "sgx", target_vendor = "fortanix"))] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod sgx;
+        pub use sgx::*;
+    } else if #[cfg(any(target_env = "wasi", target_os = "wasi"))] {
+        mod fixed_width_ints;
+        pub use fixed_width_ints::*;
+
+        mod wasi;
+        pub use wasi::*;
+    } else {
+        // non-supported targets: empty...
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/macros.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/macros.rs.html new file mode 100644 index 0000000..6abaca9 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/macros.rs.html @@ -0,0 +1,688 @@ +macros.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+
/// A macro for defining #[cfg] if-else statements.
+///
+/// This is similar to the `if/elif` C preprocessor macro by allowing definition
+/// of a cascade of `#[cfg]` cases, emitting the implementation which matches
+/// first.
+///
+/// This allows you to conveniently provide a long list #[cfg]'d blocks of code
+/// without having to rewrite each clause multiple times.
+macro_rules! cfg_if {
+    // match if/else chains with a final `else`
+    ($(
+        if #[cfg($($meta:meta),*)] { $($it:item)* }
+    ) else * else {
+        $($it2:item)*
+    }) => {
+        cfg_if! {
+            @__items
+            () ;
+            $( ( ($($meta),*) ($($it)*) ), )*
+            ( () ($($it2)*) ),
+        }
+    };
+
+    // match if/else chains lacking a final `else`
+    (
+        if #[cfg($($i_met:meta),*)] { $($i_it:item)* }
+        $(
+            else if #[cfg($($e_met:meta),*)] { $($e_it:item)* }
+        )*
+    ) => {
+        cfg_if! {
+            @__items
+            () ;
+            ( ($($i_met),*) ($($i_it)*) ),
+            $( ( ($($e_met),*) ($($e_it)*) ), )*
+            ( () () ),
+        }
+    };
+
+    // Internal and recursive macro to emit all the items
+    //
+    // Collects all the negated `cfg`s in a list at the beginning and after the
+    // semicolon is all the remaining items
+    (@__items ($($not:meta,)*) ; ) => {};
+    (@__items ($($not:meta,)*) ; ( ($($m:meta),*) ($($it:item)*) ),
+     $($rest:tt)*) => {
+        // Emit all items within one block, applying an appropriate #[cfg]. The
+        // #[cfg] will require all `$m` matchers specified and must also negate
+        // all previous matchers.
+        cfg_if! { @__apply cfg(all($($m,)* not(any($($not),*)))), $($it)* }
+
+        // Recurse to emit all other items in `$rest`, and when we do so add all
+        // our `$m` matchers to the list of `$not` matchers as future emissions
+        // will have to negate everything we just matched as well.
+        cfg_if! { @__items ($($not,)* $($m,)*) ; $($rest)* }
+    };
+
+    // Internal macro to Apply a cfg attribute to a list of items
+    (@__apply $m:meta, $($it:item)*) => {
+        $(#[$m] $it)*
+    };
+}
+
+macro_rules! s {
+    ($($(#[$attr:meta])* pub $t:ident $i:ident { $($field:tt)* })*) => ($(
+        s!(it: $(#[$attr])* pub $t $i { $($field)* });
+    )*);
+    (it: $(#[$attr:meta])* pub union $i:ident { $($field:tt)* }) => (
+        compile_error!("unions cannot derive extra traits, use s_no_extra_traits instead");
+    );
+    (it: $(#[$attr:meta])* pub struct $i:ident { $($field:tt)* }) => (
+        __item! {
+            #[repr(C)]
+            #[cfg_attr(feature = "extra_traits", derive(Debug, Eq, Hash, PartialEq))]
+            #[allow(deprecated)]
+            $(#[$attr])*
+            pub struct $i { $($field)* }
+        }
+        #[allow(deprecated)]
+        impl ::Copy for $i {}
+        #[allow(deprecated)]
+        impl ::Clone for $i {
+            fn clone(&self) -> $i { *self }
+        }
+    );
+}
+
+macro_rules! s_no_extra_traits {
+    ($($(#[$attr:meta])* pub $t:ident $i:ident { $($field:tt)* })*) => ($(
+        s_no_extra_traits!(it: $(#[$attr])* pub $t $i { $($field)* });
+    )*);
+    (it: $(#[$attr:meta])* pub union $i:ident { $($field:tt)* }) => (
+        cfg_if! {
+            if #[cfg(libc_union)] {
+                __item! {
+                    #[repr(C)]
+                    $(#[$attr])*
+                    pub union $i { $($field)* }
+                }
+
+                impl ::Copy for $i {}
+                impl ::Clone for $i {
+                    fn clone(&self) -> $i { *self }
+                }
+            }
+        }
+    );
+    (it: $(#[$attr:meta])* pub struct $i:ident { $($field:tt)* }) => (
+        __item! {
+            #[repr(C)]
+            $(#[$attr])*
+            pub struct $i { $($field)* }
+        }
+        #[allow(deprecated)]
+        impl ::Copy for $i {}
+        #[allow(deprecated)]
+        impl ::Clone for $i {
+            fn clone(&self) -> $i { *self }
+        }
+    );
+}
+
+macro_rules! e {
+    ($($(#[$attr:meta])* pub enum $i:ident { $($field:tt)* })*) => ($(
+        __item! {
+            #[cfg_attr(feature = "extra_traits", derive(Debug, Eq, Hash, PartialEq))]
+            $(#[$attr])*
+            pub enum $i { $($field)* }
+        }
+        impl ::Copy for $i {}
+        impl ::Clone for $i {
+            fn clone(&self) -> $i { *self }
+        }
+    )*);
+}
+
+macro_rules! s_paren {
+    ($($(#[$attr:meta])* pub struct $i:ident ( $($field:tt)* ); )* ) => ($(
+        __item! {
+            #[cfg_attr(feature = "extra_traits", derive(Debug, Eq, Hash, PartialEq))]
+            $(#[$attr])*
+            pub struct $i ( $($field)* );
+        }
+        impl ::Copy for $i {}
+        impl ::Clone for $i {
+            fn clone(&self) -> $i { *self }
+        }
+    )*);
+}
+
+// This is a pretty horrible hack to allow us to conditionally mark
+// some functions as 'const', without requiring users of this macro
+// to care about the "const-extern-fn" feature.
+//
+// When 'const-extern-fn' is enabled, we emit the captured 'const' keyword
+// in the expanded function.
+//
+// When 'const-extern-fn' is disabled, we always emit a plain 'pub unsafe extern fn'.
+// Note that the expression matched by the macro is exactly the same - this allows
+// users of this macro to work whether or not 'const-extern-fn' is enabled
+//
+// Unfortunately, we need to duplicate most of this macro between the 'cfg_if' blocks.
+// This is because 'const unsafe extern fn' won't even parse on older compilers,
+// so we need to avoid emitting it at all of 'const-extern-fn'.
+//
+// Specifically, moving the 'cfg_if' into the macro body will *not* work.
+// Doing so would cause the '#[cfg(feature = "const-extern-fn")]' to be emitted
+// into user code. The 'cfg' gate will not stop Rust from trying to parse the
+// 'pub const unsafe extern fn', so users would get a compiler error even when
+// the 'const-extern-fn' feature is disabled
+//
+// Note that users of this macro need to place 'const' in a weird position
+// (after the closing ')' for the arguments, but before the return type).
+// This was the only way I could satisfy the following two requirements:
+// 1. Avoid ambiguity errors from 'macro_rules!' (which happen when writing '$foo:ident fn'
+// 2. Allow users of this macro to mix 'pub fn foo' and 'pub const fn bar' within the same
+// 'f!' block
+cfg_if! {
+    if #[cfg(libc_const_extern_fn)] {
+        macro_rules! f {
+            ($($(#[$attr:meta])* pub $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                pub $($constness)* unsafe extern fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+
+        macro_rules! safe_f {
+            ($($(#[$attr:meta])* pub $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                pub $($constness)* extern fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+
+        macro_rules! const_fn {
+            ($($(#[$attr:meta])* $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                $($constness)* fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+
+    } else {
+        macro_rules! f {
+            ($($(#[$attr:meta])* pub $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                pub unsafe extern fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+
+        macro_rules! safe_f {
+            ($($(#[$attr:meta])* pub $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                pub extern fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+
+        macro_rules! const_fn {
+            ($($(#[$attr:meta])* $({$constness:ident})* fn $i:ident(
+                        $($arg:ident: $argty:ty),*
+            ) -> $ret:ty {
+                $($body:stmt);*
+            })*) => ($(
+                #[inline]
+                $(#[$attr])*
+                fn $i($($arg: $argty),*
+                ) -> $ret {
+                    $($body);*
+                }
+            )*)
+        }
+    }
+}
+
+macro_rules! __item {
+    ($i:item) => {
+        $i
+    };
+}
+
+macro_rules! align_const {
+    ($($(#[$attr:meta])*
+       pub const $name:ident : $t1:ty
+       = $t2:ident { $($field:tt)* };)*) => ($(
+        #[cfg(libc_align)]
+        $(#[$attr])*
+        pub const $name : $t1 = $t2 {
+            $($field)*
+        };
+        #[cfg(not(libc_align))]
+        $(#[$attr])*
+        pub const $name : $t1 = $t2 {
+            $($field)*
+            __align: [],
+        };
+    )*)
+}
+
+// This macro is used to deprecate items that should be accessed via the mach2 crate
+macro_rules! deprecated_mach {
+    (pub const $id:ident: $ty:ty = $expr:expr;) => {
+        #[deprecated(
+            since = "0.2.55",
+            note = "Use the `mach2` crate instead",
+        )]
+        #[allow(deprecated)]
+        pub const $id: $ty = $expr;
+    };
+    ($(pub const $id:ident: $ty:ty = $expr:expr;)*) => {
+        $(
+            deprecated_mach!(
+                pub const $id: $ty = $expr;
+            );
+        )*
+    };
+    (pub type $id:ident = $ty:ty;) => {
+        #[deprecated(
+            since = "0.2.55",
+            note = "Use the `mach2` crate instead",
+        )]
+        #[allow(deprecated)]
+        pub type $id = $ty;
+    };
+    ($(pub type $id:ident = $ty:ty;)*) => {
+        $(
+            deprecated_mach!(
+                pub type $id = $ty;
+            );
+        )*
+    }
+}
+
+#[cfg(not(libc_ptr_addr_of))]
+macro_rules! ptr_addr_of {
+    ($place:expr) => {
+        &$place
+    };
+}
+
+#[cfg(libc_ptr_addr_of)]
+macro_rules! ptr_addr_of {
+    ($place:expr) => {
+        ::core::ptr::addr_of!($place)
+    };
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/align.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/align.rs.html new file mode 100644 index 0000000..6e6b0c3 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/align.rs.html @@ -0,0 +1,14 @@ +align.rs - source
1
+2
+3
+4
+5
+6
+
s! {
+    #[repr(align(4))]
+    pub struct in6_addr {
+        pub s6_addr: [u8; 16],
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/align.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/align.rs.html new file mode 100644 index 0000000..fea6f40 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/align.rs.html @@ -0,0 +1,302 @@ +align.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+
macro_rules! expand_align {
+    () => {
+        s! {
+            #[cfg_attr(any(target_pointer_width = "32",
+                           target_arch = "x86_64",
+                           target_arch = "powerpc64",
+                           target_arch = "mips64",
+                           target_arch = "s390x",
+                           target_arch = "sparc64",
+                           target_arch = "aarch64",
+                           target_arch = "riscv64",
+                           target_arch = "riscv32",
+                           target_arch = "loongarch64"),
+                       repr(align(4)))]
+            #[cfg_attr(not(any(target_pointer_width = "32",
+                               target_arch = "x86_64",
+                               target_arch = "powerpc64",
+                               target_arch = "mips64",
+                               target_arch = "s390x",
+                               target_arch = "sparc64",
+                               target_arch = "aarch64",
+                               target_arch = "riscv64",
+                               target_arch = "riscv32",
+                               target_arch = "loongarch64")),
+                       repr(align(8)))]
+            pub struct pthread_mutexattr_t {
+                #[doc(hidden)]
+                size: [u8; ::__SIZEOF_PTHREAD_MUTEXATTR_T],
+            }
+
+            #[cfg_attr(any(target_env = "musl", target_pointer_width = "32"),
+                       repr(align(4)))]
+            #[cfg_attr(all(not(target_env = "musl"),
+                           target_pointer_width = "64"),
+                       repr(align(8)))]
+            pub struct pthread_rwlockattr_t {
+                #[doc(hidden)]
+                size: [u8; ::__SIZEOF_PTHREAD_RWLOCKATTR_T],
+            }
+
+            #[repr(align(4))]
+            pub struct pthread_condattr_t {
+                #[doc(hidden)]
+                size: [u8; ::__SIZEOF_PTHREAD_CONDATTR_T],
+            }
+
+            #[repr(align(8))]
+            pub struct fanotify_event_metadata {
+                pub event_len: __u32,
+                pub vers: __u8,
+                pub reserved: __u8,
+                pub metadata_len: __u16,
+                pub mask: __u64,
+                pub fd: ::c_int,
+                pub pid: ::c_int,
+            }
+        }
+
+        s_no_extra_traits! {
+            #[cfg_attr(all(target_env = "musl",
+                           target_pointer_width = "32"),
+                       repr(align(4)))]
+            #[cfg_attr(all(target_env = "musl",
+                           target_pointer_width = "64"),
+                       repr(align(8)))]
+            #[cfg_attr(all(not(target_env = "musl"),
+                           target_arch = "x86"),
+                       repr(align(4)))]
+            #[cfg_attr(all(not(target_env = "musl"),
+                           not(target_arch = "x86")),
+                       repr(align(8)))]
+            pub struct pthread_cond_t {
+                #[doc(hidden)]
+                size: [u8; ::__SIZEOF_PTHREAD_COND_T],
+            }
+
+            #[cfg_attr(all(target_pointer_width = "32",
+                           any(target_arch = "mips",
+                               target_arch = "arm",
+                               target_arch = "hexagon",
+                               target_arch = "m68k",
+                               target_arch = "powerpc",
+                               target_arch = "sparc",
+                               target_arch = "x86_64",
+                               target_arch = "x86")),
+                       repr(align(4)))]
+            #[cfg_attr(any(target_pointer_width = "64",
+                           not(any(target_arch = "mips",
+                                   target_arch = "arm",
+                                   target_arch = "hexagon",
+                                   target_arch = "m68k",
+                                   target_arch = "powerpc",
+                                   target_arch = "sparc",
+                                   target_arch = "x86_64",
+                                   target_arch = "x86"))),
+                       repr(align(8)))]
+            pub struct pthread_mutex_t {
+                #[doc(hidden)]
+                size: [u8; ::__SIZEOF_PTHREAD_MUTEX_T],
+            }
+
+            #[cfg_attr(all(target_pointer_width = "32",
+                           any(target_arch = "mips",
+                               target_arch = "arm",
+                               target_arch = "hexagon",
+                               target_arch = "m68k",
+                               target_arch = "powerpc",
+                               target_arch = "sparc",
+                               target_arch = "x86_64",
+                               target_arch = "x86")),
+                       repr(align(4)))]
+            #[cfg_attr(any(target_pointer_width = "64",
+                           not(any(target_arch = "mips",
+                                   target_arch = "arm",
+                                   target_arch = "hexagon",
+                                   target_arch = "m68k",
+                                   target_arch = "powerpc",
+                                   target_arch = "sparc",
+                                   target_arch = "x86_64",
+                                   target_arch = "x86"))),
+                       repr(align(8)))]
+            pub struct pthread_rwlock_t {
+                size: [u8; ::__SIZEOF_PTHREAD_RWLOCK_T],
+            }
+
+            // linux/can.h
+            #[repr(align(8))]
+            #[allow(missing_debug_implementations)]
+            pub struct can_frame {
+                pub can_id: canid_t,
+                pub can_dlc: u8,
+                __pad: u8,
+                __res0: u8,
+                __res1: u8,
+                pub data: [u8; CAN_MAX_DLEN],
+            }
+
+            #[repr(align(8))]
+            #[allow(missing_debug_implementations)]
+            pub struct canfd_frame {
+                pub can_id: canid_t,
+                pub len: u8,
+                pub flags: u8,
+                __res0: u8,
+                __res1: u8,
+                pub data: [u8; CANFD_MAX_DLEN],
+            }
+        }
+    };
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/generic/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/generic/mod.rs.html new file mode 100644 index 0000000..d4f39bd --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/generic/mod.rs.html @@ -0,0 +1,576 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+
s! {
+    pub struct termios2 {
+        pub c_iflag: ::tcflag_t,
+        pub c_oflag: ::tcflag_t,
+        pub c_cflag: ::tcflag_t,
+        pub c_lflag: ::tcflag_t,
+        pub c_line: ::cc_t,
+        pub c_cc: [::cc_t; 19],
+        pub c_ispeed: ::speed_t,
+        pub c_ospeed: ::speed_t,
+    }
+}
+
+// include/uapi/asm-generic/socket.h
+// arch/alpha/include/uapi/asm/socket.h
+// tools/include/uapi/asm-generic/socket.h
+// arch/mips/include/uapi/asm/socket.h
+pub const SOL_SOCKET: ::c_int = 1;
+
+// Defined in unix/linux_like/mod.rs
+// pub const SO_DEBUG: ::c_int = 1;
+pub const SO_REUSEADDR: ::c_int = 2;
+pub const SO_TYPE: ::c_int = 3;
+pub const SO_ERROR: ::c_int = 4;
+pub const SO_DONTROUTE: ::c_int = 5;
+pub const SO_BROADCAST: ::c_int = 6;
+pub const SO_SNDBUF: ::c_int = 7;
+pub const SO_RCVBUF: ::c_int = 8;
+pub const SO_KEEPALIVE: ::c_int = 9;
+pub const SO_OOBINLINE: ::c_int = 10;
+pub const SO_NO_CHECK: ::c_int = 11;
+pub const SO_PRIORITY: ::c_int = 12;
+pub const SO_LINGER: ::c_int = 13;
+pub const SO_BSDCOMPAT: ::c_int = 14;
+pub const SO_REUSEPORT: ::c_int = 15;
+pub const SO_PASSCRED: ::c_int = 16;
+pub const SO_PEERCRED: ::c_int = 17;
+pub const SO_RCVLOWAT: ::c_int = 18;
+pub const SO_SNDLOWAT: ::c_int = 19;
+pub const SO_RCVTIMEO: ::c_int = 20;
+pub const SO_SNDTIMEO: ::c_int = 21;
+// pub const SO_RCVTIMEO_OLD: ::c_int = 20;
+// pub const SO_SNDTIMEO_OLD: ::c_int = 21;
+pub const SO_SECURITY_AUTHENTICATION: ::c_int = 22;
+pub const SO_SECURITY_ENCRYPTION_TRANSPORT: ::c_int = 23;
+pub const SO_SECURITY_ENCRYPTION_NETWORK: ::c_int = 24;
+pub const SO_BINDTODEVICE: ::c_int = 25;
+pub const SO_ATTACH_FILTER: ::c_int = 26;
+pub const SO_DETACH_FILTER: ::c_int = 27;
+pub const SO_GET_FILTER: ::c_int = SO_ATTACH_FILTER;
+pub const SO_PEERNAME: ::c_int = 28;
+pub const SO_TIMESTAMP: ::c_int = 29;
+// pub const SO_TIMESTAMP_OLD: ::c_int = 29;
+pub const SO_ACCEPTCONN: ::c_int = 30;
+pub const SO_PEERSEC: ::c_int = 31;
+pub const SO_SNDBUFFORCE: ::c_int = 32;
+pub const SO_RCVBUFFORCE: ::c_int = 33;
+pub const SO_PASSSEC: ::c_int = 34;
+pub const SO_TIMESTAMPNS: ::c_int = 35;
+// pub const SO_TIMESTAMPNS_OLD: ::c_int = 35;
+pub const SO_MARK: ::c_int = 36;
+pub const SO_TIMESTAMPING: ::c_int = 37;
+// pub const SO_TIMESTAMPING_OLD: ::c_int = 37;
+pub const SO_PROTOCOL: ::c_int = 38;
+pub const SO_DOMAIN: ::c_int = 39;
+pub const SO_RXQ_OVFL: ::c_int = 40;
+pub const SO_WIFI_STATUS: ::c_int = 41;
+pub const SCM_WIFI_STATUS: ::c_int = SO_WIFI_STATUS;
+pub const SO_PEEK_OFF: ::c_int = 42;
+pub const SO_NOFCS: ::c_int = 43;
+pub const SO_LOCK_FILTER: ::c_int = 44;
+pub const SO_SELECT_ERR_QUEUE: ::c_int = 45;
+pub const SO_BUSY_POLL: ::c_int = 46;
+pub const SO_MAX_PACING_RATE: ::c_int = 47;
+pub const SO_BPF_EXTENSIONS: ::c_int = 48;
+pub const SO_INCOMING_CPU: ::c_int = 49;
+pub const SO_ATTACH_BPF: ::c_int = 50;
+pub const SO_DETACH_BPF: ::c_int = SO_DETACH_FILTER;
+pub const SO_ATTACH_REUSEPORT_CBPF: ::c_int = 51;
+pub const SO_ATTACH_REUSEPORT_EBPF: ::c_int = 52;
+pub const SO_CNX_ADVICE: ::c_int = 53;
+pub const SCM_TIMESTAMPING_OPT_STATS: ::c_int = 54;
+pub const SO_MEMINFO: ::c_int = 55;
+pub const SO_INCOMING_NAPI_ID: ::c_int = 56;
+pub const SO_COOKIE: ::c_int = 57;
+pub const SCM_TIMESTAMPING_PKTINFO: ::c_int = 58;
+pub const SO_PEERGROUPS: ::c_int = 59;
+pub const SO_ZEROCOPY: ::c_int = 60;
+pub const SO_TXTIME: ::c_int = 61;
+pub const SCM_TXTIME: ::c_int = SO_TXTIME;
+pub const SO_BINDTOIFINDEX: ::c_int = 62;
+cfg_if! {
+    // Some of these platforms in CI already have these constants.
+    // But they may still not have those _OLD ones.
+    if #[cfg(all(any(target_arch = "x86",
+                     target_arch = "x86_64",
+                     target_arch = "aarch64"),
+                 not(target_env = "musl")))] {
+        pub const SO_TIMESTAMP_NEW: ::c_int = 63;
+        pub const SO_TIMESTAMPNS_NEW: ::c_int = 64;
+        pub const SO_TIMESTAMPING_NEW: ::c_int = 65;
+        pub const SO_RCVTIMEO_NEW: ::c_int = 66;
+        pub const SO_SNDTIMEO_NEW: ::c_int = 67;
+        pub const SO_DETACH_REUSEPORT_BPF: ::c_int = 68;
+    }
+}
+
+cfg_if! {
+    if #[cfg(any(target_arch = "x86",
+                 target_arch = "x86_64",
+                 target_arch = "aarch64"))] {
+        pub const FICLONE: ::c_ulong = 0x40049409;
+        pub const FICLONERANGE: ::c_ulong = 0x4020940D;
+    }
+}
+// pub const SO_PREFER_BUSY_POLL: ::c_int = 69;
+// pub const SO_BUSY_POLL_BUDGET: ::c_int = 70;
+
+// Defined in unix/linux_like/mod.rs
+// pub const SCM_TIMESTAMP: ::c_int = SO_TIMESTAMP;
+pub const SCM_TIMESTAMPNS: ::c_int = SO_TIMESTAMPNS;
+pub const SCM_TIMESTAMPING: ::c_int = SO_TIMESTAMPING;
+
+// Ioctl Constants
+
+pub const TCGETS: ::Ioctl = 0x5401;
+pub const TCSETS: ::Ioctl = 0x5402;
+pub const TCSETSW: ::Ioctl = 0x5403;
+pub const TCSETSF: ::Ioctl = 0x5404;
+pub const TCGETA: ::Ioctl = 0x5405;
+pub const TCSETA: ::Ioctl = 0x5406;
+pub const TCSETAW: ::Ioctl = 0x5407;
+pub const TCSETAF: ::Ioctl = 0x5408;
+pub const TCSBRK: ::Ioctl = 0x5409;
+pub const TCXONC: ::Ioctl = 0x540A;
+pub const TCFLSH: ::Ioctl = 0x540B;
+pub const TIOCEXCL: ::Ioctl = 0x540C;
+pub const TIOCNXCL: ::Ioctl = 0x540D;
+pub const TIOCSCTTY: ::Ioctl = 0x540E;
+pub const TIOCGPGRP: ::Ioctl = 0x540F;
+pub const TIOCSPGRP: ::Ioctl = 0x5410;
+pub const TIOCOUTQ: ::Ioctl = 0x5411;
+pub const TIOCSTI: ::Ioctl = 0x5412;
+pub const TIOCGWINSZ: ::Ioctl = 0x5413;
+pub const TIOCSWINSZ: ::Ioctl = 0x5414;
+pub const TIOCMGET: ::Ioctl = 0x5415;
+pub const TIOCMBIS: ::Ioctl = 0x5416;
+pub const TIOCMBIC: ::Ioctl = 0x5417;
+pub const TIOCMSET: ::Ioctl = 0x5418;
+pub const TIOCGSOFTCAR: ::Ioctl = 0x5419;
+pub const TIOCSSOFTCAR: ::Ioctl = 0x541A;
+pub const FIONREAD: ::Ioctl = 0x541B;
+pub const TIOCINQ: ::Ioctl = FIONREAD;
+pub const TIOCLINUX: ::Ioctl = 0x541C;
+pub const TIOCCONS: ::Ioctl = 0x541D;
+pub const TIOCGSERIAL: ::Ioctl = 0x541E;
+pub const TIOCSSERIAL: ::Ioctl = 0x541F;
+pub const TIOCPKT: ::Ioctl = 0x5420;
+pub const FIONBIO: ::Ioctl = 0x5421;
+pub const TIOCNOTTY: ::Ioctl = 0x5422;
+pub const TIOCSETD: ::Ioctl = 0x5423;
+pub const TIOCGETD: ::Ioctl = 0x5424;
+pub const TCSBRKP: ::Ioctl = 0x5425;
+pub const TIOCSBRK: ::Ioctl = 0x5427;
+pub const TIOCCBRK: ::Ioctl = 0x5428;
+pub const TIOCGSID: ::Ioctl = 0x5429;
+pub const TCGETS2: ::Ioctl = 0x802c542a;
+pub const TCSETS2: ::Ioctl = 0x402c542b;
+pub const TCSETSW2: ::Ioctl = 0x402c542c;
+pub const TCSETSF2: ::Ioctl = 0x402c542d;
+pub const TIOCGRS485: ::Ioctl = 0x542E;
+pub const TIOCSRS485: ::Ioctl = 0x542F;
+pub const TIOCGPTN: ::Ioctl = 0x80045430;
+pub const TIOCSPTLCK: ::Ioctl = 0x40045431;
+pub const TIOCGDEV: ::Ioctl = 0x80045432;
+pub const TCGETX: ::Ioctl = 0x5432;
+pub const TCSETX: ::Ioctl = 0x5433;
+pub const TCSETXF: ::Ioctl = 0x5434;
+pub const TCSETXW: ::Ioctl = 0x5435;
+pub const TIOCSIG: ::Ioctl = 0x40045436;
+pub const TIOCVHANGUP: ::Ioctl = 0x5437;
+pub const TIOCGPKT: ::Ioctl = 0x80045438;
+pub const TIOCGPTLCK: ::Ioctl = 0x80045439;
+pub const TIOCGEXCL: ::Ioctl = 0x80045440;
+pub const TIOCGPTPEER: ::Ioctl = 0x5441;
+// pub const TIOCGISO7816: ::Ioctl = 0x80285442;
+// pub const TIOCSISO7816: ::Ioctl = 0xc0285443;
+pub const FIONCLEX: ::Ioctl = 0x5450;
+pub const FIOCLEX: ::Ioctl = 0x5451;
+pub const FIOASYNC: ::Ioctl = 0x5452;
+pub const TIOCSERCONFIG: ::Ioctl = 0x5453;
+pub const TIOCSERGWILD: ::Ioctl = 0x5454;
+pub const TIOCSERSWILD: ::Ioctl = 0x5455;
+pub const TIOCGLCKTRMIOS: ::Ioctl = 0x5456;
+pub const TIOCSLCKTRMIOS: ::Ioctl = 0x5457;
+pub const TIOCSERGSTRUCT: ::Ioctl = 0x5458;
+pub const TIOCSERGETLSR: ::Ioctl = 0x5459;
+pub const TIOCSERGETMULTI: ::Ioctl = 0x545A;
+pub const TIOCSERSETMULTI: ::Ioctl = 0x545B;
+pub const TIOCMIWAIT: ::Ioctl = 0x545C;
+pub const TIOCGICOUNT: ::Ioctl = 0x545D;
+pub const BLKIOMIN: ::Ioctl = 0x1278;
+pub const BLKIOOPT: ::Ioctl = 0x1279;
+pub const BLKSSZGET: ::Ioctl = 0x1268;
+pub const BLKPBSZGET: ::Ioctl = 0x127B;
+
+cfg_if! {
+    if #[cfg(any(target_arch = "arm",
+                 target_arch = "s390x"))] {
+        pub const FIOQSIZE: ::Ioctl = 0x545E;
+    } else {
+        pub const FIOQSIZE: ::Ioctl = 0x5460;
+    }
+}
+
+pub const TIOCM_LE: ::c_int = 0x001;
+pub const TIOCM_DTR: ::c_int = 0x002;
+pub const TIOCM_RTS: ::c_int = 0x004;
+pub const TIOCM_ST: ::c_int = 0x008;
+pub const TIOCM_SR: ::c_int = 0x010;
+pub const TIOCM_CTS: ::c_int = 0x020;
+pub const TIOCM_CAR: ::c_int = 0x040;
+pub const TIOCM_CD: ::c_int = TIOCM_CAR;
+pub const TIOCM_RNG: ::c_int = 0x080;
+pub const TIOCM_RI: ::c_int = TIOCM_RNG;
+pub const TIOCM_DSR: ::c_int = 0x100;
+
+pub const BOTHER: ::speed_t = 0o010000;
+pub const IBSHIFT: ::tcflag_t = 16;
+
+// RLIMIT Constants
+
+cfg_if! {
+    if #[cfg(any(target_env = "gnu",
+                 target_env = "uclibc"))] {
+
+        pub const RLIMIT_CPU: ::__rlimit_resource_t = 0;
+        pub const RLIMIT_FSIZE: ::__rlimit_resource_t = 1;
+        pub const RLIMIT_DATA: ::__rlimit_resource_t = 2;
+        pub const RLIMIT_STACK: ::__rlimit_resource_t = 3;
+        pub const RLIMIT_CORE: ::__rlimit_resource_t = 4;
+        pub const RLIMIT_RSS: ::__rlimit_resource_t = 5;
+        pub const RLIMIT_NPROC: ::__rlimit_resource_t = 6;
+        pub const RLIMIT_NOFILE: ::__rlimit_resource_t = 7;
+        pub const RLIMIT_MEMLOCK: ::__rlimit_resource_t = 8;
+        pub const RLIMIT_AS: ::__rlimit_resource_t = 9;
+        pub const RLIMIT_LOCKS: ::__rlimit_resource_t = 10;
+        pub const RLIMIT_SIGPENDING: ::__rlimit_resource_t = 11;
+        pub const RLIMIT_MSGQUEUE: ::__rlimit_resource_t = 12;
+        pub const RLIMIT_NICE: ::__rlimit_resource_t = 13;
+        pub const RLIMIT_RTPRIO: ::__rlimit_resource_t = 14;
+        pub const RLIMIT_RTTIME: ::__rlimit_resource_t = 15;
+        pub const RLIMIT_NLIMITS: ::__rlimit_resource_t = RLIM_NLIMITS;
+
+    } else if #[cfg(target_env = "musl")] {
+
+        pub const RLIMIT_CPU: ::c_int = 0;
+        pub const RLIMIT_FSIZE: ::c_int = 1;
+        pub const RLIMIT_DATA: ::c_int = 2;
+        pub const RLIMIT_STACK: ::c_int = 3;
+        pub const RLIMIT_CORE: ::c_int = 4;
+        pub const RLIMIT_RSS: ::c_int = 5;
+        pub const RLIMIT_NPROC: ::c_int = 6;
+        pub const RLIMIT_NOFILE: ::c_int = 7;
+        pub const RLIMIT_MEMLOCK: ::c_int = 8;
+        pub const RLIMIT_AS: ::c_int = 9;
+        pub const RLIMIT_LOCKS: ::c_int = 10;
+        pub const RLIMIT_SIGPENDING: ::c_int = 11;
+        pub const RLIMIT_MSGQUEUE: ::c_int = 12;
+        pub const RLIMIT_NICE: ::c_int = 13;
+        pub const RLIMIT_RTPRIO: ::c_int = 14;
+        pub const RLIMIT_RTTIME: ::c_int = 15;
+        pub const RLIM_NLIMITS: ::c_int = 15;
+        pub const RLIMIT_NLIMITS: ::c_int = RLIM_NLIMITS;
+    }
+}
+
+cfg_if! {
+    if #[cfg(target_env = "gnu")] {
+        pub const RLIM_NLIMITS: ::__rlimit_resource_t = 16;
+    }
+    else if #[cfg(target_env = "uclibc")] {
+        pub const RLIM_NLIMITS: ::__rlimit_resource_t = 15;
+    }
+}
+
+pub const RLIM_INFINITY: ::rlim_t = !0;
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/mod.rs.html new file mode 100644 index 0000000..29d416f --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/arch/mod.rs.html @@ -0,0 +1,32 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+
cfg_if! {
+    if #[cfg(any(target_arch = "mips", target_arch = "mips64"))] {
+        mod mips;
+        pub use self::mips::*;
+    } else if #[cfg(any(target_arch = "powerpc", target_arch = "powerpc64"))] {
+        mod powerpc;
+        pub use self::powerpc::*;
+    } else if #[cfg(any(target_arch = "sparc", target_arch = "sparc64"))] {
+        mod sparc;
+        pub use self::sparc::*;
+    } else {
+        mod generic;
+        pub use self::generic::*;
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/align.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/align.rs.html new file mode 100644 index 0000000..59d0d18 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/align.rs.html @@ -0,0 +1,28 @@ +align.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+
s! {
+    // FIXME this is actually a union
+    #[cfg_attr(target_pointer_width = "32",
+               repr(align(4)))]
+    #[cfg_attr(target_pointer_width = "64",
+               repr(align(8)))]
+    pub struct sem_t {
+        #[cfg(target_pointer_width = "32")]
+        __size: [::c_char; 16],
+        #[cfg(target_pointer_width = "64")]
+        __size: [::c_char; 32],
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/mod.rs.html new file mode 100644 index 0000000..c79d1d4 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/mod.rs.html @@ -0,0 +1,254 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+
//! 64-bit specific definitions for linux-like values
+
+pub type ino_t = u64;
+pub type off_t = i64;
+pub type blkcnt_t = i64;
+pub type shmatt_t = u64;
+pub type msgqnum_t = u64;
+pub type msglen_t = u64;
+pub type fsblkcnt_t = u64;
+pub type fsfilcnt_t = u64;
+pub type rlim_t = u64;
+#[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+pub type __syscall_ulong_t = ::c_ulonglong;
+#[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+pub type __syscall_ulong_t = ::c_ulong;
+
+cfg_if! {
+    if #[cfg(all(target_arch = "aarch64", target_pointer_width = "32"))] {
+        pub type clock_t = i32;
+        pub type time_t = i32;
+        pub type __fsword_t = i32;
+    } else {
+        pub type __fsword_t = i64;
+        pub type clock_t = i64;
+        pub type time_t = i64;
+    }
+}
+
+s! {
+    pub struct sigset_t {
+        #[cfg(target_pointer_width = "32")]
+        __val: [u32; 32],
+        #[cfg(target_pointer_width = "64")]
+        __val: [u64; 16],
+    }
+
+    pub struct sysinfo {
+        pub uptime: i64,
+        pub loads: [u64; 3],
+        pub totalram: u64,
+        pub freeram: u64,
+        pub sharedram: u64,
+        pub bufferram: u64,
+        pub totalswap: u64,
+        pub freeswap: u64,
+        pub procs: ::c_ushort,
+        pub pad: ::c_ushort,
+        pub totalhigh: u64,
+        pub freehigh: u64,
+        pub mem_unit: ::c_uint,
+        pub _f: [::c_char; 0],
+    }
+
+    pub struct msqid_ds {
+        pub msg_perm: ::ipc_perm,
+        pub msg_stime: ::time_t,
+        pub msg_rtime: ::time_t,
+        pub msg_ctime: ::time_t,
+        __msg_cbytes: u64,
+        pub msg_qnum: ::msgqnum_t,
+        pub msg_qbytes: ::msglen_t,
+        pub msg_lspid: ::pid_t,
+        pub msg_lrpid: ::pid_t,
+        __glibc_reserved4: u64,
+        __glibc_reserved5: u64,
+    }
+
+    pub struct semid_ds {
+        pub sem_perm: ipc_perm,
+        pub sem_otime: ::time_t,
+        #[cfg(not(any(
+            target_arch = "aarch64",
+            target_arch = "loongarch64",
+            target_arch = "mips64",
+            target_arch = "powerpc64",
+            target_arch = "riscv64",
+            target_arch = "sparc64")))]
+        __reserved: ::__syscall_ulong_t,
+        pub sem_ctime: ::time_t,
+        #[cfg(not(any(
+            target_arch = "aarch64",
+            target_arch = "loongarch64",
+            target_arch = "mips64",
+            target_arch = "powerpc64",
+            target_arch = "riscv64",
+            target_arch = "sparc64")))]
+        __reserved2: ::__syscall_ulong_t,
+        pub sem_nsems: ::__syscall_ulong_t,
+        __glibc_reserved3: ::__syscall_ulong_t,
+        __glibc_reserved4: ::__syscall_ulong_t,
+    }
+}
+
+pub const __SIZEOF_PTHREAD_RWLOCKATTR_T: usize = 8;
+
+pub const O_LARGEFILE: ::c_int = 0;
+
+cfg_if! {
+    if #[cfg(target_arch = "aarch64")] {
+        mod aarch64;
+        pub use self::aarch64::*;
+    } else if #[cfg(any(target_arch = "powerpc64"))] {
+        mod powerpc64;
+        pub use self::powerpc64::*;
+    } else if #[cfg(any(target_arch = "sparc64"))] {
+        mod sparc64;
+        pub use self::sparc64::*;
+    } else if #[cfg(any(target_arch = "mips64"))] {
+        mod mips64;
+        pub use self::mips64::*;
+    } else if #[cfg(any(target_arch = "s390x"))] {
+        mod s390x;
+        pub use self::s390x::*;
+    } else if #[cfg(any(target_arch = "x86_64"))] {
+        mod x86_64;
+        pub use self::x86_64::*;
+    } else if #[cfg(any(target_arch = "riscv64"))] {
+        mod riscv64;
+        pub use self::riscv64::*;
+    } else if #[cfg(any(target_arch = "loongarch64"))] {
+        mod loongarch64;
+        pub use self::loongarch64::*;
+    } else {
+        // Unknown target_arch
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/align.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/align.rs.html new file mode 100644 index 0000000..77f4341 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/align.rs.html @@ -0,0 +1,50 @@ +align.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+
s_no_extra_traits! {
+    #[allow(missing_debug_implementations)]
+    #[repr(align(16))]
+    pub struct max_align_t {
+        priv_: [f64; 4]
+    }
+}
+
+s! {
+    #[repr(align(8))]
+    pub struct clone_args {
+        pub flags: ::c_ulonglong,
+        pub pidfd: ::c_ulonglong,
+        pub child_tid: ::c_ulonglong,
+        pub parent_tid: ::c_ulonglong,
+        pub exit_signal: ::c_ulonglong,
+        pub stack: ::c_ulonglong,
+        pub stack_size: ::c_ulonglong,
+        pub tls: ::c_ulonglong,
+        pub set_tid: ::c_ulonglong,
+        pub set_tid_size: ::c_ulonglong,
+        pub cgroup: ::c_ulonglong,
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/mod.rs.html new file mode 100644 index 0000000..a206703 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/mod.rs.html @@ -0,0 +1,1668 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+
//! x86_64-specific definitions for 64-bit linux-like values
+
+pub type c_char = i8;
+pub type wchar_t = i32;
+pub type nlink_t = u64;
+pub type blksize_t = i64;
+pub type greg_t = i64;
+pub type suseconds_t = i64;
+pub type __u64 = ::c_ulonglong;
+pub type __s64 = ::c_longlong;
+
+s! {
+    pub struct sigaction {
+        pub sa_sigaction: ::sighandler_t,
+        pub sa_mask: ::sigset_t,
+        #[cfg(target_arch = "sparc64")]
+        __reserved0: ::c_int,
+        pub sa_flags: ::c_int,
+        pub sa_restorer: ::Option<extern fn()>,
+    }
+
+    pub struct statfs {
+        pub f_type: ::__fsword_t,
+        pub f_bsize: ::__fsword_t,
+        pub f_blocks: ::fsblkcnt_t,
+        pub f_bfree: ::fsblkcnt_t,
+        pub f_bavail: ::fsblkcnt_t,
+
+        pub f_files: ::fsfilcnt_t,
+        pub f_ffree: ::fsfilcnt_t,
+        pub f_fsid: ::fsid_t,
+
+        pub f_namelen: ::__fsword_t,
+        pub f_frsize: ::__fsword_t,
+        f_spare: [::__fsword_t; 5],
+    }
+
+    pub struct flock {
+        pub l_type: ::c_short,
+        pub l_whence: ::c_short,
+        pub l_start: ::off_t,
+        pub l_len: ::off_t,
+        pub l_pid: ::pid_t,
+    }
+
+    pub struct flock64 {
+        pub l_type: ::c_short,
+        pub l_whence: ::c_short,
+        pub l_start: ::off64_t,
+        pub l_len: ::off64_t,
+        pub l_pid: ::pid_t,
+    }
+
+    pub struct siginfo_t {
+        pub si_signo: ::c_int,
+        pub si_errno: ::c_int,
+        pub si_code: ::c_int,
+        #[doc(hidden)]
+        #[deprecated(
+            since="0.2.54",
+            note="Please leave a comment on \
+                  https://github.com/rust-lang/libc/pull/1316 if you're using \
+                  this field"
+        )]
+        pub _pad: [::c_int; 29],
+        _align: [u64; 0],
+    }
+
+    pub struct stack_t {
+        pub ss_sp: *mut ::c_void,
+        pub ss_flags: ::c_int,
+        pub ss_size: ::size_t
+    }
+
+    pub struct stat {
+        pub st_dev: ::dev_t,
+        pub st_ino: ::ino_t,
+        pub st_nlink: ::nlink_t,
+        pub st_mode: ::mode_t,
+        pub st_uid: ::uid_t,
+        pub st_gid: ::gid_t,
+        __pad0: ::c_int,
+        pub st_rdev: ::dev_t,
+        pub st_size: ::off_t,
+        pub st_blksize: ::blksize_t,
+        pub st_blocks: ::blkcnt_t,
+        pub st_atime: ::time_t,
+        pub st_atime_nsec: i64,
+        pub st_mtime: ::time_t,
+        pub st_mtime_nsec: i64,
+        pub st_ctime: ::time_t,
+        pub st_ctime_nsec: i64,
+        __unused: [i64; 3],
+    }
+
+    pub struct stat64 {
+        pub st_dev: ::dev_t,
+        pub st_ino: ::ino64_t,
+        pub st_nlink: ::nlink_t,
+        pub st_mode: ::mode_t,
+        pub st_uid: ::uid_t,
+        pub st_gid: ::gid_t,
+        __pad0: ::c_int,
+        pub st_rdev: ::dev_t,
+        pub st_size: ::off_t,
+        pub st_blksize: ::blksize_t,
+        pub st_blocks: ::blkcnt64_t,
+        pub st_atime: ::time_t,
+        pub st_atime_nsec: i64,
+        pub st_mtime: ::time_t,
+        pub st_mtime_nsec: i64,
+        pub st_ctime: ::time_t,
+        pub st_ctime_nsec: i64,
+        __reserved: [i64; 3],
+    }
+
+    pub struct statfs64 {
+        pub f_type: ::__fsword_t,
+        pub f_bsize: ::__fsword_t,
+        pub f_blocks: u64,
+        pub f_bfree: u64,
+        pub f_bavail: u64,
+        pub f_files: u64,
+        pub f_ffree: u64,
+        pub f_fsid: ::fsid_t,
+        pub f_namelen: ::__fsword_t,
+        pub f_frsize: ::__fsword_t,
+        pub f_flags: ::__fsword_t,
+        pub f_spare: [::__fsword_t; 4],
+    }
+
+    pub struct statvfs64 {
+        pub f_bsize: ::c_ulong,
+        pub f_frsize: ::c_ulong,
+        pub f_blocks: u64,
+        pub f_bfree: u64,
+        pub f_bavail: u64,
+        pub f_files: u64,
+        pub f_ffree: u64,
+        pub f_favail: u64,
+        pub f_fsid: ::c_ulong,
+        pub f_flag: ::c_ulong,
+        pub f_namemax: ::c_ulong,
+        __f_spare: [::c_int; 6],
+    }
+
+    pub struct pthread_attr_t {
+        #[cfg(target_pointer_width = "32")]
+        __size: [u32; 8],
+        #[cfg(target_pointer_width = "64")]
+        __size: [u64; 7]
+    }
+
+    pub struct _libc_fpxreg {
+        pub significand: [u16; 4],
+        pub exponent: u16,
+        __private: [u16; 3],
+    }
+
+    pub struct _libc_xmmreg {
+        pub element: [u32; 4],
+    }
+
+    pub struct _libc_fpstate {
+        pub cwd: u16,
+        pub swd: u16,
+        pub ftw: u16,
+        pub fop: u16,
+        pub rip: u64,
+        pub rdp: u64,
+        pub mxcsr: u32,
+        pub mxcr_mask: u32,
+        pub _st: [_libc_fpxreg; 8],
+        pub _xmm: [_libc_xmmreg; 16],
+        __private: [u64; 12],
+    }
+
+    pub struct user_regs_struct {
+        pub r15: ::c_ulonglong,
+        pub r14: ::c_ulonglong,
+        pub r13: ::c_ulonglong,
+        pub r12: ::c_ulonglong,
+        pub rbp: ::c_ulonglong,
+        pub rbx: ::c_ulonglong,
+        pub r11: ::c_ulonglong,
+        pub r10: ::c_ulonglong,
+        pub r9: ::c_ulonglong,
+        pub r8: ::c_ulonglong,
+        pub rax: ::c_ulonglong,
+        pub rcx: ::c_ulonglong,
+        pub rdx: ::c_ulonglong,
+        pub rsi: ::c_ulonglong,
+        pub rdi: ::c_ulonglong,
+        pub orig_rax: ::c_ulonglong,
+        pub rip: ::c_ulonglong,
+        pub cs: ::c_ulonglong,
+        pub eflags: ::c_ulonglong,
+        pub rsp: ::c_ulonglong,
+        pub ss: ::c_ulonglong,
+        pub fs_base: ::c_ulonglong,
+        pub gs_base: ::c_ulonglong,
+        pub ds: ::c_ulonglong,
+        pub es: ::c_ulonglong,
+        pub fs: ::c_ulonglong,
+        pub gs: ::c_ulonglong,
+    }
+
+    pub struct user {
+        pub regs: user_regs_struct,
+        pub u_fpvalid: ::c_int,
+        pub i387: user_fpregs_struct,
+        pub u_tsize: ::c_ulonglong,
+        pub u_dsize: ::c_ulonglong,
+        pub u_ssize: ::c_ulonglong,
+        pub start_code: ::c_ulonglong,
+        pub start_stack: ::c_ulonglong,
+        pub signal: ::c_longlong,
+        __reserved: ::c_int,
+        #[cfg(target_pointer_width = "32")]
+        __pad1: u32,
+        pub u_ar0: *mut user_regs_struct,
+        #[cfg(target_pointer_width = "32")]
+        __pad2: u32,
+        pub u_fpstate: *mut user_fpregs_struct,
+        pub magic: ::c_ulonglong,
+        pub u_comm: [::c_char; 32],
+        pub u_debugreg: [::c_ulonglong; 8],
+    }
+
+    pub struct mcontext_t {
+        pub gregs: [greg_t; 23],
+        pub fpregs: *mut _libc_fpstate,
+        __private: [u64; 8],
+    }
+
+    pub struct ipc_perm {
+        pub __key: ::key_t,
+        pub uid: ::uid_t,
+        pub gid: ::gid_t,
+        pub cuid: ::uid_t,
+        pub cgid: ::gid_t,
+        pub mode: ::c_ushort,
+        __pad1: ::c_ushort,
+        pub __seq: ::c_ushort,
+        __pad2: ::c_ushort,
+        __unused1: u64,
+        __unused2: u64
+    }
+
+    pub struct shmid_ds {
+        pub shm_perm: ::ipc_perm,
+        pub shm_segsz: ::size_t,
+        pub shm_atime: ::time_t,
+        pub shm_dtime: ::time_t,
+        pub shm_ctime: ::time_t,
+        pub shm_cpid: ::pid_t,
+        pub shm_lpid: ::pid_t,
+        pub shm_nattch: ::shmatt_t,
+        __unused4: u64,
+        __unused5: u64
+    }
+
+    pub struct seccomp_notif_sizes {
+        pub seccomp_notif: ::__u16,
+        pub seccomp_notif_resp: ::__u16,
+        pub seccomp_data: ::__u16,
+    }
+
+    pub struct ptrace_rseq_configuration {
+        pub rseq_abi_pointer: ::__u64,
+        pub rseq_abi_size: ::__u32,
+        pub signature: ::__u32,
+        pub flags: ::__u32,
+        pub pad: ::__u32,
+    }
+}
+
+s_no_extra_traits! {
+    pub struct user_fpregs_struct {
+        pub cwd: ::c_ushort,
+        pub swd: ::c_ushort,
+        pub ftw: ::c_ushort,
+        pub fop: ::c_ushort,
+        pub rip: ::c_ulonglong,
+        pub rdp: ::c_ulonglong,
+        pub mxcsr: ::c_uint,
+        pub mxcr_mask: ::c_uint,
+        pub st_space: [::c_uint; 32],
+        pub xmm_space: [::c_uint; 64],
+        padding: [::c_uint; 24],
+    }
+
+    pub struct ucontext_t {
+        pub uc_flags: ::c_ulong,
+        pub uc_link: *mut ucontext_t,
+        pub uc_stack: ::stack_t,
+        pub uc_mcontext: mcontext_t,
+        pub uc_sigmask: ::sigset_t,
+        __private: [u8; 512],
+        // FIXME: the shadow stack field requires glibc >= 2.28.
+        // Re-add once we drop compatibility with glibc versions older than
+        // 2.28.
+        //
+        // __ssp: [::c_ulonglong; 4],
+    }
+}
+
+cfg_if! {
+    if #[cfg(feature = "extra_traits")] {
+        impl PartialEq for user_fpregs_struct {
+            fn eq(&self, other: &user_fpregs_struct) -> bool {
+                self.cwd == other.cwd
+                    && self.swd == other.swd
+                    && self.ftw == other.ftw
+                    && self.fop == other.fop
+                    && self.rip == other.rip
+                    && self.rdp == other.rdp
+                    && self.mxcsr == other.mxcsr
+                    && self.mxcr_mask == other.mxcr_mask
+                    && self.st_space == other.st_space
+                    && self
+                    .xmm_space
+                    .iter()
+                    .zip(other.xmm_space.iter())
+                    .all(|(a,b)| a == b)
+                // Ignore padding field
+            }
+        }
+
+        impl Eq for user_fpregs_struct {}
+
+        impl ::fmt::Debug for user_fpregs_struct {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("user_fpregs_struct")
+                    .field("cwd", &self.cwd)
+                    .field("ftw", &self.ftw)
+                    .field("fop", &self.fop)
+                    .field("rip", &self.rip)
+                    .field("rdp", &self.rdp)
+                    .field("mxcsr", &self.mxcsr)
+                    .field("mxcr_mask", &self.mxcr_mask)
+                    .field("st_space", &self.st_space)
+                // FIXME: .field("xmm_space", &self.xmm_space)
+                // Ignore padding field
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for user_fpregs_struct {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.cwd.hash(state);
+                self.ftw.hash(state);
+                self.fop.hash(state);
+                self.rip.hash(state);
+                self.rdp.hash(state);
+                self.mxcsr.hash(state);
+                self.mxcr_mask.hash(state);
+                self.st_space.hash(state);
+                self.xmm_space.hash(state);
+                // Ignore padding field
+            }
+        }
+
+        impl PartialEq for ucontext_t {
+            fn eq(&self, other: &ucontext_t) -> bool {
+                self.uc_flags == other.uc_flags
+                    && self.uc_link == other.uc_link
+                    && self.uc_stack == other.uc_stack
+                    && self.uc_mcontext == other.uc_mcontext
+                    && self.uc_sigmask == other.uc_sigmask
+                // Ignore __private field
+            }
+        }
+
+        impl Eq for ucontext_t {}
+
+        impl ::fmt::Debug for ucontext_t {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("ucontext_t")
+                    .field("uc_flags", &self.uc_flags)
+                    .field("uc_link", &self.uc_link)
+                    .field("uc_stack", &self.uc_stack)
+                    .field("uc_mcontext", &self.uc_mcontext)
+                    .field("uc_sigmask", &self.uc_sigmask)
+                // Ignore __private field
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for ucontext_t {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.uc_flags.hash(state);
+                self.uc_link.hash(state);
+                self.uc_stack.hash(state);
+                self.uc_mcontext.hash(state);
+                self.uc_sigmask.hash(state);
+                // Ignore __private field
+            }
+        }
+    }
+}
+
+pub const POSIX_FADV_DONTNEED: ::c_int = 4;
+pub const POSIX_FADV_NOREUSE: ::c_int = 5;
+
+pub const VEOF: usize = 4;
+pub const RTLD_DEEPBIND: ::c_int = 0x8;
+pub const RTLD_GLOBAL: ::c_int = 0x100;
+pub const RTLD_NOLOAD: ::c_int = 0x4;
+
+pub const O_APPEND: ::c_int = 1024;
+pub const O_CREAT: ::c_int = 64;
+pub const O_EXCL: ::c_int = 128;
+pub const O_NOCTTY: ::c_int = 256;
+pub const O_NONBLOCK: ::c_int = 2048;
+pub const O_SYNC: ::c_int = 1052672;
+pub const O_RSYNC: ::c_int = 1052672;
+pub const O_DSYNC: ::c_int = 4096;
+pub const O_FSYNC: ::c_int = 0x101000;
+pub const O_NOATIME: ::c_int = 0o1000000;
+pub const O_PATH: ::c_int = 0o10000000;
+pub const O_TMPFILE: ::c_int = 0o20000000 | O_DIRECTORY;
+
+pub const MADV_SOFT_OFFLINE: ::c_int = 101;
+pub const MAP_GROWSDOWN: ::c_int = 0x0100;
+
+pub const EDEADLK: ::c_int = 35;
+pub const ENAMETOOLONG: ::c_int = 36;
+pub const ENOLCK: ::c_int = 37;
+pub const ENOSYS: ::c_int = 38;
+pub const ENOTEMPTY: ::c_int = 39;
+pub const ELOOP: ::c_int = 40;
+pub const ENOMSG: ::c_int = 42;
+pub const EIDRM: ::c_int = 43;
+pub const ECHRNG: ::c_int = 44;
+pub const EL2NSYNC: ::c_int = 45;
+pub const EL3HLT: ::c_int = 46;
+pub const EL3RST: ::c_int = 47;
+pub const ELNRNG: ::c_int = 48;
+pub const EUNATCH: ::c_int = 49;
+pub const ENOCSI: ::c_int = 50;
+pub const EL2HLT: ::c_int = 51;
+pub const EBADE: ::c_int = 52;
+pub const EBADR: ::c_int = 53;
+pub const EXFULL: ::c_int = 54;
+pub const ENOANO: ::c_int = 55;
+pub const EBADRQC: ::c_int = 56;
+pub const EBADSLT: ::c_int = 57;
+pub const EMULTIHOP: ::c_int = 72;
+pub const EOVERFLOW: ::c_int = 75;
+pub const ENOTUNIQ: ::c_int = 76;
+pub const EBADFD: ::c_int = 77;
+pub const EBADMSG: ::c_int = 74;
+pub const EREMCHG: ::c_int = 78;
+pub const ELIBACC: ::c_int = 79;
+pub const ELIBBAD: ::c_int = 80;
+pub const ELIBSCN: ::c_int = 81;
+pub const ELIBMAX: ::c_int = 82;
+pub const ELIBEXEC: ::c_int = 83;
+pub const EILSEQ: ::c_int = 84;
+pub const ERESTART: ::c_int = 85;
+pub const ESTRPIPE: ::c_int = 86;
+pub const EUSERS: ::c_int = 87;
+pub const ENOTSOCK: ::c_int = 88;
+pub const EDESTADDRREQ: ::c_int = 89;
+pub const EMSGSIZE: ::c_int = 90;
+pub const EPROTOTYPE: ::c_int = 91;
+pub const ENOPROTOOPT: ::c_int = 92;
+pub const EPROTONOSUPPORT: ::c_int = 93;
+pub const ESOCKTNOSUPPORT: ::c_int = 94;
+pub const EOPNOTSUPP: ::c_int = 95;
+pub const EPFNOSUPPORT: ::c_int = 96;
+pub const EAFNOSUPPORT: ::c_int = 97;
+pub const EADDRINUSE: ::c_int = 98;
+pub const EADDRNOTAVAIL: ::c_int = 99;
+pub const ENETDOWN: ::c_int = 100;
+pub const ENETUNREACH: ::c_int = 101;
+pub const ENETRESET: ::c_int = 102;
+pub const ECONNABORTED: ::c_int = 103;
+pub const ECONNRESET: ::c_int = 104;
+pub const ENOBUFS: ::c_int = 105;
+pub const EISCONN: ::c_int = 106;
+pub const ENOTCONN: ::c_int = 107;
+pub const ESHUTDOWN: ::c_int = 108;
+pub const ETOOMANYREFS: ::c_int = 109;
+pub const ETIMEDOUT: ::c_int = 110;
+pub const ECONNREFUSED: ::c_int = 111;
+pub const EHOSTDOWN: ::c_int = 112;
+pub const EHOSTUNREACH: ::c_int = 113;
+pub const EALREADY: ::c_int = 114;
+pub const EINPROGRESS: ::c_int = 115;
+pub const ESTALE: ::c_int = 116;
+pub const EDQUOT: ::c_int = 122;
+pub const ENOMEDIUM: ::c_int = 123;
+pub const EMEDIUMTYPE: ::c_int = 124;
+pub const ECANCELED: ::c_int = 125;
+pub const ENOKEY: ::c_int = 126;
+pub const EKEYEXPIRED: ::c_int = 127;
+pub const EKEYREVOKED: ::c_int = 128;
+pub const EKEYREJECTED: ::c_int = 129;
+pub const EOWNERDEAD: ::c_int = 130;
+pub const ENOTRECOVERABLE: ::c_int = 131;
+pub const EHWPOISON: ::c_int = 133;
+pub const ERFKILL: ::c_int = 132;
+
+pub const SOCK_STREAM: ::c_int = 1;
+pub const SOCK_DGRAM: ::c_int = 2;
+
+pub const SA_ONSTACK: ::c_int = 0x08000000;
+pub const SA_SIGINFO: ::c_int = 0x00000004;
+pub const SA_NOCLDWAIT: ::c_int = 0x00000002;
+
+pub const SIGTTIN: ::c_int = 21;
+pub const SIGTTOU: ::c_int = 22;
+pub const SIGXCPU: ::c_int = 24;
+pub const SIGXFSZ: ::c_int = 25;
+pub const SIGVTALRM: ::c_int = 26;
+pub const SIGPROF: ::c_int = 27;
+pub const SIGWINCH: ::c_int = 28;
+pub const SIGCHLD: ::c_int = 17;
+pub const SIGBUS: ::c_int = 7;
+pub const SIGUSR1: ::c_int = 10;
+pub const SIGUSR2: ::c_int = 12;
+pub const SIGCONT: ::c_int = 18;
+pub const SIGSTOP: ::c_int = 19;
+pub const SIGTSTP: ::c_int = 20;
+pub const SIGURG: ::c_int = 23;
+pub const SIGIO: ::c_int = 29;
+pub const SIGSYS: ::c_int = 31;
+pub const SIGSTKFLT: ::c_int = 16;
+#[deprecated(since = "0.2.55", note = "Use SIGSYS instead")]
+pub const SIGUNUSED: ::c_int = 31;
+pub const SIGPOLL: ::c_int = 29;
+pub const SIGPWR: ::c_int = 30;
+pub const SIG_SETMASK: ::c_int = 2;
+pub const SIG_BLOCK: ::c_int = 0x000000;
+pub const SIG_UNBLOCK: ::c_int = 0x01;
+
+pub const POLLWRNORM: ::c_short = 0x100;
+pub const POLLWRBAND: ::c_short = 0x200;
+
+pub const O_ASYNC: ::c_int = 0x2000;
+pub const O_NDELAY: ::c_int = 0x800;
+
+pub const PTRACE_DETACH: ::c_uint = 17;
+pub const PTRACE_GET_RSEQ_CONFIGURATION: ::c_uint = 0x420f;
+
+pub const EFD_NONBLOCK: ::c_int = 0x800;
+
+pub const F_GETLK: ::c_int = 5;
+pub const F_GETOWN: ::c_int = 9;
+pub const F_SETOWN: ::c_int = 8;
+pub const F_SETLK: ::c_int = 6;
+pub const F_SETLKW: ::c_int = 7;
+pub const F_OFD_GETLK: ::c_int = 36;
+pub const F_OFD_SETLK: ::c_int = 37;
+pub const F_OFD_SETLKW: ::c_int = 38;
+
+pub const F_RDLCK: ::c_int = 0;
+pub const F_WRLCK: ::c_int = 1;
+pub const F_UNLCK: ::c_int = 2;
+
+pub const SFD_NONBLOCK: ::c_int = 0x0800;
+
+pub const TCSANOW: ::c_int = 0;
+pub const TCSADRAIN: ::c_int = 1;
+pub const TCSAFLUSH: ::c_int = 2;
+
+pub const SFD_CLOEXEC: ::c_int = 0x080000;
+
+pub const NCCS: usize = 32;
+
+pub const O_TRUNC: ::c_int = 512;
+
+pub const O_CLOEXEC: ::c_int = 0x80000;
+
+pub const EBFONT: ::c_int = 59;
+pub const ENOSTR: ::c_int = 60;
+pub const ENODATA: ::c_int = 61;
+pub const ETIME: ::c_int = 62;
+pub const ENOSR: ::c_int = 63;
+pub const ENONET: ::c_int = 64;
+pub const ENOPKG: ::c_int = 65;
+pub const EREMOTE: ::c_int = 66;
+pub const ENOLINK: ::c_int = 67;
+pub const EADV: ::c_int = 68;
+pub const ESRMNT: ::c_int = 69;
+pub const ECOMM: ::c_int = 70;
+pub const EPROTO: ::c_int = 71;
+pub const EDOTDOT: ::c_int = 73;
+
+pub const SA_NODEFER: ::c_int = 0x40000000;
+pub const SA_RESETHAND: ::c_int = 0x80000000;
+pub const SA_RESTART: ::c_int = 0x10000000;
+pub const SA_NOCLDSTOP: ::c_int = 0x00000001;
+
+pub const EPOLL_CLOEXEC: ::c_int = 0x80000;
+
+pub const EFD_CLOEXEC: ::c_int = 0x80000;
+
+pub const __SIZEOF_PTHREAD_CONDATTR_T: usize = 4;
+pub const __SIZEOF_PTHREAD_MUTEXATTR_T: usize = 4;
+
+pub const O_DIRECT: ::c_int = 0x4000;
+pub const O_DIRECTORY: ::c_int = 0x10000;
+pub const O_NOFOLLOW: ::c_int = 0x20000;
+
+pub const MAP_HUGETLB: ::c_int = 0x040000;
+pub const MAP_LOCKED: ::c_int = 0x02000;
+pub const MAP_NORESERVE: ::c_int = 0x04000;
+pub const MAP_32BIT: ::c_int = 0x0040;
+pub const MAP_ANON: ::c_int = 0x0020;
+pub const MAP_ANONYMOUS: ::c_int = 0x0020;
+pub const MAP_DENYWRITE: ::c_int = 0x0800;
+pub const MAP_EXECUTABLE: ::c_int = 0x01000;
+pub const MAP_POPULATE: ::c_int = 0x08000;
+pub const MAP_NONBLOCK: ::c_int = 0x010000;
+pub const MAP_STACK: ::c_int = 0x020000;
+pub const MAP_SYNC: ::c_int = 0x080000;
+
+pub const EDEADLOCK: ::c_int = 35;
+pub const EUCLEAN: ::c_int = 117;
+pub const ENOTNAM: ::c_int = 118;
+pub const ENAVAIL: ::c_int = 119;
+pub const EISNAM: ::c_int = 120;
+pub const EREMOTEIO: ::c_int = 121;
+
+pub const PTRACE_GETFPREGS: ::c_uint = 14;
+pub const PTRACE_SETFPREGS: ::c_uint = 15;
+pub const PTRACE_GETFPXREGS: ::c_uint = 18;
+pub const PTRACE_SETFPXREGS: ::c_uint = 19;
+pub const PTRACE_GETREGS: ::c_uint = 12;
+pub const PTRACE_SETREGS: ::c_uint = 13;
+pub const PTRACE_PEEKSIGINFO_SHARED: ::c_uint = 1;
+pub const PTRACE_SYSEMU: ::c_uint = 31;
+pub const PTRACE_SYSEMU_SINGLESTEP: ::c_uint = 32;
+
+pub const PR_GET_SPECULATION_CTRL: ::c_int = 52;
+pub const PR_SET_SPECULATION_CTRL: ::c_int = 53;
+pub const PR_SPEC_NOT_AFFECTED: ::c_uint = 0;
+pub const PR_SPEC_PRCTL: ::c_uint = 1 << 0;
+pub const PR_SPEC_ENABLE: ::c_uint = 1 << 1;
+pub const PR_SPEC_DISABLE: ::c_uint = 1 << 2;
+pub const PR_SPEC_FORCE_DISABLE: ::c_uint = 1 << 3;
+pub const PR_SPEC_DISABLE_NOEXEC: ::c_uint = 1 << 4;
+pub const PR_SPEC_STORE_BYPASS: ::c_int = 0;
+pub const PR_SPEC_INDIRECT_BRANCH: ::c_int = 1;
+// FIXME: perharps for later
+//pub const PR_SPEC_L1D_FLUSH: ::c_int = 2;
+
+pub const MCL_CURRENT: ::c_int = 0x0001;
+pub const MCL_FUTURE: ::c_int = 0x0002;
+
+pub const SIGSTKSZ: ::size_t = 8192;
+pub const MINSIGSTKSZ: ::size_t = 2048;
+pub const CBAUD: ::tcflag_t = 0o0010017;
+pub const TAB1: ::tcflag_t = 0x00000800;
+pub const TAB2: ::tcflag_t = 0x00001000;
+pub const TAB3: ::tcflag_t = 0x00001800;
+pub const CR1: ::tcflag_t = 0x00000200;
+pub const CR2: ::tcflag_t = 0x00000400;
+pub const CR3: ::tcflag_t = 0x00000600;
+pub const FF1: ::tcflag_t = 0x00008000;
+pub const BS1: ::tcflag_t = 0x00002000;
+pub const VT1: ::tcflag_t = 0x00004000;
+pub const VWERASE: usize = 14;
+pub const VREPRINT: usize = 12;
+pub const VSUSP: usize = 10;
+pub const VSTART: usize = 8;
+pub const VSTOP: usize = 9;
+pub const VDISCARD: usize = 13;
+pub const VTIME: usize = 5;
+pub const IXON: ::tcflag_t = 0x00000400;
+pub const IXOFF: ::tcflag_t = 0x00001000;
+pub const ONLCR: ::tcflag_t = 0x4;
+pub const CSIZE: ::tcflag_t = 0x00000030;
+pub const CS6: ::tcflag_t = 0x00000010;
+pub const CS7: ::tcflag_t = 0x00000020;
+pub const CS8: ::tcflag_t = 0x00000030;
+pub const CSTOPB: ::tcflag_t = 0x00000040;
+pub const CREAD: ::tcflag_t = 0x00000080;
+pub const PARENB: ::tcflag_t = 0x00000100;
+pub const PARODD: ::tcflag_t = 0x00000200;
+pub const HUPCL: ::tcflag_t = 0x00000400;
+pub const CLOCAL: ::tcflag_t = 0x00000800;
+pub const ECHOKE: ::tcflag_t = 0x00000800;
+pub const ECHOE: ::tcflag_t = 0x00000010;
+pub const ECHOK: ::tcflag_t = 0x00000020;
+pub const ECHONL: ::tcflag_t = 0x00000040;
+pub const ECHOPRT: ::tcflag_t = 0x00000400;
+pub const ECHOCTL: ::tcflag_t = 0x00000200;
+pub const ISIG: ::tcflag_t = 0x00000001;
+pub const ICANON: ::tcflag_t = 0x00000002;
+pub const PENDIN: ::tcflag_t = 0x00004000;
+pub const NOFLSH: ::tcflag_t = 0x00000080;
+pub const CIBAUD: ::tcflag_t = 0o02003600000;
+pub const CBAUDEX: ::tcflag_t = 0o010000;
+pub const VSWTC: usize = 7;
+pub const OLCUC: ::tcflag_t = 0o000002;
+pub const NLDLY: ::tcflag_t = 0o000400;
+pub const CRDLY: ::tcflag_t = 0o003000;
+pub const TABDLY: ::tcflag_t = 0o014000;
+pub const BSDLY: ::tcflag_t = 0o020000;
+pub const FFDLY: ::tcflag_t = 0o100000;
+pub const VTDLY: ::tcflag_t = 0o040000;
+pub const XTABS: ::tcflag_t = 0o014000;
+
+pub const B0: ::speed_t = 0o000000;
+pub const B50: ::speed_t = 0o000001;
+pub const B75: ::speed_t = 0o000002;
+pub const B110: ::speed_t = 0o000003;
+pub const B134: ::speed_t = 0o000004;
+pub const B150: ::speed_t = 0o000005;
+pub const B200: ::speed_t = 0o000006;
+pub const B300: ::speed_t = 0o000007;
+pub const B600: ::speed_t = 0o000010;
+pub const B1200: ::speed_t = 0o000011;
+pub const B1800: ::speed_t = 0o000012;
+pub const B2400: ::speed_t = 0o000013;
+pub const B4800: ::speed_t = 0o000014;
+pub const B9600: ::speed_t = 0o000015;
+pub const B19200: ::speed_t = 0o000016;
+pub const B38400: ::speed_t = 0o000017;
+pub const EXTA: ::speed_t = B19200;
+pub const EXTB: ::speed_t = B38400;
+pub const B57600: ::speed_t = 0o010001;
+pub const B115200: ::speed_t = 0o010002;
+pub const B230400: ::speed_t = 0o010003;
+pub const B460800: ::speed_t = 0o010004;
+pub const B500000: ::speed_t = 0o010005;
+pub const B576000: ::speed_t = 0o010006;
+pub const B921600: ::speed_t = 0o010007;
+pub const B1000000: ::speed_t = 0o010010;
+pub const B1152000: ::speed_t = 0o010011;
+pub const B1500000: ::speed_t = 0o010012;
+pub const B2000000: ::speed_t = 0o010013;
+pub const B2500000: ::speed_t = 0o010014;
+pub const B3000000: ::speed_t = 0o010015;
+pub const B3500000: ::speed_t = 0o010016;
+pub const B4000000: ::speed_t = 0o010017;
+
+pub const VEOL: usize = 11;
+pub const VEOL2: usize = 16;
+pub const VMIN: usize = 6;
+pub const IEXTEN: ::tcflag_t = 0x00008000;
+pub const TOSTOP: ::tcflag_t = 0x00000100;
+pub const FLUSHO: ::tcflag_t = 0x00001000;
+pub const EXTPROC: ::tcflag_t = 0x00010000;
+
+// offsets in user_regs_structs, from sys/reg.h
+pub const R15: ::c_int = 0;
+pub const R14: ::c_int = 1;
+pub const R13: ::c_int = 2;
+pub const R12: ::c_int = 3;
+pub const RBP: ::c_int = 4;
+pub const RBX: ::c_int = 5;
+pub const R11: ::c_int = 6;
+pub const R10: ::c_int = 7;
+pub const R9: ::c_int = 8;
+pub const R8: ::c_int = 9;
+pub const RAX: ::c_int = 10;
+pub const RCX: ::c_int = 11;
+pub const RDX: ::c_int = 12;
+pub const RSI: ::c_int = 13;
+pub const RDI: ::c_int = 14;
+pub const ORIG_RAX: ::c_int = 15;
+pub const RIP: ::c_int = 16;
+pub const CS: ::c_int = 17;
+pub const EFLAGS: ::c_int = 18;
+pub const RSP: ::c_int = 19;
+pub const SS: ::c_int = 20;
+pub const FS_BASE: ::c_int = 21;
+pub const GS_BASE: ::c_int = 22;
+pub const DS: ::c_int = 23;
+pub const ES: ::c_int = 24;
+pub const FS: ::c_int = 25;
+pub const GS: ::c_int = 26;
+
+// offsets in mcontext_t.gregs from sys/ucontext.h
+pub const REG_R8: ::c_int = 0;
+pub const REG_R9: ::c_int = 1;
+pub const REG_R10: ::c_int = 2;
+pub const REG_R11: ::c_int = 3;
+pub const REG_R12: ::c_int = 4;
+pub const REG_R13: ::c_int = 5;
+pub const REG_R14: ::c_int = 6;
+pub const REG_R15: ::c_int = 7;
+pub const REG_RDI: ::c_int = 8;
+pub const REG_RSI: ::c_int = 9;
+pub const REG_RBP: ::c_int = 10;
+pub const REG_RBX: ::c_int = 11;
+pub const REG_RDX: ::c_int = 12;
+pub const REG_RAX: ::c_int = 13;
+pub const REG_RCX: ::c_int = 14;
+pub const REG_RSP: ::c_int = 15;
+pub const REG_RIP: ::c_int = 16;
+pub const REG_EFL: ::c_int = 17;
+pub const REG_CSGSFS: ::c_int = 18;
+pub const REG_ERR: ::c_int = 19;
+pub const REG_TRAPNO: ::c_int = 20;
+pub const REG_OLDMASK: ::c_int = 21;
+pub const REG_CR2: ::c_int = 22;
+
+pub const SECCOMP_SET_MODE_STRICT: ::c_uint = 0;
+pub const SECCOMP_SET_MODE_FILTER: ::c_uint = 1;
+pub const SECCOMP_GET_ACTION_AVAIL: ::c_uint = 2;
+pub const SECCOMP_GET_NOTIF_SIZES: ::c_uint = 3;
+
+extern "C" {
+    pub fn getcontext(ucp: *mut ucontext_t) -> ::c_int;
+    pub fn setcontext(ucp: *const ucontext_t) -> ::c_int;
+    pub fn makecontext(ucp: *mut ucontext_t, func: extern "C" fn(), argc: ::c_int, ...);
+    pub fn swapcontext(uocp: *mut ucontext_t, ucp: *const ucontext_t) -> ::c_int;
+    pub fn iopl(level: ::c_int) -> ::c_int;
+    pub fn ioperm(from: ::c_ulong, num: ::c_ulong, turn_on: ::c_int) -> ::c_int;
+}
+
+cfg_if! {
+    if #[cfg(target_pointer_width = "32")] {
+        mod x32;
+        pub use self::x32::*;
+    } else {
+        mod not_x32;
+        pub use self::not_x32::*;
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_align)] {
+        mod align;
+        pub use self::align::*;
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/not_x32.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/not_x32.rs.html new file mode 100644 index 0000000..fec9cfe --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/b64/x86_64/not_x32.rs.html @@ -0,0 +1,902 @@ +not_x32.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+
use pthread_mutex_t;
+
+pub type c_long = i64;
+pub type c_ulong = u64;
+
+s! {
+    pub struct statvfs {
+        pub f_bsize: ::c_ulong,
+        pub f_frsize: ::c_ulong,
+        pub f_blocks: ::fsblkcnt_t,
+        pub f_bfree: ::fsblkcnt_t,
+        pub f_bavail: ::fsblkcnt_t,
+        pub f_files: ::fsfilcnt_t,
+        pub f_ffree: ::fsfilcnt_t,
+        pub f_favail: ::fsfilcnt_t,
+        pub f_fsid: ::c_ulong,
+        pub f_flag: ::c_ulong,
+        pub f_namemax: ::c_ulong,
+        __f_spare: [::c_int; 6],
+    }
+}
+
+pub const __SIZEOF_PTHREAD_MUTEX_T: usize = 40;
+pub const __SIZEOF_PTHREAD_RWLOCK_T: usize = 56;
+
+align_const! {
+    #[cfg(target_endian = "little")]
+    pub const PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+    #[cfg(target_endian = "little")]
+    pub const PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+    #[cfg(target_endian = "little")]
+    pub const PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+    #[cfg(target_endian = "big")]
+    pub const PTHREAD_RECURSIVE_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+    #[cfg(target_endian = "big")]
+    pub const PTHREAD_ERRORCHECK_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+    #[cfg(target_endian = "big")]
+    pub const PTHREAD_ADAPTIVE_MUTEX_INITIALIZER_NP: ::pthread_mutex_t =
+        pthread_mutex_t {
+            size: [
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0,
+                0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            ],
+        };
+}
+
+// Syscall table
+
+pub const SYS_read: ::c_long = 0;
+pub const SYS_write: ::c_long = 1;
+pub const SYS_open: ::c_long = 2;
+pub const SYS_close: ::c_long = 3;
+pub const SYS_stat: ::c_long = 4;
+pub const SYS_fstat: ::c_long = 5;
+pub const SYS_lstat: ::c_long = 6;
+pub const SYS_poll: ::c_long = 7;
+pub const SYS_lseek: ::c_long = 8;
+pub const SYS_mmap: ::c_long = 9;
+pub const SYS_mprotect: ::c_long = 10;
+pub const SYS_munmap: ::c_long = 11;
+pub const SYS_brk: ::c_long = 12;
+pub const SYS_rt_sigaction: ::c_long = 13;
+pub const SYS_rt_sigprocmask: ::c_long = 14;
+pub const SYS_rt_sigreturn: ::c_long = 15;
+pub const SYS_ioctl: ::c_long = 16;
+pub const SYS_pread64: ::c_long = 17;
+pub const SYS_pwrite64: ::c_long = 18;
+pub const SYS_readv: ::c_long = 19;
+pub const SYS_writev: ::c_long = 20;
+pub const SYS_access: ::c_long = 21;
+pub const SYS_pipe: ::c_long = 22;
+pub const SYS_select: ::c_long = 23;
+pub const SYS_sched_yield: ::c_long = 24;
+pub const SYS_mremap: ::c_long = 25;
+pub const SYS_msync: ::c_long = 26;
+pub const SYS_mincore: ::c_long = 27;
+pub const SYS_madvise: ::c_long = 28;
+pub const SYS_shmget: ::c_long = 29;
+pub const SYS_shmat: ::c_long = 30;
+pub const SYS_shmctl: ::c_long = 31;
+pub const SYS_dup: ::c_long = 32;
+pub const SYS_dup2: ::c_long = 33;
+pub const SYS_pause: ::c_long = 34;
+pub const SYS_nanosleep: ::c_long = 35;
+pub const SYS_getitimer: ::c_long = 36;
+pub const SYS_alarm: ::c_long = 37;
+pub const SYS_setitimer: ::c_long = 38;
+pub const SYS_getpid: ::c_long = 39;
+pub const SYS_sendfile: ::c_long = 40;
+pub const SYS_socket: ::c_long = 41;
+pub const SYS_connect: ::c_long = 42;
+pub const SYS_accept: ::c_long = 43;
+pub const SYS_sendto: ::c_long = 44;
+pub const SYS_recvfrom: ::c_long = 45;
+pub const SYS_sendmsg: ::c_long = 46;
+pub const SYS_recvmsg: ::c_long = 47;
+pub const SYS_shutdown: ::c_long = 48;
+pub const SYS_bind: ::c_long = 49;
+pub const SYS_listen: ::c_long = 50;
+pub const SYS_getsockname: ::c_long = 51;
+pub const SYS_getpeername: ::c_long = 52;
+pub const SYS_socketpair: ::c_long = 53;
+pub const SYS_setsockopt: ::c_long = 54;
+pub const SYS_getsockopt: ::c_long = 55;
+pub const SYS_clone: ::c_long = 56;
+pub const SYS_fork: ::c_long = 57;
+pub const SYS_vfork: ::c_long = 58;
+pub const SYS_execve: ::c_long = 59;
+pub const SYS_exit: ::c_long = 60;
+pub const SYS_wait4: ::c_long = 61;
+pub const SYS_kill: ::c_long = 62;
+pub const SYS_uname: ::c_long = 63;
+pub const SYS_semget: ::c_long = 64;
+pub const SYS_semop: ::c_long = 65;
+pub const SYS_semctl: ::c_long = 66;
+pub const SYS_shmdt: ::c_long = 67;
+pub const SYS_msgget: ::c_long = 68;
+pub const SYS_msgsnd: ::c_long = 69;
+pub const SYS_msgrcv: ::c_long = 70;
+pub const SYS_msgctl: ::c_long = 71;
+pub const SYS_fcntl: ::c_long = 72;
+pub const SYS_flock: ::c_long = 73;
+pub const SYS_fsync: ::c_long = 74;
+pub const SYS_fdatasync: ::c_long = 75;
+pub const SYS_truncate: ::c_long = 76;
+pub const SYS_ftruncate: ::c_long = 77;
+pub const SYS_getdents: ::c_long = 78;
+pub const SYS_getcwd: ::c_long = 79;
+pub const SYS_chdir: ::c_long = 80;
+pub const SYS_fchdir: ::c_long = 81;
+pub const SYS_rename: ::c_long = 82;
+pub const SYS_mkdir: ::c_long = 83;
+pub const SYS_rmdir: ::c_long = 84;
+pub const SYS_creat: ::c_long = 85;
+pub const SYS_link: ::c_long = 86;
+pub const SYS_unlink: ::c_long = 87;
+pub const SYS_symlink: ::c_long = 88;
+pub const SYS_readlink: ::c_long = 89;
+pub const SYS_chmod: ::c_long = 90;
+pub const SYS_fchmod: ::c_long = 91;
+pub const SYS_chown: ::c_long = 92;
+pub const SYS_fchown: ::c_long = 93;
+pub const SYS_lchown: ::c_long = 94;
+pub const SYS_umask: ::c_long = 95;
+pub const SYS_gettimeofday: ::c_long = 96;
+pub const SYS_getrlimit: ::c_long = 97;
+pub const SYS_getrusage: ::c_long = 98;
+pub const SYS_sysinfo: ::c_long = 99;
+pub const SYS_times: ::c_long = 100;
+pub const SYS_ptrace: ::c_long = 101;
+pub const SYS_getuid: ::c_long = 102;
+pub const SYS_syslog: ::c_long = 103;
+pub const SYS_getgid: ::c_long = 104;
+pub const SYS_setuid: ::c_long = 105;
+pub const SYS_setgid: ::c_long = 106;
+pub const SYS_geteuid: ::c_long = 107;
+pub const SYS_getegid: ::c_long = 108;
+pub const SYS_setpgid: ::c_long = 109;
+pub const SYS_getppid: ::c_long = 110;
+pub const SYS_getpgrp: ::c_long = 111;
+pub const SYS_setsid: ::c_long = 112;
+pub const SYS_setreuid: ::c_long = 113;
+pub const SYS_setregid: ::c_long = 114;
+pub const SYS_getgroups: ::c_long = 115;
+pub const SYS_setgroups: ::c_long = 116;
+pub const SYS_setresuid: ::c_long = 117;
+pub const SYS_getresuid: ::c_long = 118;
+pub const SYS_setresgid: ::c_long = 119;
+pub const SYS_getresgid: ::c_long = 120;
+pub const SYS_getpgid: ::c_long = 121;
+pub const SYS_setfsuid: ::c_long = 122;
+pub const SYS_setfsgid: ::c_long = 123;
+pub const SYS_getsid: ::c_long = 124;
+pub const SYS_capget: ::c_long = 125;
+pub const SYS_capset: ::c_long = 126;
+pub const SYS_rt_sigpending: ::c_long = 127;
+pub const SYS_rt_sigtimedwait: ::c_long = 128;
+pub const SYS_rt_sigqueueinfo: ::c_long = 129;
+pub const SYS_rt_sigsuspend: ::c_long = 130;
+pub const SYS_sigaltstack: ::c_long = 131;
+pub const SYS_utime: ::c_long = 132;
+pub const SYS_mknod: ::c_long = 133;
+pub const SYS_uselib: ::c_long = 134;
+pub const SYS_personality: ::c_long = 135;
+pub const SYS_ustat: ::c_long = 136;
+pub const SYS_statfs: ::c_long = 137;
+pub const SYS_fstatfs: ::c_long = 138;
+pub const SYS_sysfs: ::c_long = 139;
+pub const SYS_getpriority: ::c_long = 140;
+pub const SYS_setpriority: ::c_long = 141;
+pub const SYS_sched_setparam: ::c_long = 142;
+pub const SYS_sched_getparam: ::c_long = 143;
+pub const SYS_sched_setscheduler: ::c_long = 144;
+pub const SYS_sched_getscheduler: ::c_long = 145;
+pub const SYS_sched_get_priority_max: ::c_long = 146;
+pub const SYS_sched_get_priority_min: ::c_long = 147;
+pub const SYS_sched_rr_get_interval: ::c_long = 148;
+pub const SYS_mlock: ::c_long = 149;
+pub const SYS_munlock: ::c_long = 150;
+pub const SYS_mlockall: ::c_long = 151;
+pub const SYS_munlockall: ::c_long = 152;
+pub const SYS_vhangup: ::c_long = 153;
+pub const SYS_modify_ldt: ::c_long = 154;
+pub const SYS_pivot_root: ::c_long = 155;
+pub const SYS__sysctl: ::c_long = 156;
+pub const SYS_prctl: ::c_long = 157;
+pub const SYS_arch_prctl: ::c_long = 158;
+pub const SYS_adjtimex: ::c_long = 159;
+pub const SYS_setrlimit: ::c_long = 160;
+pub const SYS_chroot: ::c_long = 161;
+pub const SYS_sync: ::c_long = 162;
+pub const SYS_acct: ::c_long = 163;
+pub const SYS_settimeofday: ::c_long = 164;
+pub const SYS_mount: ::c_long = 165;
+pub const SYS_umount2: ::c_long = 166;
+pub const SYS_swapon: ::c_long = 167;
+pub const SYS_swapoff: ::c_long = 168;
+pub const SYS_reboot: ::c_long = 169;
+pub const SYS_sethostname: ::c_long = 170;
+pub const SYS_setdomainname: ::c_long = 171;
+pub const SYS_iopl: ::c_long = 172;
+pub const SYS_ioperm: ::c_long = 173;
+pub const SYS_create_module: ::c_long = 174;
+pub const SYS_init_module: ::c_long = 175;
+pub const SYS_delete_module: ::c_long = 176;
+pub const SYS_get_kernel_syms: ::c_long = 177;
+pub const SYS_query_module: ::c_long = 178;
+pub const SYS_quotactl: ::c_long = 179;
+pub const SYS_nfsservctl: ::c_long = 180;
+pub const SYS_getpmsg: ::c_long = 181;
+pub const SYS_putpmsg: ::c_long = 182;
+pub const SYS_afs_syscall: ::c_long = 183;
+pub const SYS_tuxcall: ::c_long = 184;
+pub const SYS_security: ::c_long = 185;
+pub const SYS_gettid: ::c_long = 186;
+pub const SYS_readahead: ::c_long = 187;
+pub const SYS_setxattr: ::c_long = 188;
+pub const SYS_lsetxattr: ::c_long = 189;
+pub const SYS_fsetxattr: ::c_long = 190;
+pub const SYS_getxattr: ::c_long = 191;
+pub const SYS_lgetxattr: ::c_long = 192;
+pub const SYS_fgetxattr: ::c_long = 193;
+pub const SYS_listxattr: ::c_long = 194;
+pub const SYS_llistxattr: ::c_long = 195;
+pub const SYS_flistxattr: ::c_long = 196;
+pub const SYS_removexattr: ::c_long = 197;
+pub const SYS_lremovexattr: ::c_long = 198;
+pub const SYS_fremovexattr: ::c_long = 199;
+pub const SYS_tkill: ::c_long = 200;
+pub const SYS_time: ::c_long = 201;
+pub const SYS_futex: ::c_long = 202;
+pub const SYS_sched_setaffinity: ::c_long = 203;
+pub const SYS_sched_getaffinity: ::c_long = 204;
+pub const SYS_set_thread_area: ::c_long = 205;
+pub const SYS_io_setup: ::c_long = 206;
+pub const SYS_io_destroy: ::c_long = 207;
+pub const SYS_io_getevents: ::c_long = 208;
+pub const SYS_io_submit: ::c_long = 209;
+pub const SYS_io_cancel: ::c_long = 210;
+pub const SYS_get_thread_area: ::c_long = 211;
+pub const SYS_lookup_dcookie: ::c_long = 212;
+pub const SYS_epoll_create: ::c_long = 213;
+pub const SYS_epoll_ctl_old: ::c_long = 214;
+pub const SYS_epoll_wait_old: ::c_long = 215;
+pub const SYS_remap_file_pages: ::c_long = 216;
+pub const SYS_getdents64: ::c_long = 217;
+pub const SYS_set_tid_address: ::c_long = 218;
+pub const SYS_restart_syscall: ::c_long = 219;
+pub const SYS_semtimedop: ::c_long = 220;
+pub const SYS_fadvise64: ::c_long = 221;
+pub const SYS_timer_create: ::c_long = 222;
+pub const SYS_timer_settime: ::c_long = 223;
+pub const SYS_timer_gettime: ::c_long = 224;
+pub const SYS_timer_getoverrun: ::c_long = 225;
+pub const SYS_timer_delete: ::c_long = 226;
+pub const SYS_clock_settime: ::c_long = 227;
+pub const SYS_clock_gettime: ::c_long = 228;
+pub const SYS_clock_getres: ::c_long = 229;
+pub const SYS_clock_nanosleep: ::c_long = 230;
+pub const SYS_exit_group: ::c_long = 231;
+pub const SYS_epoll_wait: ::c_long = 232;
+pub const SYS_epoll_ctl: ::c_long = 233;
+pub const SYS_tgkill: ::c_long = 234;
+pub const SYS_utimes: ::c_long = 235;
+pub const SYS_vserver: ::c_long = 236;
+pub const SYS_mbind: ::c_long = 237;
+pub const SYS_set_mempolicy: ::c_long = 238;
+pub const SYS_get_mempolicy: ::c_long = 239;
+pub const SYS_mq_open: ::c_long = 240;
+pub const SYS_mq_unlink: ::c_long = 241;
+pub const SYS_mq_timedsend: ::c_long = 242;
+pub const SYS_mq_timedreceive: ::c_long = 243;
+pub const SYS_mq_notify: ::c_long = 244;
+pub const SYS_mq_getsetattr: ::c_long = 245;
+pub const SYS_kexec_load: ::c_long = 246;
+pub const SYS_waitid: ::c_long = 247;
+pub const SYS_add_key: ::c_long = 248;
+pub const SYS_request_key: ::c_long = 249;
+pub const SYS_keyctl: ::c_long = 250;
+pub const SYS_ioprio_set: ::c_long = 251;
+pub const SYS_ioprio_get: ::c_long = 252;
+pub const SYS_inotify_init: ::c_long = 253;
+pub const SYS_inotify_add_watch: ::c_long = 254;
+pub const SYS_inotify_rm_watch: ::c_long = 255;
+pub const SYS_migrate_pages: ::c_long = 256;
+pub const SYS_openat: ::c_long = 257;
+pub const SYS_mkdirat: ::c_long = 258;
+pub const SYS_mknodat: ::c_long = 259;
+pub const SYS_fchownat: ::c_long = 260;
+pub const SYS_futimesat: ::c_long = 261;
+pub const SYS_newfstatat: ::c_long = 262;
+pub const SYS_unlinkat: ::c_long = 263;
+pub const SYS_renameat: ::c_long = 264;
+pub const SYS_linkat: ::c_long = 265;
+pub const SYS_symlinkat: ::c_long = 266;
+pub const SYS_readlinkat: ::c_long = 267;
+pub const SYS_fchmodat: ::c_long = 268;
+pub const SYS_faccessat: ::c_long = 269;
+pub const SYS_pselect6: ::c_long = 270;
+pub const SYS_ppoll: ::c_long = 271;
+pub const SYS_unshare: ::c_long = 272;
+pub const SYS_set_robust_list: ::c_long = 273;
+pub const SYS_get_robust_list: ::c_long = 274;
+pub const SYS_splice: ::c_long = 275;
+pub const SYS_tee: ::c_long = 276;
+pub const SYS_sync_file_range: ::c_long = 277;
+pub const SYS_vmsplice: ::c_long = 278;
+pub const SYS_move_pages: ::c_long = 279;
+pub const SYS_utimensat: ::c_long = 280;
+pub const SYS_epoll_pwait: ::c_long = 281;
+pub const SYS_signalfd: ::c_long = 282;
+pub const SYS_timerfd_create: ::c_long = 283;
+pub const SYS_eventfd: ::c_long = 284;
+pub const SYS_fallocate: ::c_long = 285;
+pub const SYS_timerfd_settime: ::c_long = 286;
+pub const SYS_timerfd_gettime: ::c_long = 287;
+pub const SYS_accept4: ::c_long = 288;
+pub const SYS_signalfd4: ::c_long = 289;
+pub const SYS_eventfd2: ::c_long = 290;
+pub const SYS_epoll_create1: ::c_long = 291;
+pub const SYS_dup3: ::c_long = 292;
+pub const SYS_pipe2: ::c_long = 293;
+pub const SYS_inotify_init1: ::c_long = 294;
+pub const SYS_preadv: ::c_long = 295;
+pub const SYS_pwritev: ::c_long = 296;
+pub const SYS_rt_tgsigqueueinfo: ::c_long = 297;
+pub const SYS_perf_event_open: ::c_long = 298;
+pub const SYS_recvmmsg: ::c_long = 299;
+pub const SYS_fanotify_init: ::c_long = 300;
+pub const SYS_fanotify_mark: ::c_long = 301;
+pub const SYS_prlimit64: ::c_long = 302;
+pub const SYS_name_to_handle_at: ::c_long = 303;
+pub const SYS_open_by_handle_at: ::c_long = 304;
+pub const SYS_clock_adjtime: ::c_long = 305;
+pub const SYS_syncfs: ::c_long = 306;
+pub const SYS_sendmmsg: ::c_long = 307;
+pub const SYS_setns: ::c_long = 308;
+pub const SYS_getcpu: ::c_long = 309;
+pub const SYS_process_vm_readv: ::c_long = 310;
+pub const SYS_process_vm_writev: ::c_long = 311;
+pub const SYS_kcmp: ::c_long = 312;
+pub const SYS_finit_module: ::c_long = 313;
+pub const SYS_sched_setattr: ::c_long = 314;
+pub const SYS_sched_getattr: ::c_long = 315;
+pub const SYS_renameat2: ::c_long = 316;
+pub const SYS_seccomp: ::c_long = 317;
+pub const SYS_getrandom: ::c_long = 318;
+pub const SYS_memfd_create: ::c_long = 319;
+pub const SYS_kexec_file_load: ::c_long = 320;
+pub const SYS_bpf: ::c_long = 321;
+pub const SYS_execveat: ::c_long = 322;
+pub const SYS_userfaultfd: ::c_long = 323;
+pub const SYS_membarrier: ::c_long = 324;
+pub const SYS_mlock2: ::c_long = 325;
+pub const SYS_copy_file_range: ::c_long = 326;
+pub const SYS_preadv2: ::c_long = 327;
+pub const SYS_pwritev2: ::c_long = 328;
+pub const SYS_pkey_mprotect: ::c_long = 329;
+pub const SYS_pkey_alloc: ::c_long = 330;
+pub const SYS_pkey_free: ::c_long = 331;
+pub const SYS_statx: ::c_long = 332;
+pub const SYS_rseq: ::c_long = 334;
+pub const SYS_pidfd_send_signal: ::c_long = 424;
+pub const SYS_io_uring_setup: ::c_long = 425;
+pub const SYS_io_uring_enter: ::c_long = 426;
+pub const SYS_io_uring_register: ::c_long = 427;
+pub const SYS_open_tree: ::c_long = 428;
+pub const SYS_move_mount: ::c_long = 429;
+pub const SYS_fsopen: ::c_long = 430;
+pub const SYS_fsconfig: ::c_long = 431;
+pub const SYS_fsmount: ::c_long = 432;
+pub const SYS_fspick: ::c_long = 433;
+pub const SYS_pidfd_open: ::c_long = 434;
+pub const SYS_clone3: ::c_long = 435;
+pub const SYS_close_range: ::c_long = 436;
+pub const SYS_openat2: ::c_long = 437;
+pub const SYS_pidfd_getfd: ::c_long = 438;
+pub const SYS_faccessat2: ::c_long = 439;
+pub const SYS_process_madvise: ::c_long = 440;
+pub const SYS_epoll_pwait2: ::c_long = 441;
+pub const SYS_mount_setattr: ::c_long = 442;
+pub const SYS_quotactl_fd: ::c_long = 443;
+pub const SYS_landlock_create_ruleset: ::c_long = 444;
+pub const SYS_landlock_add_rule: ::c_long = 445;
+pub const SYS_landlock_restrict_self: ::c_long = 446;
+pub const SYS_memfd_secret: ::c_long = 447;
+pub const SYS_process_mrelease: ::c_long = 448;
+pub const SYS_futex_waitv: ::c_long = 449;
+pub const SYS_set_mempolicy_home_node: ::c_long = 450;
+
+extern "C" {
+    pub fn sysctl(
+        name: *mut ::c_int,
+        namelen: ::c_int,
+        oldp: *mut ::c_void,
+        oldlenp: *mut ::size_t,
+        newp: *mut ::c_void,
+        newlen: ::size_t,
+    ) -> ::c_int;
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/mod.rs.html new file mode 100644 index 0000000..edcd3db --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/gnu/mod.rs.html @@ -0,0 +1,2820 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+
pub type pthread_t = c_ulong;
+pub type __priority_which_t = ::c_uint;
+pub type __rlimit_resource_t = ::c_uint;
+pub type Lmid_t = ::c_long;
+pub type regoff_t = ::c_int;
+
+cfg_if! {
+    if #[cfg(doc)] {
+        // Used in `linux::arch` to define ioctl constants.
+        pub(crate) type Ioctl = ::c_ulong;
+    } else {
+        #[doc(hidden)]
+        pub type Ioctl = ::c_ulong;
+    }
+}
+
+s! {
+    pub struct statx {
+        pub stx_mask: u32,
+        pub stx_blksize: u32,
+        pub stx_attributes: u64,
+        pub stx_nlink: u32,
+        pub stx_uid: u32,
+        pub stx_gid: u32,
+        pub stx_mode: u16,
+        __statx_pad1: [u16; 1],
+        pub stx_ino: u64,
+        pub stx_size: u64,
+        pub stx_blocks: u64,
+        pub stx_attributes_mask: u64,
+        pub stx_atime: ::statx_timestamp,
+        pub stx_btime: ::statx_timestamp,
+        pub stx_ctime: ::statx_timestamp,
+        pub stx_mtime: ::statx_timestamp,
+        pub stx_rdev_major: u32,
+        pub stx_rdev_minor: u32,
+        pub stx_dev_major: u32,
+        pub stx_dev_minor: u32,
+        pub stx_mnt_id: u64,
+        __statx_pad2: u64,
+        __statx_pad3: [u64; 12],
+    }
+
+    pub struct statx_timestamp {
+        pub tv_sec: i64,
+        pub tv_nsec: u32,
+        pub __statx_timestamp_pad1: [i32; 1],
+    }
+
+    pub struct aiocb {
+        pub aio_fildes: ::c_int,
+        pub aio_lio_opcode: ::c_int,
+        pub aio_reqprio: ::c_int,
+        pub aio_buf: *mut ::c_void,
+        pub aio_nbytes: ::size_t,
+        pub aio_sigevent: ::sigevent,
+        __next_prio: *mut aiocb,
+        __abs_prio: ::c_int,
+        __policy: ::c_int,
+        __error_code: ::c_int,
+        __return_value: ::ssize_t,
+        pub aio_offset: off_t,
+        #[cfg(all(not(target_arch = "x86_64"), target_pointer_width = "32"))]
+        __unused1: [::c_char; 4],
+        __glibc_reserved: [::c_char; 32]
+    }
+
+    pub struct __exit_status {
+        pub e_termination: ::c_short,
+        pub e_exit: ::c_short,
+    }
+
+    pub struct __timeval {
+        pub tv_sec: i32,
+        pub tv_usec: i32,
+    }
+
+    pub struct glob64_t {
+        pub gl_pathc: ::size_t,
+        pub gl_pathv: *mut *mut ::c_char,
+        pub gl_offs: ::size_t,
+        pub gl_flags: ::c_int,
+
+        __unused1: *mut ::c_void,
+        __unused2: *mut ::c_void,
+        __unused3: *mut ::c_void,
+        __unused4: *mut ::c_void,
+        __unused5: *mut ::c_void,
+    }
+
+    pub struct msghdr {
+        pub msg_name: *mut ::c_void,
+        pub msg_namelen: ::socklen_t,
+        pub msg_iov: *mut ::iovec,
+        pub msg_iovlen: ::size_t,
+        pub msg_control: *mut ::c_void,
+        pub msg_controllen: ::size_t,
+        pub msg_flags: ::c_int,
+    }
+
+    pub struct cmsghdr {
+        pub cmsg_len: ::size_t,
+        pub cmsg_level: ::c_int,
+        pub cmsg_type: ::c_int,
+    }
+
+    pub struct termios {
+        pub c_iflag: ::tcflag_t,
+        pub c_oflag: ::tcflag_t,
+        pub c_cflag: ::tcflag_t,
+        pub c_lflag: ::tcflag_t,
+        pub c_line: ::cc_t,
+        pub c_cc: [::cc_t; ::NCCS],
+        #[cfg(not(any(
+            target_arch = "sparc",
+            target_arch = "sparc64",
+            target_arch = "mips",
+            target_arch = "mips64")))]
+        pub c_ispeed: ::speed_t,
+        #[cfg(not(any(
+            target_arch = "sparc",
+            target_arch = "sparc64",
+            target_arch = "mips",
+            target_arch = "mips64")))]
+        pub c_ospeed: ::speed_t,
+    }
+
+    pub struct mallinfo {
+        pub arena: ::c_int,
+        pub ordblks: ::c_int,
+        pub smblks: ::c_int,
+        pub hblks: ::c_int,
+        pub hblkhd: ::c_int,
+        pub usmblks: ::c_int,
+        pub fsmblks: ::c_int,
+        pub uordblks: ::c_int,
+        pub fordblks: ::c_int,
+        pub keepcost: ::c_int,
+    }
+
+    pub struct mallinfo2 {
+        pub arena: ::size_t,
+        pub ordblks: ::size_t,
+        pub smblks: ::size_t,
+        pub hblks: ::size_t,
+        pub hblkhd: ::size_t,
+        pub usmblks: ::size_t,
+        pub fsmblks: ::size_t,
+        pub uordblks: ::size_t,
+        pub fordblks: ::size_t,
+        pub keepcost: ::size_t,
+    }
+
+    pub struct nl_pktinfo {
+        pub group: u32,
+    }
+
+    pub struct nl_mmap_req {
+        pub nm_block_size: ::c_uint,
+        pub nm_block_nr: ::c_uint,
+        pub nm_frame_size: ::c_uint,
+        pub nm_frame_nr: ::c_uint,
+    }
+
+    pub struct nl_mmap_hdr {
+        pub nm_status: ::c_uint,
+        pub nm_len: ::c_uint,
+        pub nm_group: u32,
+        pub nm_pid: u32,
+        pub nm_uid: u32,
+        pub nm_gid: u32,
+    }
+
+    pub struct rtentry {
+        pub rt_pad1: ::c_ulong,
+        pub rt_dst: ::sockaddr,
+        pub rt_gateway: ::sockaddr,
+        pub rt_genmask: ::sockaddr,
+        pub rt_flags: ::c_ushort,
+        pub rt_pad2: ::c_short,
+        pub rt_pad3: ::c_ulong,
+        pub rt_tos: ::c_uchar,
+        pub rt_class: ::c_uchar,
+        #[cfg(target_pointer_width = "64")]
+        pub rt_pad4: [::c_short; 3usize],
+        #[cfg(not(target_pointer_width = "64"))]
+        pub rt_pad4: ::c_short,
+        pub rt_metric: ::c_short,
+        pub rt_dev: *mut ::c_char,
+        pub rt_mtu: ::c_ulong,
+        pub rt_window: ::c_ulong,
+        pub rt_irtt: ::c_ushort,
+    }
+
+    pub struct timex {
+        pub modes: ::c_uint,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub offset: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub offset: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub freq: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub freq: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub maxerror: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub maxerror: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub esterror: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub esterror: ::c_long,
+        pub status: ::c_int,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub constant: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub constant: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub precision: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub precision: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub tolerance: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub tolerance: ::c_long,
+        pub time: ::timeval,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub tick: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub tick: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub ppsfreq: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub ppsfreq: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub jitter: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub jitter: ::c_long,
+        pub shift: ::c_int,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub stabil: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub stabil: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub jitcnt: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub jitcnt: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub calcnt: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub calcnt: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub errcnt: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub errcnt: ::c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub stbcnt: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub stbcnt: ::c_long,
+        pub tai: ::c_int,
+        pub __unused1: i32,
+        pub __unused2: i32,
+        pub __unused3: i32,
+        pub __unused4: i32,
+        pub __unused5: i32,
+        pub __unused6: i32,
+        pub __unused7: i32,
+        pub __unused8: i32,
+        pub __unused9: i32,
+        pub __unused10: i32,
+        pub __unused11: i32,
+    }
+
+    pub struct ntptimeval {
+        pub time: ::timeval,
+        pub maxerror: ::c_long,
+        pub esterror: ::c_long,
+        pub tai: ::c_long,
+        pub __glibc_reserved1: ::c_long,
+        pub __glibc_reserved2: ::c_long,
+        pub __glibc_reserved3: ::c_long,
+        pub __glibc_reserved4: ::c_long,
+    }
+
+    pub struct regex_t {
+        __buffer: *mut ::c_void,
+        __allocated: ::size_t,
+        __used: ::size_t,
+        __syntax: ::c_ulong,
+        __fastmap: *mut ::c_char,
+        __translate: *mut ::c_char,
+        __re_nsub: ::size_t,
+        __bitfield: u8,
+    }
+
+    pub struct Elf64_Chdr {
+        pub ch_type: ::Elf64_Word,
+        pub ch_reserved: ::Elf64_Word,
+        pub ch_size: ::Elf64_Xword,
+        pub ch_addralign: ::Elf64_Xword,
+    }
+
+    pub struct Elf32_Chdr {
+        pub ch_type: ::Elf32_Word,
+        pub ch_size: ::Elf32_Word,
+        pub ch_addralign: ::Elf32_Word,
+    }
+
+    pub struct seminfo {
+        pub semmap: ::c_int,
+        pub semmni: ::c_int,
+        pub semmns: ::c_int,
+        pub semmnu: ::c_int,
+        pub semmsl: ::c_int,
+        pub semopm: ::c_int,
+        pub semume: ::c_int,
+        pub semusz: ::c_int,
+        pub semvmx: ::c_int,
+        pub semaem: ::c_int,
+    }
+
+    pub struct ptrace_peeksiginfo_args {
+        pub off: ::__u64,
+        pub flags: ::__u32,
+        pub nr: ::__s32,
+    }
+
+    pub struct __c_anonymous_ptrace_syscall_info_entry {
+        pub nr: ::__u64,
+        pub args: [::__u64; 6],
+    }
+
+    pub struct __c_anonymous_ptrace_syscall_info_exit {
+        pub sval: ::__s64,
+        pub is_error: ::__u8,
+    }
+
+    pub struct __c_anonymous_ptrace_syscall_info_seccomp {
+        pub nr: ::__u64,
+        pub args: [::__u64; 6],
+        pub ret_data: ::__u32,
+    }
+
+    pub struct ptrace_syscall_info {
+        pub op: ::__u8,
+        pub pad: [::__u8; 3],
+        pub arch: ::__u32,
+        pub instruction_pointer: ::__u64,
+        pub stack_pointer: ::__u64,
+        #[cfg(libc_union)]
+        pub u: __c_anonymous_ptrace_syscall_info_data,
+    }
+}
+
+impl siginfo_t {
+    pub unsafe fn si_addr(&self) -> *mut ::c_void {
+        #[repr(C)]
+        struct siginfo_sigfault {
+            _si_signo: ::c_int,
+            _si_errno: ::c_int,
+            _si_code: ::c_int,
+            si_addr: *mut ::c_void,
+        }
+        (*(self as *const siginfo_t as *const siginfo_sigfault)).si_addr
+    }
+
+    pub unsafe fn si_value(&self) -> ::sigval {
+        #[repr(C)]
+        struct siginfo_timer {
+            _si_signo: ::c_int,
+            _si_errno: ::c_int,
+            _si_code: ::c_int,
+            _si_tid: ::c_int,
+            _si_overrun: ::c_int,
+            si_sigval: ::sigval,
+        }
+        (*(self as *const siginfo_t as *const siginfo_timer)).si_sigval
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_union)] {
+        // Internal, for casts to access union fields
+        #[repr(C)]
+        struct sifields_sigchld {
+            si_pid: ::pid_t,
+            si_uid: ::uid_t,
+            si_status: ::c_int,
+            si_utime: ::c_long,
+            si_stime: ::c_long,
+        }
+        impl ::Copy for sifields_sigchld {}
+        impl ::Clone for sifields_sigchld {
+            fn clone(&self) -> sifields_sigchld {
+                *self
+            }
+        }
+
+        // Internal, for casts to access union fields
+        #[repr(C)]
+        union sifields {
+            _align_pointer: *mut ::c_void,
+            sigchld: sifields_sigchld,
+        }
+
+        // Internal, for casts to access union fields. Note that some variants
+        // of sifields start with a pointer, which makes the alignment of
+        // sifields vary on 32-bit and 64-bit architectures.
+        #[repr(C)]
+        struct siginfo_f {
+            _siginfo_base: [::c_int; 3],
+            sifields: sifields,
+        }
+
+        impl siginfo_t {
+            unsafe fn sifields(&self) -> &sifields {
+                &(*(self as *const siginfo_t as *const siginfo_f)).sifields
+            }
+
+            pub unsafe fn si_pid(&self) -> ::pid_t {
+                self.sifields().sigchld.si_pid
+            }
+
+            pub unsafe fn si_uid(&self) -> ::uid_t {
+                self.sifields().sigchld.si_uid
+            }
+
+            pub unsafe fn si_status(&self) -> ::c_int {
+                self.sifields().sigchld.si_status
+            }
+
+            pub unsafe fn si_utime(&self) -> ::c_long {
+                self.sifields().sigchld.si_utime
+            }
+
+            pub unsafe fn si_stime(&self) -> ::c_long {
+                self.sifields().sigchld.si_stime
+            }
+        }
+
+        pub union __c_anonymous_ptrace_syscall_info_data {
+            pub entry: __c_anonymous_ptrace_syscall_info_entry,
+            pub exit: __c_anonymous_ptrace_syscall_info_exit,
+            pub seccomp: __c_anonymous_ptrace_syscall_info_seccomp,
+        }
+        impl ::Copy for __c_anonymous_ptrace_syscall_info_data {}
+        impl ::Clone for __c_anonymous_ptrace_syscall_info_data {
+            fn clone(&self) -> __c_anonymous_ptrace_syscall_info_data {
+                *self
+            }
+        }
+    }
+}
+
+s_no_extra_traits! {
+    pub struct utmpx {
+        pub ut_type: ::c_short,
+        pub ut_pid: ::pid_t,
+        pub ut_line: [::c_char; __UT_LINESIZE],
+        pub ut_id: [::c_char; 4],
+
+        pub ut_user: [::c_char; __UT_NAMESIZE],
+        pub ut_host: [::c_char; __UT_HOSTSIZE],
+        pub ut_exit: __exit_status,
+
+        #[cfg(any(target_arch = "aarch64",
+                  target_arch = "s390x",
+                  target_arch = "loongarch64",
+                  all(target_pointer_width = "32",
+                      not(target_arch = "x86_64"))))]
+        pub ut_session: ::c_long,
+        #[cfg(any(target_arch = "aarch64",
+                  target_arch = "s390x",
+                  target_arch = "loongarch64",
+                  all(target_pointer_width = "32",
+                      not(target_arch = "x86_64"))))]
+        pub ut_tv: ::timeval,
+
+        #[cfg(not(any(target_arch = "aarch64",
+                      target_arch = "s390x",
+                      target_arch = "loongarch64",
+                      all(target_pointer_width = "32",
+                          not(target_arch = "x86_64")))))]
+        pub ut_session: i32,
+        #[cfg(not(any(target_arch = "aarch64",
+                      target_arch = "s390x",
+                      target_arch = "loongarch64",
+                      all(target_pointer_width = "32",
+                          not(target_arch = "x86_64")))))]
+        pub ut_tv: __timeval,
+
+        pub ut_addr_v6: [i32; 4],
+        __glibc_reserved: [::c_char; 20],
+    }
+}
+
+cfg_if! {
+    if #[cfg(feature = "extra_traits")] {
+        impl PartialEq for utmpx {
+            fn eq(&self, other: &utmpx) -> bool {
+                self.ut_type == other.ut_type
+                    && self.ut_pid == other.ut_pid
+                    && self.ut_line == other.ut_line
+                    && self.ut_id == other.ut_id
+                    && self.ut_user == other.ut_user
+                    && self
+                    .ut_host
+                    .iter()
+                    .zip(other.ut_host.iter())
+                    .all(|(a,b)| a == b)
+                    && self.ut_exit == other.ut_exit
+                    && self.ut_session == other.ut_session
+                    && self.ut_tv == other.ut_tv
+                    && self.ut_addr_v6 == other.ut_addr_v6
+                    && self.__glibc_reserved == other.__glibc_reserved
+            }
+        }
+
+        impl Eq for utmpx {}
+
+        impl ::fmt::Debug for utmpx {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("utmpx")
+                    .field("ut_type", &self.ut_type)
+                    .field("ut_pid", &self.ut_pid)
+                    .field("ut_line", &self.ut_line)
+                    .field("ut_id", &self.ut_id)
+                    .field("ut_user", &self.ut_user)
+                // FIXME: .field("ut_host", &self.ut_host)
+                    .field("ut_exit", &self.ut_exit)
+                    .field("ut_session", &self.ut_session)
+                    .field("ut_tv", &self.ut_tv)
+                    .field("ut_addr_v6", &self.ut_addr_v6)
+                    .field("__glibc_reserved", &self.__glibc_reserved)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for utmpx {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.ut_type.hash(state);
+                self.ut_pid.hash(state);
+                self.ut_line.hash(state);
+                self.ut_id.hash(state);
+                self.ut_user.hash(state);
+                self.ut_host.hash(state);
+                self.ut_exit.hash(state);
+                self.ut_session.hash(state);
+                self.ut_tv.hash(state);
+                self.ut_addr_v6.hash(state);
+                self.__glibc_reserved.hash(state);
+            }
+        }
+
+        #[cfg(libc_union)]
+        impl PartialEq for __c_anonymous_ptrace_syscall_info_data {
+            fn eq(&self, other: &__c_anonymous_ptrace_syscall_info_data) -> bool {
+                unsafe {
+                self.entry == other.entry ||
+                    self.exit == other.exit ||
+                    self.seccomp == other.seccomp
+                }
+            }
+        }
+
+        #[cfg(libc_union)]
+        impl Eq for __c_anonymous_ptrace_syscall_info_data {}
+
+        #[cfg(libc_union)]
+        impl ::fmt::Debug for __c_anonymous_ptrace_syscall_info_data {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                unsafe {
+                f.debug_struct("__c_anonymous_ptrace_syscall_info_data")
+                    .field("entry", &self.entry)
+                    .field("exit", &self.exit)
+                    .field("seccomp", &self.seccomp)
+                    .finish()
+                }
+            }
+        }
+
+        #[cfg(libc_union)]
+        impl ::hash::Hash for __c_anonymous_ptrace_syscall_info_data {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                unsafe {
+                self.entry.hash(state);
+                self.exit.hash(state);
+                self.seccomp.hash(state);
+                }
+            }
+        }
+    }
+}
+
+// include/uapi/asm-generic/hugetlb_encode.h
+pub const HUGETLB_FLAG_ENCODE_SHIFT: ::c_int = 26;
+pub const HUGETLB_FLAG_ENCODE_MASK: ::c_int = 0x3f;
+
+pub const HUGETLB_FLAG_ENCODE_64KB: ::c_int = 16 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_512KB: ::c_int = 19 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_1MB: ::c_int = 20 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_2MB: ::c_int = 21 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_8MB: ::c_int = 23 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_16MB: ::c_int = 24 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_32MB: ::c_int = 25 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_256MB: ::c_int = 28 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_512MB: ::c_int = 29 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_1GB: ::c_int = 30 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_2GB: ::c_int = 31 << HUGETLB_FLAG_ENCODE_SHIFT;
+pub const HUGETLB_FLAG_ENCODE_16GB: ::c_int = 34 << HUGETLB_FLAG_ENCODE_SHIFT;
+
+// include/uapi/linux/mman.h
+/*
+ * Huge page size encoding when MAP_HUGETLB is specified, and a huge page
+ * size other than the default is desired.  See hugetlb_encode.h.
+ * All known huge page size encodings are provided here.  It is the
+ * responsibility of the application to know which sizes are supported on
+ * the running system.  See mmap(2) man page for details.
+ */
+pub const MAP_HUGE_SHIFT: ::c_int = HUGETLB_FLAG_ENCODE_SHIFT;
+pub const MAP_HUGE_MASK: ::c_int = HUGETLB_FLAG_ENCODE_MASK;
+
+pub const MAP_HUGE_64KB: ::c_int = HUGETLB_FLAG_ENCODE_64KB;
+pub const MAP_HUGE_512KB: ::c_int = HUGETLB_FLAG_ENCODE_512KB;
+pub const MAP_HUGE_1MB: ::c_int = HUGETLB_FLAG_ENCODE_1MB;
+pub const MAP_HUGE_2MB: ::c_int = HUGETLB_FLAG_ENCODE_2MB;
+pub const MAP_HUGE_8MB: ::c_int = HUGETLB_FLAG_ENCODE_8MB;
+pub const MAP_HUGE_16MB: ::c_int = HUGETLB_FLAG_ENCODE_16MB;
+pub const MAP_HUGE_32MB: ::c_int = HUGETLB_FLAG_ENCODE_32MB;
+pub const MAP_HUGE_256MB: ::c_int = HUGETLB_FLAG_ENCODE_256MB;
+pub const MAP_HUGE_512MB: ::c_int = HUGETLB_FLAG_ENCODE_512MB;
+pub const MAP_HUGE_1GB: ::c_int = HUGETLB_FLAG_ENCODE_1GB;
+pub const MAP_HUGE_2GB: ::c_int = HUGETLB_FLAG_ENCODE_2GB;
+pub const MAP_HUGE_16GB: ::c_int = HUGETLB_FLAG_ENCODE_16GB;
+
+pub const PRIO_PROCESS: ::__priority_which_t = 0;
+pub const PRIO_PGRP: ::__priority_which_t = 1;
+pub const PRIO_USER: ::__priority_which_t = 2;
+
+pub const MS_RMT_MASK: ::c_ulong = 0x02800051;
+
+pub const __UT_LINESIZE: usize = 32;
+pub const __UT_NAMESIZE: usize = 32;
+pub const __UT_HOSTSIZE: usize = 256;
+pub const EMPTY: ::c_short = 0;
+pub const RUN_LVL: ::c_short = 1;
+pub const BOOT_TIME: ::c_short = 2;
+pub const NEW_TIME: ::c_short = 3;
+pub const OLD_TIME: ::c_short = 4;
+pub const INIT_PROCESS: ::c_short = 5;
+pub const LOGIN_PROCESS: ::c_short = 6;
+pub const USER_PROCESS: ::c_short = 7;
+pub const DEAD_PROCESS: ::c_short = 8;
+pub const ACCOUNTING: ::c_short = 9;
+
+// dlfcn.h
+pub const LM_ID_BASE: ::c_long = 0;
+pub const LM_ID_NEWLM: ::c_long = -1;
+
+pub const RTLD_DI_LMID: ::c_int = 1;
+pub const RTLD_DI_LINKMAP: ::c_int = 2;
+pub const RTLD_DI_CONFIGADDR: ::c_int = 3;
+pub const RTLD_DI_SERINFO: ::c_int = 4;
+pub const RTLD_DI_SERINFOSIZE: ::c_int = 5;
+pub const RTLD_DI_ORIGIN: ::c_int = 6;
+pub const RTLD_DI_PROFILENAME: ::c_int = 7;
+pub const RTLD_DI_PROFILEOUT: ::c_int = 8;
+pub const RTLD_DI_TLS_MODID: ::c_int = 9;
+pub const RTLD_DI_TLS_DATA: ::c_int = 10;
+
+pub const SOCK_NONBLOCK: ::c_int = O_NONBLOCK;
+pub const PIDFD_NONBLOCK: ::c_uint = O_NONBLOCK as ::c_uint;
+
+pub const SOL_RXRPC: ::c_int = 272;
+pub const SOL_PPPOL2TP: ::c_int = 273;
+pub const SOL_PNPIPE: ::c_int = 275;
+pub const SOL_RDS: ::c_int = 276;
+pub const SOL_IUCV: ::c_int = 277;
+pub const SOL_CAIF: ::c_int = 278;
+pub const SOL_NFC: ::c_int = 280;
+pub const SOL_XDP: ::c_int = 283;
+
+pub const MSG_TRYHARD: ::c_int = 4;
+
+pub const LC_PAPER: ::c_int = 7;
+pub const LC_NAME: ::c_int = 8;
+pub const LC_ADDRESS: ::c_int = 9;
+pub const LC_TELEPHONE: ::c_int = 10;
+pub const LC_MEASUREMENT: ::c_int = 11;
+pub const LC_IDENTIFICATION: ::c_int = 12;
+pub const LC_PAPER_MASK: ::c_int = 1 << LC_PAPER;
+pub const LC_NAME_MASK: ::c_int = 1 << LC_NAME;
+pub const LC_ADDRESS_MASK: ::c_int = 1 << LC_ADDRESS;
+pub const LC_TELEPHONE_MASK: ::c_int = 1 << LC_TELEPHONE;
+pub const LC_MEASUREMENT_MASK: ::c_int = 1 << LC_MEASUREMENT;
+pub const LC_IDENTIFICATION_MASK: ::c_int = 1 << LC_IDENTIFICATION;
+pub const LC_ALL_MASK: ::c_int = ::LC_CTYPE_MASK
+    | ::LC_NUMERIC_MASK
+    | ::LC_TIME_MASK
+    | ::LC_COLLATE_MASK
+    | ::LC_MONETARY_MASK
+    | ::LC_MESSAGES_MASK
+    | LC_PAPER_MASK
+    | LC_NAME_MASK
+    | LC_ADDRESS_MASK
+    | LC_TELEPHONE_MASK
+    | LC_MEASUREMENT_MASK
+    | LC_IDENTIFICATION_MASK;
+
+pub const ENOTSUP: ::c_int = EOPNOTSUPP;
+
+pub const SOCK_SEQPACKET: ::c_int = 5;
+pub const SOCK_DCCP: ::c_int = 6;
+pub const SOCK_PACKET: ::c_int = 10;
+
+pub const FAN_MARK_INODE: ::c_uint = 0x0000_0000;
+pub const FAN_MARK_MOUNT: ::c_uint = 0x0000_0010;
+// NOTE: FAN_MARK_FILESYSTEM requires Linux Kernel >= 4.20.0
+pub const FAN_MARK_FILESYSTEM: ::c_uint = 0x0000_0100;
+
+pub const AF_IB: ::c_int = 27;
+pub const AF_MPLS: ::c_int = 28;
+pub const AF_NFC: ::c_int = 39;
+pub const AF_VSOCK: ::c_int = 40;
+pub const AF_XDP: ::c_int = 44;
+pub const PF_IB: ::c_int = AF_IB;
+pub const PF_MPLS: ::c_int = AF_MPLS;
+pub const PF_NFC: ::c_int = AF_NFC;
+pub const PF_VSOCK: ::c_int = AF_VSOCK;
+pub const PF_XDP: ::c_int = AF_XDP;
+
+/* DCCP socket options */
+pub const DCCP_SOCKOPT_PACKET_SIZE: ::c_int = 1;
+pub const DCCP_SOCKOPT_SERVICE: ::c_int = 2;
+pub const DCCP_SOCKOPT_CHANGE_L: ::c_int = 3;
+pub const DCCP_SOCKOPT_CHANGE_R: ::c_int = 4;
+pub const DCCP_SOCKOPT_GET_CUR_MPS: ::c_int = 5;
+pub const DCCP_SOCKOPT_SERVER_TIMEWAIT: ::c_int = 6;
+pub const DCCP_SOCKOPT_SEND_CSCOV: ::c_int = 10;
+pub const DCCP_SOCKOPT_RECV_CSCOV: ::c_int = 11;
+pub const DCCP_SOCKOPT_AVAILABLE_CCIDS: ::c_int = 12;
+pub const DCCP_SOCKOPT_CCID: ::c_int = 13;
+pub const DCCP_SOCKOPT_TX_CCID: ::c_int = 14;
+pub const DCCP_SOCKOPT_RX_CCID: ::c_int = 15;
+pub const DCCP_SOCKOPT_QPOLICY_ID: ::c_int = 16;
+pub const DCCP_SOCKOPT_QPOLICY_TXQLEN: ::c_int = 17;
+pub const DCCP_SOCKOPT_CCID_RX_INFO: ::c_int = 128;
+pub const DCCP_SOCKOPT_CCID_TX_INFO: ::c_int = 192;
+
+/// maximum number of services provided on the same listening port
+pub const DCCP_SERVICE_LIST_MAX_LEN: ::c_int = 32;
+
+pub const SIGEV_THREAD_ID: ::c_int = 4;
+
+pub const BUFSIZ: ::c_uint = 8192;
+pub const TMP_MAX: ::c_uint = 238328;
+pub const FOPEN_MAX: ::c_uint = 16;
+pub const FILENAME_MAX: ::c_uint = 4096;
+pub const POSIX_MADV_DONTNEED: ::c_int = 4;
+pub const _SC_EQUIV_CLASS_MAX: ::c_int = 41;
+pub const _SC_CHARCLASS_NAME_MAX: ::c_int = 45;
+pub const _SC_PII: ::c_int = 53;
+pub const _SC_PII_XTI: ::c_int = 54;
+pub const _SC_PII_SOCKET: ::c_int = 55;
+pub const _SC_PII_INTERNET: ::c_int = 56;
+pub const _SC_PII_OSI: ::c_int = 57;
+pub const _SC_POLL: ::c_int = 58;
+pub const _SC_SELECT: ::c_int = 59;
+pub const _SC_PII_INTERNET_STREAM: ::c_int = 61;
+pub const _SC_PII_INTERNET_DGRAM: ::c_int = 62;
+pub const _SC_PII_OSI_COTS: ::c_int = 63;
+pub const _SC_PII_OSI_CLTS: ::c_int = 64;
+pub const _SC_PII_OSI_M: ::c_int = 65;
+pub const _SC_T_IOV_MAX: ::c_int = 66;
+pub const _SC_2_C_VERSION: ::c_int = 96;
+pub const _SC_CHAR_BIT: ::c_int = 101;
+pub const _SC_CHAR_MAX: ::c_int = 102;
+pub const _SC_CHAR_MIN: ::c_int = 103;
+pub const _SC_INT_MAX: ::c_int = 104;
+pub const _SC_INT_MIN: ::c_int = 105;
+pub const _SC_LONG_BIT: ::c_int = 106;
+pub const _SC_WORD_BIT: ::c_int = 107;
+pub const _SC_MB_LEN_MAX: ::c_int = 108;
+pub const _SC_SSIZE_MAX: ::c_int = 110;
+pub const _SC_SCHAR_MAX: ::c_int = 111;
+pub const _SC_SCHAR_MIN: ::c_int = 112;
+pub const _SC_SHRT_MAX: ::c_int = 113;
+pub const _SC_SHRT_MIN: ::c_int = 114;
+pub const _SC_UCHAR_MAX: ::c_int = 115;
+pub const _SC_UINT_MAX: ::c_int = 116;
+pub const _SC_ULONG_MAX: ::c_int = 117;
+pub const _SC_USHRT_MAX: ::c_int = 118;
+pub const _SC_NL_ARGMAX: ::c_int = 119;
+pub const _SC_NL_LANGMAX: ::c_int = 120;
+pub const _SC_NL_MSGMAX: ::c_int = 121;
+pub const _SC_NL_NMAX: ::c_int = 122;
+pub const _SC_NL_SETMAX: ::c_int = 123;
+pub const _SC_NL_TEXTMAX: ::c_int = 124;
+pub const _SC_BASE: ::c_int = 134;
+pub const _SC_C_LANG_SUPPORT: ::c_int = 135;
+pub const _SC_C_LANG_SUPPORT_R: ::c_int = 136;
+pub const _SC_DEVICE_IO: ::c_int = 140;
+pub const _SC_DEVICE_SPECIFIC: ::c_int = 141;
+pub const _SC_DEVICE_SPECIFIC_R: ::c_int = 142;
+pub const _SC_FD_MGMT: ::c_int = 143;
+pub const _SC_FIFO: ::c_int = 144;
+pub const _SC_PIPE: ::c_int = 145;
+pub const _SC_FILE_ATTRIBUTES: ::c_int = 146;
+pub const _SC_FILE_LOCKING: ::c_int = 147;
+pub const _SC_FILE_SYSTEM: ::c_int = 148;
+pub const _SC_MULTI_PROCESS: ::c_int = 150;
+pub const _SC_SINGLE_PROCESS: ::c_int = 151;
+pub const _SC_NETWORKING: ::c_int = 152;
+pub const _SC_REGEX_VERSION: ::c_int = 156;
+pub const _SC_SIGNALS: ::c_int = 158;
+pub const _SC_SYSTEM_DATABASE: ::c_int = 162;
+pub const _SC_SYSTEM_DATABASE_R: ::c_int = 163;
+pub const _SC_USER_GROUPS: ::c_int = 166;
+pub const _SC_USER_GROUPS_R: ::c_int = 167;
+pub const _SC_LEVEL1_ICACHE_SIZE: ::c_int = 185;
+pub const _SC_LEVEL1_ICACHE_ASSOC: ::c_int = 186;
+pub const _SC_LEVEL1_ICACHE_LINESIZE: ::c_int = 187;
+pub const _SC_LEVEL1_DCACHE_SIZE: ::c_int = 188;
+pub const _SC_LEVEL1_DCACHE_ASSOC: ::c_int = 189;
+pub const _SC_LEVEL1_DCACHE_LINESIZE: ::c_int = 190;
+pub const _SC_LEVEL2_CACHE_SIZE: ::c_int = 191;
+pub const _SC_LEVEL2_CACHE_ASSOC: ::c_int = 192;
+pub const _SC_LEVEL2_CACHE_LINESIZE: ::c_int = 193;
+pub const _SC_LEVEL3_CACHE_SIZE: ::c_int = 194;
+pub const _SC_LEVEL3_CACHE_ASSOC: ::c_int = 195;
+pub const _SC_LEVEL3_CACHE_LINESIZE: ::c_int = 196;
+pub const _SC_LEVEL4_CACHE_SIZE: ::c_int = 197;
+pub const _SC_LEVEL4_CACHE_ASSOC: ::c_int = 198;
+pub const _SC_LEVEL4_CACHE_LINESIZE: ::c_int = 199;
+pub const O_ACCMODE: ::c_int = 3;
+pub const ST_RELATIME: ::c_ulong = 4096;
+pub const NI_MAXHOST: ::socklen_t = 1025;
+
+// Most `*_SUPER_MAGIC` constants are defined at the `linux_like` level; the
+// following are only available on newer Linux versions than the versions
+// currently used in CI in some configurations, so we define them here.
+cfg_if! {
+    if #[cfg(not(target_arch = "s390x"))] {
+        pub const BINDERFS_SUPER_MAGIC: ::c_long = 0x6c6f6f70;
+        pub const XFS_SUPER_MAGIC: ::c_long = 0x58465342;
+    } else if #[cfg(target_arch = "s390x")] {
+        pub const BINDERFS_SUPER_MAGIC: ::c_uint = 0x6c6f6f70;
+        pub const XFS_SUPER_MAGIC: ::c_uint = 0x58465342;
+    }
+}
+
+pub const CPU_SETSIZE: ::c_int = 0x400;
+
+pub const PTRACE_TRACEME: ::c_uint = 0;
+pub const PTRACE_PEEKTEXT: ::c_uint = 1;
+pub const PTRACE_PEEKDATA: ::c_uint = 2;
+pub const PTRACE_PEEKUSER: ::c_uint = 3;
+pub const PTRACE_POKETEXT: ::c_uint = 4;
+pub const PTRACE_POKEDATA: ::c_uint = 5;
+pub const PTRACE_POKEUSER: ::c_uint = 6;
+pub const PTRACE_CONT: ::c_uint = 7;
+pub const PTRACE_KILL: ::c_uint = 8;
+pub const PTRACE_SINGLESTEP: ::c_uint = 9;
+pub const PTRACE_ATTACH: ::c_uint = 16;
+pub const PTRACE_SYSCALL: ::c_uint = 24;
+pub const PTRACE_SETOPTIONS: ::c_uint = 0x4200;
+pub const PTRACE_GETEVENTMSG: ::c_uint = 0x4201;
+pub const PTRACE_GETSIGINFO: ::c_uint = 0x4202;
+pub const PTRACE_SETSIGINFO: ::c_uint = 0x4203;
+pub const PTRACE_GETREGSET: ::c_uint = 0x4204;
+pub const PTRACE_SETREGSET: ::c_uint = 0x4205;
+pub const PTRACE_SEIZE: ::c_uint = 0x4206;
+pub const PTRACE_INTERRUPT: ::c_uint = 0x4207;
+pub const PTRACE_LISTEN: ::c_uint = 0x4208;
+pub const PTRACE_PEEKSIGINFO: ::c_uint = 0x4209;
+pub const PTRACE_GET_SYSCALL_INFO: ::c_uint = 0x420e;
+
+// linux/fs.h
+
+// Flags for preadv2/pwritev2
+pub const RWF_HIPRI: ::c_int = 0x00000001;
+pub const RWF_DSYNC: ::c_int = 0x00000002;
+pub const RWF_SYNC: ::c_int = 0x00000004;
+pub const RWF_NOWAIT: ::c_int = 0x00000008;
+pub const RWF_APPEND: ::c_int = 0x00000010;
+
+// linux/rtnetlink.h
+pub const TCA_PAD: ::c_ushort = 9;
+pub const TCA_DUMP_INVISIBLE: ::c_ushort = 10;
+pub const TCA_CHAIN: ::c_ushort = 11;
+pub const TCA_HW_OFFLOAD: ::c_ushort = 12;
+
+pub const RTM_DELNETCONF: u16 = 81;
+pub const RTM_NEWSTATS: u16 = 92;
+pub const RTM_GETSTATS: u16 = 94;
+pub const RTM_NEWCACHEREPORT: u16 = 96;
+
+pub const RTM_F_LOOKUP_TABLE: ::c_uint = 0x1000;
+pub const RTM_F_FIB_MATCH: ::c_uint = 0x2000;
+
+pub const RTA_VIA: ::c_ushort = 18;
+pub const RTA_NEWDST: ::c_ushort = 19;
+pub const RTA_PREF: ::c_ushort = 20;
+pub const RTA_ENCAP_TYPE: ::c_ushort = 21;
+pub const RTA_ENCAP: ::c_ushort = 22;
+pub const RTA_EXPIRES: ::c_ushort = 23;
+pub const RTA_PAD: ::c_ushort = 24;
+pub const RTA_UID: ::c_ushort = 25;
+pub const RTA_TTL_PROPAGATE: ::c_ushort = 26;
+
+// linux/neighbor.h
+pub const NTF_EXT_LEARNED: u8 = 0x10;
+pub const NTF_OFFLOADED: u8 = 0x20;
+
+pub const NDA_MASTER: ::c_ushort = 9;
+pub const NDA_LINK_NETNSID: ::c_ushort = 10;
+pub const NDA_SRC_VNI: ::c_ushort = 11;
+
+// linux/personality.h
+pub const UNAME26: ::c_int = 0x0020000;
+pub const FDPIC_FUNCPTRS: ::c_int = 0x0080000;
+
+// linux/if_addr.h
+pub const IFA_FLAGS: ::c_ushort = 8;
+
+pub const IFA_F_MANAGETEMPADDR: u32 = 0x100;
+pub const IFA_F_NOPREFIXROUTE: u32 = 0x200;
+pub const IFA_F_MCAUTOJOIN: u32 = 0x400;
+pub const IFA_F_STABLE_PRIVACY: u32 = 0x800;
+
+pub const MAX_LINKS: ::c_int = 32;
+
+pub const GENL_UNS_ADMIN_PERM: ::c_int = 0x10;
+
+pub const GENL_ID_VFS_DQUOT: ::c_int = ::NLMSG_MIN_TYPE + 1;
+pub const GENL_ID_PMCRAID: ::c_int = ::NLMSG_MIN_TYPE + 2;
+
+// elf.h
+pub const NT_PRSTATUS: ::c_int = 1;
+pub const NT_PRFPREG: ::c_int = 2;
+pub const NT_FPREGSET: ::c_int = 2;
+pub const NT_PRPSINFO: ::c_int = 3;
+pub const NT_PRXREG: ::c_int = 4;
+pub const NT_TASKSTRUCT: ::c_int = 4;
+pub const NT_PLATFORM: ::c_int = 5;
+pub const NT_AUXV: ::c_int = 6;
+pub const NT_GWINDOWS: ::c_int = 7;
+pub const NT_ASRS: ::c_int = 8;
+pub const NT_PSTATUS: ::c_int = 10;
+pub const NT_PSINFO: ::c_int = 13;
+pub const NT_PRCRED: ::c_int = 14;
+pub const NT_UTSNAME: ::c_int = 15;
+pub const NT_LWPSTATUS: ::c_int = 16;
+pub const NT_LWPSINFO: ::c_int = 17;
+pub const NT_PRFPXREG: ::c_int = 20;
+
+pub const ELFOSABI_ARM_AEABI: u8 = 64;
+
+// linux/keyctl.h
+pub const KEYCTL_DH_COMPUTE: u32 = 23;
+pub const KEYCTL_PKEY_QUERY: u32 = 24;
+pub const KEYCTL_PKEY_ENCRYPT: u32 = 25;
+pub const KEYCTL_PKEY_DECRYPT: u32 = 26;
+pub const KEYCTL_PKEY_SIGN: u32 = 27;
+pub const KEYCTL_PKEY_VERIFY: u32 = 28;
+pub const KEYCTL_RESTRICT_KEYRING: u32 = 29;
+
+pub const KEYCTL_SUPPORTS_ENCRYPT: u32 = 0x01;
+pub const KEYCTL_SUPPORTS_DECRYPT: u32 = 0x02;
+pub const KEYCTL_SUPPORTS_SIGN: u32 = 0x04;
+pub const KEYCTL_SUPPORTS_VERIFY: u32 = 0x08;
+cfg_if! {
+    if #[cfg(not(any(target_arch="mips", target_arch="mips64")))] {
+        pub const KEYCTL_MOVE: u32 = 30;
+        pub const KEYCTL_CAPABILITIES: u32 = 31;
+
+        pub const KEYCTL_CAPS0_CAPABILITIES: u32 = 0x01;
+        pub const KEYCTL_CAPS0_PERSISTENT_KEYRINGS: u32 = 0x02;
+        pub const KEYCTL_CAPS0_DIFFIE_HELLMAN: u32 = 0x04;
+        pub const KEYCTL_CAPS0_PUBLIC_KEY: u32 = 0x08;
+        pub const KEYCTL_CAPS0_BIG_KEY: u32 = 0x10;
+        pub const KEYCTL_CAPS0_INVALIDATE: u32 = 0x20;
+        pub const KEYCTL_CAPS0_RESTRICT_KEYRING: u32 = 0x40;
+        pub const KEYCTL_CAPS0_MOVE: u32 = 0x80;
+        pub const KEYCTL_CAPS1_NS_KEYRING_NAME: u32 = 0x01;
+        pub const KEYCTL_CAPS1_NS_KEY_TAG: u32 = 0x02;
+    }
+}
+
+pub const M_MXFAST: ::c_int = 1;
+pub const M_NLBLKS: ::c_int = 2;
+pub const M_GRAIN: ::c_int = 3;
+pub const M_KEEP: ::c_int = 4;
+pub const M_TRIM_THRESHOLD: ::c_int = -1;
+pub const M_TOP_PAD: ::c_int = -2;
+pub const M_MMAP_THRESHOLD: ::c_int = -3;
+pub const M_MMAP_MAX: ::c_int = -4;
+pub const M_CHECK_ACTION: ::c_int = -5;
+pub const M_PERTURB: ::c_int = -6;
+pub const M_ARENA_TEST: ::c_int = -7;
+pub const M_ARENA_MAX: ::c_int = -8;
+
+pub const AT_STATX_SYNC_TYPE: ::c_int = 0x6000;
+pub const AT_STATX_SYNC_AS_STAT: ::c_int = 0x0000;
+pub const AT_STATX_FORCE_SYNC: ::c_int = 0x2000;
+pub const AT_STATX_DONT_SYNC: ::c_int = 0x4000;
+pub const STATX_TYPE: ::c_uint = 0x0001;
+pub const STATX_MODE: ::c_uint = 0x0002;
+pub const STATX_NLINK: ::c_uint = 0x0004;
+pub const STATX_UID: ::c_uint = 0x0008;
+pub const STATX_GID: ::c_uint = 0x0010;
+pub const STATX_ATIME: ::c_uint = 0x0020;
+pub const STATX_MTIME: ::c_uint = 0x0040;
+pub const STATX_CTIME: ::c_uint = 0x0080;
+pub const STATX_INO: ::c_uint = 0x0100;
+pub const STATX_SIZE: ::c_uint = 0x0200;
+pub const STATX_BLOCKS: ::c_uint = 0x0400;
+pub const STATX_BASIC_STATS: ::c_uint = 0x07ff;
+pub const STATX_BTIME: ::c_uint = 0x0800;
+pub const STATX_MNT_ID: ::c_uint = 0x1000;
+pub const STATX_ALL: ::c_uint = 0x0fff;
+pub const STATX__RESERVED: ::c_int = 0x80000000;
+pub const STATX_ATTR_COMPRESSED: ::c_int = 0x0004;
+pub const STATX_ATTR_IMMUTABLE: ::c_int = 0x0010;
+pub const STATX_ATTR_APPEND: ::c_int = 0x0020;
+pub const STATX_ATTR_NODUMP: ::c_int = 0x0040;
+pub const STATX_ATTR_ENCRYPTED: ::c_int = 0x0800;
+pub const STATX_ATTR_AUTOMOUNT: ::c_int = 0x1000;
+pub const STATX_ATTR_MOUNT_ROOT: ::c_int = 0x2000;
+pub const STATX_ATTR_VERITY: ::c_int = 0x00100000;
+pub const STATX_ATTR_DAX: ::c_int = 0x00200000;
+
+pub const SOMAXCONN: ::c_int = 4096;
+
+//sys/timex.h
+pub const ADJ_OFFSET: ::c_uint = 0x0001;
+pub const ADJ_FREQUENCY: ::c_uint = 0x0002;
+pub const ADJ_MAXERROR: ::c_uint = 0x0004;
+pub const ADJ_ESTERROR: ::c_uint = 0x0008;
+pub const ADJ_STATUS: ::c_uint = 0x0010;
+pub const ADJ_TIMECONST: ::c_uint = 0x0020;
+pub const ADJ_TAI: ::c_uint = 0x0080;
+pub const ADJ_SETOFFSET: ::c_uint = 0x0100;
+pub const ADJ_MICRO: ::c_uint = 0x1000;
+pub const ADJ_NANO: ::c_uint = 0x2000;
+pub const ADJ_TICK: ::c_uint = 0x4000;
+pub const ADJ_OFFSET_SINGLESHOT: ::c_uint = 0x8001;
+pub const ADJ_OFFSET_SS_READ: ::c_uint = 0xa001;
+pub const MOD_OFFSET: ::c_uint = ADJ_OFFSET;
+pub const MOD_FREQUENCY: ::c_uint = ADJ_FREQUENCY;
+pub const MOD_MAXERROR: ::c_uint = ADJ_MAXERROR;
+pub const MOD_ESTERROR: ::c_uint = ADJ_ESTERROR;
+pub const MOD_STATUS: ::c_uint = ADJ_STATUS;
+pub const MOD_TIMECONST: ::c_uint = ADJ_TIMECONST;
+pub const MOD_CLKB: ::c_uint = ADJ_TICK;
+pub const MOD_CLKA: ::c_uint = ADJ_OFFSET_SINGLESHOT;
+pub const MOD_TAI: ::c_uint = ADJ_TAI;
+pub const MOD_MICRO: ::c_uint = ADJ_MICRO;
+pub const MOD_NANO: ::c_uint = ADJ_NANO;
+pub const STA_PLL: ::c_int = 0x0001;
+pub const STA_PPSFREQ: ::c_int = 0x0002;
+pub const STA_PPSTIME: ::c_int = 0x0004;
+pub const STA_FLL: ::c_int = 0x0008;
+pub const STA_INS: ::c_int = 0x0010;
+pub const STA_DEL: ::c_int = 0x0020;
+pub const STA_UNSYNC: ::c_int = 0x0040;
+pub const STA_FREQHOLD: ::c_int = 0x0080;
+pub const STA_PPSSIGNAL: ::c_int = 0x0100;
+pub const STA_PPSJITTER: ::c_int = 0x0200;
+pub const STA_PPSWANDER: ::c_int = 0x0400;
+pub const STA_PPSERROR: ::c_int = 0x0800;
+pub const STA_CLOCKERR: ::c_int = 0x1000;
+pub const STA_NANO: ::c_int = 0x2000;
+pub const STA_MODE: ::c_int = 0x4000;
+pub const STA_CLK: ::c_int = 0x8000;
+pub const STA_RONLY: ::c_int = STA_PPSSIGNAL
+    | STA_PPSJITTER
+    | STA_PPSWANDER
+    | STA_PPSERROR
+    | STA_CLOCKERR
+    | STA_NANO
+    | STA_MODE
+    | STA_CLK;
+pub const NTP_API: ::c_int = 4;
+pub const TIME_OK: ::c_int = 0;
+pub const TIME_INS: ::c_int = 1;
+pub const TIME_DEL: ::c_int = 2;
+pub const TIME_OOP: ::c_int = 3;
+pub const TIME_WAIT: ::c_int = 4;
+pub const TIME_ERROR: ::c_int = 5;
+pub const TIME_BAD: ::c_int = TIME_ERROR;
+pub const MAXTC: ::c_long = 6;
+
+cfg_if! {
+    if #[cfg(any(
+        target_arch = "arm",
+        target_arch = "x86",
+        target_arch = "x86_64",
+        target_arch = "s390x",
+        target_arch = "riscv64",
+        target_arch = "riscv32"
+    ))] {
+        pub const PTHREAD_STACK_MIN: ::size_t = 16384;
+    } else if #[cfg(any(
+               target_arch = "sparc",
+               target_arch = "sparc64"
+           ))] {
+        pub const PTHREAD_STACK_MIN: ::size_t = 0x6000;
+    } else {
+        pub const PTHREAD_STACK_MIN: ::size_t = 131072;
+    }
+}
+pub const PTHREAD_MUTEX_ADAPTIVE_NP: ::c_int = 3;
+
+pub const REG_STARTEND: ::c_int = 4;
+
+pub const REG_EEND: ::c_int = 14;
+pub const REG_ESIZE: ::c_int = 15;
+pub const REG_ERPAREN: ::c_int = 16;
+
+extern "C" {
+    pub fn fgetspent_r(
+        fp: *mut ::FILE,
+        spbuf: *mut ::spwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        spbufp: *mut *mut ::spwd,
+    ) -> ::c_int;
+    pub fn sgetspent_r(
+        s: *const ::c_char,
+        spbuf: *mut ::spwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        spbufp: *mut *mut ::spwd,
+    ) -> ::c_int;
+    pub fn getspent_r(
+        spbuf: *mut ::spwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        spbufp: *mut *mut ::spwd,
+    ) -> ::c_int;
+    pub fn qsort_r(
+        base: *mut ::c_void,
+        num: ::size_t,
+        size: ::size_t,
+        compar: ::Option<
+            unsafe extern "C" fn(*const ::c_void, *const ::c_void, *mut ::c_void) -> ::c_int,
+        >,
+        arg: *mut ::c_void,
+    );
+    pub fn sendmmsg(
+        sockfd: ::c_int,
+        msgvec: *mut ::mmsghdr,
+        vlen: ::c_uint,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn recvmmsg(
+        sockfd: ::c_int,
+        msgvec: *mut ::mmsghdr,
+        vlen: ::c_uint,
+        flags: ::c_int,
+        timeout: *mut ::timespec,
+    ) -> ::c_int;
+
+    pub fn getrlimit64(resource: ::__rlimit_resource_t, rlim: *mut ::rlimit64) -> ::c_int;
+    pub fn setrlimit64(resource: ::__rlimit_resource_t, rlim: *const ::rlimit64) -> ::c_int;
+    pub fn getrlimit(resource: ::__rlimit_resource_t, rlim: *mut ::rlimit) -> ::c_int;
+    pub fn setrlimit(resource: ::__rlimit_resource_t, rlim: *const ::rlimit) -> ::c_int;
+    pub fn prlimit(
+        pid: ::pid_t,
+        resource: ::__rlimit_resource_t,
+        new_limit: *const ::rlimit,
+        old_limit: *mut ::rlimit,
+    ) -> ::c_int;
+    pub fn prlimit64(
+        pid: ::pid_t,
+        resource: ::__rlimit_resource_t,
+        new_limit: *const ::rlimit64,
+        old_limit: *mut ::rlimit64,
+    ) -> ::c_int;
+    pub fn utmpname(file: *const ::c_char) -> ::c_int;
+    pub fn utmpxname(file: *const ::c_char) -> ::c_int;
+    pub fn getutxent() -> *mut utmpx;
+    pub fn getutxid(ut: *const utmpx) -> *mut utmpx;
+    pub fn getutxline(ut: *const utmpx) -> *mut utmpx;
+    pub fn pututxline(ut: *const utmpx) -> *mut utmpx;
+    pub fn setutxent();
+    pub fn endutxent();
+    pub fn getpt() -> ::c_int;
+    pub fn mallopt(param: ::c_int, value: ::c_int) -> ::c_int;
+    pub fn gettimeofday(tp: *mut ::timeval, tz: *mut ::timezone) -> ::c_int;
+    pub fn statx(
+        dirfd: ::c_int,
+        pathname: *const c_char,
+        flags: ::c_int,
+        mask: ::c_uint,
+        statxbuf: *mut statx,
+    ) -> ::c_int;
+    pub fn getentropy(buf: *mut ::c_void, buflen: ::size_t) -> ::c_int;
+    pub fn getrandom(buf: *mut ::c_void, buflen: ::size_t, flags: ::c_uint) -> ::ssize_t;
+    pub fn getauxval(type_: ::c_ulong) -> ::c_ulong;
+
+    pub fn adjtimex(buf: *mut timex) -> ::c_int;
+    pub fn ntp_adjtime(buf: *mut timex) -> ::c_int;
+    #[link_name = "ntp_gettimex"]
+    pub fn ntp_gettime(buf: *mut ntptimeval) -> ::c_int;
+    pub fn clock_adjtime(clk_id: ::clockid_t, buf: *mut ::timex) -> ::c_int;
+
+    pub fn copy_file_range(
+        fd_in: ::c_int,
+        off_in: *mut ::off64_t,
+        fd_out: ::c_int,
+        off_out: *mut ::off64_t,
+        len: ::size_t,
+        flags: ::c_uint,
+    ) -> ::ssize_t;
+    pub fn fanotify_mark(
+        fd: ::c_int,
+        flags: ::c_uint,
+        mask: u64,
+        dirfd: ::c_int,
+        path: *const ::c_char,
+    ) -> ::c_int;
+    pub fn preadv2(
+        fd: ::c_int,
+        iov: *const ::iovec,
+        iovcnt: ::c_int,
+        offset: ::off_t,
+        flags: ::c_int,
+    ) -> ::ssize_t;
+    pub fn pwritev2(
+        fd: ::c_int,
+        iov: *const ::iovec,
+        iovcnt: ::c_int,
+        offset: ::off_t,
+        flags: ::c_int,
+    ) -> ::ssize_t;
+    pub fn preadv64v2(
+        fd: ::c_int,
+        iov: *const ::iovec,
+        iovcnt: ::c_int,
+        offset: ::off64_t,
+        flags: ::c_int,
+    ) -> ::ssize_t;
+    pub fn pwritev64v2(
+        fd: ::c_int,
+        iov: *const ::iovec,
+        iovcnt: ::c_int,
+        offset: ::off64_t,
+        flags: ::c_int,
+    ) -> ::ssize_t;
+    pub fn renameat2(
+        olddirfd: ::c_int,
+        oldpath: *const ::c_char,
+        newdirfd: ::c_int,
+        newpath: *const ::c_char,
+        flags: ::c_uint,
+    ) -> ::c_int;
+
+    // Added in `glibc` 2.25
+    pub fn explicit_bzero(s: *mut ::c_void, len: ::size_t);
+    // Added in `glibc` 2.29
+    pub fn reallocarray(ptr: *mut ::c_void, nmemb: ::size_t, size: ::size_t) -> *mut ::c_void;
+
+    pub fn ctermid(s: *mut ::c_char) -> *mut ::c_char;
+}
+
+extern "C" {
+    pub fn ioctl(fd: ::c_int, request: ::c_ulong, ...) -> ::c_int;
+    pub fn backtrace(buf: *mut *mut ::c_void, sz: ::c_int) -> ::c_int;
+    pub fn glob64(
+        pattern: *const ::c_char,
+        flags: ::c_int,
+        errfunc: ::Option<extern "C" fn(epath: *const ::c_char, errno: ::c_int) -> ::c_int>,
+        pglob: *mut glob64_t,
+    ) -> ::c_int;
+    pub fn globfree64(pglob: *mut glob64_t);
+    pub fn ptrace(request: ::c_uint, ...) -> ::c_long;
+    pub fn pthread_attr_getaffinity_np(
+        attr: *const ::pthread_attr_t,
+        cpusetsize: ::size_t,
+        cpuset: *mut ::cpu_set_t,
+    ) -> ::c_int;
+    pub fn pthread_attr_setaffinity_np(
+        attr: *mut ::pthread_attr_t,
+        cpusetsize: ::size_t,
+        cpuset: *const ::cpu_set_t,
+    ) -> ::c_int;
+    pub fn getpriority(which: ::__priority_which_t, who: ::id_t) -> ::c_int;
+    pub fn setpriority(which: ::__priority_which_t, who: ::id_t, prio: ::c_int) -> ::c_int;
+    pub fn pthread_rwlockattr_getkind_np(
+        attr: *const ::pthread_rwlockattr_t,
+        val: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_rwlockattr_setkind_np(
+        attr: *mut ::pthread_rwlockattr_t,
+        val: ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_sigqueue(thread: ::pthread_t, sig: ::c_int, value: ::sigval) -> ::c_int;
+    pub fn mallinfo() -> ::mallinfo;
+    pub fn mallinfo2() -> ::mallinfo2;
+    pub fn malloc_info(options: ::c_int, stream: *mut ::FILE) -> ::c_int;
+    pub fn malloc_usable_size(ptr: *mut ::c_void) -> ::size_t;
+    pub fn getpwent_r(
+        pwd: *mut ::passwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::passwd,
+    ) -> ::c_int;
+    pub fn getgrent_r(
+        grp: *mut ::group,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::group,
+    ) -> ::c_int;
+    pub fn fgetpwent_r(
+        stream: *mut ::FILE,
+        pwd: *mut ::passwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::passwd,
+    ) -> ::c_int;
+    pub fn fgetgrent_r(
+        stream: *mut ::FILE,
+        grp: *mut ::group,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::group,
+    ) -> ::c_int;
+
+    pub fn sethostid(hostid: ::c_long) -> ::c_int;
+
+    pub fn memfd_create(name: *const ::c_char, flags: ::c_uint) -> ::c_int;
+    pub fn mlock2(addr: *const ::c_void, len: ::size_t, flags: ::c_uint) -> ::c_int;
+
+    pub fn euidaccess(pathname: *const ::c_char, mode: ::c_int) -> ::c_int;
+    pub fn eaccess(pathname: *const ::c_char, mode: ::c_int) -> ::c_int;
+
+    pub fn asctime_r(tm: *const ::tm, buf: *mut ::c_char) -> *mut ::c_char;
+    pub fn ctime_r(timep: *const time_t, buf: *mut ::c_char) -> *mut ::c_char;
+
+    pub fn strftime(
+        s: *mut ::c_char,
+        max: ::size_t,
+        format: *const ::c_char,
+        tm: *const ::tm,
+    ) -> ::size_t;
+    pub fn strptime(s: *const ::c_char, format: *const ::c_char, tm: *mut ::tm) -> *mut ::c_char;
+
+    pub fn dirname(path: *mut ::c_char) -> *mut ::c_char;
+    /// POSIX version of `basename(3)`, defined in `libgen.h`.
+    #[link_name = "__xpg_basename"]
+    pub fn posix_basename(path: *mut ::c_char) -> *mut ::c_char;
+    /// GNU version of `basename(3)`, defined in `string.h`.
+    #[link_name = "basename"]
+    pub fn gnu_basename(path: *const ::c_char) -> *mut ::c_char;
+}
+
+extern "C" {
+    pub fn dlmopen(lmid: Lmid_t, filename: *const ::c_char, flag: ::c_int) -> *mut ::c_void;
+    pub fn dlinfo(handle: *mut ::c_void, request: ::c_int, info: *mut ::c_void) -> ::c_int;
+    pub fn dladdr1(
+        addr: *const ::c_void,
+        info: *mut ::Dl_info,
+        extra_info: *mut *mut ::c_void,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn malloc_trim(__pad: ::size_t) -> ::c_int;
+}
+
+extern "C" {
+    pub fn gnu_get_libc_release() -> *const ::c_char;
+    pub fn gnu_get_libc_version() -> *const ::c_char;
+}
+
+cfg_if! {
+    if #[cfg(any(target_arch = "x86",
+                 target_arch = "arm",
+                 target_arch = "m68k",
+                 target_arch = "mips",
+                 target_arch = "powerpc",
+                 target_arch = "sparc",
+                 target_arch = "riscv32"))] {
+        mod b32;
+        pub use self::b32::*;
+    } else if #[cfg(any(target_arch = "x86_64",
+                        target_arch = "aarch64",
+                        target_arch = "powerpc64",
+                        target_arch = "mips64",
+                        target_arch = "s390x",
+                        target_arch = "sparc64",
+                        target_arch = "riscv64",
+                        target_arch = "loongarch64"))] {
+        mod b64;
+        pub use self::b64::*;
+    } else {
+        // Unknown target_arch
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_align)] {
+        mod align;
+        pub use self::align::*;
+    } else {
+        mod no_align;
+        pub use self::no_align::*;
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/mod.rs.html new file mode 100644 index 0000000..3d0cf08 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/mod.rs.html @@ -0,0 +1,8986 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+1410
+1411
+1412
+1413
+1414
+1415
+1416
+1417
+1418
+1419
+1420
+1421
+1422
+1423
+1424
+1425
+1426
+1427
+1428
+1429
+1430
+1431
+1432
+1433
+1434
+1435
+1436
+1437
+1438
+1439
+1440
+1441
+1442
+1443
+1444
+1445
+1446
+1447
+1448
+1449
+1450
+1451
+1452
+1453
+1454
+1455
+1456
+1457
+1458
+1459
+1460
+1461
+1462
+1463
+1464
+1465
+1466
+1467
+1468
+1469
+1470
+1471
+1472
+1473
+1474
+1475
+1476
+1477
+1478
+1479
+1480
+1481
+1482
+1483
+1484
+1485
+1486
+1487
+1488
+1489
+1490
+1491
+1492
+1493
+1494
+1495
+1496
+1497
+1498
+1499
+1500
+1501
+1502
+1503
+1504
+1505
+1506
+1507
+1508
+1509
+1510
+1511
+1512
+1513
+1514
+1515
+1516
+1517
+1518
+1519
+1520
+1521
+1522
+1523
+1524
+1525
+1526
+1527
+1528
+1529
+1530
+1531
+1532
+1533
+1534
+1535
+1536
+1537
+1538
+1539
+1540
+1541
+1542
+1543
+1544
+1545
+1546
+1547
+1548
+1549
+1550
+1551
+1552
+1553
+1554
+1555
+1556
+1557
+1558
+1559
+1560
+1561
+1562
+1563
+1564
+1565
+1566
+1567
+1568
+1569
+1570
+1571
+1572
+1573
+1574
+1575
+1576
+1577
+1578
+1579
+1580
+1581
+1582
+1583
+1584
+1585
+1586
+1587
+1588
+1589
+1590
+1591
+1592
+1593
+1594
+1595
+1596
+1597
+1598
+1599
+1600
+1601
+1602
+1603
+1604
+1605
+1606
+1607
+1608
+1609
+1610
+1611
+1612
+1613
+1614
+1615
+1616
+1617
+1618
+1619
+1620
+1621
+1622
+1623
+1624
+1625
+1626
+1627
+1628
+1629
+1630
+1631
+1632
+1633
+1634
+1635
+1636
+1637
+1638
+1639
+1640
+1641
+1642
+1643
+1644
+1645
+1646
+1647
+1648
+1649
+1650
+1651
+1652
+1653
+1654
+1655
+1656
+1657
+1658
+1659
+1660
+1661
+1662
+1663
+1664
+1665
+1666
+1667
+1668
+1669
+1670
+1671
+1672
+1673
+1674
+1675
+1676
+1677
+1678
+1679
+1680
+1681
+1682
+1683
+1684
+1685
+1686
+1687
+1688
+1689
+1690
+1691
+1692
+1693
+1694
+1695
+1696
+1697
+1698
+1699
+1700
+1701
+1702
+1703
+1704
+1705
+1706
+1707
+1708
+1709
+1710
+1711
+1712
+1713
+1714
+1715
+1716
+1717
+1718
+1719
+1720
+1721
+1722
+1723
+1724
+1725
+1726
+1727
+1728
+1729
+1730
+1731
+1732
+1733
+1734
+1735
+1736
+1737
+1738
+1739
+1740
+1741
+1742
+1743
+1744
+1745
+1746
+1747
+1748
+1749
+1750
+1751
+1752
+1753
+1754
+1755
+1756
+1757
+1758
+1759
+1760
+1761
+1762
+1763
+1764
+1765
+1766
+1767
+1768
+1769
+1770
+1771
+1772
+1773
+1774
+1775
+1776
+1777
+1778
+1779
+1780
+1781
+1782
+1783
+1784
+1785
+1786
+1787
+1788
+1789
+1790
+1791
+1792
+1793
+1794
+1795
+1796
+1797
+1798
+1799
+1800
+1801
+1802
+1803
+1804
+1805
+1806
+1807
+1808
+1809
+1810
+1811
+1812
+1813
+1814
+1815
+1816
+1817
+1818
+1819
+1820
+1821
+1822
+1823
+1824
+1825
+1826
+1827
+1828
+1829
+1830
+1831
+1832
+1833
+1834
+1835
+1836
+1837
+1838
+1839
+1840
+1841
+1842
+1843
+1844
+1845
+1846
+1847
+1848
+1849
+1850
+1851
+1852
+1853
+1854
+1855
+1856
+1857
+1858
+1859
+1860
+1861
+1862
+1863
+1864
+1865
+1866
+1867
+1868
+1869
+1870
+1871
+1872
+1873
+1874
+1875
+1876
+1877
+1878
+1879
+1880
+1881
+1882
+1883
+1884
+1885
+1886
+1887
+1888
+1889
+1890
+1891
+1892
+1893
+1894
+1895
+1896
+1897
+1898
+1899
+1900
+1901
+1902
+1903
+1904
+1905
+1906
+1907
+1908
+1909
+1910
+1911
+1912
+1913
+1914
+1915
+1916
+1917
+1918
+1919
+1920
+1921
+1922
+1923
+1924
+1925
+1926
+1927
+1928
+1929
+1930
+1931
+1932
+1933
+1934
+1935
+1936
+1937
+1938
+1939
+1940
+1941
+1942
+1943
+1944
+1945
+1946
+1947
+1948
+1949
+1950
+1951
+1952
+1953
+1954
+1955
+1956
+1957
+1958
+1959
+1960
+1961
+1962
+1963
+1964
+1965
+1966
+1967
+1968
+1969
+1970
+1971
+1972
+1973
+1974
+1975
+1976
+1977
+1978
+1979
+1980
+1981
+1982
+1983
+1984
+1985
+1986
+1987
+1988
+1989
+1990
+1991
+1992
+1993
+1994
+1995
+1996
+1997
+1998
+1999
+2000
+2001
+2002
+2003
+2004
+2005
+2006
+2007
+2008
+2009
+2010
+2011
+2012
+2013
+2014
+2015
+2016
+2017
+2018
+2019
+2020
+2021
+2022
+2023
+2024
+2025
+2026
+2027
+2028
+2029
+2030
+2031
+2032
+2033
+2034
+2035
+2036
+2037
+2038
+2039
+2040
+2041
+2042
+2043
+2044
+2045
+2046
+2047
+2048
+2049
+2050
+2051
+2052
+2053
+2054
+2055
+2056
+2057
+2058
+2059
+2060
+2061
+2062
+2063
+2064
+2065
+2066
+2067
+2068
+2069
+2070
+2071
+2072
+2073
+2074
+2075
+2076
+2077
+2078
+2079
+2080
+2081
+2082
+2083
+2084
+2085
+2086
+2087
+2088
+2089
+2090
+2091
+2092
+2093
+2094
+2095
+2096
+2097
+2098
+2099
+2100
+2101
+2102
+2103
+2104
+2105
+2106
+2107
+2108
+2109
+2110
+2111
+2112
+2113
+2114
+2115
+2116
+2117
+2118
+2119
+2120
+2121
+2122
+2123
+2124
+2125
+2126
+2127
+2128
+2129
+2130
+2131
+2132
+2133
+2134
+2135
+2136
+2137
+2138
+2139
+2140
+2141
+2142
+2143
+2144
+2145
+2146
+2147
+2148
+2149
+2150
+2151
+2152
+2153
+2154
+2155
+2156
+2157
+2158
+2159
+2160
+2161
+2162
+2163
+2164
+2165
+2166
+2167
+2168
+2169
+2170
+2171
+2172
+2173
+2174
+2175
+2176
+2177
+2178
+2179
+2180
+2181
+2182
+2183
+2184
+2185
+2186
+2187
+2188
+2189
+2190
+2191
+2192
+2193
+2194
+2195
+2196
+2197
+2198
+2199
+2200
+2201
+2202
+2203
+2204
+2205
+2206
+2207
+2208
+2209
+2210
+2211
+2212
+2213
+2214
+2215
+2216
+2217
+2218
+2219
+2220
+2221
+2222
+2223
+2224
+2225
+2226
+2227
+2228
+2229
+2230
+2231
+2232
+2233
+2234
+2235
+2236
+2237
+2238
+2239
+2240
+2241
+2242
+2243
+2244
+2245
+2246
+2247
+2248
+2249
+2250
+2251
+2252
+2253
+2254
+2255
+2256
+2257
+2258
+2259
+2260
+2261
+2262
+2263
+2264
+2265
+2266
+2267
+2268
+2269
+2270
+2271
+2272
+2273
+2274
+2275
+2276
+2277
+2278
+2279
+2280
+2281
+2282
+2283
+2284
+2285
+2286
+2287
+2288
+2289
+2290
+2291
+2292
+2293
+2294
+2295
+2296
+2297
+2298
+2299
+2300
+2301
+2302
+2303
+2304
+2305
+2306
+2307
+2308
+2309
+2310
+2311
+2312
+2313
+2314
+2315
+2316
+2317
+2318
+2319
+2320
+2321
+2322
+2323
+2324
+2325
+2326
+2327
+2328
+2329
+2330
+2331
+2332
+2333
+2334
+2335
+2336
+2337
+2338
+2339
+2340
+2341
+2342
+2343
+2344
+2345
+2346
+2347
+2348
+2349
+2350
+2351
+2352
+2353
+2354
+2355
+2356
+2357
+2358
+2359
+2360
+2361
+2362
+2363
+2364
+2365
+2366
+2367
+2368
+2369
+2370
+2371
+2372
+2373
+2374
+2375
+2376
+2377
+2378
+2379
+2380
+2381
+2382
+2383
+2384
+2385
+2386
+2387
+2388
+2389
+2390
+2391
+2392
+2393
+2394
+2395
+2396
+2397
+2398
+2399
+2400
+2401
+2402
+2403
+2404
+2405
+2406
+2407
+2408
+2409
+2410
+2411
+2412
+2413
+2414
+2415
+2416
+2417
+2418
+2419
+2420
+2421
+2422
+2423
+2424
+2425
+2426
+2427
+2428
+2429
+2430
+2431
+2432
+2433
+2434
+2435
+2436
+2437
+2438
+2439
+2440
+2441
+2442
+2443
+2444
+2445
+2446
+2447
+2448
+2449
+2450
+2451
+2452
+2453
+2454
+2455
+2456
+2457
+2458
+2459
+2460
+2461
+2462
+2463
+2464
+2465
+2466
+2467
+2468
+2469
+2470
+2471
+2472
+2473
+2474
+2475
+2476
+2477
+2478
+2479
+2480
+2481
+2482
+2483
+2484
+2485
+2486
+2487
+2488
+2489
+2490
+2491
+2492
+2493
+2494
+2495
+2496
+2497
+2498
+2499
+2500
+2501
+2502
+2503
+2504
+2505
+2506
+2507
+2508
+2509
+2510
+2511
+2512
+2513
+2514
+2515
+2516
+2517
+2518
+2519
+2520
+2521
+2522
+2523
+2524
+2525
+2526
+2527
+2528
+2529
+2530
+2531
+2532
+2533
+2534
+2535
+2536
+2537
+2538
+2539
+2540
+2541
+2542
+2543
+2544
+2545
+2546
+2547
+2548
+2549
+2550
+2551
+2552
+2553
+2554
+2555
+2556
+2557
+2558
+2559
+2560
+2561
+2562
+2563
+2564
+2565
+2566
+2567
+2568
+2569
+2570
+2571
+2572
+2573
+2574
+2575
+2576
+2577
+2578
+2579
+2580
+2581
+2582
+2583
+2584
+2585
+2586
+2587
+2588
+2589
+2590
+2591
+2592
+2593
+2594
+2595
+2596
+2597
+2598
+2599
+2600
+2601
+2602
+2603
+2604
+2605
+2606
+2607
+2608
+2609
+2610
+2611
+2612
+2613
+2614
+2615
+2616
+2617
+2618
+2619
+2620
+2621
+2622
+2623
+2624
+2625
+2626
+2627
+2628
+2629
+2630
+2631
+2632
+2633
+2634
+2635
+2636
+2637
+2638
+2639
+2640
+2641
+2642
+2643
+2644
+2645
+2646
+2647
+2648
+2649
+2650
+2651
+2652
+2653
+2654
+2655
+2656
+2657
+2658
+2659
+2660
+2661
+2662
+2663
+2664
+2665
+2666
+2667
+2668
+2669
+2670
+2671
+2672
+2673
+2674
+2675
+2676
+2677
+2678
+2679
+2680
+2681
+2682
+2683
+2684
+2685
+2686
+2687
+2688
+2689
+2690
+2691
+2692
+2693
+2694
+2695
+2696
+2697
+2698
+2699
+2700
+2701
+2702
+2703
+2704
+2705
+2706
+2707
+2708
+2709
+2710
+2711
+2712
+2713
+2714
+2715
+2716
+2717
+2718
+2719
+2720
+2721
+2722
+2723
+2724
+2725
+2726
+2727
+2728
+2729
+2730
+2731
+2732
+2733
+2734
+2735
+2736
+2737
+2738
+2739
+2740
+2741
+2742
+2743
+2744
+2745
+2746
+2747
+2748
+2749
+2750
+2751
+2752
+2753
+2754
+2755
+2756
+2757
+2758
+2759
+2760
+2761
+2762
+2763
+2764
+2765
+2766
+2767
+2768
+2769
+2770
+2771
+2772
+2773
+2774
+2775
+2776
+2777
+2778
+2779
+2780
+2781
+2782
+2783
+2784
+2785
+2786
+2787
+2788
+2789
+2790
+2791
+2792
+2793
+2794
+2795
+2796
+2797
+2798
+2799
+2800
+2801
+2802
+2803
+2804
+2805
+2806
+2807
+2808
+2809
+2810
+2811
+2812
+2813
+2814
+2815
+2816
+2817
+2818
+2819
+2820
+2821
+2822
+2823
+2824
+2825
+2826
+2827
+2828
+2829
+2830
+2831
+2832
+2833
+2834
+2835
+2836
+2837
+2838
+2839
+2840
+2841
+2842
+2843
+2844
+2845
+2846
+2847
+2848
+2849
+2850
+2851
+2852
+2853
+2854
+2855
+2856
+2857
+2858
+2859
+2860
+2861
+2862
+2863
+2864
+2865
+2866
+2867
+2868
+2869
+2870
+2871
+2872
+2873
+2874
+2875
+2876
+2877
+2878
+2879
+2880
+2881
+2882
+2883
+2884
+2885
+2886
+2887
+2888
+2889
+2890
+2891
+2892
+2893
+2894
+2895
+2896
+2897
+2898
+2899
+2900
+2901
+2902
+2903
+2904
+2905
+2906
+2907
+2908
+2909
+2910
+2911
+2912
+2913
+2914
+2915
+2916
+2917
+2918
+2919
+2920
+2921
+2922
+2923
+2924
+2925
+2926
+2927
+2928
+2929
+2930
+2931
+2932
+2933
+2934
+2935
+2936
+2937
+2938
+2939
+2940
+2941
+2942
+2943
+2944
+2945
+2946
+2947
+2948
+2949
+2950
+2951
+2952
+2953
+2954
+2955
+2956
+2957
+2958
+2959
+2960
+2961
+2962
+2963
+2964
+2965
+2966
+2967
+2968
+2969
+2970
+2971
+2972
+2973
+2974
+2975
+2976
+2977
+2978
+2979
+2980
+2981
+2982
+2983
+2984
+2985
+2986
+2987
+2988
+2989
+2990
+2991
+2992
+2993
+2994
+2995
+2996
+2997
+2998
+2999
+3000
+3001
+3002
+3003
+3004
+3005
+3006
+3007
+3008
+3009
+3010
+3011
+3012
+3013
+3014
+3015
+3016
+3017
+3018
+3019
+3020
+3021
+3022
+3023
+3024
+3025
+3026
+3027
+3028
+3029
+3030
+3031
+3032
+3033
+3034
+3035
+3036
+3037
+3038
+3039
+3040
+3041
+3042
+3043
+3044
+3045
+3046
+3047
+3048
+3049
+3050
+3051
+3052
+3053
+3054
+3055
+3056
+3057
+3058
+3059
+3060
+3061
+3062
+3063
+3064
+3065
+3066
+3067
+3068
+3069
+3070
+3071
+3072
+3073
+3074
+3075
+3076
+3077
+3078
+3079
+3080
+3081
+3082
+3083
+3084
+3085
+3086
+3087
+3088
+3089
+3090
+3091
+3092
+3093
+3094
+3095
+3096
+3097
+3098
+3099
+3100
+3101
+3102
+3103
+3104
+3105
+3106
+3107
+3108
+3109
+3110
+3111
+3112
+3113
+3114
+3115
+3116
+3117
+3118
+3119
+3120
+3121
+3122
+3123
+3124
+3125
+3126
+3127
+3128
+3129
+3130
+3131
+3132
+3133
+3134
+3135
+3136
+3137
+3138
+3139
+3140
+3141
+3142
+3143
+3144
+3145
+3146
+3147
+3148
+3149
+3150
+3151
+3152
+3153
+3154
+3155
+3156
+3157
+3158
+3159
+3160
+3161
+3162
+3163
+3164
+3165
+3166
+3167
+3168
+3169
+3170
+3171
+3172
+3173
+3174
+3175
+3176
+3177
+3178
+3179
+3180
+3181
+3182
+3183
+3184
+3185
+3186
+3187
+3188
+3189
+3190
+3191
+3192
+3193
+3194
+3195
+3196
+3197
+3198
+3199
+3200
+3201
+3202
+3203
+3204
+3205
+3206
+3207
+3208
+3209
+3210
+3211
+3212
+3213
+3214
+3215
+3216
+3217
+3218
+3219
+3220
+3221
+3222
+3223
+3224
+3225
+3226
+3227
+3228
+3229
+3230
+3231
+3232
+3233
+3234
+3235
+3236
+3237
+3238
+3239
+3240
+3241
+3242
+3243
+3244
+3245
+3246
+3247
+3248
+3249
+3250
+3251
+3252
+3253
+3254
+3255
+3256
+3257
+3258
+3259
+3260
+3261
+3262
+3263
+3264
+3265
+3266
+3267
+3268
+3269
+3270
+3271
+3272
+3273
+3274
+3275
+3276
+3277
+3278
+3279
+3280
+3281
+3282
+3283
+3284
+3285
+3286
+3287
+3288
+3289
+3290
+3291
+3292
+3293
+3294
+3295
+3296
+3297
+3298
+3299
+3300
+3301
+3302
+3303
+3304
+3305
+3306
+3307
+3308
+3309
+3310
+3311
+3312
+3313
+3314
+3315
+3316
+3317
+3318
+3319
+3320
+3321
+3322
+3323
+3324
+3325
+3326
+3327
+3328
+3329
+3330
+3331
+3332
+3333
+3334
+3335
+3336
+3337
+3338
+3339
+3340
+3341
+3342
+3343
+3344
+3345
+3346
+3347
+3348
+3349
+3350
+3351
+3352
+3353
+3354
+3355
+3356
+3357
+3358
+3359
+3360
+3361
+3362
+3363
+3364
+3365
+3366
+3367
+3368
+3369
+3370
+3371
+3372
+3373
+3374
+3375
+3376
+3377
+3378
+3379
+3380
+3381
+3382
+3383
+3384
+3385
+3386
+3387
+3388
+3389
+3390
+3391
+3392
+3393
+3394
+3395
+3396
+3397
+3398
+3399
+3400
+3401
+3402
+3403
+3404
+3405
+3406
+3407
+3408
+3409
+3410
+3411
+3412
+3413
+3414
+3415
+3416
+3417
+3418
+3419
+3420
+3421
+3422
+3423
+3424
+3425
+3426
+3427
+3428
+3429
+3430
+3431
+3432
+3433
+3434
+3435
+3436
+3437
+3438
+3439
+3440
+3441
+3442
+3443
+3444
+3445
+3446
+3447
+3448
+3449
+3450
+3451
+3452
+3453
+3454
+3455
+3456
+3457
+3458
+3459
+3460
+3461
+3462
+3463
+3464
+3465
+3466
+3467
+3468
+3469
+3470
+3471
+3472
+3473
+3474
+3475
+3476
+3477
+3478
+3479
+3480
+3481
+3482
+3483
+3484
+3485
+3486
+3487
+3488
+3489
+3490
+3491
+3492
+3493
+3494
+3495
+3496
+3497
+3498
+3499
+3500
+3501
+3502
+3503
+3504
+3505
+3506
+3507
+3508
+3509
+3510
+3511
+3512
+3513
+3514
+3515
+3516
+3517
+3518
+3519
+3520
+3521
+3522
+3523
+3524
+3525
+3526
+3527
+3528
+3529
+3530
+3531
+3532
+3533
+3534
+3535
+3536
+3537
+3538
+3539
+3540
+3541
+3542
+3543
+3544
+3545
+3546
+3547
+3548
+3549
+3550
+3551
+3552
+3553
+3554
+3555
+3556
+3557
+3558
+3559
+3560
+3561
+3562
+3563
+3564
+3565
+3566
+3567
+3568
+3569
+3570
+3571
+3572
+3573
+3574
+3575
+3576
+3577
+3578
+3579
+3580
+3581
+3582
+3583
+3584
+3585
+3586
+3587
+3588
+3589
+3590
+3591
+3592
+3593
+3594
+3595
+3596
+3597
+3598
+3599
+3600
+3601
+3602
+3603
+3604
+3605
+3606
+3607
+3608
+3609
+3610
+3611
+3612
+3613
+3614
+3615
+3616
+3617
+3618
+3619
+3620
+3621
+3622
+3623
+3624
+3625
+3626
+3627
+3628
+3629
+3630
+3631
+3632
+3633
+3634
+3635
+3636
+3637
+3638
+3639
+3640
+3641
+3642
+3643
+3644
+3645
+3646
+3647
+3648
+3649
+3650
+3651
+3652
+3653
+3654
+3655
+3656
+3657
+3658
+3659
+3660
+3661
+3662
+3663
+3664
+3665
+3666
+3667
+3668
+3669
+3670
+3671
+3672
+3673
+3674
+3675
+3676
+3677
+3678
+3679
+3680
+3681
+3682
+3683
+3684
+3685
+3686
+3687
+3688
+3689
+3690
+3691
+3692
+3693
+3694
+3695
+3696
+3697
+3698
+3699
+3700
+3701
+3702
+3703
+3704
+3705
+3706
+3707
+3708
+3709
+3710
+3711
+3712
+3713
+3714
+3715
+3716
+3717
+3718
+3719
+3720
+3721
+3722
+3723
+3724
+3725
+3726
+3727
+3728
+3729
+3730
+3731
+3732
+3733
+3734
+3735
+3736
+3737
+3738
+3739
+3740
+3741
+3742
+3743
+3744
+3745
+3746
+3747
+3748
+3749
+3750
+3751
+3752
+3753
+3754
+3755
+3756
+3757
+3758
+3759
+3760
+3761
+3762
+3763
+3764
+3765
+3766
+3767
+3768
+3769
+3770
+3771
+3772
+3773
+3774
+3775
+3776
+3777
+3778
+3779
+3780
+3781
+3782
+3783
+3784
+3785
+3786
+3787
+3788
+3789
+3790
+3791
+3792
+3793
+3794
+3795
+3796
+3797
+3798
+3799
+3800
+3801
+3802
+3803
+3804
+3805
+3806
+3807
+3808
+3809
+3810
+3811
+3812
+3813
+3814
+3815
+3816
+3817
+3818
+3819
+3820
+3821
+3822
+3823
+3824
+3825
+3826
+3827
+3828
+3829
+3830
+3831
+3832
+3833
+3834
+3835
+3836
+3837
+3838
+3839
+3840
+3841
+3842
+3843
+3844
+3845
+3846
+3847
+3848
+3849
+3850
+3851
+3852
+3853
+3854
+3855
+3856
+3857
+3858
+3859
+3860
+3861
+3862
+3863
+3864
+3865
+3866
+3867
+3868
+3869
+3870
+3871
+3872
+3873
+3874
+3875
+3876
+3877
+3878
+3879
+3880
+3881
+3882
+3883
+3884
+3885
+3886
+3887
+3888
+3889
+3890
+3891
+3892
+3893
+3894
+3895
+3896
+3897
+3898
+3899
+3900
+3901
+3902
+3903
+3904
+3905
+3906
+3907
+3908
+3909
+3910
+3911
+3912
+3913
+3914
+3915
+3916
+3917
+3918
+3919
+3920
+3921
+3922
+3923
+3924
+3925
+3926
+3927
+3928
+3929
+3930
+3931
+3932
+3933
+3934
+3935
+3936
+3937
+3938
+3939
+3940
+3941
+3942
+3943
+3944
+3945
+3946
+3947
+3948
+3949
+3950
+3951
+3952
+3953
+3954
+3955
+3956
+3957
+3958
+3959
+3960
+3961
+3962
+3963
+3964
+3965
+3966
+3967
+3968
+3969
+3970
+3971
+3972
+3973
+3974
+3975
+3976
+3977
+3978
+3979
+3980
+3981
+3982
+3983
+3984
+3985
+3986
+3987
+3988
+3989
+3990
+3991
+3992
+3993
+3994
+3995
+3996
+3997
+3998
+3999
+4000
+4001
+4002
+4003
+4004
+4005
+4006
+4007
+4008
+4009
+4010
+4011
+4012
+4013
+4014
+4015
+4016
+4017
+4018
+4019
+4020
+4021
+4022
+4023
+4024
+4025
+4026
+4027
+4028
+4029
+4030
+4031
+4032
+4033
+4034
+4035
+4036
+4037
+4038
+4039
+4040
+4041
+4042
+4043
+4044
+4045
+4046
+4047
+4048
+4049
+4050
+4051
+4052
+4053
+4054
+4055
+4056
+4057
+4058
+4059
+4060
+4061
+4062
+4063
+4064
+4065
+4066
+4067
+4068
+4069
+4070
+4071
+4072
+4073
+4074
+4075
+4076
+4077
+4078
+4079
+4080
+4081
+4082
+4083
+4084
+4085
+4086
+4087
+4088
+4089
+4090
+4091
+4092
+4093
+4094
+4095
+4096
+4097
+4098
+4099
+4100
+4101
+4102
+4103
+4104
+4105
+4106
+4107
+4108
+4109
+4110
+4111
+4112
+4113
+4114
+4115
+4116
+4117
+4118
+4119
+4120
+4121
+4122
+4123
+4124
+4125
+4126
+4127
+4128
+4129
+4130
+4131
+4132
+4133
+4134
+4135
+4136
+4137
+4138
+4139
+4140
+4141
+4142
+4143
+4144
+4145
+4146
+4147
+4148
+4149
+4150
+4151
+4152
+4153
+4154
+4155
+4156
+4157
+4158
+4159
+4160
+4161
+4162
+4163
+4164
+4165
+4166
+4167
+4168
+4169
+4170
+4171
+4172
+4173
+4174
+4175
+4176
+4177
+4178
+4179
+4180
+4181
+4182
+4183
+4184
+4185
+4186
+4187
+4188
+4189
+4190
+4191
+4192
+4193
+4194
+4195
+4196
+4197
+4198
+4199
+4200
+4201
+4202
+4203
+4204
+4205
+4206
+4207
+4208
+4209
+4210
+4211
+4212
+4213
+4214
+4215
+4216
+4217
+4218
+4219
+4220
+4221
+4222
+4223
+4224
+4225
+4226
+4227
+4228
+4229
+4230
+4231
+4232
+4233
+4234
+4235
+4236
+4237
+4238
+4239
+4240
+4241
+4242
+4243
+4244
+4245
+4246
+4247
+4248
+4249
+4250
+4251
+4252
+4253
+4254
+4255
+4256
+4257
+4258
+4259
+4260
+4261
+4262
+4263
+4264
+4265
+4266
+4267
+4268
+4269
+4270
+4271
+4272
+4273
+4274
+4275
+4276
+4277
+4278
+4279
+4280
+4281
+4282
+4283
+4284
+4285
+4286
+4287
+4288
+4289
+4290
+4291
+4292
+4293
+4294
+4295
+4296
+4297
+4298
+4299
+4300
+4301
+4302
+4303
+4304
+4305
+4306
+4307
+4308
+4309
+4310
+4311
+4312
+4313
+4314
+4315
+4316
+4317
+4318
+4319
+4320
+4321
+4322
+4323
+4324
+4325
+4326
+4327
+4328
+4329
+4330
+4331
+4332
+4333
+4334
+4335
+4336
+4337
+4338
+4339
+4340
+4341
+4342
+4343
+4344
+4345
+4346
+4347
+4348
+4349
+4350
+4351
+4352
+4353
+4354
+4355
+4356
+4357
+4358
+4359
+4360
+4361
+4362
+4363
+4364
+4365
+4366
+4367
+4368
+4369
+4370
+4371
+4372
+4373
+4374
+4375
+4376
+4377
+4378
+4379
+4380
+4381
+4382
+4383
+4384
+4385
+4386
+4387
+4388
+4389
+4390
+4391
+4392
+4393
+4394
+4395
+4396
+4397
+4398
+4399
+4400
+4401
+4402
+4403
+4404
+4405
+4406
+4407
+4408
+4409
+4410
+4411
+4412
+4413
+4414
+4415
+4416
+4417
+4418
+4419
+4420
+4421
+4422
+4423
+4424
+4425
+4426
+4427
+4428
+4429
+4430
+4431
+4432
+4433
+4434
+4435
+4436
+4437
+4438
+4439
+4440
+4441
+4442
+4443
+4444
+4445
+4446
+4447
+4448
+4449
+4450
+4451
+4452
+4453
+4454
+4455
+4456
+4457
+4458
+4459
+4460
+4461
+4462
+4463
+4464
+4465
+4466
+4467
+4468
+4469
+4470
+4471
+4472
+4473
+4474
+4475
+4476
+4477
+4478
+4479
+4480
+4481
+4482
+4483
+4484
+4485
+4486
+4487
+4488
+4489
+4490
+4491
+4492
+
//! Linux-specific definitions for linux-like values
+
+pub type useconds_t = u32;
+pub type dev_t = u64;
+pub type socklen_t = u32;
+pub type mode_t = u32;
+pub type ino64_t = u64;
+pub type off64_t = i64;
+pub type blkcnt64_t = i64;
+pub type rlim64_t = u64;
+pub type mqd_t = ::c_int;
+pub type nfds_t = ::c_ulong;
+pub type nl_item = ::c_int;
+pub type idtype_t = ::c_uint;
+pub type loff_t = ::c_longlong;
+pub type pthread_key_t = ::c_uint;
+pub type pthread_spinlock_t = ::c_int;
+
+pub type __u8 = ::c_uchar;
+pub type __u16 = ::c_ushort;
+pub type __s16 = ::c_short;
+pub type __u32 = ::c_uint;
+pub type __s32 = ::c_int;
+
+pub type Elf32_Half = u16;
+pub type Elf32_Word = u32;
+pub type Elf32_Off = u32;
+pub type Elf32_Addr = u32;
+
+pub type Elf64_Half = u16;
+pub type Elf64_Word = u32;
+pub type Elf64_Off = u64;
+pub type Elf64_Addr = u64;
+pub type Elf64_Xword = u64;
+pub type Elf64_Sxword = i64;
+
+pub type Elf32_Section = u16;
+pub type Elf64_Section = u16;
+
+// linux/can.h
+pub type canid_t = u32;
+
+// linux/can/j1939.h
+pub type can_err_mask_t = u32;
+pub type pgn_t = u32;
+pub type priority_t = u8;
+pub type name_t = u64;
+
+pub type iconv_t = *mut ::c_void;
+
+#[cfg_attr(feature = "extra_traits", derive(Debug))]
+pub enum fpos64_t {} // FIXME: fill this out with a struct
+impl ::Copy for fpos64_t {}
+impl ::Clone for fpos64_t {
+    fn clone(&self) -> fpos64_t {
+        *self
+    }
+}
+
+s! {
+    pub struct rlimit64 {
+        pub rlim_cur: rlim64_t,
+        pub rlim_max: rlim64_t,
+    }
+
+    pub struct glob_t {
+        pub gl_pathc: ::size_t,
+        pub gl_pathv: *mut *mut c_char,
+        pub gl_offs: ::size_t,
+        pub gl_flags: ::c_int,
+
+        __unused1: *mut ::c_void,
+        __unused2: *mut ::c_void,
+        __unused3: *mut ::c_void,
+        __unused4: *mut ::c_void,
+        __unused5: *mut ::c_void,
+    }
+
+    pub struct passwd {
+        pub pw_name: *mut ::c_char,
+        pub pw_passwd: *mut ::c_char,
+        pub pw_uid: ::uid_t,
+        pub pw_gid: ::gid_t,
+        pub pw_gecos: *mut ::c_char,
+        pub pw_dir: *mut ::c_char,
+        pub pw_shell: *mut ::c_char,
+    }
+
+    pub struct spwd {
+        pub sp_namp: *mut ::c_char,
+        pub sp_pwdp: *mut ::c_char,
+        pub sp_lstchg: ::c_long,
+        pub sp_min: ::c_long,
+        pub sp_max: ::c_long,
+        pub sp_warn: ::c_long,
+        pub sp_inact: ::c_long,
+        pub sp_expire: ::c_long,
+        pub sp_flag: ::c_ulong,
+    }
+
+    pub struct dqblk {
+        pub dqb_bhardlimit: u64,
+        pub dqb_bsoftlimit: u64,
+        pub dqb_curspace: u64,
+        pub dqb_ihardlimit: u64,
+        pub dqb_isoftlimit: u64,
+        pub dqb_curinodes: u64,
+        pub dqb_btime: u64,
+        pub dqb_itime: u64,
+        pub dqb_valid: u32,
+    }
+
+    pub struct signalfd_siginfo {
+        pub ssi_signo: u32,
+        pub ssi_errno: i32,
+        pub ssi_code: i32,
+        pub ssi_pid: u32,
+        pub ssi_uid: u32,
+        pub ssi_fd: i32,
+        pub ssi_tid: u32,
+        pub ssi_band: u32,
+        pub ssi_overrun: u32,
+        pub ssi_trapno: u32,
+        pub ssi_status: i32,
+        pub ssi_int: i32,
+        pub ssi_ptr: u64,
+        pub ssi_utime: u64,
+        pub ssi_stime: u64,
+        pub ssi_addr: u64,
+        pub ssi_addr_lsb: u16,
+        _pad2: u16,
+        pub ssi_syscall: i32,
+        pub ssi_call_addr: u64,
+        pub ssi_arch: u32,
+        _pad: [u8; 28],
+    }
+
+    pub struct itimerspec {
+        pub it_interval: ::timespec,
+        pub it_value: ::timespec,
+    }
+
+    pub struct fsid_t {
+        __val: [::c_int; 2],
+    }
+
+    pub struct packet_mreq {
+        pub mr_ifindex: ::c_int,
+        pub mr_type: ::c_ushort,
+        pub mr_alen: ::c_ushort,
+        pub mr_address: [::c_uchar; 8],
+    }
+
+    pub struct cpu_set_t {
+        #[cfg(all(target_pointer_width = "32",
+                  not(target_arch = "x86_64")))]
+        bits: [u32; 32],
+        #[cfg(not(all(target_pointer_width = "32",
+                      not(target_arch = "x86_64"))))]
+        bits: [u64; 16],
+    }
+
+    pub struct if_nameindex {
+        pub if_index: ::c_uint,
+        pub if_name: *mut ::c_char,
+    }
+
+    // System V IPC
+    pub struct msginfo {
+        pub msgpool: ::c_int,
+        pub msgmap: ::c_int,
+        pub msgmax: ::c_int,
+        pub msgmnb: ::c_int,
+        pub msgmni: ::c_int,
+        pub msgssz: ::c_int,
+        pub msgtql: ::c_int,
+        pub msgseg: ::c_ushort,
+    }
+
+    pub struct sembuf {
+        pub sem_num: ::c_ushort,
+        pub sem_op: ::c_short,
+        pub sem_flg: ::c_short,
+    }
+
+    pub struct input_event {
+        pub time: ::timeval,
+        pub type_: ::__u16,
+        pub code: ::__u16,
+        pub value: ::__s32,
+    }
+
+    pub struct input_id {
+        pub bustype: ::__u16,
+        pub vendor: ::__u16,
+        pub product: ::__u16,
+        pub version: ::__u16,
+    }
+
+    pub struct input_absinfo {
+        pub value: ::__s32,
+        pub minimum: ::__s32,
+        pub maximum: ::__s32,
+        pub fuzz: ::__s32,
+        pub flat: ::__s32,
+        pub resolution: ::__s32,
+    }
+
+    pub struct input_keymap_entry {
+        pub flags: ::__u8,
+        pub len: ::__u8,
+        pub index: ::__u16,
+        pub keycode: ::__u32,
+        pub scancode: [::__u8; 32],
+    }
+
+    pub struct input_mask {
+        pub type_: ::__u32,
+        pub codes_size: ::__u32,
+        pub codes_ptr: ::__u64,
+    }
+
+    pub struct ff_replay {
+        pub length: ::__u16,
+        pub delay: ::__u16,
+    }
+
+    pub struct ff_trigger {
+        pub button: ::__u16,
+        pub interval: ::__u16,
+    }
+
+    pub struct ff_envelope {
+        pub attack_length: ::__u16,
+        pub attack_level: ::__u16,
+        pub fade_length: ::__u16,
+        pub fade_level: ::__u16,
+    }
+
+    pub struct ff_constant_effect {
+        pub level: ::__s16,
+        pub envelope: ff_envelope,
+    }
+
+    pub struct ff_ramp_effect {
+        pub start_level: ::__s16,
+        pub end_level: ::__s16,
+        pub envelope: ff_envelope,
+    }
+
+    pub struct ff_condition_effect {
+        pub right_saturation: ::__u16,
+        pub left_saturation: ::__u16,
+
+        pub right_coeff: ::__s16,
+        pub left_coeff: ::__s16,
+
+        pub deadband: ::__u16,
+        pub center: ::__s16,
+    }
+
+    pub struct ff_periodic_effect {
+        pub waveform: ::__u16,
+        pub period: ::__u16,
+        pub magnitude: ::__s16,
+        pub offset: ::__s16,
+        pub phase: ::__u16,
+
+        pub envelope: ff_envelope,
+
+        pub custom_len: ::__u32,
+        pub custom_data: *mut ::__s16,
+    }
+
+    pub struct ff_rumble_effect {
+        pub strong_magnitude: ::__u16,
+        pub weak_magnitude: ::__u16,
+    }
+
+    pub struct ff_effect {
+        pub type_: ::__u16,
+        pub id: ::__s16,
+        pub direction: ::__u16,
+        pub trigger: ff_trigger,
+        pub replay: ff_replay,
+        // FIXME this is actually a union
+        #[cfg(target_pointer_width = "64")]
+        pub u: [u64; 4],
+        #[cfg(target_pointer_width = "32")]
+        pub u: [u32; 7],
+    }
+
+    pub struct uinput_ff_upload {
+        pub request_id: ::__u32,
+        pub retval: ::__s32,
+        pub effect: ff_effect,
+        pub old: ff_effect,
+    }
+
+    pub struct uinput_ff_erase {
+        pub request_id: ::__u32,
+        pub retval: ::__s32,
+        pub effect_id: ::__u32,
+    }
+
+    pub struct uinput_abs_setup {
+        pub code: ::__u16,
+        pub absinfo: input_absinfo,
+    }
+
+    pub struct dl_phdr_info {
+        #[cfg(target_pointer_width = "64")]
+        pub dlpi_addr: Elf64_Addr,
+        #[cfg(target_pointer_width = "32")]
+        pub dlpi_addr: Elf32_Addr,
+
+        pub dlpi_name: *const ::c_char,
+
+        #[cfg(target_pointer_width = "64")]
+        pub dlpi_phdr: *const Elf64_Phdr,
+        #[cfg(target_pointer_width = "32")]
+        pub dlpi_phdr: *const Elf32_Phdr,
+
+        #[cfg(target_pointer_width = "64")]
+        pub dlpi_phnum: Elf64_Half,
+        #[cfg(target_pointer_width = "32")]
+        pub dlpi_phnum: Elf32_Half,
+
+        // As of uClibc 1.0.36, the following fields are
+        // gated behind a "#if 0" block which always evaluates
+        // to false. So I'm just removing these, and if uClibc changes
+        // the #if block in the future to include the following fields, these
+        // will probably need including here. tsidea, skrap
+        #[cfg(not(target_env = "uclibc"))]
+        pub dlpi_adds: ::c_ulonglong,
+        #[cfg(not(target_env = "uclibc"))]
+        pub dlpi_subs: ::c_ulonglong,
+        #[cfg(not(target_env = "uclibc"))]
+        pub dlpi_tls_modid: ::size_t,
+        #[cfg(not(target_env = "uclibc"))]
+        pub dlpi_tls_data: *mut ::c_void,
+    }
+
+    pub struct Elf32_Ehdr {
+        pub e_ident: [::c_uchar; 16],
+        pub e_type: Elf32_Half,
+        pub e_machine: Elf32_Half,
+        pub e_version: Elf32_Word,
+        pub e_entry: Elf32_Addr,
+        pub e_phoff: Elf32_Off,
+        pub e_shoff: Elf32_Off,
+        pub e_flags: Elf32_Word,
+        pub e_ehsize: Elf32_Half,
+        pub e_phentsize: Elf32_Half,
+        pub e_phnum: Elf32_Half,
+        pub e_shentsize: Elf32_Half,
+        pub e_shnum: Elf32_Half,
+        pub e_shstrndx: Elf32_Half,
+    }
+
+    pub struct Elf64_Ehdr {
+        pub e_ident: [::c_uchar; 16],
+        pub e_type: Elf64_Half,
+        pub e_machine: Elf64_Half,
+        pub e_version: Elf64_Word,
+        pub e_entry: Elf64_Addr,
+        pub e_phoff: Elf64_Off,
+        pub e_shoff: Elf64_Off,
+        pub e_flags: Elf64_Word,
+        pub e_ehsize: Elf64_Half,
+        pub e_phentsize: Elf64_Half,
+        pub e_phnum: Elf64_Half,
+        pub e_shentsize: Elf64_Half,
+        pub e_shnum: Elf64_Half,
+        pub e_shstrndx: Elf64_Half,
+    }
+
+    pub struct Elf32_Sym {
+        pub st_name: Elf32_Word,
+        pub st_value: Elf32_Addr,
+        pub st_size: Elf32_Word,
+        pub st_info: ::c_uchar,
+        pub st_other: ::c_uchar,
+        pub st_shndx: Elf32_Section,
+    }
+
+    pub struct Elf64_Sym {
+        pub st_name: Elf64_Word,
+        pub st_info: ::c_uchar,
+        pub st_other: ::c_uchar,
+        pub st_shndx: Elf64_Section,
+        pub st_value: Elf64_Addr,
+        pub st_size: Elf64_Xword,
+    }
+
+    pub struct Elf32_Phdr {
+        pub p_type: Elf32_Word,
+        pub p_offset: Elf32_Off,
+        pub p_vaddr: Elf32_Addr,
+        pub p_paddr: Elf32_Addr,
+        pub p_filesz: Elf32_Word,
+        pub p_memsz: Elf32_Word,
+        pub p_flags: Elf32_Word,
+        pub p_align: Elf32_Word,
+    }
+
+    pub struct Elf64_Phdr {
+        pub p_type: Elf64_Word,
+        pub p_flags: Elf64_Word,
+        pub p_offset: Elf64_Off,
+        pub p_vaddr: Elf64_Addr,
+        pub p_paddr: Elf64_Addr,
+        pub p_filesz: Elf64_Xword,
+        pub p_memsz: Elf64_Xword,
+        pub p_align: Elf64_Xword,
+    }
+
+    pub struct Elf32_Shdr {
+        pub sh_name: Elf32_Word,
+        pub sh_type: Elf32_Word,
+        pub sh_flags: Elf32_Word,
+        pub sh_addr: Elf32_Addr,
+        pub sh_offset: Elf32_Off,
+        pub sh_size: Elf32_Word,
+        pub sh_link: Elf32_Word,
+        pub sh_info: Elf32_Word,
+        pub sh_addralign: Elf32_Word,
+        pub sh_entsize: Elf32_Word,
+    }
+
+    pub struct Elf64_Shdr {
+        pub sh_name: Elf64_Word,
+        pub sh_type: Elf64_Word,
+        pub sh_flags: Elf64_Xword,
+        pub sh_addr: Elf64_Addr,
+        pub sh_offset: Elf64_Off,
+        pub sh_size: Elf64_Xword,
+        pub sh_link: Elf64_Word,
+        pub sh_info: Elf64_Word,
+        pub sh_addralign: Elf64_Xword,
+        pub sh_entsize: Elf64_Xword,
+    }
+
+    pub struct ucred {
+        pub pid: ::pid_t,
+        pub uid: ::uid_t,
+        pub gid: ::gid_t,
+    }
+
+    pub struct mntent {
+        pub mnt_fsname: *mut ::c_char,
+        pub mnt_dir: *mut ::c_char,
+        pub mnt_type: *mut ::c_char,
+        pub mnt_opts: *mut ::c_char,
+        pub mnt_freq: ::c_int,
+        pub mnt_passno: ::c_int,
+    }
+
+    pub struct posix_spawn_file_actions_t {
+        __allocated: ::c_int,
+        __used: ::c_int,
+        __actions: *mut ::c_int,
+        __pad: [::c_int; 16],
+    }
+
+    pub struct posix_spawnattr_t {
+        __flags: ::c_short,
+        __pgrp: ::pid_t,
+        __sd: ::sigset_t,
+        __ss: ::sigset_t,
+        #[cfg(target_env = "musl")]
+        __prio: ::c_int,
+        #[cfg(not(target_env = "musl"))]
+        __sp: ::sched_param,
+        __policy: ::c_int,
+        __pad: [::c_int; 16],
+    }
+
+    pub struct genlmsghdr {
+        pub cmd: u8,
+        pub version: u8,
+        pub reserved: u16,
+    }
+
+    pub struct in6_pktinfo {
+        pub ipi6_addr: ::in6_addr,
+        pub ipi6_ifindex: ::c_uint,
+    }
+
+    pub struct arpd_request {
+        pub req: ::c_ushort,
+        pub ip: u32,
+        pub dev: ::c_ulong,
+        pub stamp: ::c_ulong,
+        pub updated: ::c_ulong,
+        pub ha: [::c_uchar; ::MAX_ADDR_LEN],
+    }
+
+    pub struct inotify_event {
+        pub wd: ::c_int,
+        pub mask: u32,
+        pub cookie: u32,
+        pub len: u32
+    }
+
+    pub struct fanotify_response {
+        pub fd: ::c_int,
+        pub response: __u32,
+    }
+
+    pub struct sockaddr_vm {
+        pub svm_family: ::sa_family_t,
+        pub svm_reserved1: ::c_ushort,
+        pub svm_port: ::c_uint,
+        pub svm_cid: ::c_uint,
+        pub svm_zero: [u8; 4]
+    }
+
+    pub struct regmatch_t {
+        pub rm_so: regoff_t,
+        pub rm_eo: regoff_t,
+    }
+
+    pub struct sock_extended_err {
+        pub ee_errno: u32,
+        pub ee_origin: u8,
+        pub ee_type: u8,
+        pub ee_code: u8,
+        pub ee_pad: u8,
+        pub ee_info: u32,
+        pub ee_data: u32,
+    }
+
+    // linux/can.h
+    pub struct __c_anonymous_sockaddr_can_tp {
+        pub rx_id: canid_t,
+        pub tx_id: canid_t,
+    }
+
+    pub struct __c_anonymous_sockaddr_can_j1939 {
+        pub name: u64,
+        pub pgn: u32,
+        pub addr: u8,
+    }
+
+    pub struct can_filter {
+        pub can_id: canid_t,
+        pub can_mask: canid_t,
+    }
+
+    // linux/can/j1939.h
+    pub struct j1939_filter {
+        pub name: name_t,
+        pub name_mask: name_t,
+        pub pgn: pgn_t,
+        pub pgn_mask: pgn_t,
+        pub addr: u8,
+        pub addr_mask: u8,
+    }
+
+    // linux/filter.h
+    pub struct sock_filter {
+        pub code: ::__u16,
+        pub jt: ::__u8,
+        pub jf: ::__u8,
+        pub k: ::__u32,
+    }
+
+    pub struct sock_fprog {
+        pub len: ::c_ushort,
+        pub filter: *mut sock_filter,
+    }
+
+    // linux/seccomp.h
+    pub struct seccomp_data {
+        pub nr: ::c_int,
+        pub arch: ::__u32,
+        pub instruction_pointer: ::__u64,
+        pub args: [::__u64; 6],
+    }
+
+    pub struct nlmsghdr {
+        pub nlmsg_len: u32,
+        pub nlmsg_type: u16,
+        pub nlmsg_flags: u16,
+        pub nlmsg_seq: u32,
+        pub nlmsg_pid: u32,
+    }
+
+    pub struct nlmsgerr {
+        pub error: ::c_int,
+        pub msg: nlmsghdr,
+    }
+
+    pub struct nlattr {
+        pub nla_len: u16,
+        pub nla_type: u16,
+    }
+
+    pub struct file_clone_range {
+        pub src_fd: ::__s64,
+        pub src_offset: ::__u64,
+        pub src_length: ::__u64,
+        pub dest_offset: ::__u64,
+    }
+
+    pub struct __c_anonymous_ifru_map {
+        pub mem_start: ::c_ulong,
+        pub mem_end: ::c_ulong,
+        pub base_addr: ::c_ushort,
+        pub irq: ::c_uchar,
+        pub dma: ::c_uchar,
+        pub port: ::c_uchar,
+    }
+
+   pub struct in6_ifreq {
+       pub ifr6_addr: ::in6_addr,
+       pub ifr6_prefixlen: u32,
+       pub ifr6_ifindex: ::c_int,
+   }
+
+    pub struct option {
+        pub name: *const ::c_char,
+        pub has_arg: ::c_int,
+        pub flag: *mut ::c_int,
+        pub val: ::c_int,
+    }
+}
+
+s_no_extra_traits! {
+    pub struct sockaddr_nl {
+        pub nl_family: ::sa_family_t,
+        nl_pad: ::c_ushort,
+        pub nl_pid: u32,
+        pub nl_groups: u32
+    }
+
+    pub struct dirent {
+        pub d_ino: ::ino_t,
+        pub d_off: ::off_t,
+        pub d_reclen: ::c_ushort,
+        pub d_type: ::c_uchar,
+        pub d_name: [::c_char; 256],
+    }
+
+    pub struct dirent64 {
+        pub d_ino: ::ino64_t,
+        pub d_off: ::off64_t,
+        pub d_reclen: ::c_ushort,
+        pub d_type: ::c_uchar,
+        pub d_name: [::c_char; 256],
+    }
+
+    pub struct sockaddr_alg {
+        pub salg_family: ::sa_family_t,
+        pub salg_type: [::c_uchar; 14],
+        pub salg_feat: u32,
+        pub salg_mask: u32,
+        pub salg_name: [::c_uchar; 64],
+    }
+
+    pub struct uinput_setup {
+        pub id: input_id,
+        pub name: [::c_char; UINPUT_MAX_NAME_SIZE],
+        pub ff_effects_max: ::__u32,
+    }
+
+    pub struct uinput_user_dev {
+        pub name: [::c_char; UINPUT_MAX_NAME_SIZE],
+        pub id: input_id,
+        pub ff_effects_max: ::__u32,
+        pub absmax: [::__s32; ABS_CNT],
+        pub absmin: [::__s32; ABS_CNT],
+        pub absfuzz: [::__s32; ABS_CNT],
+        pub absflat: [::__s32; ABS_CNT],
+    }
+
+    /// WARNING: The `PartialEq`, `Eq` and `Hash` implementations of this
+    /// type are unsound and will be removed in the future.
+    #[deprecated(
+        note = "this struct has unsafe trait implementations that will be \
+                removed in the future",
+        since = "0.2.80"
+    )]
+    pub struct af_alg_iv {
+        pub ivlen: u32,
+        pub iv: [::c_uchar; 0],
+    }
+
+    // x32 compatibility
+    // See https://sourceware.org/bugzilla/show_bug.cgi?id=21279
+    pub struct mq_attr {
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub mq_flags: i64,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub mq_maxmsg: i64,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub mq_msgsize: i64,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub mq_curmsgs: i64,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pad: [i64; 4],
+
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub mq_flags: ::c_long,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub mq_maxmsg: ::c_long,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub mq_msgsize: ::c_long,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub mq_curmsgs: ::c_long,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pad: [::c_long; 4],
+    }
+
+    #[cfg(libc_union)]
+    pub union __c_anonymous_ifr_ifru {
+        pub ifru_addr: ::sockaddr,
+        pub ifru_dstaddr: ::sockaddr,
+        pub ifru_broadaddr: ::sockaddr,
+        pub ifru_netmask: ::sockaddr,
+        pub ifru_hwaddr: ::sockaddr,
+        pub ifru_flags: ::c_short,
+        pub ifru_ifindex: ::c_int,
+        pub ifru_metric: ::c_int,
+        pub ifru_mtu: ::c_int,
+        pub ifru_map: __c_anonymous_ifru_map,
+        pub ifru_slave: [::c_char; ::IFNAMSIZ],
+        pub ifru_newname: [::c_char; ::IFNAMSIZ],
+        pub ifru_data: *mut ::c_char,
+    }
+
+    pub struct ifreq {
+        /// interface name, e.g. "en0"
+        pub ifr_name: [::c_char; ::IFNAMSIZ],
+        #[cfg(libc_union)]
+        pub ifr_ifru: __c_anonymous_ifr_ifru,
+        #[cfg(not(libc_union))]
+        pub ifr_ifru: ::sockaddr,
+    }
+}
+
+s_no_extra_traits! {
+    // linux/net_tstamp.h
+    #[allow(missing_debug_implementations)]
+    pub struct sock_txtime {
+        pub clockid: ::clockid_t,
+        pub flags: ::__u32,
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_union)] {
+        s_no_extra_traits! {
+            // linux/can.h
+            #[allow(missing_debug_implementations)]
+            pub union __c_anonymous_sockaddr_can_can_addr {
+                pub tp: __c_anonymous_sockaddr_can_tp,
+                pub j1939: __c_anonymous_sockaddr_can_j1939,
+            }
+
+            #[allow(missing_debug_implementations)]
+            pub struct sockaddr_can {
+                pub can_family: ::sa_family_t,
+                pub can_ifindex: ::c_int,
+                pub can_addr: __c_anonymous_sockaddr_can_can_addr,
+            }
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(feature = "extra_traits")] {
+        impl PartialEq for sockaddr_nl {
+            fn eq(&self, other: &sockaddr_nl) -> bool {
+                self.nl_family == other.nl_family &&
+                    self.nl_pid == other.nl_pid &&
+                    self.nl_groups == other.nl_groups
+            }
+        }
+        impl Eq for sockaddr_nl {}
+        impl ::fmt::Debug for sockaddr_nl {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("sockaddr_nl")
+                    .field("nl_family", &self.nl_family)
+                    .field("nl_pid", &self.nl_pid)
+                    .field("nl_groups", &self.nl_groups)
+                    .finish()
+            }
+        }
+        impl ::hash::Hash for sockaddr_nl {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.nl_family.hash(state);
+                self.nl_pid.hash(state);
+                self.nl_groups.hash(state);
+            }
+        }
+
+        impl PartialEq for dirent {
+            fn eq(&self, other: &dirent) -> bool {
+                self.d_ino == other.d_ino
+                    && self.d_off == other.d_off
+                    && self.d_reclen == other.d_reclen
+                    && self.d_type == other.d_type
+                    && self
+                    .d_name
+                    .iter()
+                    .zip(other.d_name.iter())
+                    .all(|(a,b)| a == b)
+            }
+        }
+
+        impl Eq for dirent {}
+
+        impl ::fmt::Debug for dirent {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("dirent")
+                    .field("d_ino", &self.d_ino)
+                    .field("d_off", &self.d_off)
+                    .field("d_reclen", &self.d_reclen)
+                    .field("d_type", &self.d_type)
+                // FIXME: .field("d_name", &self.d_name)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for dirent {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.d_ino.hash(state);
+                self.d_off.hash(state);
+                self.d_reclen.hash(state);
+                self.d_type.hash(state);
+                self.d_name.hash(state);
+            }
+        }
+
+        impl PartialEq for dirent64 {
+            fn eq(&self, other: &dirent64) -> bool {
+                self.d_ino == other.d_ino
+                    && self.d_off == other.d_off
+                    && self.d_reclen == other.d_reclen
+                    && self.d_type == other.d_type
+                    && self
+                    .d_name
+                    .iter()
+                    .zip(other.d_name.iter())
+                    .all(|(a,b)| a == b)
+            }
+        }
+
+        impl Eq for dirent64 {}
+
+        impl ::fmt::Debug for dirent64 {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("dirent64")
+                    .field("d_ino", &self.d_ino)
+                    .field("d_off", &self.d_off)
+                    .field("d_reclen", &self.d_reclen)
+                    .field("d_type", &self.d_type)
+                // FIXME: .field("d_name", &self.d_name)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for dirent64 {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.d_ino.hash(state);
+                self.d_off.hash(state);
+                self.d_reclen.hash(state);
+                self.d_type.hash(state);
+                self.d_name.hash(state);
+            }
+        }
+
+        impl PartialEq for pthread_cond_t {
+            fn eq(&self, other: &pthread_cond_t) -> bool {
+                self.size.iter().zip(other.size.iter()).all(|(a,b)| a == b)
+            }
+        }
+
+        impl Eq for pthread_cond_t {}
+
+        impl ::fmt::Debug for pthread_cond_t {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("pthread_cond_t")
+                // FIXME: .field("size", &self.size)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for pthread_cond_t {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.size.hash(state);
+            }
+        }
+
+        impl PartialEq for pthread_mutex_t {
+            fn eq(&self, other: &pthread_mutex_t) -> bool {
+                self.size.iter().zip(other.size.iter()).all(|(a,b)| a == b)
+            }
+        }
+
+        impl Eq for pthread_mutex_t {}
+
+        impl ::fmt::Debug for pthread_mutex_t {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("pthread_mutex_t")
+                // FIXME: .field("size", &self.size)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for pthread_mutex_t {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.size.hash(state);
+            }
+        }
+
+        impl PartialEq for pthread_rwlock_t {
+            fn eq(&self, other: &pthread_rwlock_t) -> bool {
+                self.size.iter().zip(other.size.iter()).all(|(a,b)| a == b)
+            }
+        }
+
+        impl Eq for pthread_rwlock_t {}
+
+        impl ::fmt::Debug for pthread_rwlock_t {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("pthread_rwlock_t")
+                // FIXME: .field("size", &self.size)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for pthread_rwlock_t {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.size.hash(state);
+            }
+        }
+
+        impl PartialEq for sockaddr_alg {
+            fn eq(&self, other: &sockaddr_alg) -> bool {
+                self.salg_family == other.salg_family
+                    && self
+                    .salg_type
+                    .iter()
+                    .zip(other.salg_type.iter())
+                    .all(|(a, b)| a == b)
+                    && self.salg_feat == other.salg_feat
+                    && self.salg_mask == other.salg_mask
+                    && self
+                    .salg_name
+                    .iter()
+                    .zip(other.salg_name.iter())
+                    .all(|(a, b)| a == b)
+           }
+        }
+
+        impl Eq for sockaddr_alg {}
+
+        impl ::fmt::Debug for sockaddr_alg {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("sockaddr_alg")
+                    .field("salg_family", &self.salg_family)
+                    .field("salg_type", &self.salg_type)
+                    .field("salg_feat", &self.salg_feat)
+                    .field("salg_mask", &self.salg_mask)
+                    .field("salg_name", &&self.salg_name[..])
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for sockaddr_alg {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.salg_family.hash(state);
+                self.salg_type.hash(state);
+                self.salg_feat.hash(state);
+                self.salg_mask.hash(state);
+                self.salg_name.hash(state);
+            }
+        }
+
+        impl PartialEq for uinput_setup {
+            fn eq(&self, other: &uinput_setup) -> bool {
+                self.id == other.id
+                    && self.name[..] == other.name[..]
+                    && self.ff_effects_max == other.ff_effects_max
+           }
+        }
+        impl Eq for uinput_setup {}
+
+        impl ::fmt::Debug for uinput_setup {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("uinput_setup")
+                    .field("id", &self.id)
+                    .field("name", &&self.name[..])
+                    .field("ff_effects_max", &self.ff_effects_max)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for uinput_setup {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.id.hash(state);
+                self.name.hash(state);
+                self.ff_effects_max.hash(state);
+            }
+        }
+
+        impl PartialEq for uinput_user_dev {
+            fn eq(&self, other: &uinput_user_dev) -> bool {
+                 self.name[..] == other.name[..]
+                    && self.id == other.id
+                    && self.ff_effects_max == other.ff_effects_max
+                    && self.absmax[..] == other.absmax[..]
+                    && self.absmin[..] == other.absmin[..]
+                    && self.absfuzz[..] == other.absfuzz[..]
+                    && self.absflat[..] == other.absflat[..]
+           }
+        }
+        impl Eq for uinput_user_dev {}
+
+        impl ::fmt::Debug for uinput_user_dev {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("uinput_setup")
+                    .field("name", &&self.name[..])
+                    .field("id", &self.id)
+                    .field("ff_effects_max", &self.ff_effects_max)
+                    .field("absmax", &&self.absmax[..])
+                    .field("absmin", &&self.absmin[..])
+                    .field("absfuzz", &&self.absfuzz[..])
+                    .field("absflat", &&self.absflat[..])
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for uinput_user_dev {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.name.hash(state);
+                self.id.hash(state);
+                self.ff_effects_max.hash(state);
+                self.absmax.hash(state);
+                self.absmin.hash(state);
+                self.absfuzz.hash(state);
+                self.absflat.hash(state);
+            }
+        }
+
+        #[allow(deprecated)]
+        impl af_alg_iv {
+            fn as_slice(&self) -> &[u8] {
+                unsafe {
+                    ::core::slice::from_raw_parts(
+                        self.iv.as_ptr(),
+                        self.ivlen as usize
+                    )
+                }
+            }
+        }
+
+        #[allow(deprecated)]
+        impl PartialEq for af_alg_iv {
+            fn eq(&self, other: &af_alg_iv) -> bool {
+                *self.as_slice() == *other.as_slice()
+           }
+        }
+
+        #[allow(deprecated)]
+        impl Eq for af_alg_iv {}
+
+        #[allow(deprecated)]
+        impl ::fmt::Debug for af_alg_iv {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("af_alg_iv")
+                    .field("ivlen", &self.ivlen)
+                    .finish()
+            }
+        }
+
+        #[allow(deprecated)]
+        impl ::hash::Hash for af_alg_iv {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.as_slice().hash(state);
+            }
+        }
+
+        impl PartialEq for mq_attr {
+            fn eq(&self, other: &mq_attr) -> bool {
+                self.mq_flags == other.mq_flags &&
+                self.mq_maxmsg == other.mq_maxmsg &&
+                self.mq_msgsize == other.mq_msgsize &&
+                self.mq_curmsgs == other.mq_curmsgs
+            }
+        }
+        impl Eq for mq_attr {}
+        impl ::fmt::Debug for mq_attr {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("mq_attr")
+                    .field("mq_flags", &self.mq_flags)
+                    .field("mq_maxmsg", &self.mq_maxmsg)
+                    .field("mq_msgsize", &self.mq_msgsize)
+                    .field("mq_curmsgs", &self.mq_curmsgs)
+                    .finish()
+            }
+        }
+        impl ::hash::Hash for mq_attr {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.mq_flags.hash(state);
+                self.mq_maxmsg.hash(state);
+                self.mq_msgsize.hash(state);
+                self.mq_curmsgs.hash(state);
+            }
+        }
+        #[cfg(libc_union)]
+        impl ::fmt::Debug for __c_anonymous_ifr_ifru {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("ifr_ifru")
+                    .field("ifru_addr", unsafe { &self.ifru_addr })
+                    .field("ifru_dstaddr", unsafe { &self.ifru_dstaddr })
+                    .field("ifru_broadaddr", unsafe { &self.ifru_broadaddr })
+                    .field("ifru_netmask", unsafe { &self.ifru_netmask })
+                    .field("ifru_hwaddr", unsafe { &self.ifru_hwaddr })
+                    .field("ifru_flags", unsafe { &self.ifru_flags })
+                    .field("ifru_ifindex", unsafe { &self.ifru_ifindex })
+                    .field("ifru_metric", unsafe { &self.ifru_metric })
+                    .field("ifru_mtu", unsafe { &self.ifru_mtu })
+                    .field("ifru_map", unsafe { &self.ifru_map })
+                    .field("ifru_slave", unsafe { &self.ifru_slave })
+                    .field("ifru_newname", unsafe { &self.ifru_newname })
+                    .field("ifru_data", unsafe { &self.ifru_data })
+                    .finish()
+            }
+        }
+        impl ::fmt::Debug for ifreq {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("ifreq")
+                    .field("ifr_name", &self.ifr_name)
+                    .field("ifr_ifru", &self.ifr_ifru)
+                    .finish()
+            }
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(any(target_env = "gnu", target_env = "musl"))] {
+        pub const ABDAY_1: ::nl_item = 0x20000;
+        pub const ABDAY_2: ::nl_item = 0x20001;
+        pub const ABDAY_3: ::nl_item = 0x20002;
+        pub const ABDAY_4: ::nl_item = 0x20003;
+        pub const ABDAY_5: ::nl_item = 0x20004;
+        pub const ABDAY_6: ::nl_item = 0x20005;
+        pub const ABDAY_7: ::nl_item = 0x20006;
+
+        pub const DAY_1: ::nl_item = 0x20007;
+        pub const DAY_2: ::nl_item = 0x20008;
+        pub const DAY_3: ::nl_item = 0x20009;
+        pub const DAY_4: ::nl_item = 0x2000A;
+        pub const DAY_5: ::nl_item = 0x2000B;
+        pub const DAY_6: ::nl_item = 0x2000C;
+        pub const DAY_7: ::nl_item = 0x2000D;
+
+        pub const ABMON_1: ::nl_item = 0x2000E;
+        pub const ABMON_2: ::nl_item = 0x2000F;
+        pub const ABMON_3: ::nl_item = 0x20010;
+        pub const ABMON_4: ::nl_item = 0x20011;
+        pub const ABMON_5: ::nl_item = 0x20012;
+        pub const ABMON_6: ::nl_item = 0x20013;
+        pub const ABMON_7: ::nl_item = 0x20014;
+        pub const ABMON_8: ::nl_item = 0x20015;
+        pub const ABMON_9: ::nl_item = 0x20016;
+        pub const ABMON_10: ::nl_item = 0x20017;
+        pub const ABMON_11: ::nl_item = 0x20018;
+        pub const ABMON_12: ::nl_item = 0x20019;
+
+        pub const MON_1: ::nl_item = 0x2001A;
+        pub const MON_2: ::nl_item = 0x2001B;
+        pub const MON_3: ::nl_item = 0x2001C;
+        pub const MON_4: ::nl_item = 0x2001D;
+        pub const MON_5: ::nl_item = 0x2001E;
+        pub const MON_6: ::nl_item = 0x2001F;
+        pub const MON_7: ::nl_item = 0x20020;
+        pub const MON_8: ::nl_item = 0x20021;
+        pub const MON_9: ::nl_item = 0x20022;
+        pub const MON_10: ::nl_item = 0x20023;
+        pub const MON_11: ::nl_item = 0x20024;
+        pub const MON_12: ::nl_item = 0x20025;
+
+        pub const AM_STR: ::nl_item = 0x20026;
+        pub const PM_STR: ::nl_item = 0x20027;
+
+        pub const D_T_FMT: ::nl_item = 0x20028;
+        pub const D_FMT: ::nl_item = 0x20029;
+        pub const T_FMT: ::nl_item = 0x2002A;
+        pub const T_FMT_AMPM: ::nl_item = 0x2002B;
+
+        pub const ERA: ::nl_item = 0x2002C;
+        pub const ERA_D_FMT: ::nl_item = 0x2002E;
+        pub const ALT_DIGITS: ::nl_item = 0x2002F;
+        pub const ERA_D_T_FMT: ::nl_item = 0x20030;
+        pub const ERA_T_FMT: ::nl_item = 0x20031;
+
+        pub const CODESET: ::nl_item = 14;
+        pub const CRNCYSTR: ::nl_item = 0x4000F;
+        pub const RADIXCHAR: ::nl_item = 0x10000;
+        pub const THOUSEP: ::nl_item = 0x10001;
+        pub const YESEXPR: ::nl_item = 0x50000;
+        pub const NOEXPR: ::nl_item = 0x50001;
+        pub const YESSTR: ::nl_item = 0x50002;
+        pub const NOSTR: ::nl_item = 0x50003;
+    }
+}
+
+pub const RUSAGE_CHILDREN: ::c_int = -1;
+pub const L_tmpnam: ::c_uint = 20;
+pub const _PC_LINK_MAX: ::c_int = 0;
+pub const _PC_MAX_CANON: ::c_int = 1;
+pub const _PC_MAX_INPUT: ::c_int = 2;
+pub const _PC_NAME_MAX: ::c_int = 3;
+pub const _PC_PATH_MAX: ::c_int = 4;
+pub const _PC_PIPE_BUF: ::c_int = 5;
+pub const _PC_CHOWN_RESTRICTED: ::c_int = 6;
+pub const _PC_NO_TRUNC: ::c_int = 7;
+pub const _PC_VDISABLE: ::c_int = 8;
+pub const _PC_SYNC_IO: ::c_int = 9;
+pub const _PC_ASYNC_IO: ::c_int = 10;
+pub const _PC_PRIO_IO: ::c_int = 11;
+pub const _PC_SOCK_MAXBUF: ::c_int = 12;
+pub const _PC_FILESIZEBITS: ::c_int = 13;
+pub const _PC_REC_INCR_XFER_SIZE: ::c_int = 14;
+pub const _PC_REC_MAX_XFER_SIZE: ::c_int = 15;
+pub const _PC_REC_MIN_XFER_SIZE: ::c_int = 16;
+pub const _PC_REC_XFER_ALIGN: ::c_int = 17;
+pub const _PC_ALLOC_SIZE_MIN: ::c_int = 18;
+pub const _PC_SYMLINK_MAX: ::c_int = 19;
+pub const _PC_2_SYMLINKS: ::c_int = 20;
+
+pub const MS_NOUSER: ::c_ulong = 0xffffffff80000000;
+
+pub const _SC_ARG_MAX: ::c_int = 0;
+pub const _SC_CHILD_MAX: ::c_int = 1;
+pub const _SC_CLK_TCK: ::c_int = 2;
+pub const _SC_NGROUPS_MAX: ::c_int = 3;
+pub const _SC_OPEN_MAX: ::c_int = 4;
+pub const _SC_STREAM_MAX: ::c_int = 5;
+pub const _SC_TZNAME_MAX: ::c_int = 6;
+pub const _SC_JOB_CONTROL: ::c_int = 7;
+pub const _SC_SAVED_IDS: ::c_int = 8;
+pub const _SC_REALTIME_SIGNALS: ::c_int = 9;
+pub const _SC_PRIORITY_SCHEDULING: ::c_int = 10;
+pub const _SC_TIMERS: ::c_int = 11;
+pub const _SC_ASYNCHRONOUS_IO: ::c_int = 12;
+pub const _SC_PRIORITIZED_IO: ::c_int = 13;
+pub const _SC_SYNCHRONIZED_IO: ::c_int = 14;
+pub const _SC_FSYNC: ::c_int = 15;
+pub const _SC_MAPPED_FILES: ::c_int = 16;
+pub const _SC_MEMLOCK: ::c_int = 17;
+pub const _SC_MEMLOCK_RANGE: ::c_int = 18;
+pub const _SC_MEMORY_PROTECTION: ::c_int = 19;
+pub const _SC_MESSAGE_PASSING: ::c_int = 20;
+pub const _SC_SEMAPHORES: ::c_int = 21;
+pub const _SC_SHARED_MEMORY_OBJECTS: ::c_int = 22;
+pub const _SC_AIO_LISTIO_MAX: ::c_int = 23;
+pub const _SC_AIO_MAX: ::c_int = 24;
+pub const _SC_AIO_PRIO_DELTA_MAX: ::c_int = 25;
+pub const _SC_DELAYTIMER_MAX: ::c_int = 26;
+pub const _SC_MQ_OPEN_MAX: ::c_int = 27;
+pub const _SC_MQ_PRIO_MAX: ::c_int = 28;
+pub const _SC_VERSION: ::c_int = 29;
+pub const _SC_PAGESIZE: ::c_int = 30;
+pub const _SC_PAGE_SIZE: ::c_int = _SC_PAGESIZE;
+pub const _SC_RTSIG_MAX: ::c_int = 31;
+pub const _SC_SEM_NSEMS_MAX: ::c_int = 32;
+pub const _SC_SEM_VALUE_MAX: ::c_int = 33;
+pub const _SC_SIGQUEUE_MAX: ::c_int = 34;
+pub const _SC_TIMER_MAX: ::c_int = 35;
+pub const _SC_BC_BASE_MAX: ::c_int = 36;
+pub const _SC_BC_DIM_MAX: ::c_int = 37;
+pub const _SC_BC_SCALE_MAX: ::c_int = 38;
+pub const _SC_BC_STRING_MAX: ::c_int = 39;
+pub const _SC_COLL_WEIGHTS_MAX: ::c_int = 40;
+pub const _SC_EXPR_NEST_MAX: ::c_int = 42;
+pub const _SC_LINE_MAX: ::c_int = 43;
+pub const _SC_RE_DUP_MAX: ::c_int = 44;
+pub const _SC_2_VERSION: ::c_int = 46;
+pub const _SC_2_C_BIND: ::c_int = 47;
+pub const _SC_2_C_DEV: ::c_int = 48;
+pub const _SC_2_FORT_DEV: ::c_int = 49;
+pub const _SC_2_FORT_RUN: ::c_int = 50;
+pub const _SC_2_SW_DEV: ::c_int = 51;
+pub const _SC_2_LOCALEDEF: ::c_int = 52;
+pub const _SC_UIO_MAXIOV: ::c_int = 60;
+pub const _SC_IOV_MAX: ::c_int = 60;
+pub const _SC_THREADS: ::c_int = 67;
+pub const _SC_THREAD_SAFE_FUNCTIONS: ::c_int = 68;
+pub const _SC_GETGR_R_SIZE_MAX: ::c_int = 69;
+pub const _SC_GETPW_R_SIZE_MAX: ::c_int = 70;
+pub const _SC_LOGIN_NAME_MAX: ::c_int = 71;
+pub const _SC_TTY_NAME_MAX: ::c_int = 72;
+pub const _SC_THREAD_DESTRUCTOR_ITERATIONS: ::c_int = 73;
+pub const _SC_THREAD_KEYS_MAX: ::c_int = 74;
+pub const _SC_THREAD_STACK_MIN: ::c_int = 75;
+pub const _SC_THREAD_THREADS_MAX: ::c_int = 76;
+pub const _SC_THREAD_ATTR_STACKADDR: ::c_int = 77;
+pub const _SC_THREAD_ATTR_STACKSIZE: ::c_int = 78;
+pub const _SC_THREAD_PRIORITY_SCHEDULING: ::c_int = 79;
+pub const _SC_THREAD_PRIO_INHERIT: ::c_int = 80;
+pub const _SC_THREAD_PRIO_PROTECT: ::c_int = 81;
+pub const _SC_THREAD_PROCESS_SHARED: ::c_int = 82;
+pub const _SC_NPROCESSORS_CONF: ::c_int = 83;
+pub const _SC_NPROCESSORS_ONLN: ::c_int = 84;
+pub const _SC_PHYS_PAGES: ::c_int = 85;
+pub const _SC_AVPHYS_PAGES: ::c_int = 86;
+pub const _SC_ATEXIT_MAX: ::c_int = 87;
+pub const _SC_PASS_MAX: ::c_int = 88;
+pub const _SC_XOPEN_VERSION: ::c_int = 89;
+pub const _SC_XOPEN_XCU_VERSION: ::c_int = 90;
+pub const _SC_XOPEN_UNIX: ::c_int = 91;
+pub const _SC_XOPEN_CRYPT: ::c_int = 92;
+pub const _SC_XOPEN_ENH_I18N: ::c_int = 93;
+pub const _SC_XOPEN_SHM: ::c_int = 94;
+pub const _SC_2_CHAR_TERM: ::c_int = 95;
+pub const _SC_2_UPE: ::c_int = 97;
+pub const _SC_XOPEN_XPG2: ::c_int = 98;
+pub const _SC_XOPEN_XPG3: ::c_int = 99;
+pub const _SC_XOPEN_XPG4: ::c_int = 100;
+pub const _SC_NZERO: ::c_int = 109;
+pub const _SC_XBS5_ILP32_OFF32: ::c_int = 125;
+pub const _SC_XBS5_ILP32_OFFBIG: ::c_int = 126;
+pub const _SC_XBS5_LP64_OFF64: ::c_int = 127;
+pub const _SC_XBS5_LPBIG_OFFBIG: ::c_int = 128;
+pub const _SC_XOPEN_LEGACY: ::c_int = 129;
+pub const _SC_XOPEN_REALTIME: ::c_int = 130;
+pub const _SC_XOPEN_REALTIME_THREADS: ::c_int = 131;
+pub const _SC_ADVISORY_INFO: ::c_int = 132;
+pub const _SC_BARRIERS: ::c_int = 133;
+pub const _SC_CLOCK_SELECTION: ::c_int = 137;
+pub const _SC_CPUTIME: ::c_int = 138;
+pub const _SC_THREAD_CPUTIME: ::c_int = 139;
+pub const _SC_MONOTONIC_CLOCK: ::c_int = 149;
+pub const _SC_READER_WRITER_LOCKS: ::c_int = 153;
+pub const _SC_SPIN_LOCKS: ::c_int = 154;
+pub const _SC_REGEXP: ::c_int = 155;
+pub const _SC_SHELL: ::c_int = 157;
+pub const _SC_SPAWN: ::c_int = 159;
+pub const _SC_SPORADIC_SERVER: ::c_int = 160;
+pub const _SC_THREAD_SPORADIC_SERVER: ::c_int = 161;
+pub const _SC_TIMEOUTS: ::c_int = 164;
+pub const _SC_TYPED_MEMORY_OBJECTS: ::c_int = 165;
+pub const _SC_2_PBS: ::c_int = 168;
+pub const _SC_2_PBS_ACCOUNTING: ::c_int = 169;
+pub const _SC_2_PBS_LOCATE: ::c_int = 170;
+pub const _SC_2_PBS_MESSAGE: ::c_int = 171;
+pub const _SC_2_PBS_TRACK: ::c_int = 172;
+pub const _SC_SYMLOOP_MAX: ::c_int = 173;
+pub const _SC_STREAMS: ::c_int = 174;
+pub const _SC_2_PBS_CHECKPOINT: ::c_int = 175;
+pub const _SC_V6_ILP32_OFF32: ::c_int = 176;
+pub const _SC_V6_ILP32_OFFBIG: ::c_int = 177;
+pub const _SC_V6_LP64_OFF64: ::c_int = 178;
+pub const _SC_V6_LPBIG_OFFBIG: ::c_int = 179;
+pub const _SC_HOST_NAME_MAX: ::c_int = 180;
+pub const _SC_TRACE: ::c_int = 181;
+pub const _SC_TRACE_EVENT_FILTER: ::c_int = 182;
+pub const _SC_TRACE_INHERIT: ::c_int = 183;
+pub const _SC_TRACE_LOG: ::c_int = 184;
+pub const _SC_IPV6: ::c_int = 235;
+pub const _SC_RAW_SOCKETS: ::c_int = 236;
+pub const _SC_V7_ILP32_OFF32: ::c_int = 237;
+pub const _SC_V7_ILP32_OFFBIG: ::c_int = 238;
+pub const _SC_V7_LP64_OFF64: ::c_int = 239;
+pub const _SC_V7_LPBIG_OFFBIG: ::c_int = 240;
+pub const _SC_SS_REPL_MAX: ::c_int = 241;
+pub const _SC_TRACE_EVENT_NAME_MAX: ::c_int = 242;
+pub const _SC_TRACE_NAME_MAX: ::c_int = 243;
+pub const _SC_TRACE_SYS_MAX: ::c_int = 244;
+pub const _SC_TRACE_USER_EVENT_MAX: ::c_int = 245;
+pub const _SC_XOPEN_STREAMS: ::c_int = 246;
+pub const _SC_THREAD_ROBUST_PRIO_INHERIT: ::c_int = 247;
+pub const _SC_THREAD_ROBUST_PRIO_PROTECT: ::c_int = 248;
+
+pub const RLIM_SAVED_MAX: ::rlim_t = RLIM_INFINITY;
+pub const RLIM_SAVED_CUR: ::rlim_t = RLIM_INFINITY;
+
+// elf.h - Fields in the e_ident array.
+pub const EI_NIDENT: usize = 16;
+
+pub const EI_MAG0: usize = 0;
+pub const ELFMAG0: u8 = 0x7f;
+pub const EI_MAG1: usize = 1;
+pub const ELFMAG1: u8 = b'E';
+pub const EI_MAG2: usize = 2;
+pub const ELFMAG2: u8 = b'L';
+pub const EI_MAG3: usize = 3;
+pub const ELFMAG3: u8 = b'F';
+pub const SELFMAG: usize = 4;
+
+pub const EI_CLASS: usize = 4;
+pub const ELFCLASSNONE: u8 = 0;
+pub const ELFCLASS32: u8 = 1;
+pub const ELFCLASS64: u8 = 2;
+pub const ELFCLASSNUM: usize = 3;
+
+pub const EI_DATA: usize = 5;
+pub const ELFDATANONE: u8 = 0;
+pub const ELFDATA2LSB: u8 = 1;
+pub const ELFDATA2MSB: u8 = 2;
+pub const ELFDATANUM: usize = 3;
+
+pub const EI_VERSION: usize = 6;
+
+pub const EI_OSABI: usize = 7;
+pub const ELFOSABI_NONE: u8 = 0;
+pub const ELFOSABI_SYSV: u8 = 0;
+pub const ELFOSABI_HPUX: u8 = 1;
+pub const ELFOSABI_NETBSD: u8 = 2;
+pub const ELFOSABI_GNU: u8 = 3;
+pub const ELFOSABI_LINUX: u8 = ELFOSABI_GNU;
+pub const ELFOSABI_SOLARIS: u8 = 6;
+pub const ELFOSABI_AIX: u8 = 7;
+pub const ELFOSABI_IRIX: u8 = 8;
+pub const ELFOSABI_FREEBSD: u8 = 9;
+pub const ELFOSABI_TRU64: u8 = 10;
+pub const ELFOSABI_MODESTO: u8 = 11;
+pub const ELFOSABI_OPENBSD: u8 = 12;
+pub const ELFOSABI_ARM: u8 = 97;
+pub const ELFOSABI_STANDALONE: u8 = 255;
+
+pub const EI_ABIVERSION: usize = 8;
+
+pub const EI_PAD: usize = 9;
+
+// elf.h - Legal values for e_type (object file type).
+pub const ET_NONE: u16 = 0;
+pub const ET_REL: u16 = 1;
+pub const ET_EXEC: u16 = 2;
+pub const ET_DYN: u16 = 3;
+pub const ET_CORE: u16 = 4;
+pub const ET_NUM: u16 = 5;
+pub const ET_LOOS: u16 = 0xfe00;
+pub const ET_HIOS: u16 = 0xfeff;
+pub const ET_LOPROC: u16 = 0xff00;
+pub const ET_HIPROC: u16 = 0xffff;
+
+// elf.h - Legal values for e_machine (architecture).
+pub const EM_NONE: u16 = 0;
+pub const EM_M32: u16 = 1;
+pub const EM_SPARC: u16 = 2;
+pub const EM_386: u16 = 3;
+pub const EM_68K: u16 = 4;
+pub const EM_88K: u16 = 5;
+pub const EM_860: u16 = 7;
+pub const EM_MIPS: u16 = 8;
+pub const EM_S370: u16 = 9;
+pub const EM_MIPS_RS3_LE: u16 = 10;
+pub const EM_PARISC: u16 = 15;
+pub const EM_VPP500: u16 = 17;
+pub const EM_SPARC32PLUS: u16 = 18;
+pub const EM_960: u16 = 19;
+pub const EM_PPC: u16 = 20;
+pub const EM_PPC64: u16 = 21;
+pub const EM_S390: u16 = 22;
+pub const EM_V800: u16 = 36;
+pub const EM_FR20: u16 = 37;
+pub const EM_RH32: u16 = 38;
+pub const EM_RCE: u16 = 39;
+pub const EM_ARM: u16 = 40;
+pub const EM_FAKE_ALPHA: u16 = 41;
+pub const EM_SH: u16 = 42;
+pub const EM_SPARCV9: u16 = 43;
+pub const EM_TRICORE: u16 = 44;
+pub const EM_ARC: u16 = 45;
+pub const EM_H8_300: u16 = 46;
+pub const EM_H8_300H: u16 = 47;
+pub const EM_H8S: u16 = 48;
+pub const EM_H8_500: u16 = 49;
+pub const EM_IA_64: u16 = 50;
+pub const EM_MIPS_X: u16 = 51;
+pub const EM_COLDFIRE: u16 = 52;
+pub const EM_68HC12: u16 = 53;
+pub const EM_MMA: u16 = 54;
+pub const EM_PCP: u16 = 55;
+pub const EM_NCPU: u16 = 56;
+pub const EM_NDR1: u16 = 57;
+pub const EM_STARCORE: u16 = 58;
+pub const EM_ME16: u16 = 59;
+pub const EM_ST100: u16 = 60;
+pub const EM_TINYJ: u16 = 61;
+pub const EM_X86_64: u16 = 62;
+pub const EM_PDSP: u16 = 63;
+pub const EM_FX66: u16 = 66;
+pub const EM_ST9PLUS: u16 = 67;
+pub const EM_ST7: u16 = 68;
+pub const EM_68HC16: u16 = 69;
+pub const EM_68HC11: u16 = 70;
+pub const EM_68HC08: u16 = 71;
+pub const EM_68HC05: u16 = 72;
+pub const EM_SVX: u16 = 73;
+pub const EM_ST19: u16 = 74;
+pub const EM_VAX: u16 = 75;
+pub const EM_CRIS: u16 = 76;
+pub const EM_JAVELIN: u16 = 77;
+pub const EM_FIREPATH: u16 = 78;
+pub const EM_ZSP: u16 = 79;
+pub const EM_MMIX: u16 = 80;
+pub const EM_HUANY: u16 = 81;
+pub const EM_PRISM: u16 = 82;
+pub const EM_AVR: u16 = 83;
+pub const EM_FR30: u16 = 84;
+pub const EM_D10V: u16 = 85;
+pub const EM_D30V: u16 = 86;
+pub const EM_V850: u16 = 87;
+pub const EM_M32R: u16 = 88;
+pub const EM_MN10300: u16 = 89;
+pub const EM_MN10200: u16 = 90;
+pub const EM_PJ: u16 = 91;
+pub const EM_OPENRISC: u16 = 92;
+pub const EM_ARC_A5: u16 = 93;
+pub const EM_XTENSA: u16 = 94;
+pub const EM_AARCH64: u16 = 183;
+pub const EM_TILEPRO: u16 = 188;
+pub const EM_TILEGX: u16 = 191;
+pub const EM_ALPHA: u16 = 0x9026;
+
+// elf.h - Legal values for e_version (version).
+pub const EV_NONE: u32 = 0;
+pub const EV_CURRENT: u32 = 1;
+pub const EV_NUM: u32 = 2;
+
+// elf.h - Legal values for p_type (segment type).
+pub const PT_NULL: u32 = 0;
+pub const PT_LOAD: u32 = 1;
+pub const PT_DYNAMIC: u32 = 2;
+pub const PT_INTERP: u32 = 3;
+pub const PT_NOTE: u32 = 4;
+pub const PT_SHLIB: u32 = 5;
+pub const PT_PHDR: u32 = 6;
+pub const PT_TLS: u32 = 7;
+pub const PT_NUM: u32 = 8;
+pub const PT_LOOS: u32 = 0x60000000;
+pub const PT_GNU_EH_FRAME: u32 = 0x6474e550;
+pub const PT_GNU_STACK: u32 = 0x6474e551;
+pub const PT_GNU_RELRO: u32 = 0x6474e552;
+pub const PT_LOSUNW: u32 = 0x6ffffffa;
+pub const PT_SUNWBSS: u32 = 0x6ffffffa;
+pub const PT_SUNWSTACK: u32 = 0x6ffffffb;
+pub const PT_HISUNW: u32 = 0x6fffffff;
+pub const PT_HIOS: u32 = 0x6fffffff;
+pub const PT_LOPROC: u32 = 0x70000000;
+pub const PT_HIPROC: u32 = 0x7fffffff;
+
+// Legal values for p_flags (segment flags).
+pub const PF_X: u32 = 1 << 0;
+pub const PF_W: u32 = 1 << 1;
+pub const PF_R: u32 = 1 << 2;
+pub const PF_MASKOS: u32 = 0x0ff00000;
+pub const PF_MASKPROC: u32 = 0xf0000000;
+
+// elf.h - Legal values for a_type (entry type).
+pub const AT_NULL: ::c_ulong = 0;
+pub const AT_IGNORE: ::c_ulong = 1;
+pub const AT_EXECFD: ::c_ulong = 2;
+pub const AT_PHDR: ::c_ulong = 3;
+pub const AT_PHENT: ::c_ulong = 4;
+pub const AT_PHNUM: ::c_ulong = 5;
+pub const AT_PAGESZ: ::c_ulong = 6;
+pub const AT_BASE: ::c_ulong = 7;
+pub const AT_FLAGS: ::c_ulong = 8;
+pub const AT_ENTRY: ::c_ulong = 9;
+pub const AT_NOTELF: ::c_ulong = 10;
+pub const AT_UID: ::c_ulong = 11;
+pub const AT_EUID: ::c_ulong = 12;
+pub const AT_GID: ::c_ulong = 13;
+pub const AT_EGID: ::c_ulong = 14;
+pub const AT_PLATFORM: ::c_ulong = 15;
+pub const AT_HWCAP: ::c_ulong = 16;
+pub const AT_CLKTCK: ::c_ulong = 17;
+
+pub const AT_SECURE: ::c_ulong = 23;
+pub const AT_BASE_PLATFORM: ::c_ulong = 24;
+pub const AT_RANDOM: ::c_ulong = 25;
+pub const AT_HWCAP2: ::c_ulong = 26;
+
+pub const AT_EXECFN: ::c_ulong = 31;
+
+pub const GLOB_ERR: ::c_int = 1 << 0;
+pub const GLOB_MARK: ::c_int = 1 << 1;
+pub const GLOB_NOSORT: ::c_int = 1 << 2;
+pub const GLOB_DOOFFS: ::c_int = 1 << 3;
+pub const GLOB_NOCHECK: ::c_int = 1 << 4;
+pub const GLOB_APPEND: ::c_int = 1 << 5;
+pub const GLOB_NOESCAPE: ::c_int = 1 << 6;
+
+pub const GLOB_NOSPACE: ::c_int = 1;
+pub const GLOB_ABORTED: ::c_int = 2;
+pub const GLOB_NOMATCH: ::c_int = 3;
+
+pub const POSIX_MADV_NORMAL: ::c_int = 0;
+pub const POSIX_MADV_RANDOM: ::c_int = 1;
+pub const POSIX_MADV_SEQUENTIAL: ::c_int = 2;
+pub const POSIX_MADV_WILLNEED: ::c_int = 3;
+pub const POSIX_SPAWN_USEVFORK: ::c_int = 64;
+pub const POSIX_SPAWN_SETSID: ::c_int = 128;
+
+pub const S_IEXEC: mode_t = 64;
+pub const S_IWRITE: mode_t = 128;
+pub const S_IREAD: mode_t = 256;
+
+pub const F_LOCK: ::c_int = 1;
+pub const F_TEST: ::c_int = 3;
+pub const F_TLOCK: ::c_int = 2;
+pub const F_ULOCK: ::c_int = 0;
+
+pub const F_SEAL_FUTURE_WRITE: ::c_int = 0x0010;
+
+pub const IFF_LOWER_UP: ::c_int = 0x10000;
+pub const IFF_DORMANT: ::c_int = 0x20000;
+pub const IFF_ECHO: ::c_int = 0x40000;
+
+// linux/if_addr.h
+pub const IFA_UNSPEC: ::c_ushort = 0;
+pub const IFA_ADDRESS: ::c_ushort = 1;
+pub const IFA_LOCAL: ::c_ushort = 2;
+pub const IFA_LABEL: ::c_ushort = 3;
+pub const IFA_BROADCAST: ::c_ushort = 4;
+pub const IFA_ANYCAST: ::c_ushort = 5;
+pub const IFA_CACHEINFO: ::c_ushort = 6;
+pub const IFA_MULTICAST: ::c_ushort = 7;
+
+pub const IFA_F_SECONDARY: u32 = 0x01;
+pub const IFA_F_TEMPORARY: u32 = 0x01;
+pub const IFA_F_NODAD: u32 = 0x02;
+pub const IFA_F_OPTIMISTIC: u32 = 0x04;
+pub const IFA_F_DADFAILED: u32 = 0x08;
+pub const IFA_F_HOMEADDRESS: u32 = 0x10;
+pub const IFA_F_DEPRECATED: u32 = 0x20;
+pub const IFA_F_TENTATIVE: u32 = 0x40;
+pub const IFA_F_PERMANENT: u32 = 0x80;
+
+// linux/if_link.h
+pub const IFLA_UNSPEC: ::c_ushort = 0;
+pub const IFLA_ADDRESS: ::c_ushort = 1;
+pub const IFLA_BROADCAST: ::c_ushort = 2;
+pub const IFLA_IFNAME: ::c_ushort = 3;
+pub const IFLA_MTU: ::c_ushort = 4;
+pub const IFLA_LINK: ::c_ushort = 5;
+pub const IFLA_QDISC: ::c_ushort = 6;
+pub const IFLA_STATS: ::c_ushort = 7;
+pub const IFLA_COST: ::c_ushort = 8;
+pub const IFLA_PRIORITY: ::c_ushort = 9;
+pub const IFLA_MASTER: ::c_ushort = 10;
+pub const IFLA_WIRELESS: ::c_ushort = 11;
+pub const IFLA_PROTINFO: ::c_ushort = 12;
+pub const IFLA_TXQLEN: ::c_ushort = 13;
+pub const IFLA_MAP: ::c_ushort = 14;
+pub const IFLA_WEIGHT: ::c_ushort = 15;
+pub const IFLA_OPERSTATE: ::c_ushort = 16;
+pub const IFLA_LINKMODE: ::c_ushort = 17;
+pub const IFLA_LINKINFO: ::c_ushort = 18;
+pub const IFLA_NET_NS_PID: ::c_ushort = 19;
+pub const IFLA_IFALIAS: ::c_ushort = 20;
+pub const IFLA_NUM_VF: ::c_ushort = 21;
+pub const IFLA_VFINFO_LIST: ::c_ushort = 22;
+pub const IFLA_STATS64: ::c_ushort = 23;
+pub const IFLA_VF_PORTS: ::c_ushort = 24;
+pub const IFLA_PORT_SELF: ::c_ushort = 25;
+pub const IFLA_AF_SPEC: ::c_ushort = 26;
+pub const IFLA_GROUP: ::c_ushort = 27;
+pub const IFLA_NET_NS_FD: ::c_ushort = 28;
+pub const IFLA_EXT_MASK: ::c_ushort = 29;
+pub const IFLA_PROMISCUITY: ::c_ushort = 30;
+pub const IFLA_NUM_TX_QUEUES: ::c_ushort = 31;
+pub const IFLA_NUM_RX_QUEUES: ::c_ushort = 32;
+pub const IFLA_CARRIER: ::c_ushort = 33;
+pub const IFLA_PHYS_PORT_ID: ::c_ushort = 34;
+pub const IFLA_CARRIER_CHANGES: ::c_ushort = 35;
+pub const IFLA_PHYS_SWITCH_ID: ::c_ushort = 36;
+pub const IFLA_LINK_NETNSID: ::c_ushort = 37;
+pub const IFLA_PHYS_PORT_NAME: ::c_ushort = 38;
+pub const IFLA_PROTO_DOWN: ::c_ushort = 39;
+pub const IFLA_GSO_MAX_SEGS: ::c_ushort = 40;
+pub const IFLA_GSO_MAX_SIZE: ::c_ushort = 41;
+pub const IFLA_PAD: ::c_ushort = 42;
+pub const IFLA_XDP: ::c_ushort = 43;
+pub const IFLA_EVENT: ::c_ushort = 44;
+pub const IFLA_NEW_NETNSID: ::c_ushort = 45;
+pub const IFLA_IF_NETNSID: ::c_ushort = 46;
+pub const IFLA_TARGET_NETNSID: ::c_ushort = IFLA_IF_NETNSID;
+pub const IFLA_CARRIER_UP_COUNT: ::c_ushort = 47;
+pub const IFLA_CARRIER_DOWN_COUNT: ::c_ushort = 48;
+pub const IFLA_NEW_IFINDEX: ::c_ushort = 49;
+pub const IFLA_MIN_MTU: ::c_ushort = 50;
+pub const IFLA_MAX_MTU: ::c_ushort = 51;
+pub const IFLA_PROP_LIST: ::c_ushort = 52;
+pub const IFLA_ALT_IFNAME: ::c_ushort = 53;
+pub const IFLA_PERM_ADDRESS: ::c_ushort = 54;
+pub const IFLA_PROTO_DOWN_REASON: ::c_ushort = 55;
+
+pub const IFLA_INFO_UNSPEC: ::c_ushort = 0;
+pub const IFLA_INFO_KIND: ::c_ushort = 1;
+pub const IFLA_INFO_DATA: ::c_ushort = 2;
+pub const IFLA_INFO_XSTATS: ::c_ushort = 3;
+pub const IFLA_INFO_SLAVE_KIND: ::c_ushort = 4;
+pub const IFLA_INFO_SLAVE_DATA: ::c_ushort = 5;
+
+// linux/if_tun.h
+pub const IFF_TUN: ::c_int = 0x0001;
+pub const IFF_TAP: ::c_int = 0x0002;
+pub const IFF_NO_PI: ::c_int = 0x1000;
+// Read queue size
+pub const TUN_READQ_SIZE: ::c_short = 500;
+// TUN device type flags: deprecated. Use IFF_TUN/IFF_TAP instead.
+pub const TUN_TUN_DEV: ::c_short = ::IFF_TUN as ::c_short;
+pub const TUN_TAP_DEV: ::c_short = ::IFF_TAP as ::c_short;
+pub const TUN_TYPE_MASK: ::c_short = 0x000f;
+// This flag has no real effect
+pub const IFF_ONE_QUEUE: ::c_int = 0x2000;
+pub const IFF_VNET_HDR: ::c_int = 0x4000;
+pub const IFF_TUN_EXCL: ::c_int = 0x8000;
+pub const IFF_MULTI_QUEUE: ::c_int = 0x0100;
+pub const IFF_ATTACH_QUEUE: ::c_int = 0x0200;
+pub const IFF_DETACH_QUEUE: ::c_int = 0x0400;
+// read-only flag
+pub const IFF_PERSIST: ::c_int = 0x0800;
+pub const IFF_NOFILTER: ::c_int = 0x1000;
+
+// Since Linux 3.1
+pub const SEEK_DATA: ::c_int = 3;
+pub const SEEK_HOLE: ::c_int = 4;
+
+pub const ST_RDONLY: ::c_ulong = 1;
+pub const ST_NOSUID: ::c_ulong = 2;
+pub const ST_NODEV: ::c_ulong = 4;
+pub const ST_NOEXEC: ::c_ulong = 8;
+pub const ST_SYNCHRONOUS: ::c_ulong = 16;
+pub const ST_MANDLOCK: ::c_ulong = 64;
+pub const ST_WRITE: ::c_ulong = 128;
+pub const ST_APPEND: ::c_ulong = 256;
+pub const ST_IMMUTABLE: ::c_ulong = 512;
+pub const ST_NOATIME: ::c_ulong = 1024;
+pub const ST_NODIRATIME: ::c_ulong = 2048;
+
+pub const RTLD_NEXT: *mut ::c_void = -1i64 as *mut ::c_void;
+pub const RTLD_DEFAULT: *mut ::c_void = 0i64 as *mut ::c_void;
+pub const RTLD_NODELETE: ::c_int = 0x1000;
+pub const RTLD_NOW: ::c_int = 0x2;
+
+pub const AT_EACCESS: ::c_int = 0x200;
+
+// linux/mempolicy.h
+pub const MPOL_DEFAULT: ::c_int = 0;
+pub const MPOL_PREFERRED: ::c_int = 1;
+pub const MPOL_BIND: ::c_int = 2;
+pub const MPOL_INTERLEAVE: ::c_int = 3;
+pub const MPOL_LOCAL: ::c_int = 4;
+pub const MPOL_F_NUMA_BALANCING: ::c_int = 1 << 13;
+pub const MPOL_F_RELATIVE_NODES: ::c_int = 1 << 14;
+pub const MPOL_F_STATIC_NODES: ::c_int = 1 << 15;
+
+align_const! {
+    pub const PTHREAD_MUTEX_INITIALIZER: pthread_mutex_t = pthread_mutex_t {
+        size: [0; __SIZEOF_PTHREAD_MUTEX_T],
+    };
+    pub const PTHREAD_COND_INITIALIZER: pthread_cond_t = pthread_cond_t {
+        size: [0; __SIZEOF_PTHREAD_COND_T],
+    };
+    pub const PTHREAD_RWLOCK_INITIALIZER: pthread_rwlock_t = pthread_rwlock_t {
+        size: [0; __SIZEOF_PTHREAD_RWLOCK_T],
+    };
+}
+pub const PTHREAD_MUTEX_NORMAL: ::c_int = 0;
+pub const PTHREAD_MUTEX_RECURSIVE: ::c_int = 1;
+pub const PTHREAD_MUTEX_ERRORCHECK: ::c_int = 2;
+pub const PTHREAD_MUTEX_DEFAULT: ::c_int = PTHREAD_MUTEX_NORMAL;
+pub const PTHREAD_MUTEX_STALLED: ::c_int = 0;
+pub const PTHREAD_MUTEX_ROBUST: ::c_int = 1;
+pub const PTHREAD_PRIO_NONE: ::c_int = 0;
+pub const PTHREAD_PRIO_INHERIT: ::c_int = 1;
+pub const PTHREAD_PRIO_PROTECT: ::c_int = 2;
+pub const PTHREAD_PROCESS_PRIVATE: ::c_int = 0;
+pub const PTHREAD_PROCESS_SHARED: ::c_int = 1;
+pub const __SIZEOF_PTHREAD_COND_T: usize = 48;
+
+pub const RENAME_NOREPLACE: ::c_uint = 1;
+pub const RENAME_EXCHANGE: ::c_uint = 2;
+pub const RENAME_WHITEOUT: ::c_uint = 4;
+
+pub const SCHED_OTHER: ::c_int = 0;
+pub const SCHED_FIFO: ::c_int = 1;
+pub const SCHED_RR: ::c_int = 2;
+pub const SCHED_BATCH: ::c_int = 3;
+pub const SCHED_IDLE: ::c_int = 5;
+
+pub const SCHED_RESET_ON_FORK: ::c_int = 0x40000000;
+
+pub const CLONE_PIDFD: ::c_int = 0x1000;
+
+// netinet/in.h
+// NOTE: These are in addition to the constants defined in src/unix/mod.rs
+
+/// Multipath TCP
+pub const IPPROTO_MPTCP: ::c_int = 262;
+#[deprecated(
+    since = "0.2.80",
+    note = "This value was increased in the newer kernel \
+            and we'll change this following upstream in the future release. \
+            See #1896 for more info."
+)]
+pub const IPPROTO_MAX: ::c_int = 256;
+
+// System V IPC
+pub const IPC_PRIVATE: ::key_t = 0;
+
+pub const IPC_CREAT: ::c_int = 0o1000;
+pub const IPC_EXCL: ::c_int = 0o2000;
+pub const IPC_NOWAIT: ::c_int = 0o4000;
+
+pub const IPC_RMID: ::c_int = 0;
+pub const IPC_SET: ::c_int = 1;
+pub const IPC_STAT: ::c_int = 2;
+pub const IPC_INFO: ::c_int = 3;
+pub const MSG_STAT: ::c_int = 11;
+pub const MSG_INFO: ::c_int = 12;
+
+pub const MSG_NOERROR: ::c_int = 0o10000;
+pub const MSG_EXCEPT: ::c_int = 0o20000;
+pub const MSG_ZEROCOPY: ::c_int = 0x4000000;
+
+pub const SHM_R: ::c_int = 0o400;
+pub const SHM_W: ::c_int = 0o200;
+
+pub const SHM_RDONLY: ::c_int = 0o10000;
+pub const SHM_RND: ::c_int = 0o20000;
+pub const SHM_REMAP: ::c_int = 0o40000;
+
+pub const SHM_LOCK: ::c_int = 11;
+pub const SHM_UNLOCK: ::c_int = 12;
+
+pub const SHM_HUGETLB: ::c_int = 0o4000;
+#[cfg(not(all(target_env = "uclibc", target_arch = "mips")))]
+pub const SHM_NORESERVE: ::c_int = 0o10000;
+
+pub const QFMT_VFS_OLD: ::c_int = 1;
+pub const QFMT_VFS_V0: ::c_int = 2;
+pub const QFMT_VFS_V1: ::c_int = 4;
+
+pub const EFD_SEMAPHORE: ::c_int = 0x1;
+
+pub const LOG_NFACILITIES: ::c_int = 24;
+
+pub const SEM_FAILED: *mut ::sem_t = 0 as *mut sem_t;
+
+pub const RB_AUTOBOOT: ::c_int = 0x01234567u32 as i32;
+pub const RB_HALT_SYSTEM: ::c_int = 0xcdef0123u32 as i32;
+pub const RB_ENABLE_CAD: ::c_int = 0x89abcdefu32 as i32;
+pub const RB_DISABLE_CAD: ::c_int = 0x00000000u32 as i32;
+pub const RB_POWER_OFF: ::c_int = 0x4321fedcu32 as i32;
+pub const RB_SW_SUSPEND: ::c_int = 0xd000fce2u32 as i32;
+pub const RB_KEXEC: ::c_int = 0x45584543u32 as i32;
+
+pub const AI_PASSIVE: ::c_int = 0x0001;
+pub const AI_CANONNAME: ::c_int = 0x0002;
+pub const AI_NUMERICHOST: ::c_int = 0x0004;
+pub const AI_V4MAPPED: ::c_int = 0x0008;
+pub const AI_ALL: ::c_int = 0x0010;
+pub const AI_ADDRCONFIG: ::c_int = 0x0020;
+
+pub const AI_NUMERICSERV: ::c_int = 0x0400;
+
+pub const EAI_BADFLAGS: ::c_int = -1;
+pub const EAI_NONAME: ::c_int = -2;
+pub const EAI_AGAIN: ::c_int = -3;
+pub const EAI_FAIL: ::c_int = -4;
+pub const EAI_NODATA: ::c_int = -5;
+pub const EAI_FAMILY: ::c_int = -6;
+pub const EAI_SOCKTYPE: ::c_int = -7;
+pub const EAI_SERVICE: ::c_int = -8;
+pub const EAI_MEMORY: ::c_int = -10;
+pub const EAI_SYSTEM: ::c_int = -11;
+pub const EAI_OVERFLOW: ::c_int = -12;
+
+pub const NI_NUMERICHOST: ::c_int = 1;
+pub const NI_NUMERICSERV: ::c_int = 2;
+pub const NI_NOFQDN: ::c_int = 4;
+pub const NI_NAMEREQD: ::c_int = 8;
+pub const NI_DGRAM: ::c_int = 16;
+
+pub const SYNC_FILE_RANGE_WAIT_BEFORE: ::c_uint = 1;
+pub const SYNC_FILE_RANGE_WRITE: ::c_uint = 2;
+pub const SYNC_FILE_RANGE_WAIT_AFTER: ::c_uint = 4;
+
+cfg_if! {
+    if #[cfg(not(target_env = "uclibc"))] {
+        pub const AIO_CANCELED: ::c_int = 0;
+        pub const AIO_NOTCANCELED: ::c_int = 1;
+        pub const AIO_ALLDONE: ::c_int = 2;
+        pub const LIO_READ: ::c_int = 0;
+        pub const LIO_WRITE: ::c_int = 1;
+        pub const LIO_NOP: ::c_int = 2;
+        pub const LIO_WAIT: ::c_int = 0;
+        pub const LIO_NOWAIT: ::c_int = 1;
+        pub const RUSAGE_THREAD: ::c_int = 1;
+        pub const MSG_COPY: ::c_int = 0o40000;
+        pub const SHM_EXEC: ::c_int = 0o100000;
+        pub const IPV6_MULTICAST_ALL: ::c_int = 29;
+        pub const IPV6_ROUTER_ALERT_ISOLATE: ::c_int = 30;
+        pub const PACKET_MR_UNICAST: ::c_int = 3;
+        pub const PTRACE_EVENT_STOP: ::c_int = 128;
+        pub const UDP_SEGMENT: ::c_int = 103;
+        pub const UDP_GRO: ::c_int = 104;
+    }
+}
+
+pub const MREMAP_MAYMOVE: ::c_int = 1;
+pub const MREMAP_FIXED: ::c_int = 2;
+pub const MREMAP_DONTUNMAP: ::c_int = 4;
+
+pub const PR_SET_PDEATHSIG: ::c_int = 1;
+pub const PR_GET_PDEATHSIG: ::c_int = 2;
+
+pub const PR_GET_DUMPABLE: ::c_int = 3;
+pub const PR_SET_DUMPABLE: ::c_int = 4;
+
+pub const PR_GET_UNALIGN: ::c_int = 5;
+pub const PR_SET_UNALIGN: ::c_int = 6;
+pub const PR_UNALIGN_NOPRINT: ::c_int = 1;
+pub const PR_UNALIGN_SIGBUS: ::c_int = 2;
+
+pub const PR_GET_KEEPCAPS: ::c_int = 7;
+pub const PR_SET_KEEPCAPS: ::c_int = 8;
+
+pub const PR_GET_FPEMU: ::c_int = 9;
+pub const PR_SET_FPEMU: ::c_int = 10;
+pub const PR_FPEMU_NOPRINT: ::c_int = 1;
+pub const PR_FPEMU_SIGFPE: ::c_int = 2;
+
+pub const PR_GET_FPEXC: ::c_int = 11;
+pub const PR_SET_FPEXC: ::c_int = 12;
+pub const PR_FP_EXC_SW_ENABLE: ::c_int = 0x80;
+pub const PR_FP_EXC_DIV: ::c_int = 0x010000;
+pub const PR_FP_EXC_OVF: ::c_int = 0x020000;
+pub const PR_FP_EXC_UND: ::c_int = 0x040000;
+pub const PR_FP_EXC_RES: ::c_int = 0x080000;
+pub const PR_FP_EXC_INV: ::c_int = 0x100000;
+pub const PR_FP_EXC_DISABLED: ::c_int = 0;
+pub const PR_FP_EXC_NONRECOV: ::c_int = 1;
+pub const PR_FP_EXC_ASYNC: ::c_int = 2;
+pub const PR_FP_EXC_PRECISE: ::c_int = 3;
+
+pub const PR_GET_TIMING: ::c_int = 13;
+pub const PR_SET_TIMING: ::c_int = 14;
+pub const PR_TIMING_STATISTICAL: ::c_int = 0;
+pub const PR_TIMING_TIMESTAMP: ::c_int = 1;
+
+pub const PR_SET_NAME: ::c_int = 15;
+pub const PR_GET_NAME: ::c_int = 16;
+
+pub const PR_GET_ENDIAN: ::c_int = 19;
+pub const PR_SET_ENDIAN: ::c_int = 20;
+pub const PR_ENDIAN_BIG: ::c_int = 0;
+pub const PR_ENDIAN_LITTLE: ::c_int = 1;
+pub const PR_ENDIAN_PPC_LITTLE: ::c_int = 2;
+
+pub const PR_GET_SECCOMP: ::c_int = 21;
+pub const PR_SET_SECCOMP: ::c_int = 22;
+
+pub const PR_CAPBSET_READ: ::c_int = 23;
+pub const PR_CAPBSET_DROP: ::c_int = 24;
+
+pub const PR_GET_TSC: ::c_int = 25;
+pub const PR_SET_TSC: ::c_int = 26;
+pub const PR_TSC_ENABLE: ::c_int = 1;
+pub const PR_TSC_SIGSEGV: ::c_int = 2;
+
+pub const PR_GET_SECUREBITS: ::c_int = 27;
+pub const PR_SET_SECUREBITS: ::c_int = 28;
+
+pub const PR_SET_TIMERSLACK: ::c_int = 29;
+pub const PR_GET_TIMERSLACK: ::c_int = 30;
+
+pub const PR_TASK_PERF_EVENTS_DISABLE: ::c_int = 31;
+pub const PR_TASK_PERF_EVENTS_ENABLE: ::c_int = 32;
+
+pub const PR_MCE_KILL: ::c_int = 33;
+pub const PR_MCE_KILL_CLEAR: ::c_int = 0;
+pub const PR_MCE_KILL_SET: ::c_int = 1;
+
+pub const PR_MCE_KILL_LATE: ::c_int = 0;
+pub const PR_MCE_KILL_EARLY: ::c_int = 1;
+pub const PR_MCE_KILL_DEFAULT: ::c_int = 2;
+
+pub const PR_MCE_KILL_GET: ::c_int = 34;
+
+pub const PR_SET_MM: ::c_int = 35;
+pub const PR_SET_MM_START_CODE: ::c_int = 1;
+pub const PR_SET_MM_END_CODE: ::c_int = 2;
+pub const PR_SET_MM_START_DATA: ::c_int = 3;
+pub const PR_SET_MM_END_DATA: ::c_int = 4;
+pub const PR_SET_MM_START_STACK: ::c_int = 5;
+pub const PR_SET_MM_START_BRK: ::c_int = 6;
+pub const PR_SET_MM_BRK: ::c_int = 7;
+pub const PR_SET_MM_ARG_START: ::c_int = 8;
+pub const PR_SET_MM_ARG_END: ::c_int = 9;
+pub const PR_SET_MM_ENV_START: ::c_int = 10;
+pub const PR_SET_MM_ENV_END: ::c_int = 11;
+pub const PR_SET_MM_AUXV: ::c_int = 12;
+pub const PR_SET_MM_EXE_FILE: ::c_int = 13;
+pub const PR_SET_MM_MAP: ::c_int = 14;
+pub const PR_SET_MM_MAP_SIZE: ::c_int = 15;
+
+pub const PR_SET_PTRACER: ::c_int = 0x59616d61;
+
+pub const PR_SET_CHILD_SUBREAPER: ::c_int = 36;
+pub const PR_GET_CHILD_SUBREAPER: ::c_int = 37;
+
+pub const PR_SET_NO_NEW_PRIVS: ::c_int = 38;
+pub const PR_GET_NO_NEW_PRIVS: ::c_int = 39;
+
+pub const PR_GET_TID_ADDRESS: ::c_int = 40;
+
+pub const PR_SET_THP_DISABLE: ::c_int = 41;
+pub const PR_GET_THP_DISABLE: ::c_int = 42;
+
+pub const PR_MPX_ENABLE_MANAGEMENT: ::c_int = 43;
+pub const PR_MPX_DISABLE_MANAGEMENT: ::c_int = 44;
+
+pub const PR_SET_FP_MODE: ::c_int = 45;
+pub const PR_GET_FP_MODE: ::c_int = 46;
+pub const PR_FP_MODE_FR: ::c_int = 1 << 0;
+pub const PR_FP_MODE_FRE: ::c_int = 1 << 1;
+
+pub const PR_CAP_AMBIENT: ::c_int = 47;
+pub const PR_CAP_AMBIENT_IS_SET: ::c_int = 1;
+pub const PR_CAP_AMBIENT_RAISE: ::c_int = 2;
+pub const PR_CAP_AMBIENT_LOWER: ::c_int = 3;
+pub const PR_CAP_AMBIENT_CLEAR_ALL: ::c_int = 4;
+
+pub const PR_SET_VMA: ::c_int = 0x53564d41;
+pub const PR_SET_VMA_ANON_NAME: ::c_int = 0;
+
+pub const GRND_NONBLOCK: ::c_uint = 0x0001;
+pub const GRND_RANDOM: ::c_uint = 0x0002;
+pub const GRND_INSECURE: ::c_uint = 0x0004;
+
+pub const SECCOMP_MODE_DISABLED: ::c_uint = 0;
+pub const SECCOMP_MODE_STRICT: ::c_uint = 1;
+pub const SECCOMP_MODE_FILTER: ::c_uint = 2;
+
+pub const SECCOMP_FILTER_FLAG_TSYNC: ::c_ulong = 1;
+pub const SECCOMP_FILTER_FLAG_LOG: ::c_ulong = 2;
+pub const SECCOMP_FILTER_FLAG_SPEC_ALLOW: ::c_ulong = 4;
+
+pub const SECCOMP_RET_KILL_PROCESS: ::c_uint = 0x80000000;
+pub const SECCOMP_RET_KILL_THREAD: ::c_uint = 0x00000000;
+pub const SECCOMP_RET_KILL: ::c_uint = SECCOMP_RET_KILL_THREAD;
+pub const SECCOMP_RET_TRAP: ::c_uint = 0x00030000;
+pub const SECCOMP_RET_ERRNO: ::c_uint = 0x00050000;
+pub const SECCOMP_RET_TRACE: ::c_uint = 0x7ff00000;
+pub const SECCOMP_RET_LOG: ::c_uint = 0x7ffc0000;
+pub const SECCOMP_RET_ALLOW: ::c_uint = 0x7fff0000;
+
+pub const SECCOMP_RET_ACTION_FULL: ::c_uint = 0xffff0000;
+pub const SECCOMP_RET_ACTION: ::c_uint = 0x7fff0000;
+pub const SECCOMP_RET_DATA: ::c_uint = 0x0000ffff;
+
+pub const ITIMER_REAL: ::c_int = 0;
+pub const ITIMER_VIRTUAL: ::c_int = 1;
+pub const ITIMER_PROF: ::c_int = 2;
+
+pub const TFD_CLOEXEC: ::c_int = O_CLOEXEC;
+pub const TFD_NONBLOCK: ::c_int = O_NONBLOCK;
+pub const TFD_TIMER_ABSTIME: ::c_int = 1;
+pub const TFD_TIMER_CANCEL_ON_SET: ::c_int = 2;
+
+pub const _POSIX_VDISABLE: ::cc_t = 0;
+
+pub const FALLOC_FL_KEEP_SIZE: ::c_int = 0x01;
+pub const FALLOC_FL_PUNCH_HOLE: ::c_int = 0x02;
+pub const FALLOC_FL_COLLAPSE_RANGE: ::c_int = 0x08;
+pub const FALLOC_FL_ZERO_RANGE: ::c_int = 0x10;
+pub const FALLOC_FL_INSERT_RANGE: ::c_int = 0x20;
+pub const FALLOC_FL_UNSHARE_RANGE: ::c_int = 0x40;
+
+#[deprecated(
+    since = "0.2.55",
+    note = "ENOATTR is not available on Linux; use ENODATA instead"
+)]
+pub const ENOATTR: ::c_int = ::ENODATA;
+
+pub const SO_ORIGINAL_DST: ::c_int = 80;
+
+pub const IP_RECVFRAGSIZE: ::c_int = 25;
+
+pub const IPV6_FLOWINFO: ::c_int = 11;
+pub const IPV6_FLOWLABEL_MGR: ::c_int = 32;
+pub const IPV6_FLOWINFO_SEND: ::c_int = 33;
+pub const IPV6_RECVFRAGSIZE: ::c_int = 77;
+pub const IPV6_FREEBIND: ::c_int = 78;
+pub const IPV6_FLOWINFO_FLOWLABEL: ::c_int = 0x000fffff;
+pub const IPV6_FLOWINFO_PRIORITY: ::c_int = 0x0ff00000;
+
+pub const IPV6_RTHDR_LOOSE: ::c_int = 0;
+pub const IPV6_RTHDR_STRICT: ::c_int = 1;
+
+// SO_MEMINFO offsets
+pub const SK_MEMINFO_RMEM_ALLOC: ::c_int = 0;
+pub const SK_MEMINFO_RCVBUF: ::c_int = 1;
+pub const SK_MEMINFO_WMEM_ALLOC: ::c_int = 2;
+pub const SK_MEMINFO_SNDBUF: ::c_int = 3;
+pub const SK_MEMINFO_FWD_ALLOC: ::c_int = 4;
+pub const SK_MEMINFO_WMEM_QUEUED: ::c_int = 5;
+pub const SK_MEMINFO_OPTMEM: ::c_int = 6;
+pub const SK_MEMINFO_BACKLOG: ::c_int = 7;
+pub const SK_MEMINFO_DROPS: ::c_int = 8;
+
+pub const IUTF8: ::tcflag_t = 0x00004000;
+#[cfg(not(all(target_env = "uclibc", target_arch = "mips")))]
+pub const CMSPAR: ::tcflag_t = 0o10000000000;
+
+pub const MFD_CLOEXEC: ::c_uint = 0x0001;
+pub const MFD_ALLOW_SEALING: ::c_uint = 0x0002;
+pub const MFD_HUGETLB: ::c_uint = 0x0004;
+pub const MFD_HUGE_64KB: ::c_uint = 0x40000000;
+pub const MFD_HUGE_512KB: ::c_uint = 0x4c000000;
+pub const MFD_HUGE_1MB: ::c_uint = 0x50000000;
+pub const MFD_HUGE_2MB: ::c_uint = 0x54000000;
+pub const MFD_HUGE_8MB: ::c_uint = 0x5c000000;
+pub const MFD_HUGE_16MB: ::c_uint = 0x60000000;
+pub const MFD_HUGE_32MB: ::c_uint = 0x64000000;
+pub const MFD_HUGE_256MB: ::c_uint = 0x70000000;
+pub const MFD_HUGE_512MB: ::c_uint = 0x74000000;
+pub const MFD_HUGE_1GB: ::c_uint = 0x78000000;
+pub const MFD_HUGE_2GB: ::c_uint = 0x7c000000;
+pub const MFD_HUGE_16GB: ::c_uint = 0x88000000;
+pub const MFD_HUGE_MASK: ::c_uint = 63;
+pub const MFD_HUGE_SHIFT: ::c_uint = 26;
+
+// linux/close_range.h
+pub const CLOSE_RANGE_UNSHARE: ::c_uint = 1 << 1;
+pub const CLOSE_RANGE_CLOEXEC: ::c_uint = 1 << 2;
+
+// linux/filter.h
+pub const SKF_AD_OFF: ::c_int = -0x1000;
+pub const SKF_AD_PROTOCOL: ::c_int = 0;
+pub const SKF_AD_PKTTYPE: ::c_int = 4;
+pub const SKF_AD_IFINDEX: ::c_int = 8;
+pub const SKF_AD_NLATTR: ::c_int = 12;
+pub const SKF_AD_NLATTR_NEST: ::c_int = 16;
+pub const SKF_AD_MARK: ::c_int = 20;
+pub const SKF_AD_QUEUE: ::c_int = 24;
+pub const SKF_AD_HATYPE: ::c_int = 28;
+pub const SKF_AD_RXHASH: ::c_int = 32;
+pub const SKF_AD_CPU: ::c_int = 36;
+pub const SKF_AD_ALU_XOR_X: ::c_int = 40;
+pub const SKF_AD_VLAN_TAG: ::c_int = 44;
+pub const SKF_AD_VLAN_TAG_PRESENT: ::c_int = 48;
+pub const SKF_AD_PAY_OFFSET: ::c_int = 52;
+pub const SKF_AD_RANDOM: ::c_int = 56;
+pub const SKF_AD_VLAN_TPID: ::c_int = 60;
+pub const SKF_AD_MAX: ::c_int = 64;
+pub const SKF_NET_OFF: ::c_int = -0x100000;
+pub const SKF_LL_OFF: ::c_int = -0x200000;
+pub const BPF_NET_OFF: ::c_int = SKF_NET_OFF;
+pub const BPF_LL_OFF: ::c_int = SKF_LL_OFF;
+pub const BPF_MEMWORDS: ::c_int = 16;
+pub const BPF_MAXINSNS: ::c_int = 4096;
+
+// linux/bpf_common.h
+pub const BPF_LD: ::__u32 = 0x00;
+pub const BPF_LDX: ::__u32 = 0x01;
+pub const BPF_ST: ::__u32 = 0x02;
+pub const BPF_STX: ::__u32 = 0x03;
+pub const BPF_ALU: ::__u32 = 0x04;
+pub const BPF_JMP: ::__u32 = 0x05;
+pub const BPF_RET: ::__u32 = 0x06;
+pub const BPF_MISC: ::__u32 = 0x07;
+pub const BPF_W: ::__u32 = 0x00;
+pub const BPF_H: ::__u32 = 0x08;
+pub const BPF_B: ::__u32 = 0x10;
+pub const BPF_IMM: ::__u32 = 0x00;
+pub const BPF_ABS: ::__u32 = 0x20;
+pub const BPF_IND: ::__u32 = 0x40;
+pub const BPF_MEM: ::__u32 = 0x60;
+pub const BPF_LEN: ::__u32 = 0x80;
+pub const BPF_MSH: ::__u32 = 0xa0;
+pub const BPF_ADD: ::__u32 = 0x00;
+pub const BPF_SUB: ::__u32 = 0x10;
+pub const BPF_MUL: ::__u32 = 0x20;
+pub const BPF_DIV: ::__u32 = 0x30;
+pub const BPF_OR: ::__u32 = 0x40;
+pub const BPF_AND: ::__u32 = 0x50;
+pub const BPF_LSH: ::__u32 = 0x60;
+pub const BPF_RSH: ::__u32 = 0x70;
+pub const BPF_NEG: ::__u32 = 0x80;
+pub const BPF_MOD: ::__u32 = 0x90;
+pub const BPF_XOR: ::__u32 = 0xa0;
+pub const BPF_JA: ::__u32 = 0x00;
+pub const BPF_JEQ: ::__u32 = 0x10;
+pub const BPF_JGT: ::__u32 = 0x20;
+pub const BPF_JGE: ::__u32 = 0x30;
+pub const BPF_JSET: ::__u32 = 0x40;
+pub const BPF_K: ::__u32 = 0x00;
+pub const BPF_X: ::__u32 = 0x08;
+
+// linux/openat2.h
+pub const RESOLVE_NO_XDEV: ::__u64 = 0x01;
+pub const RESOLVE_NO_MAGICLINKS: ::__u64 = 0x02;
+pub const RESOLVE_NO_SYMLINKS: ::__u64 = 0x04;
+pub const RESOLVE_BENEATH: ::__u64 = 0x08;
+pub const RESOLVE_IN_ROOT: ::__u64 = 0x10;
+pub const RESOLVE_CACHED: ::__u64 = 0x20;
+
+// linux/if_ether.h
+pub const ETH_ALEN: ::c_int = 6;
+pub const ETH_HLEN: ::c_int = 14;
+pub const ETH_ZLEN: ::c_int = 60;
+pub const ETH_DATA_LEN: ::c_int = 1500;
+pub const ETH_FRAME_LEN: ::c_int = 1514;
+pub const ETH_FCS_LEN: ::c_int = 4;
+
+// These are the defined Ethernet Protocol ID's.
+pub const ETH_P_LOOP: ::c_int = 0x0060;
+pub const ETH_P_PUP: ::c_int = 0x0200;
+pub const ETH_P_PUPAT: ::c_int = 0x0201;
+pub const ETH_P_IP: ::c_int = 0x0800;
+pub const ETH_P_X25: ::c_int = 0x0805;
+pub const ETH_P_ARP: ::c_int = 0x0806;
+pub const ETH_P_BPQ: ::c_int = 0x08FF;
+pub const ETH_P_IEEEPUP: ::c_int = 0x0a00;
+pub const ETH_P_IEEEPUPAT: ::c_int = 0x0a01;
+pub const ETH_P_BATMAN: ::c_int = 0x4305;
+pub const ETH_P_DEC: ::c_int = 0x6000;
+pub const ETH_P_DNA_DL: ::c_int = 0x6001;
+pub const ETH_P_DNA_RC: ::c_int = 0x6002;
+pub const ETH_P_DNA_RT: ::c_int = 0x6003;
+pub const ETH_P_LAT: ::c_int = 0x6004;
+pub const ETH_P_DIAG: ::c_int = 0x6005;
+pub const ETH_P_CUST: ::c_int = 0x6006;
+pub const ETH_P_SCA: ::c_int = 0x6007;
+pub const ETH_P_TEB: ::c_int = 0x6558;
+pub const ETH_P_RARP: ::c_int = 0x8035;
+pub const ETH_P_ATALK: ::c_int = 0x809B;
+pub const ETH_P_AARP: ::c_int = 0x80F3;
+pub const ETH_P_8021Q: ::c_int = 0x8100;
+pub const ETH_P_IPX: ::c_int = 0x8137;
+pub const ETH_P_IPV6: ::c_int = 0x86DD;
+pub const ETH_P_PAUSE: ::c_int = 0x8808;
+pub const ETH_P_SLOW: ::c_int = 0x8809;
+pub const ETH_P_WCCP: ::c_int = 0x883E;
+pub const ETH_P_MPLS_UC: ::c_int = 0x8847;
+pub const ETH_P_MPLS_MC: ::c_int = 0x8848;
+pub const ETH_P_ATMMPOA: ::c_int = 0x884c;
+pub const ETH_P_PPP_DISC: ::c_int = 0x8863;
+pub const ETH_P_PPP_SES: ::c_int = 0x8864;
+pub const ETH_P_LINK_CTL: ::c_int = 0x886c;
+pub const ETH_P_ATMFATE: ::c_int = 0x8884;
+pub const ETH_P_PAE: ::c_int = 0x888E;
+pub const ETH_P_AOE: ::c_int = 0x88A2;
+pub const ETH_P_8021AD: ::c_int = 0x88A8;
+pub const ETH_P_802_EX1: ::c_int = 0x88B5;
+pub const ETH_P_TIPC: ::c_int = 0x88CA;
+pub const ETH_P_MACSEC: ::c_int = 0x88E5;
+pub const ETH_P_8021AH: ::c_int = 0x88E7;
+pub const ETH_P_MVRP: ::c_int = 0x88F5;
+pub const ETH_P_1588: ::c_int = 0x88F7;
+pub const ETH_P_PRP: ::c_int = 0x88FB;
+pub const ETH_P_FCOE: ::c_int = 0x8906;
+pub const ETH_P_TDLS: ::c_int = 0x890D;
+pub const ETH_P_FIP: ::c_int = 0x8914;
+pub const ETH_P_80221: ::c_int = 0x8917;
+pub const ETH_P_LOOPBACK: ::c_int = 0x9000;
+pub const ETH_P_QINQ1: ::c_int = 0x9100;
+pub const ETH_P_QINQ2: ::c_int = 0x9200;
+pub const ETH_P_QINQ3: ::c_int = 0x9300;
+pub const ETH_P_EDSA: ::c_int = 0xDADA;
+pub const ETH_P_AF_IUCV: ::c_int = 0xFBFB;
+
+pub const ETH_P_802_3_MIN: ::c_int = 0x0600;
+
+// Non DIX types. Won't clash for 1500 types.
+pub const ETH_P_802_3: ::c_int = 0x0001;
+pub const ETH_P_AX25: ::c_int = 0x0002;
+pub const ETH_P_ALL: ::c_int = 0x0003;
+pub const ETH_P_802_2: ::c_int = 0x0004;
+pub const ETH_P_SNAP: ::c_int = 0x0005;
+pub const ETH_P_DDCMP: ::c_int = 0x0006;
+pub const ETH_P_WAN_PPP: ::c_int = 0x0007;
+pub const ETH_P_PPP_MP: ::c_int = 0x0008;
+pub const ETH_P_LOCALTALK: ::c_int = 0x0009;
+pub const ETH_P_CANFD: ::c_int = 0x000D;
+pub const ETH_P_PPPTALK: ::c_int = 0x0010;
+pub const ETH_P_TR_802_2: ::c_int = 0x0011;
+pub const ETH_P_MOBITEX: ::c_int = 0x0015;
+pub const ETH_P_CONTROL: ::c_int = 0x0016;
+pub const ETH_P_IRDA: ::c_int = 0x0017;
+pub const ETH_P_ECONET: ::c_int = 0x0018;
+pub const ETH_P_HDLC: ::c_int = 0x0019;
+pub const ETH_P_ARCNET: ::c_int = 0x001A;
+pub const ETH_P_DSA: ::c_int = 0x001B;
+pub const ETH_P_TRAILER: ::c_int = 0x001C;
+pub const ETH_P_PHONET: ::c_int = 0x00F5;
+pub const ETH_P_IEEE802154: ::c_int = 0x00F6;
+pub const ETH_P_CAIF: ::c_int = 0x00F7;
+
+pub const POSIX_SPAWN_RESETIDS: ::c_int = 0x01;
+pub const POSIX_SPAWN_SETPGROUP: ::c_int = 0x02;
+pub const POSIX_SPAWN_SETSIGDEF: ::c_int = 0x04;
+pub const POSIX_SPAWN_SETSIGMASK: ::c_int = 0x08;
+pub const POSIX_SPAWN_SETSCHEDPARAM: ::c_int = 0x10;
+pub const POSIX_SPAWN_SETSCHEDULER: ::c_int = 0x20;
+
+pub const NLMSG_NOOP: ::c_int = 0x1;
+pub const NLMSG_ERROR: ::c_int = 0x2;
+pub const NLMSG_DONE: ::c_int = 0x3;
+pub const NLMSG_OVERRUN: ::c_int = 0x4;
+pub const NLMSG_MIN_TYPE: ::c_int = 0x10;
+
+// linux/netfilter/nfnetlink.h
+pub const NFNLGRP_NONE: ::c_int = 0;
+pub const NFNLGRP_CONNTRACK_NEW: ::c_int = 1;
+pub const NFNLGRP_CONNTRACK_UPDATE: ::c_int = 2;
+pub const NFNLGRP_CONNTRACK_DESTROY: ::c_int = 3;
+pub const NFNLGRP_CONNTRACK_EXP_NEW: ::c_int = 4;
+pub const NFNLGRP_CONNTRACK_EXP_UPDATE: ::c_int = 5;
+pub const NFNLGRP_CONNTRACK_EXP_DESTROY: ::c_int = 6;
+pub const NFNLGRP_NFTABLES: ::c_int = 7;
+pub const NFNLGRP_ACCT_QUOTA: ::c_int = 8;
+pub const NFNLGRP_NFTRACE: ::c_int = 9;
+
+pub const NFNETLINK_V0: ::c_int = 0;
+
+pub const NFNL_SUBSYS_NONE: ::c_int = 0;
+pub const NFNL_SUBSYS_CTNETLINK: ::c_int = 1;
+pub const NFNL_SUBSYS_CTNETLINK_EXP: ::c_int = 2;
+pub const NFNL_SUBSYS_QUEUE: ::c_int = 3;
+pub const NFNL_SUBSYS_ULOG: ::c_int = 4;
+pub const NFNL_SUBSYS_OSF: ::c_int = 5;
+pub const NFNL_SUBSYS_IPSET: ::c_int = 6;
+pub const NFNL_SUBSYS_ACCT: ::c_int = 7;
+pub const NFNL_SUBSYS_CTNETLINK_TIMEOUT: ::c_int = 8;
+pub const NFNL_SUBSYS_CTHELPER: ::c_int = 9;
+pub const NFNL_SUBSYS_NFTABLES: ::c_int = 10;
+pub const NFNL_SUBSYS_NFT_COMPAT: ::c_int = 11;
+pub const NFNL_SUBSYS_HOOK: ::c_int = 12;
+pub const NFNL_SUBSYS_COUNT: ::c_int = 13;
+
+pub const NFNL_MSG_BATCH_BEGIN: ::c_int = NLMSG_MIN_TYPE;
+pub const NFNL_MSG_BATCH_END: ::c_int = NLMSG_MIN_TYPE + 1;
+
+pub const NFNL_BATCH_UNSPEC: ::c_int = 0;
+pub const NFNL_BATCH_GENID: ::c_int = 1;
+
+// linux/netfilter/nfnetlink_log.h
+pub const NFULNL_MSG_PACKET: ::c_int = 0;
+pub const NFULNL_MSG_CONFIG: ::c_int = 1;
+
+pub const NFULA_VLAN_UNSPEC: ::c_int = 0;
+pub const NFULA_VLAN_PROTO: ::c_int = 1;
+pub const NFULA_VLAN_TCI: ::c_int = 2;
+
+pub const NFULA_UNSPEC: ::c_int = 0;
+pub const NFULA_PACKET_HDR: ::c_int = 1;
+pub const NFULA_MARK: ::c_int = 2;
+pub const NFULA_TIMESTAMP: ::c_int = 3;
+pub const NFULA_IFINDEX_INDEV: ::c_int = 4;
+pub const NFULA_IFINDEX_OUTDEV: ::c_int = 5;
+pub const NFULA_IFINDEX_PHYSINDEV: ::c_int = 6;
+pub const NFULA_IFINDEX_PHYSOUTDEV: ::c_int = 7;
+pub const NFULA_HWADDR: ::c_int = 8;
+pub const NFULA_PAYLOAD: ::c_int = 9;
+pub const NFULA_PREFIX: ::c_int = 10;
+pub const NFULA_UID: ::c_int = 11;
+pub const NFULA_SEQ: ::c_int = 12;
+pub const NFULA_SEQ_GLOBAL: ::c_int = 13;
+pub const NFULA_GID: ::c_int = 14;
+pub const NFULA_HWTYPE: ::c_int = 15;
+pub const NFULA_HWHEADER: ::c_int = 16;
+pub const NFULA_HWLEN: ::c_int = 17;
+pub const NFULA_CT: ::c_int = 18;
+pub const NFULA_CT_INFO: ::c_int = 19;
+pub const NFULA_VLAN: ::c_int = 20;
+pub const NFULA_L2HDR: ::c_int = 21;
+
+pub const NFULNL_CFG_CMD_NONE: ::c_int = 0;
+pub const NFULNL_CFG_CMD_BIND: ::c_int = 1;
+pub const NFULNL_CFG_CMD_UNBIND: ::c_int = 2;
+pub const NFULNL_CFG_CMD_PF_BIND: ::c_int = 3;
+pub const NFULNL_CFG_CMD_PF_UNBIND: ::c_int = 4;
+
+pub const NFULA_CFG_UNSPEC: ::c_int = 0;
+pub const NFULA_CFG_CMD: ::c_int = 1;
+pub const NFULA_CFG_MODE: ::c_int = 2;
+pub const NFULA_CFG_NLBUFSIZ: ::c_int = 3;
+pub const NFULA_CFG_TIMEOUT: ::c_int = 4;
+pub const NFULA_CFG_QTHRESH: ::c_int = 5;
+pub const NFULA_CFG_FLAGS: ::c_int = 6;
+
+pub const NFULNL_COPY_NONE: ::c_int = 0x00;
+pub const NFULNL_COPY_META: ::c_int = 0x01;
+pub const NFULNL_COPY_PACKET: ::c_int = 0x02;
+
+pub const NFULNL_CFG_F_SEQ: ::c_int = 0x0001;
+pub const NFULNL_CFG_F_SEQ_GLOBAL: ::c_int = 0x0002;
+pub const NFULNL_CFG_F_CONNTRACK: ::c_int = 0x0004;
+
+// linux/netfilter/nfnetlink_queue.h
+pub const NFQNL_MSG_PACKET: ::c_int = 0;
+pub const NFQNL_MSG_VERDICT: ::c_int = 1;
+pub const NFQNL_MSG_CONFIG: ::c_int = 2;
+pub const NFQNL_MSG_VERDICT_BATCH: ::c_int = 3;
+
+pub const NFQA_UNSPEC: ::c_int = 0;
+pub const NFQA_PACKET_HDR: ::c_int = 1;
+pub const NFQA_VERDICT_HDR: ::c_int = 2;
+pub const NFQA_MARK: ::c_int = 3;
+pub const NFQA_TIMESTAMP: ::c_int = 4;
+pub const NFQA_IFINDEX_INDEV: ::c_int = 5;
+pub const NFQA_IFINDEX_OUTDEV: ::c_int = 6;
+pub const NFQA_IFINDEX_PHYSINDEV: ::c_int = 7;
+pub const NFQA_IFINDEX_PHYSOUTDEV: ::c_int = 8;
+pub const NFQA_HWADDR: ::c_int = 9;
+pub const NFQA_PAYLOAD: ::c_int = 10;
+pub const NFQA_CT: ::c_int = 11;
+pub const NFQA_CT_INFO: ::c_int = 12;
+pub const NFQA_CAP_LEN: ::c_int = 13;
+pub const NFQA_SKB_INFO: ::c_int = 14;
+pub const NFQA_EXP: ::c_int = 15;
+pub const NFQA_UID: ::c_int = 16;
+pub const NFQA_GID: ::c_int = 17;
+pub const NFQA_SECCTX: ::c_int = 18;
+pub const NFQA_VLAN: ::c_int = 19;
+pub const NFQA_L2HDR: ::c_int = 20;
+pub const NFQA_PRIORITY: ::c_int = 21;
+
+pub const NFQA_VLAN_UNSPEC: ::c_int = 0;
+pub const NFQA_VLAN_PROTO: ::c_int = 1;
+pub const NFQA_VLAN_TCI: ::c_int = 2;
+
+pub const NFQNL_CFG_CMD_NONE: ::c_int = 0;
+pub const NFQNL_CFG_CMD_BIND: ::c_int = 1;
+pub const NFQNL_CFG_CMD_UNBIND: ::c_int = 2;
+pub const NFQNL_CFG_CMD_PF_BIND: ::c_int = 3;
+pub const NFQNL_CFG_CMD_PF_UNBIND: ::c_int = 4;
+
+pub const NFQNL_COPY_NONE: ::c_int = 0;
+pub const NFQNL_COPY_META: ::c_int = 1;
+pub const NFQNL_COPY_PACKET: ::c_int = 2;
+
+pub const NFQA_CFG_UNSPEC: ::c_int = 0;
+pub const NFQA_CFG_CMD: ::c_int = 1;
+pub const NFQA_CFG_PARAMS: ::c_int = 2;
+pub const NFQA_CFG_QUEUE_MAXLEN: ::c_int = 3;
+pub const NFQA_CFG_MASK: ::c_int = 4;
+pub const NFQA_CFG_FLAGS: ::c_int = 5;
+
+pub const NFQA_CFG_F_FAIL_OPEN: ::c_int = 0x0001;
+pub const NFQA_CFG_F_CONNTRACK: ::c_int = 0x0002;
+pub const NFQA_CFG_F_GSO: ::c_int = 0x0004;
+pub const NFQA_CFG_F_UID_GID: ::c_int = 0x0008;
+pub const NFQA_CFG_F_SECCTX: ::c_int = 0x0010;
+pub const NFQA_CFG_F_MAX: ::c_int = 0x0020;
+
+pub const NFQA_SKB_CSUMNOTREADY: ::c_int = 0x0001;
+pub const NFQA_SKB_GSO: ::c_int = 0x0002;
+pub const NFQA_SKB_CSUM_NOTVERIFIED: ::c_int = 0x0004;
+
+// linux/genetlink.h
+
+pub const GENL_NAMSIZ: ::c_int = 16;
+
+pub const GENL_MIN_ID: ::c_int = NLMSG_MIN_TYPE;
+pub const GENL_MAX_ID: ::c_int = 1023;
+
+pub const GENL_ADMIN_PERM: ::c_int = 0x01;
+pub const GENL_CMD_CAP_DO: ::c_int = 0x02;
+pub const GENL_CMD_CAP_DUMP: ::c_int = 0x04;
+pub const GENL_CMD_CAP_HASPOL: ::c_int = 0x08;
+
+pub const GENL_ID_CTRL: ::c_int = NLMSG_MIN_TYPE;
+
+pub const CTRL_CMD_UNSPEC: ::c_int = 0;
+pub const CTRL_CMD_NEWFAMILY: ::c_int = 1;
+pub const CTRL_CMD_DELFAMILY: ::c_int = 2;
+pub const CTRL_CMD_GETFAMILY: ::c_int = 3;
+pub const CTRL_CMD_NEWOPS: ::c_int = 4;
+pub const CTRL_CMD_DELOPS: ::c_int = 5;
+pub const CTRL_CMD_GETOPS: ::c_int = 6;
+pub const CTRL_CMD_NEWMCAST_GRP: ::c_int = 7;
+pub const CTRL_CMD_DELMCAST_GRP: ::c_int = 8;
+pub const CTRL_CMD_GETMCAST_GRP: ::c_int = 9;
+
+pub const CTRL_ATTR_UNSPEC: ::c_int = 0;
+pub const CTRL_ATTR_FAMILY_ID: ::c_int = 1;
+pub const CTRL_ATTR_FAMILY_NAME: ::c_int = 2;
+pub const CTRL_ATTR_VERSION: ::c_int = 3;
+pub const CTRL_ATTR_HDRSIZE: ::c_int = 4;
+pub const CTRL_ATTR_MAXATTR: ::c_int = 5;
+pub const CTRL_ATTR_OPS: ::c_int = 6;
+pub const CTRL_ATTR_MCAST_GROUPS: ::c_int = 7;
+
+pub const CTRL_ATTR_OP_UNSPEC: ::c_int = 0;
+pub const CTRL_ATTR_OP_ID: ::c_int = 1;
+pub const CTRL_ATTR_OP_FLAGS: ::c_int = 2;
+
+pub const CTRL_ATTR_MCAST_GRP_UNSPEC: ::c_int = 0;
+pub const CTRL_ATTR_MCAST_GRP_NAME: ::c_int = 1;
+pub const CTRL_ATTR_MCAST_GRP_ID: ::c_int = 2;
+
+// linux/if_packet.h
+pub const PACKET_ADD_MEMBERSHIP: ::c_int = 1;
+pub const PACKET_DROP_MEMBERSHIP: ::c_int = 2;
+
+pub const PACKET_MR_MULTICAST: ::c_int = 0;
+pub const PACKET_MR_PROMISC: ::c_int = 1;
+pub const PACKET_MR_ALLMULTI: ::c_int = 2;
+
+// linux/netfilter.h
+pub const NF_DROP: ::c_int = 0;
+pub const NF_ACCEPT: ::c_int = 1;
+pub const NF_STOLEN: ::c_int = 2;
+pub const NF_QUEUE: ::c_int = 3;
+pub const NF_REPEAT: ::c_int = 4;
+pub const NF_STOP: ::c_int = 5;
+pub const NF_MAX_VERDICT: ::c_int = NF_STOP;
+
+pub const NF_VERDICT_MASK: ::c_int = 0x000000ff;
+pub const NF_VERDICT_FLAG_QUEUE_BYPASS: ::c_int = 0x00008000;
+
+pub const NF_VERDICT_QMASK: ::c_int = 0xffff0000;
+pub const NF_VERDICT_QBITS: ::c_int = 16;
+
+pub const NF_VERDICT_BITS: ::c_int = 16;
+
+pub const NF_INET_PRE_ROUTING: ::c_int = 0;
+pub const NF_INET_LOCAL_IN: ::c_int = 1;
+pub const NF_INET_FORWARD: ::c_int = 2;
+pub const NF_INET_LOCAL_OUT: ::c_int = 3;
+pub const NF_INET_POST_ROUTING: ::c_int = 4;
+pub const NF_INET_NUMHOOKS: ::c_int = 5;
+
+// Some NFPROTO are not compatible with musl and are defined in submodules.
+pub const NFPROTO_UNSPEC: ::c_int = 0;
+pub const NFPROTO_IPV4: ::c_int = 2;
+pub const NFPROTO_ARP: ::c_int = 3;
+pub const NFPROTO_BRIDGE: ::c_int = 7;
+pub const NFPROTO_IPV6: ::c_int = 10;
+pub const NFPROTO_DECNET: ::c_int = 12;
+pub const NFPROTO_NUMPROTO: ::c_int = 13;
+pub const NFPROTO_INET: ::c_int = 1;
+pub const NFPROTO_NETDEV: ::c_int = 5;
+
+pub const NF_NETDEV_INGRESS: ::c_int = 0;
+pub const NF_NETDEV_NUMHOOKS: ::c_int = 1;
+
+// linux/netfilter_ipv4.h
+pub const NF_IP_PRE_ROUTING: ::c_int = 0;
+pub const NF_IP_LOCAL_IN: ::c_int = 1;
+pub const NF_IP_FORWARD: ::c_int = 2;
+pub const NF_IP_LOCAL_OUT: ::c_int = 3;
+pub const NF_IP_POST_ROUTING: ::c_int = 4;
+pub const NF_IP_NUMHOOKS: ::c_int = 5;
+
+pub const NF_IP_PRI_FIRST: ::c_int = ::INT_MIN;
+pub const NF_IP_PRI_CONNTRACK_DEFRAG: ::c_int = -400;
+pub const NF_IP_PRI_RAW: ::c_int = -300;
+pub const NF_IP_PRI_SELINUX_FIRST: ::c_int = -225;
+pub const NF_IP_PRI_CONNTRACK: ::c_int = -200;
+pub const NF_IP_PRI_MANGLE: ::c_int = -150;
+pub const NF_IP_PRI_NAT_DST: ::c_int = -100;
+pub const NF_IP_PRI_FILTER: ::c_int = 0;
+pub const NF_IP_PRI_SECURITY: ::c_int = 50;
+pub const NF_IP_PRI_NAT_SRC: ::c_int = 100;
+pub const NF_IP_PRI_SELINUX_LAST: ::c_int = 225;
+pub const NF_IP_PRI_CONNTRACK_HELPER: ::c_int = 300;
+pub const NF_IP_PRI_CONNTRACK_CONFIRM: ::c_int = ::INT_MAX;
+pub const NF_IP_PRI_LAST: ::c_int = ::INT_MAX;
+
+// linux/netfilter_ipv6.h
+pub const NF_IP6_PRE_ROUTING: ::c_int = 0;
+pub const NF_IP6_LOCAL_IN: ::c_int = 1;
+pub const NF_IP6_FORWARD: ::c_int = 2;
+pub const NF_IP6_LOCAL_OUT: ::c_int = 3;
+pub const NF_IP6_POST_ROUTING: ::c_int = 4;
+pub const NF_IP6_NUMHOOKS: ::c_int = 5;
+
+pub const NF_IP6_PRI_FIRST: ::c_int = ::INT_MIN;
+pub const NF_IP6_PRI_CONNTRACK_DEFRAG: ::c_int = -400;
+pub const NF_IP6_PRI_RAW: ::c_int = -300;
+pub const NF_IP6_PRI_SELINUX_FIRST: ::c_int = -225;
+pub const NF_IP6_PRI_CONNTRACK: ::c_int = -200;
+pub const NF_IP6_PRI_MANGLE: ::c_int = -150;
+pub const NF_IP6_PRI_NAT_DST: ::c_int = -100;
+pub const NF_IP6_PRI_FILTER: ::c_int = 0;
+pub const NF_IP6_PRI_SECURITY: ::c_int = 50;
+pub const NF_IP6_PRI_NAT_SRC: ::c_int = 100;
+pub const NF_IP6_PRI_SELINUX_LAST: ::c_int = 225;
+pub const NF_IP6_PRI_CONNTRACK_HELPER: ::c_int = 300;
+pub const NF_IP6_PRI_LAST: ::c_int = ::INT_MAX;
+
+// linux/netfilter_ipv6/ip6_tables.h
+pub const IP6T_SO_ORIGINAL_DST: ::c_int = 80;
+
+pub const SIOCADDRT: ::c_ulong = 0x0000890B;
+pub const SIOCDELRT: ::c_ulong = 0x0000890C;
+pub const SIOCGIFNAME: ::c_ulong = 0x00008910;
+pub const SIOCSIFLINK: ::c_ulong = 0x00008911;
+pub const SIOCGIFCONF: ::c_ulong = 0x00008912;
+pub const SIOCGIFFLAGS: ::c_ulong = 0x00008913;
+pub const SIOCSIFFLAGS: ::c_ulong = 0x00008914;
+pub const SIOCGIFADDR: ::c_ulong = 0x00008915;
+pub const SIOCSIFADDR: ::c_ulong = 0x00008916;
+pub const SIOCGIFDSTADDR: ::c_ulong = 0x00008917;
+pub const SIOCSIFDSTADDR: ::c_ulong = 0x00008918;
+pub const SIOCGIFBRDADDR: ::c_ulong = 0x00008919;
+pub const SIOCSIFBRDADDR: ::c_ulong = 0x0000891A;
+pub const SIOCGIFNETMASK: ::c_ulong = 0x0000891B;
+pub const SIOCSIFNETMASK: ::c_ulong = 0x0000891C;
+pub const SIOCGIFMETRIC: ::c_ulong = 0x0000891D;
+pub const SIOCSIFMETRIC: ::c_ulong = 0x0000891E;
+pub const SIOCGIFMEM: ::c_ulong = 0x0000891F;
+pub const SIOCSIFMEM: ::c_ulong = 0x00008920;
+pub const SIOCGIFMTU: ::c_ulong = 0x00008921;
+pub const SIOCSIFMTU: ::c_ulong = 0x00008922;
+pub const SIOCSIFHWADDR: ::c_ulong = 0x00008924;
+pub const SIOCGIFENCAP: ::c_ulong = 0x00008925;
+pub const SIOCSIFENCAP: ::c_ulong = 0x00008926;
+pub const SIOCGIFHWADDR: ::c_ulong = 0x00008927;
+pub const SIOCGIFSLAVE: ::c_ulong = 0x00008929;
+pub const SIOCSIFSLAVE: ::c_ulong = 0x00008930;
+pub const SIOCADDMULTI: ::c_ulong = 0x00008931;
+pub const SIOCDELMULTI: ::c_ulong = 0x00008932;
+pub const SIOCGIFINDEX: ::c_ulong = 0x00008933;
+pub const SIOGIFINDEX: ::c_ulong = SIOCGIFINDEX;
+pub const SIOCSIFPFLAGS: ::c_ulong = 0x00008934;
+pub const SIOCGIFPFLAGS: ::c_ulong = 0x00008935;
+pub const SIOCDIFADDR: ::c_ulong = 0x00008936;
+pub const SIOCSIFHWBROADCAST: ::c_ulong = 0x00008937;
+pub const SIOCGIFCOUNT: ::c_ulong = 0x00008938;
+pub const SIOCGIFBR: ::c_ulong = 0x00008940;
+pub const SIOCSIFBR: ::c_ulong = 0x00008941;
+pub const SIOCGIFTXQLEN: ::c_ulong = 0x00008942;
+pub const SIOCSIFTXQLEN: ::c_ulong = 0x00008943;
+pub const SIOCETHTOOL: ::c_ulong = 0x00008946;
+pub const SIOCGMIIPHY: ::c_ulong = 0x00008947;
+pub const SIOCGMIIREG: ::c_ulong = 0x00008948;
+pub const SIOCSMIIREG: ::c_ulong = 0x00008949;
+pub const SIOCWANDEV: ::c_ulong = 0x0000894A;
+pub const SIOCOUTQNSD: ::c_ulong = 0x0000894B;
+pub const SIOCGSKNS: ::c_ulong = 0x0000894C;
+pub const SIOCDARP: ::c_ulong = 0x00008953;
+pub const SIOCGARP: ::c_ulong = 0x00008954;
+pub const SIOCSARP: ::c_ulong = 0x00008955;
+pub const SIOCDRARP: ::c_ulong = 0x00008960;
+pub const SIOCGRARP: ::c_ulong = 0x00008961;
+pub const SIOCSRARP: ::c_ulong = 0x00008962;
+pub const SIOCGIFMAP: ::c_ulong = 0x00008970;
+pub const SIOCSIFMAP: ::c_ulong = 0x00008971;
+
+pub const IPTOS_TOS_MASK: u8 = 0x1E;
+pub const IPTOS_PREC_MASK: u8 = 0xE0;
+
+pub const IPTOS_ECN_NOT_ECT: u8 = 0x00;
+
+pub const RTF_UP: ::c_ushort = 0x0001;
+pub const RTF_GATEWAY: ::c_ushort = 0x0002;
+
+pub const RTF_HOST: ::c_ushort = 0x0004;
+pub const RTF_REINSTATE: ::c_ushort = 0x0008;
+pub const RTF_DYNAMIC: ::c_ushort = 0x0010;
+pub const RTF_MODIFIED: ::c_ushort = 0x0020;
+pub const RTF_MTU: ::c_ushort = 0x0040;
+pub const RTF_MSS: ::c_ushort = RTF_MTU;
+pub const RTF_WINDOW: ::c_ushort = 0x0080;
+pub const RTF_IRTT: ::c_ushort = 0x0100;
+pub const RTF_REJECT: ::c_ushort = 0x0200;
+pub const RTF_STATIC: ::c_ushort = 0x0400;
+pub const RTF_XRESOLVE: ::c_ushort = 0x0800;
+pub const RTF_NOFORWARD: ::c_ushort = 0x1000;
+pub const RTF_THROW: ::c_ushort = 0x2000;
+pub const RTF_NOPMTUDISC: ::c_ushort = 0x4000;
+
+pub const RTF_DEFAULT: u32 = 0x00010000;
+pub const RTF_ALLONLINK: u32 = 0x00020000;
+pub const RTF_ADDRCONF: u32 = 0x00040000;
+pub const RTF_LINKRT: u32 = 0x00100000;
+pub const RTF_NONEXTHOP: u32 = 0x00200000;
+pub const RTF_CACHE: u32 = 0x01000000;
+pub const RTF_FLOW: u32 = 0x02000000;
+pub const RTF_POLICY: u32 = 0x04000000;
+
+pub const RTCF_VALVE: u32 = 0x00200000;
+pub const RTCF_MASQ: u32 = 0x00400000;
+pub const RTCF_NAT: u32 = 0x00800000;
+pub const RTCF_DOREDIRECT: u32 = 0x01000000;
+pub const RTCF_LOG: u32 = 0x02000000;
+pub const RTCF_DIRECTSRC: u32 = 0x04000000;
+
+pub const RTF_LOCAL: u32 = 0x80000000;
+pub const RTF_INTERFACE: u32 = 0x40000000;
+pub const RTF_MULTICAST: u32 = 0x20000000;
+pub const RTF_BROADCAST: u32 = 0x10000000;
+pub const RTF_NAT: u32 = 0x08000000;
+pub const RTF_ADDRCLASSMASK: u32 = 0xF8000000;
+
+pub const RT_CLASS_UNSPEC: u8 = 0;
+pub const RT_CLASS_DEFAULT: u8 = 253;
+pub const RT_CLASS_MAIN: u8 = 254;
+pub const RT_CLASS_LOCAL: u8 = 255;
+pub const RT_CLASS_MAX: u8 = 255;
+
+// linux/neighbor.h
+pub const NUD_NONE: u16 = 0x00;
+pub const NUD_INCOMPLETE: u16 = 0x01;
+pub const NUD_REACHABLE: u16 = 0x02;
+pub const NUD_STALE: u16 = 0x04;
+pub const NUD_DELAY: u16 = 0x08;
+pub const NUD_PROBE: u16 = 0x10;
+pub const NUD_FAILED: u16 = 0x20;
+pub const NUD_NOARP: u16 = 0x40;
+pub const NUD_PERMANENT: u16 = 0x80;
+
+pub const NTF_USE: u8 = 0x01;
+pub const NTF_SELF: u8 = 0x02;
+pub const NTF_MASTER: u8 = 0x04;
+pub const NTF_PROXY: u8 = 0x08;
+pub const NTF_ROUTER: u8 = 0x80;
+
+pub const NDA_UNSPEC: ::c_ushort = 0;
+pub const NDA_DST: ::c_ushort = 1;
+pub const NDA_LLADDR: ::c_ushort = 2;
+pub const NDA_CACHEINFO: ::c_ushort = 3;
+pub const NDA_PROBES: ::c_ushort = 4;
+pub const NDA_VLAN: ::c_ushort = 5;
+pub const NDA_PORT: ::c_ushort = 6;
+pub const NDA_VNI: ::c_ushort = 7;
+pub const NDA_IFINDEX: ::c_ushort = 8;
+
+// linux/netlink.h
+pub const NLA_ALIGNTO: ::c_int = 4;
+
+pub const NETLINK_ROUTE: ::c_int = 0;
+pub const NETLINK_UNUSED: ::c_int = 1;
+pub const NETLINK_USERSOCK: ::c_int = 2;
+pub const NETLINK_FIREWALL: ::c_int = 3;
+pub const NETLINK_SOCK_DIAG: ::c_int = 4;
+pub const NETLINK_NFLOG: ::c_int = 5;
+pub const NETLINK_XFRM: ::c_int = 6;
+pub const NETLINK_SELINUX: ::c_int = 7;
+pub const NETLINK_ISCSI: ::c_int = 8;
+pub const NETLINK_AUDIT: ::c_int = 9;
+pub const NETLINK_FIB_LOOKUP: ::c_int = 10;
+pub const NETLINK_CONNECTOR: ::c_int = 11;
+pub const NETLINK_NETFILTER: ::c_int = 12;
+pub const NETLINK_IP6_FW: ::c_int = 13;
+pub const NETLINK_DNRTMSG: ::c_int = 14;
+pub const NETLINK_KOBJECT_UEVENT: ::c_int = 15;
+pub const NETLINK_GENERIC: ::c_int = 16;
+pub const NETLINK_SCSITRANSPORT: ::c_int = 18;
+pub const NETLINK_ECRYPTFS: ::c_int = 19;
+pub const NETLINK_RDMA: ::c_int = 20;
+pub const NETLINK_CRYPTO: ::c_int = 21;
+pub const NETLINK_INET_DIAG: ::c_int = NETLINK_SOCK_DIAG;
+
+pub const NLM_F_REQUEST: ::c_int = 1;
+pub const NLM_F_MULTI: ::c_int = 2;
+pub const NLM_F_ACK: ::c_int = 4;
+pub const NLM_F_ECHO: ::c_int = 8;
+pub const NLM_F_DUMP_INTR: ::c_int = 16;
+pub const NLM_F_DUMP_FILTERED: ::c_int = 32;
+
+pub const NLM_F_ROOT: ::c_int = 0x100;
+pub const NLM_F_MATCH: ::c_int = 0x200;
+pub const NLM_F_ATOMIC: ::c_int = 0x400;
+pub const NLM_F_DUMP: ::c_int = NLM_F_ROOT | NLM_F_MATCH;
+
+pub const NLM_F_REPLACE: ::c_int = 0x100;
+pub const NLM_F_EXCL: ::c_int = 0x200;
+pub const NLM_F_CREATE: ::c_int = 0x400;
+pub const NLM_F_APPEND: ::c_int = 0x800;
+
+pub const NETLINK_ADD_MEMBERSHIP: ::c_int = 1;
+pub const NETLINK_DROP_MEMBERSHIP: ::c_int = 2;
+pub const NETLINK_PKTINFO: ::c_int = 3;
+pub const NETLINK_BROADCAST_ERROR: ::c_int = 4;
+pub const NETLINK_NO_ENOBUFS: ::c_int = 5;
+pub const NETLINK_RX_RING: ::c_int = 6;
+pub const NETLINK_TX_RING: ::c_int = 7;
+pub const NETLINK_LISTEN_ALL_NSID: ::c_int = 8;
+pub const NETLINK_LIST_MEMBERSHIPS: ::c_int = 9;
+pub const NETLINK_CAP_ACK: ::c_int = 10;
+pub const NETLINK_EXT_ACK: ::c_int = 11;
+pub const NETLINK_GET_STRICT_CHK: ::c_int = 12;
+
+pub const NLA_F_NESTED: ::c_int = 1 << 15;
+pub const NLA_F_NET_BYTEORDER: ::c_int = 1 << 14;
+pub const NLA_TYPE_MASK: ::c_int = !(NLA_F_NESTED | NLA_F_NET_BYTEORDER);
+
+// linux/rtnetlink.h
+pub const TCA_UNSPEC: ::c_ushort = 0;
+pub const TCA_KIND: ::c_ushort = 1;
+pub const TCA_OPTIONS: ::c_ushort = 2;
+pub const TCA_STATS: ::c_ushort = 3;
+pub const TCA_XSTATS: ::c_ushort = 4;
+pub const TCA_RATE: ::c_ushort = 5;
+pub const TCA_FCNT: ::c_ushort = 6;
+pub const TCA_STATS2: ::c_ushort = 7;
+pub const TCA_STAB: ::c_ushort = 8;
+
+pub const RTM_NEWLINK: u16 = 16;
+pub const RTM_DELLINK: u16 = 17;
+pub const RTM_GETLINK: u16 = 18;
+pub const RTM_SETLINK: u16 = 19;
+pub const RTM_NEWADDR: u16 = 20;
+pub const RTM_DELADDR: u16 = 21;
+pub const RTM_GETADDR: u16 = 22;
+pub const RTM_NEWROUTE: u16 = 24;
+pub const RTM_DELROUTE: u16 = 25;
+pub const RTM_GETROUTE: u16 = 26;
+pub const RTM_NEWNEIGH: u16 = 28;
+pub const RTM_DELNEIGH: u16 = 29;
+pub const RTM_GETNEIGH: u16 = 30;
+pub const RTM_NEWRULE: u16 = 32;
+pub const RTM_DELRULE: u16 = 33;
+pub const RTM_GETRULE: u16 = 34;
+pub const RTM_NEWQDISC: u16 = 36;
+pub const RTM_DELQDISC: u16 = 37;
+pub const RTM_GETQDISC: u16 = 38;
+pub const RTM_NEWTCLASS: u16 = 40;
+pub const RTM_DELTCLASS: u16 = 41;
+pub const RTM_GETTCLASS: u16 = 42;
+pub const RTM_NEWTFILTER: u16 = 44;
+pub const RTM_DELTFILTER: u16 = 45;
+pub const RTM_GETTFILTER: u16 = 46;
+pub const RTM_NEWACTION: u16 = 48;
+pub const RTM_DELACTION: u16 = 49;
+pub const RTM_GETACTION: u16 = 50;
+pub const RTM_NEWPREFIX: u16 = 52;
+pub const RTM_GETMULTICAST: u16 = 58;
+pub const RTM_GETANYCAST: u16 = 62;
+pub const RTM_NEWNEIGHTBL: u16 = 64;
+pub const RTM_GETNEIGHTBL: u16 = 66;
+pub const RTM_SETNEIGHTBL: u16 = 67;
+pub const RTM_NEWNDUSEROPT: u16 = 68;
+pub const RTM_NEWADDRLABEL: u16 = 72;
+pub const RTM_DELADDRLABEL: u16 = 73;
+pub const RTM_GETADDRLABEL: u16 = 74;
+pub const RTM_GETDCB: u16 = 78;
+pub const RTM_SETDCB: u16 = 79;
+pub const RTM_NEWNETCONF: u16 = 80;
+pub const RTM_GETNETCONF: u16 = 82;
+pub const RTM_NEWMDB: u16 = 84;
+pub const RTM_DELMDB: u16 = 85;
+pub const RTM_GETMDB: u16 = 86;
+pub const RTM_NEWNSID: u16 = 88;
+pub const RTM_DELNSID: u16 = 89;
+pub const RTM_GETNSID: u16 = 90;
+
+pub const RTM_F_NOTIFY: ::c_uint = 0x100;
+pub const RTM_F_CLONED: ::c_uint = 0x200;
+pub const RTM_F_EQUALIZE: ::c_uint = 0x400;
+pub const RTM_F_PREFIX: ::c_uint = 0x800;
+
+pub const RTA_UNSPEC: ::c_ushort = 0;
+pub const RTA_DST: ::c_ushort = 1;
+pub const RTA_SRC: ::c_ushort = 2;
+pub const RTA_IIF: ::c_ushort = 3;
+pub const RTA_OIF: ::c_ushort = 4;
+pub const RTA_GATEWAY: ::c_ushort = 5;
+pub const RTA_PRIORITY: ::c_ushort = 6;
+pub const RTA_PREFSRC: ::c_ushort = 7;
+pub const RTA_METRICS: ::c_ushort = 8;
+pub const RTA_MULTIPATH: ::c_ushort = 9;
+pub const RTA_PROTOINFO: ::c_ushort = 10; // No longer used
+pub const RTA_FLOW: ::c_ushort = 11;
+pub const RTA_CACHEINFO: ::c_ushort = 12;
+pub const RTA_SESSION: ::c_ushort = 13; // No longer used
+pub const RTA_MP_ALGO: ::c_ushort = 14; // No longer used
+pub const RTA_TABLE: ::c_ushort = 15;
+pub const RTA_MARK: ::c_ushort = 16;
+pub const RTA_MFC_STATS: ::c_ushort = 17;
+
+pub const RTN_UNSPEC: ::c_uchar = 0;
+pub const RTN_UNICAST: ::c_uchar = 1;
+pub const RTN_LOCAL: ::c_uchar = 2;
+pub const RTN_BROADCAST: ::c_uchar = 3;
+pub const RTN_ANYCAST: ::c_uchar = 4;
+pub const RTN_MULTICAST: ::c_uchar = 5;
+pub const RTN_BLACKHOLE: ::c_uchar = 6;
+pub const RTN_UNREACHABLE: ::c_uchar = 7;
+pub const RTN_PROHIBIT: ::c_uchar = 8;
+pub const RTN_THROW: ::c_uchar = 9;
+pub const RTN_NAT: ::c_uchar = 10;
+pub const RTN_XRESOLVE: ::c_uchar = 11;
+
+pub const RTPROT_UNSPEC: ::c_uchar = 0;
+pub const RTPROT_REDIRECT: ::c_uchar = 1;
+pub const RTPROT_KERNEL: ::c_uchar = 2;
+pub const RTPROT_BOOT: ::c_uchar = 3;
+pub const RTPROT_STATIC: ::c_uchar = 4;
+
+pub const RT_SCOPE_UNIVERSE: ::c_uchar = 0;
+pub const RT_SCOPE_SITE: ::c_uchar = 200;
+pub const RT_SCOPE_LINK: ::c_uchar = 253;
+pub const RT_SCOPE_HOST: ::c_uchar = 254;
+pub const RT_SCOPE_NOWHERE: ::c_uchar = 255;
+
+pub const RT_TABLE_UNSPEC: ::c_uchar = 0;
+pub const RT_TABLE_COMPAT: ::c_uchar = 252;
+pub const RT_TABLE_DEFAULT: ::c_uchar = 253;
+pub const RT_TABLE_MAIN: ::c_uchar = 254;
+pub const RT_TABLE_LOCAL: ::c_uchar = 255;
+
+pub const RTMSG_OVERRUN: u32 = ::NLMSG_OVERRUN as u32;
+pub const RTMSG_NEWDEVICE: u32 = 0x11;
+pub const RTMSG_DELDEVICE: u32 = 0x12;
+pub const RTMSG_NEWROUTE: u32 = 0x21;
+pub const RTMSG_DELROUTE: u32 = 0x22;
+pub const RTMSG_NEWRULE: u32 = 0x31;
+pub const RTMSG_DELRULE: u32 = 0x32;
+pub const RTMSG_CONTROL: u32 = 0x40;
+pub const RTMSG_AR_FAILED: u32 = 0x51;
+
+pub const MAX_ADDR_LEN: usize = 7;
+pub const ARPD_UPDATE: ::c_ushort = 0x01;
+pub const ARPD_LOOKUP: ::c_ushort = 0x02;
+pub const ARPD_FLUSH: ::c_ushort = 0x03;
+pub const ATF_MAGIC: ::c_int = 0x80;
+
+// userspace compat definitions for RTNLGRP_*
+pub const RTMGRP_LINK: ::c_int = 0x00001;
+pub const RTMGRP_NOTIFY: ::c_int = 0x00002;
+pub const RTMGRP_NEIGH: ::c_int = 0x00004;
+pub const RTMGRP_TC: ::c_int = 0x00008;
+pub const RTMGRP_IPV4_IFADDR: ::c_int = 0x00010;
+pub const RTMGRP_IPV4_MROUTE: ::c_int = 0x00020;
+pub const RTMGRP_IPV4_ROUTE: ::c_int = 0x00040;
+pub const RTMGRP_IPV4_RULE: ::c_int = 0x00080;
+pub const RTMGRP_IPV6_IFADDR: ::c_int = 0x00100;
+pub const RTMGRP_IPV6_MROUTE: ::c_int = 0x00200;
+pub const RTMGRP_IPV6_ROUTE: ::c_int = 0x00400;
+pub const RTMGRP_IPV6_IFINFO: ::c_int = 0x00800;
+pub const RTMGRP_DECnet_IFADDR: ::c_int = 0x01000;
+pub const RTMGRP_DECnet_ROUTE: ::c_int = 0x04000;
+pub const RTMGRP_IPV6_PREFIX: ::c_int = 0x20000;
+
+// enum rtnetlink_groups
+pub const RTNLGRP_NONE: ::c_uint = 0x00;
+pub const RTNLGRP_LINK: ::c_uint = 0x01;
+pub const RTNLGRP_NOTIFY: ::c_uint = 0x02;
+pub const RTNLGRP_NEIGH: ::c_uint = 0x03;
+pub const RTNLGRP_TC: ::c_uint = 0x04;
+pub const RTNLGRP_IPV4_IFADDR: ::c_uint = 0x05;
+pub const RTNLGRP_IPV4_MROUTE: ::c_uint = 0x06;
+pub const RTNLGRP_IPV4_ROUTE: ::c_uint = 0x07;
+pub const RTNLGRP_IPV4_RULE: ::c_uint = 0x08;
+pub const RTNLGRP_IPV6_IFADDR: ::c_uint = 0x09;
+pub const RTNLGRP_IPV6_MROUTE: ::c_uint = 0x0a;
+pub const RTNLGRP_IPV6_ROUTE: ::c_uint = 0x0b;
+pub const RTNLGRP_IPV6_IFINFO: ::c_uint = 0x0c;
+pub const RTNLGRP_DECnet_IFADDR: ::c_uint = 0x0d;
+pub const RTNLGRP_NOP2: ::c_uint = 0x0e;
+pub const RTNLGRP_DECnet_ROUTE: ::c_uint = 0x0f;
+pub const RTNLGRP_DECnet_RULE: ::c_uint = 0x10;
+pub const RTNLGRP_NOP4: ::c_uint = 0x11;
+pub const RTNLGRP_IPV6_PREFIX: ::c_uint = 0x12;
+pub const RTNLGRP_IPV6_RULE: ::c_uint = 0x13;
+pub const RTNLGRP_ND_USEROPT: ::c_uint = 0x14;
+pub const RTNLGRP_PHONET_IFADDR: ::c_uint = 0x15;
+pub const RTNLGRP_PHONET_ROUTE: ::c_uint = 0x16;
+pub const RTNLGRP_DCB: ::c_uint = 0x17;
+pub const RTNLGRP_IPV4_NETCONF: ::c_uint = 0x18;
+pub const RTNLGRP_IPV6_NETCONF: ::c_uint = 0x19;
+pub const RTNLGRP_MDB: ::c_uint = 0x1a;
+pub const RTNLGRP_MPLS_ROUTE: ::c_uint = 0x1b;
+pub const RTNLGRP_NSID: ::c_uint = 0x1c;
+pub const RTNLGRP_MPLS_NETCONF: ::c_uint = 0x1d;
+pub const RTNLGRP_IPV4_MROUTE_R: ::c_uint = 0x1e;
+pub const RTNLGRP_IPV6_MROUTE_R: ::c_uint = 0x1f;
+pub const RTNLGRP_NEXTHOP: ::c_uint = 0x20;
+pub const RTNLGRP_BRVLAN: ::c_uint = 0x21;
+pub const RTNLGRP_MCTP_IFADDR: ::c_uint = 0x22;
+pub const RTNLGRP_TUNNEL: ::c_uint = 0x23;
+pub const RTNLGRP_STATS: ::c_uint = 0x24;
+
+// linux/module.h
+pub const MODULE_INIT_IGNORE_MODVERSIONS: ::c_uint = 0x0001;
+pub const MODULE_INIT_IGNORE_VERMAGIC: ::c_uint = 0x0002;
+
+// linux/net_tstamp.h
+pub const SOF_TIMESTAMPING_TX_HARDWARE: ::c_uint = 1 << 0;
+pub const SOF_TIMESTAMPING_TX_SOFTWARE: ::c_uint = 1 << 1;
+pub const SOF_TIMESTAMPING_RX_HARDWARE: ::c_uint = 1 << 2;
+pub const SOF_TIMESTAMPING_RX_SOFTWARE: ::c_uint = 1 << 3;
+pub const SOF_TIMESTAMPING_SOFTWARE: ::c_uint = 1 << 4;
+pub const SOF_TIMESTAMPING_SYS_HARDWARE: ::c_uint = 1 << 5;
+pub const SOF_TIMESTAMPING_RAW_HARDWARE: ::c_uint = 1 << 6;
+pub const SOF_TIMESTAMPING_OPT_ID: ::c_uint = 1 << 7;
+pub const SOF_TIMESTAMPING_TX_SCHED: ::c_uint = 1 << 8;
+pub const SOF_TIMESTAMPING_TX_ACK: ::c_uint = 1 << 9;
+pub const SOF_TIMESTAMPING_OPT_CMSG: ::c_uint = 1 << 10;
+pub const SOF_TIMESTAMPING_OPT_TSONLY: ::c_uint = 1 << 11;
+pub const SOF_TIMESTAMPING_OPT_STATS: ::c_uint = 1 << 12;
+pub const SOF_TIMESTAMPING_OPT_PKTINFO: ::c_uint = 1 << 13;
+pub const SOF_TIMESTAMPING_OPT_TX_SWHW: ::c_uint = 1 << 14;
+pub const SOF_TXTIME_DEADLINE_MODE: u32 = 1 << 0;
+pub const SOF_TXTIME_REPORT_ERRORS: u32 = 1 << 1;
+
+// linux/if_alg.h
+pub const ALG_SET_KEY: ::c_int = 1;
+pub const ALG_SET_IV: ::c_int = 2;
+pub const ALG_SET_OP: ::c_int = 3;
+pub const ALG_SET_AEAD_ASSOCLEN: ::c_int = 4;
+pub const ALG_SET_AEAD_AUTHSIZE: ::c_int = 5;
+
+pub const ALG_OP_DECRYPT: ::c_int = 0;
+pub const ALG_OP_ENCRYPT: ::c_int = 1;
+
+// include/uapi/linux/udp.h
+pub const UDP_CORK: ::c_int = 1;
+pub const UDP_ENCAP: ::c_int = 100;
+pub const UDP_NO_CHECK6_TX: ::c_int = 101;
+pub const UDP_NO_CHECK6_RX: ::c_int = 102;
+
+// include/uapi/linux/mman.h
+pub const MAP_SHARED_VALIDATE: ::c_int = 0x3;
+
+// include/uapi/asm-generic/mman-common.h
+pub const MAP_FIXED_NOREPLACE: ::c_int = 0x100000;
+pub const MLOCK_ONFAULT: ::c_uint = 0x01;
+
+// uapi/linux/vm_sockets.h
+pub const VMADDR_CID_ANY: ::c_uint = 0xFFFFFFFF;
+pub const VMADDR_CID_HYPERVISOR: ::c_uint = 0;
+#[deprecated(
+    since = "0.2.74",
+    note = "VMADDR_CID_RESERVED is removed since Linux v5.6 and \
+            replaced with VMADDR_CID_LOCAL"
+)]
+pub const VMADDR_CID_RESERVED: ::c_uint = 1;
+pub const VMADDR_CID_LOCAL: ::c_uint = 1;
+pub const VMADDR_CID_HOST: ::c_uint = 2;
+pub const VMADDR_PORT_ANY: ::c_uint = 0xFFFFFFFF;
+
+// uapi/linux/inotify.h
+pub const IN_ACCESS: u32 = 0x0000_0001;
+pub const IN_MODIFY: u32 = 0x0000_0002;
+pub const IN_ATTRIB: u32 = 0x0000_0004;
+pub const IN_CLOSE_WRITE: u32 = 0x0000_0008;
+pub const IN_CLOSE_NOWRITE: u32 = 0x0000_0010;
+pub const IN_CLOSE: u32 = IN_CLOSE_WRITE | IN_CLOSE_NOWRITE;
+pub const IN_OPEN: u32 = 0x0000_0020;
+pub const IN_MOVED_FROM: u32 = 0x0000_0040;
+pub const IN_MOVED_TO: u32 = 0x0000_0080;
+pub const IN_MOVE: u32 = IN_MOVED_FROM | IN_MOVED_TO;
+pub const IN_CREATE: u32 = 0x0000_0100;
+pub const IN_DELETE: u32 = 0x0000_0200;
+pub const IN_DELETE_SELF: u32 = 0x0000_0400;
+pub const IN_MOVE_SELF: u32 = 0x0000_0800;
+pub const IN_UNMOUNT: u32 = 0x0000_2000;
+pub const IN_Q_OVERFLOW: u32 = 0x0000_4000;
+pub const IN_IGNORED: u32 = 0x0000_8000;
+pub const IN_ONLYDIR: u32 = 0x0100_0000;
+pub const IN_DONT_FOLLOW: u32 = 0x0200_0000;
+// pub const IN_EXCL_UNLINK:   u32 = 0x0400_0000;
+
+// linux/keyctl.h
+pub const KEY_SPEC_THREAD_KEYRING: i32 = -1;
+pub const KEY_SPEC_PROCESS_KEYRING: i32 = -2;
+pub const KEY_SPEC_SESSION_KEYRING: i32 = -3;
+pub const KEY_SPEC_USER_KEYRING: i32 = -4;
+pub const KEY_SPEC_USER_SESSION_KEYRING: i32 = -5;
+pub const KEY_SPEC_GROUP_KEYRING: i32 = -6;
+pub const KEY_SPEC_REQKEY_AUTH_KEY: i32 = -7;
+pub const KEY_SPEC_REQUESTOR_KEYRING: i32 = -8;
+
+pub const KEY_REQKEY_DEFL_NO_CHANGE: i32 = -1;
+pub const KEY_REQKEY_DEFL_DEFAULT: i32 = 0;
+pub const KEY_REQKEY_DEFL_THREAD_KEYRING: i32 = 1;
+pub const KEY_REQKEY_DEFL_PROCESS_KEYRING: i32 = 2;
+pub const KEY_REQKEY_DEFL_SESSION_KEYRING: i32 = 3;
+pub const KEY_REQKEY_DEFL_USER_KEYRING: i32 = 4;
+pub const KEY_REQKEY_DEFL_USER_SESSION_KEYRING: i32 = 5;
+pub const KEY_REQKEY_DEFL_GROUP_KEYRING: i32 = 6;
+pub const KEY_REQKEY_DEFL_REQUESTOR_KEYRING: i32 = 7;
+
+pub const KEYCTL_GET_KEYRING_ID: u32 = 0;
+pub const KEYCTL_JOIN_SESSION_KEYRING: u32 = 1;
+pub const KEYCTL_UPDATE: u32 = 2;
+pub const KEYCTL_REVOKE: u32 = 3;
+pub const KEYCTL_CHOWN: u32 = 4;
+pub const KEYCTL_SETPERM: u32 = 5;
+pub const KEYCTL_DESCRIBE: u32 = 6;
+pub const KEYCTL_CLEAR: u32 = 7;
+pub const KEYCTL_LINK: u32 = 8;
+pub const KEYCTL_UNLINK: u32 = 9;
+pub const KEYCTL_SEARCH: u32 = 10;
+pub const KEYCTL_READ: u32 = 11;
+pub const KEYCTL_INSTANTIATE: u32 = 12;
+pub const KEYCTL_NEGATE: u32 = 13;
+pub const KEYCTL_SET_REQKEY_KEYRING: u32 = 14;
+pub const KEYCTL_SET_TIMEOUT: u32 = 15;
+pub const KEYCTL_ASSUME_AUTHORITY: u32 = 16;
+pub const KEYCTL_GET_SECURITY: u32 = 17;
+pub const KEYCTL_SESSION_TO_PARENT: u32 = 18;
+pub const KEYCTL_REJECT: u32 = 19;
+pub const KEYCTL_INSTANTIATE_IOV: u32 = 20;
+pub const KEYCTL_INVALIDATE: u32 = 21;
+pub const KEYCTL_GET_PERSISTENT: u32 = 22;
+
+// pub const IN_MASK_CREATE:   u32 = 0x1000_0000;
+// pub const IN_MASK_ADD:      u32 = 0x2000_0000;
+pub const IN_ISDIR: u32 = 0x4000_0000;
+pub const IN_ONESHOT: u32 = 0x8000_0000;
+
+pub const IN_ALL_EVENTS: u32 = IN_ACCESS
+    | IN_MODIFY
+    | IN_ATTRIB
+    | IN_CLOSE_WRITE
+    | IN_CLOSE_NOWRITE
+    | IN_OPEN
+    | IN_MOVED_FROM
+    | IN_MOVED_TO
+    | IN_DELETE
+    | IN_CREATE
+    | IN_DELETE_SELF
+    | IN_MOVE_SELF;
+
+pub const IN_CLOEXEC: ::c_int = O_CLOEXEC;
+pub const IN_NONBLOCK: ::c_int = O_NONBLOCK;
+
+// uapi/linux/netfilter/nf_tables.h
+pub const NFT_TABLE_MAXNAMELEN: ::c_int = 256;
+pub const NFT_CHAIN_MAXNAMELEN: ::c_int = 256;
+pub const NFT_SET_MAXNAMELEN: ::c_int = 256;
+pub const NFT_OBJ_MAXNAMELEN: ::c_int = 256;
+pub const NFT_USERDATA_MAXLEN: ::c_int = 256;
+
+pub const NFT_REG_VERDICT: ::c_int = 0;
+pub const NFT_REG_1: ::c_int = 1;
+pub const NFT_REG_2: ::c_int = 2;
+pub const NFT_REG_3: ::c_int = 3;
+pub const NFT_REG_4: ::c_int = 4;
+pub const __NFT_REG_MAX: ::c_int = 5;
+pub const NFT_REG32_00: ::c_int = 8;
+pub const NFT_REG32_01: ::c_int = 9;
+pub const NFT_REG32_02: ::c_int = 10;
+pub const NFT_REG32_03: ::c_int = 11;
+pub const NFT_REG32_04: ::c_int = 12;
+pub const NFT_REG32_05: ::c_int = 13;
+pub const NFT_REG32_06: ::c_int = 14;
+pub const NFT_REG32_07: ::c_int = 15;
+pub const NFT_REG32_08: ::c_int = 16;
+pub const NFT_REG32_09: ::c_int = 17;
+pub const NFT_REG32_10: ::c_int = 18;
+pub const NFT_REG32_11: ::c_int = 19;
+pub const NFT_REG32_12: ::c_int = 20;
+pub const NFT_REG32_13: ::c_int = 21;
+pub const NFT_REG32_14: ::c_int = 22;
+pub const NFT_REG32_15: ::c_int = 23;
+
+pub const NFT_REG_SIZE: ::c_int = 16;
+pub const NFT_REG32_SIZE: ::c_int = 4;
+
+pub const NFT_CONTINUE: ::c_int = -1;
+pub const NFT_BREAK: ::c_int = -2;
+pub const NFT_JUMP: ::c_int = -3;
+pub const NFT_GOTO: ::c_int = -4;
+pub const NFT_RETURN: ::c_int = -5;
+
+pub const NFT_MSG_NEWTABLE: ::c_int = 0;
+pub const NFT_MSG_GETTABLE: ::c_int = 1;
+pub const NFT_MSG_DELTABLE: ::c_int = 2;
+pub const NFT_MSG_NEWCHAIN: ::c_int = 3;
+pub const NFT_MSG_GETCHAIN: ::c_int = 4;
+pub const NFT_MSG_DELCHAIN: ::c_int = 5;
+pub const NFT_MSG_NEWRULE: ::c_int = 6;
+pub const NFT_MSG_GETRULE: ::c_int = 7;
+pub const NFT_MSG_DELRULE: ::c_int = 8;
+pub const NFT_MSG_NEWSET: ::c_int = 9;
+pub const NFT_MSG_GETSET: ::c_int = 10;
+pub const NFT_MSG_DELSET: ::c_int = 11;
+pub const NFT_MSG_NEWSETELEM: ::c_int = 12;
+pub const NFT_MSG_GETSETELEM: ::c_int = 13;
+pub const NFT_MSG_DELSETELEM: ::c_int = 14;
+pub const NFT_MSG_NEWGEN: ::c_int = 15;
+pub const NFT_MSG_GETGEN: ::c_int = 16;
+pub const NFT_MSG_TRACE: ::c_int = 17;
+cfg_if! {
+    if #[cfg(not(target_arch = "sparc64"))] {
+        pub const NFT_MSG_NEWOBJ: ::c_int = 18;
+        pub const NFT_MSG_GETOBJ: ::c_int = 19;
+        pub const NFT_MSG_DELOBJ: ::c_int = 20;
+        pub const NFT_MSG_GETOBJ_RESET: ::c_int = 21;
+    }
+}
+pub const NFT_MSG_MAX: ::c_int = 25;
+
+pub const NFT_SET_ANONYMOUS: ::c_int = 0x1;
+pub const NFT_SET_CONSTANT: ::c_int = 0x2;
+pub const NFT_SET_INTERVAL: ::c_int = 0x4;
+pub const NFT_SET_MAP: ::c_int = 0x8;
+pub const NFT_SET_TIMEOUT: ::c_int = 0x10;
+pub const NFT_SET_EVAL: ::c_int = 0x20;
+
+pub const NFT_SET_POL_PERFORMANCE: ::c_int = 0;
+pub const NFT_SET_POL_MEMORY: ::c_int = 1;
+
+pub const NFT_SET_ELEM_INTERVAL_END: ::c_int = 0x1;
+
+pub const NFT_DATA_VALUE: ::c_uint = 0;
+pub const NFT_DATA_VERDICT: ::c_uint = 0xffffff00;
+
+pub const NFT_DATA_RESERVED_MASK: ::c_uint = 0xffffff00;
+
+pub const NFT_DATA_VALUE_MAXLEN: ::c_int = 64;
+
+pub const NFT_BYTEORDER_NTOH: ::c_int = 0;
+pub const NFT_BYTEORDER_HTON: ::c_int = 1;
+
+pub const NFT_CMP_EQ: ::c_int = 0;
+pub const NFT_CMP_NEQ: ::c_int = 1;
+pub const NFT_CMP_LT: ::c_int = 2;
+pub const NFT_CMP_LTE: ::c_int = 3;
+pub const NFT_CMP_GT: ::c_int = 4;
+pub const NFT_CMP_GTE: ::c_int = 5;
+
+pub const NFT_RANGE_EQ: ::c_int = 0;
+pub const NFT_RANGE_NEQ: ::c_int = 1;
+
+pub const NFT_LOOKUP_F_INV: ::c_int = 1 << 0;
+
+pub const NFT_DYNSET_OP_ADD: ::c_int = 0;
+pub const NFT_DYNSET_OP_UPDATE: ::c_int = 1;
+
+pub const NFT_DYNSET_F_INV: ::c_int = 1 << 0;
+
+pub const NFT_PAYLOAD_LL_HEADER: ::c_int = 0;
+pub const NFT_PAYLOAD_NETWORK_HEADER: ::c_int = 1;
+pub const NFT_PAYLOAD_TRANSPORT_HEADER: ::c_int = 2;
+
+pub const NFT_PAYLOAD_CSUM_NONE: ::c_int = 0;
+pub const NFT_PAYLOAD_CSUM_INET: ::c_int = 1;
+
+pub const NFT_META_LEN: ::c_int = 0;
+pub const NFT_META_PROTOCOL: ::c_int = 1;
+pub const NFT_META_PRIORITY: ::c_int = 2;
+pub const NFT_META_MARK: ::c_int = 3;
+pub const NFT_META_IIF: ::c_int = 4;
+pub const NFT_META_OIF: ::c_int = 5;
+pub const NFT_META_IIFNAME: ::c_int = 6;
+pub const NFT_META_OIFNAME: ::c_int = 7;
+pub const NFT_META_IIFTYPE: ::c_int = 8;
+pub const NFT_META_OIFTYPE: ::c_int = 9;
+pub const NFT_META_SKUID: ::c_int = 10;
+pub const NFT_META_SKGID: ::c_int = 11;
+pub const NFT_META_NFTRACE: ::c_int = 12;
+pub const NFT_META_RTCLASSID: ::c_int = 13;
+pub const NFT_META_SECMARK: ::c_int = 14;
+pub const NFT_META_NFPROTO: ::c_int = 15;
+pub const NFT_META_L4PROTO: ::c_int = 16;
+pub const NFT_META_BRI_IIFNAME: ::c_int = 17;
+pub const NFT_META_BRI_OIFNAME: ::c_int = 18;
+pub const NFT_META_PKTTYPE: ::c_int = 19;
+pub const NFT_META_CPU: ::c_int = 20;
+pub const NFT_META_IIFGROUP: ::c_int = 21;
+pub const NFT_META_OIFGROUP: ::c_int = 22;
+pub const NFT_META_CGROUP: ::c_int = 23;
+pub const NFT_META_PRANDOM: ::c_int = 24;
+
+pub const NFT_CT_STATE: ::c_int = 0;
+pub const NFT_CT_DIRECTION: ::c_int = 1;
+pub const NFT_CT_STATUS: ::c_int = 2;
+pub const NFT_CT_MARK: ::c_int = 3;
+pub const NFT_CT_SECMARK: ::c_int = 4;
+pub const NFT_CT_EXPIRATION: ::c_int = 5;
+pub const NFT_CT_HELPER: ::c_int = 6;
+pub const NFT_CT_L3PROTOCOL: ::c_int = 7;
+pub const NFT_CT_SRC: ::c_int = 8;
+pub const NFT_CT_DST: ::c_int = 9;
+pub const NFT_CT_PROTOCOL: ::c_int = 10;
+pub const NFT_CT_PROTO_SRC: ::c_int = 11;
+pub const NFT_CT_PROTO_DST: ::c_int = 12;
+pub const NFT_CT_LABELS: ::c_int = 13;
+pub const NFT_CT_PKTS: ::c_int = 14;
+pub const NFT_CT_BYTES: ::c_int = 15;
+
+pub const NFT_LIMIT_PKTS: ::c_int = 0;
+pub const NFT_LIMIT_PKT_BYTES: ::c_int = 1;
+
+pub const NFT_LIMIT_F_INV: ::c_int = 1 << 0;
+
+pub const NFT_QUEUE_FLAG_BYPASS: ::c_int = 0x01;
+pub const NFT_QUEUE_FLAG_CPU_FANOUT: ::c_int = 0x02;
+pub const NFT_QUEUE_FLAG_MASK: ::c_int = 0x03;
+
+pub const NFT_QUOTA_F_INV: ::c_int = 1 << 0;
+
+pub const NFT_REJECT_ICMP_UNREACH: ::c_int = 0;
+pub const NFT_REJECT_TCP_RST: ::c_int = 1;
+pub const NFT_REJECT_ICMPX_UNREACH: ::c_int = 2;
+
+pub const NFT_REJECT_ICMPX_NO_ROUTE: ::c_int = 0;
+pub const NFT_REJECT_ICMPX_PORT_UNREACH: ::c_int = 1;
+pub const NFT_REJECT_ICMPX_HOST_UNREACH: ::c_int = 2;
+pub const NFT_REJECT_ICMPX_ADMIN_PROHIBITED: ::c_int = 3;
+
+pub const NFT_NAT_SNAT: ::c_int = 0;
+pub const NFT_NAT_DNAT: ::c_int = 1;
+
+pub const NFT_TRACETYPE_UNSPEC: ::c_int = 0;
+pub const NFT_TRACETYPE_POLICY: ::c_int = 1;
+pub const NFT_TRACETYPE_RETURN: ::c_int = 2;
+pub const NFT_TRACETYPE_RULE: ::c_int = 3;
+
+pub const NFT_NG_INCREMENTAL: ::c_int = 0;
+pub const NFT_NG_RANDOM: ::c_int = 1;
+
+// linux/input.h
+pub const FF_MAX: ::__u16 = 0x7f;
+pub const FF_CNT: usize = FF_MAX as usize + 1;
+
+// linux/input-event-codes.h
+pub const INPUT_PROP_MAX: ::__u16 = 0x1f;
+pub const INPUT_PROP_CNT: usize = INPUT_PROP_MAX as usize + 1;
+pub const EV_MAX: ::__u16 = 0x1f;
+pub const EV_CNT: usize = EV_MAX as usize + 1;
+pub const SYN_MAX: ::__u16 = 0xf;
+pub const SYN_CNT: usize = SYN_MAX as usize + 1;
+pub const KEY_MAX: ::__u16 = 0x2ff;
+pub const KEY_CNT: usize = KEY_MAX as usize + 1;
+pub const REL_MAX: ::__u16 = 0x0f;
+pub const REL_CNT: usize = REL_MAX as usize + 1;
+pub const ABS_MAX: ::__u16 = 0x3f;
+pub const ABS_CNT: usize = ABS_MAX as usize + 1;
+pub const SW_MAX: ::__u16 = 0x10;
+pub const SW_CNT: usize = SW_MAX as usize + 1;
+pub const MSC_MAX: ::__u16 = 0x07;
+pub const MSC_CNT: usize = MSC_MAX as usize + 1;
+pub const LED_MAX: ::__u16 = 0x0f;
+pub const LED_CNT: usize = LED_MAX as usize + 1;
+pub const REP_MAX: ::__u16 = 0x01;
+pub const REP_CNT: usize = REP_MAX as usize + 1;
+pub const SND_MAX: ::__u16 = 0x07;
+pub const SND_CNT: usize = SND_MAX as usize + 1;
+
+// linux/uinput.h
+pub const UINPUT_VERSION: ::c_uint = 5;
+pub const UINPUT_MAX_NAME_SIZE: usize = 80;
+
+// uapi/linux/fanotify.h
+pub const FAN_ACCESS: u64 = 0x0000_0001;
+pub const FAN_MODIFY: u64 = 0x0000_0002;
+pub const FAN_CLOSE_WRITE: u64 = 0x0000_0008;
+pub const FAN_CLOSE_NOWRITE: u64 = 0x0000_0010;
+pub const FAN_OPEN: u64 = 0x0000_0020;
+
+pub const FAN_Q_OVERFLOW: u64 = 0x0000_4000;
+
+pub const FAN_OPEN_PERM: u64 = 0x0001_0000;
+pub const FAN_ACCESS_PERM: u64 = 0x0002_0000;
+
+pub const FAN_ONDIR: u64 = 0x4000_0000;
+
+pub const FAN_EVENT_ON_CHILD: u64 = 0x0800_0000;
+
+pub const FAN_CLOSE: u64 = FAN_CLOSE_WRITE | FAN_CLOSE_NOWRITE;
+
+pub const FAN_CLOEXEC: ::c_uint = 0x0000_0001;
+pub const FAN_NONBLOCK: ::c_uint = 0x0000_0002;
+
+pub const FAN_CLASS_NOTIF: ::c_uint = 0x0000_0000;
+pub const FAN_CLASS_CONTENT: ::c_uint = 0x0000_0004;
+pub const FAN_CLASS_PRE_CONTENT: ::c_uint = 0x0000_0008;
+
+pub const FAN_UNLIMITED_QUEUE: ::c_uint = 0x0000_0010;
+pub const FAN_UNLIMITED_MARKS: ::c_uint = 0x0000_0020;
+
+pub const FAN_MARK_ADD: ::c_uint = 0x0000_0001;
+pub const FAN_MARK_REMOVE: ::c_uint = 0x0000_0002;
+pub const FAN_MARK_DONT_FOLLOW: ::c_uint = 0x0000_0004;
+pub const FAN_MARK_ONLYDIR: ::c_uint = 0x0000_0008;
+pub const FAN_MARK_IGNORED_MASK: ::c_uint = 0x0000_0020;
+pub const FAN_MARK_IGNORED_SURV_MODIFY: ::c_uint = 0x0000_0040;
+pub const FAN_MARK_FLUSH: ::c_uint = 0x0000_0080;
+
+pub const FANOTIFY_METADATA_VERSION: u8 = 3;
+
+pub const FAN_ALLOW: u32 = 0x01;
+pub const FAN_DENY: u32 = 0x02;
+
+pub const FAN_NOFD: ::c_int = -1;
+
+pub const FUTEX_WAIT: ::c_int = 0;
+pub const FUTEX_WAKE: ::c_int = 1;
+pub const FUTEX_FD: ::c_int = 2;
+pub const FUTEX_REQUEUE: ::c_int = 3;
+pub const FUTEX_CMP_REQUEUE: ::c_int = 4;
+pub const FUTEX_WAKE_OP: ::c_int = 5;
+pub const FUTEX_LOCK_PI: ::c_int = 6;
+pub const FUTEX_UNLOCK_PI: ::c_int = 7;
+pub const FUTEX_TRYLOCK_PI: ::c_int = 8;
+pub const FUTEX_WAIT_BITSET: ::c_int = 9;
+pub const FUTEX_WAKE_BITSET: ::c_int = 10;
+pub const FUTEX_WAIT_REQUEUE_PI: ::c_int = 11;
+pub const FUTEX_CMP_REQUEUE_PI: ::c_int = 12;
+pub const FUTEX_LOCK_PI2: ::c_int = 13;
+
+pub const FUTEX_PRIVATE_FLAG: ::c_int = 128;
+pub const FUTEX_CLOCK_REALTIME: ::c_int = 256;
+pub const FUTEX_CMD_MASK: ::c_int = !(FUTEX_PRIVATE_FLAG | FUTEX_CLOCK_REALTIME);
+
+// linux/reboot.h
+pub const LINUX_REBOOT_MAGIC1: ::c_int = 0xfee1dead;
+pub const LINUX_REBOOT_MAGIC2: ::c_int = 672274793;
+pub const LINUX_REBOOT_MAGIC2A: ::c_int = 85072278;
+pub const LINUX_REBOOT_MAGIC2B: ::c_int = 369367448;
+pub const LINUX_REBOOT_MAGIC2C: ::c_int = 537993216;
+
+pub const LINUX_REBOOT_CMD_RESTART: ::c_int = 0x01234567;
+pub const LINUX_REBOOT_CMD_HALT: ::c_int = 0xCDEF0123;
+pub const LINUX_REBOOT_CMD_CAD_ON: ::c_int = 0x89ABCDEF;
+pub const LINUX_REBOOT_CMD_CAD_OFF: ::c_int = 0x00000000;
+pub const LINUX_REBOOT_CMD_POWER_OFF: ::c_int = 0x4321FEDC;
+pub const LINUX_REBOOT_CMD_RESTART2: ::c_int = 0xA1B2C3D4;
+pub const LINUX_REBOOT_CMD_SW_SUSPEND: ::c_int = 0xD000FCE2;
+pub const LINUX_REBOOT_CMD_KEXEC: ::c_int = 0x45584543;
+
+pub const REG_EXTENDED: ::c_int = 1;
+pub const REG_ICASE: ::c_int = 2;
+pub const REG_NEWLINE: ::c_int = 4;
+pub const REG_NOSUB: ::c_int = 8;
+
+pub const REG_NOTBOL: ::c_int = 1;
+pub const REG_NOTEOL: ::c_int = 2;
+
+pub const REG_ENOSYS: ::c_int = -1;
+pub const REG_NOMATCH: ::c_int = 1;
+pub const REG_BADPAT: ::c_int = 2;
+pub const REG_ECOLLATE: ::c_int = 3;
+pub const REG_ECTYPE: ::c_int = 4;
+pub const REG_EESCAPE: ::c_int = 5;
+pub const REG_ESUBREG: ::c_int = 6;
+pub const REG_EBRACK: ::c_int = 7;
+pub const REG_EPAREN: ::c_int = 8;
+pub const REG_EBRACE: ::c_int = 9;
+pub const REG_BADBR: ::c_int = 10;
+pub const REG_ERANGE: ::c_int = 11;
+pub const REG_ESPACE: ::c_int = 12;
+pub const REG_BADRPT: ::c_int = 13;
+
+// linux/errqueue.h
+pub const SO_EE_ORIGIN_NONE: u8 = 0;
+pub const SO_EE_ORIGIN_LOCAL: u8 = 1;
+pub const SO_EE_ORIGIN_ICMP: u8 = 2;
+pub const SO_EE_ORIGIN_ICMP6: u8 = 3;
+pub const SO_EE_ORIGIN_TXSTATUS: u8 = 4;
+pub const SO_EE_ORIGIN_TIMESTAMPING: u8 = SO_EE_ORIGIN_TXSTATUS;
+
+// errno.h
+pub const EPERM: ::c_int = 1;
+pub const ENOENT: ::c_int = 2;
+pub const ESRCH: ::c_int = 3;
+pub const EINTR: ::c_int = 4;
+pub const EIO: ::c_int = 5;
+pub const ENXIO: ::c_int = 6;
+pub const E2BIG: ::c_int = 7;
+pub const ENOEXEC: ::c_int = 8;
+pub const EBADF: ::c_int = 9;
+pub const ECHILD: ::c_int = 10;
+pub const EAGAIN: ::c_int = 11;
+pub const ENOMEM: ::c_int = 12;
+pub const EACCES: ::c_int = 13;
+pub const EFAULT: ::c_int = 14;
+pub const ENOTBLK: ::c_int = 15;
+pub const EBUSY: ::c_int = 16;
+pub const EEXIST: ::c_int = 17;
+pub const EXDEV: ::c_int = 18;
+pub const ENODEV: ::c_int = 19;
+pub const ENOTDIR: ::c_int = 20;
+pub const EISDIR: ::c_int = 21;
+pub const EINVAL: ::c_int = 22;
+pub const ENFILE: ::c_int = 23;
+pub const EMFILE: ::c_int = 24;
+pub const ENOTTY: ::c_int = 25;
+pub const ETXTBSY: ::c_int = 26;
+pub const EFBIG: ::c_int = 27;
+pub const ENOSPC: ::c_int = 28;
+pub const ESPIPE: ::c_int = 29;
+pub const EROFS: ::c_int = 30;
+pub const EMLINK: ::c_int = 31;
+pub const EPIPE: ::c_int = 32;
+pub const EDOM: ::c_int = 33;
+pub const ERANGE: ::c_int = 34;
+pub const EWOULDBLOCK: ::c_int = EAGAIN;
+
+// linux/can.h
+pub const CAN_EFF_FLAG: canid_t = 0x80000000;
+pub const CAN_RTR_FLAG: canid_t = 0x40000000;
+pub const CAN_ERR_FLAG: canid_t = 0x20000000;
+pub const CAN_SFF_MASK: canid_t = 0x000007FF;
+pub const CAN_EFF_MASK: canid_t = 0x1FFFFFFF;
+pub const CAN_ERR_MASK: canid_t = 0x1FFFFFFF;
+
+pub const CAN_SFF_ID_BITS: ::c_int = 11;
+pub const CAN_EFF_ID_BITS: ::c_int = 29;
+
+pub const CAN_MAX_DLC: ::c_int = 8;
+pub const CAN_MAX_DLEN: usize = 8;
+pub const CANFD_MAX_DLC: ::c_int = 15;
+pub const CANFD_MAX_DLEN: usize = 64;
+
+pub const CANFD_BRS: ::c_int = 0x01;
+pub const CANFD_ESI: ::c_int = 0x02;
+
+cfg_if! {
+    if #[cfg(libc_align)] {
+        pub const CAN_MTU: usize = ::mem::size_of::<can_frame>();
+        pub const CANFD_MTU: usize = ::mem::size_of::<canfd_frame>();
+    }
+}
+
+pub const CAN_RAW: ::c_int = 1;
+pub const CAN_BCM: ::c_int = 2;
+pub const CAN_TP16: ::c_int = 3;
+pub const CAN_TP20: ::c_int = 4;
+pub const CAN_MCNET: ::c_int = 5;
+pub const CAN_ISOTP: ::c_int = 6;
+pub const CAN_J1939: ::c_int = 7;
+pub const CAN_NPROTO: ::c_int = 8;
+
+pub const SOL_CAN_BASE: ::c_int = 100;
+
+pub const CAN_INV_FILTER: canid_t = 0x20000000;
+pub const CAN_RAW_FILTER_MAX: ::c_int = 512;
+
+// linux/can/raw.h
+pub const SOL_CAN_RAW: ::c_int = SOL_CAN_BASE + CAN_RAW;
+pub const CAN_RAW_FILTER: ::c_int = 1;
+pub const CAN_RAW_ERR_FILTER: ::c_int = 2;
+pub const CAN_RAW_LOOPBACK: ::c_int = 3;
+pub const CAN_RAW_RECV_OWN_MSGS: ::c_int = 4;
+pub const CAN_RAW_FD_FRAMES: ::c_int = 5;
+pub const CAN_RAW_JOIN_FILTERS: ::c_int = 6;
+
+// linux/can/j1939.h
+pub const SOL_CAN_J1939: ::c_int = SOL_CAN_BASE + CAN_J1939;
+
+pub const J1939_MAX_UNICAST_ADDR: ::c_uchar = 0xfd;
+pub const J1939_IDLE_ADDR: ::c_uchar = 0xfe;
+pub const J1939_NO_ADDR: ::c_uchar = 0xff;
+pub const J1939_NO_NAME: ::c_ulong = 0;
+pub const J1939_PGN_REQUEST: ::c_uint = 0x0ea00;
+pub const J1939_PGN_ADDRESS_CLAIMED: ::c_uint = 0x0ee00;
+pub const J1939_PGN_ADDRESS_COMMANDED: ::c_uint = 0x0fed8;
+pub const J1939_PGN_PDU1_MAX: ::c_uint = 0x3ff00;
+pub const J1939_PGN_MAX: ::c_uint = 0x3ffff;
+pub const J1939_NO_PGN: ::c_uint = 0x40000;
+
+pub const SO_J1939_FILTER: ::c_int = 1;
+pub const SO_J1939_PROMISC: ::c_int = 2;
+pub const SO_J1939_SEND_PRIO: ::c_int = 3;
+pub const SO_J1939_ERRQUEUE: ::c_int = 4;
+
+pub const SCM_J1939_DEST_ADDR: ::c_int = 1;
+pub const SCM_J1939_DEST_NAME: ::c_int = 2;
+pub const SCM_J1939_PRIO: ::c_int = 3;
+pub const SCM_J1939_ERRQUEUE: ::c_int = 4;
+
+pub const J1939_NLA_PAD: ::c_int = 0;
+pub const J1939_NLA_BYTES_ACKED: ::c_int = 1;
+pub const J1939_NLA_TOTAL_SIZE: ::c_int = 2;
+pub const J1939_NLA_PGN: ::c_int = 3;
+pub const J1939_NLA_SRC_NAME: ::c_int = 4;
+pub const J1939_NLA_DEST_NAME: ::c_int = 5;
+pub const J1939_NLA_SRC_ADDR: ::c_int = 6;
+pub const J1939_NLA_DEST_ADDR: ::c_int = 7;
+
+pub const J1939_EE_INFO_NONE: ::c_int = 0;
+pub const J1939_EE_INFO_TX_ABORT: ::c_int = 1;
+pub const J1939_EE_INFO_RX_RTS: ::c_int = 2;
+pub const J1939_EE_INFO_RX_DPO: ::c_int = 3;
+pub const J1939_EE_INFO_RX_ABORT: ::c_int = 4;
+
+pub const J1939_FILTER_MAX: ::c_int = 512;
+
+f! {
+    pub fn NLA_ALIGN(len: ::c_int) -> ::c_int {
+        return ((len) + NLA_ALIGNTO - 1) & !(NLA_ALIGNTO - 1)
+    }
+
+    pub fn CMSG_NXTHDR(mhdr: *const msghdr,
+                       cmsg: *const cmsghdr) -> *mut cmsghdr {
+        if ((*cmsg).cmsg_len as usize) < ::mem::size_of::<cmsghdr>() {
+            return 0 as *mut cmsghdr;
+        };
+        let next = (cmsg as usize +
+                    super::CMSG_ALIGN((*cmsg).cmsg_len as usize))
+            as *mut cmsghdr;
+        let max = (*mhdr).msg_control as usize
+            + (*mhdr).msg_controllen as usize;
+        if (next.offset(1)) as usize > max ||
+            next as usize + super::CMSG_ALIGN((*next).cmsg_len as usize) > max
+        {
+            0 as *mut cmsghdr
+        } else {
+            next as *mut cmsghdr
+        }
+    }
+
+    pub fn CPU_ALLOC_SIZE(count: ::c_int) -> ::size_t {
+        let _dummy: cpu_set_t = ::mem::zeroed();
+        let size_in_bits = 8 * ::mem::size_of_val(&_dummy.bits[0]);
+        ((count as ::size_t + size_in_bits - 1) / 8) as ::size_t
+    }
+
+    pub fn CPU_ZERO(cpuset: &mut cpu_set_t) -> () {
+        for slot in cpuset.bits.iter_mut() {
+            *slot = 0;
+        }
+    }
+
+    pub fn CPU_SET(cpu: usize, cpuset: &mut cpu_set_t) -> () {
+        let size_in_bits
+            = 8 * ::mem::size_of_val(&cpuset.bits[0]); // 32, 64 etc
+        let (idx, offset) = (cpu / size_in_bits, cpu % size_in_bits);
+        cpuset.bits[idx] |= 1 << offset;
+        ()
+    }
+
+    pub fn CPU_CLR(cpu: usize, cpuset: &mut cpu_set_t) -> () {
+        let size_in_bits
+            = 8 * ::mem::size_of_val(&cpuset.bits[0]); // 32, 64 etc
+        let (idx, offset) = (cpu / size_in_bits, cpu % size_in_bits);
+        cpuset.bits[idx] &= !(1 << offset);
+        ()
+    }
+
+    pub fn CPU_ISSET(cpu: usize, cpuset: &cpu_set_t) -> bool {
+        let size_in_bits = 8 * ::mem::size_of_val(&cpuset.bits[0]);
+        let (idx, offset) = (cpu / size_in_bits, cpu % size_in_bits);
+        0 != (cpuset.bits[idx] & (1 << offset))
+    }
+
+    pub fn CPU_COUNT_S(size: usize, cpuset: &cpu_set_t) -> ::c_int {
+        let mut s: u32 = 0;
+        let size_of_mask = ::mem::size_of_val(&cpuset.bits[0]);
+        for i in cpuset.bits[..(size / size_of_mask)].iter() {
+            s += i.count_ones();
+        };
+        s as ::c_int
+    }
+
+    pub fn CPU_COUNT(cpuset: &cpu_set_t) -> ::c_int {
+        CPU_COUNT_S(::mem::size_of::<cpu_set_t>(), cpuset)
+    }
+
+    pub fn CPU_EQUAL(set1: &cpu_set_t, set2: &cpu_set_t) -> bool {
+        set1.bits == set2.bits
+    }
+
+    pub fn major(dev: ::dev_t) -> ::c_uint {
+        let mut major = 0;
+        major |= (dev & 0x00000000000fff00) >> 8;
+        major |= (dev & 0xfffff00000000000) >> 32;
+        major as ::c_uint
+    }
+
+    pub fn minor(dev: ::dev_t) -> ::c_uint {
+        let mut minor = 0;
+        minor |= (dev & 0x00000000000000ff) >> 0;
+        minor |= (dev & 0x00000ffffff00000) >> 12;
+        minor as ::c_uint
+    }
+
+    pub fn IPTOS_TOS(tos: u8) -> u8 {
+        tos & IPTOS_TOS_MASK
+    }
+
+    pub fn IPTOS_PREC(tos: u8) -> u8 {
+        tos & IPTOS_PREC_MASK
+    }
+
+    pub fn RT_TOS(tos: u8) -> u8 {
+        tos & ::IPTOS_TOS_MASK
+    }
+
+    pub fn RT_ADDRCLASS(flags: u32) -> u32 {
+        flags >> 23
+    }
+
+    pub fn RT_LOCALADDR(flags: u32) -> bool {
+        (flags & RTF_ADDRCLASSMASK) == (RTF_LOCAL | RTF_INTERFACE)
+    }
+
+    pub fn SO_EE_OFFENDER(ee: *const ::sock_extended_err) -> *mut ::sockaddr {
+        ee.offset(1) as *mut ::sockaddr
+    }
+
+    pub fn BPF_RVAL(code: ::__u32) -> ::__u32 {
+        code & 0x18
+    }
+
+    pub fn BPF_MISCOP(code: ::__u32) -> ::__u32 {
+        code & 0xf8
+    }
+
+    pub fn BPF_STMT(code: ::__u16, k: ::__u32) -> sock_filter {
+        sock_filter{code: code, jt: 0, jf: 0, k: k}
+    }
+
+    pub fn BPF_JUMP(code: ::__u16, k: ::__u32, jt: ::__u8, jf: ::__u8) -> sock_filter {
+        sock_filter{code: code, jt: jt, jf: jf, k: k}
+    }
+}
+
+safe_f! {
+    pub {const} fn makedev(major: ::c_uint, minor: ::c_uint) -> ::dev_t {
+        let major = major as ::dev_t;
+        let minor = minor as ::dev_t;
+        let mut dev = 0;
+        dev |= (major & 0x00000fff) << 8;
+        dev |= (major & 0xfffff000) << 32;
+        dev |= (minor & 0x000000ff) << 0;
+        dev |= (minor & 0xffffff00) << 12;
+        dev
+    }
+}
+
+cfg_if! {
+    if #[cfg(not(target_env = "uclibc"))] {
+        extern "C" {
+            pub fn aio_read(aiocbp: *mut aiocb) -> ::c_int;
+            pub fn aio_write(aiocbp: *mut aiocb) -> ::c_int;
+            pub fn aio_fsync(op: ::c_int, aiocbp: *mut aiocb) -> ::c_int;
+            pub fn aio_error(aiocbp: *const aiocb) -> ::c_int;
+            pub fn aio_return(aiocbp: *mut aiocb) -> ::ssize_t;
+            pub fn aio_suspend(
+                aiocb_list: *const *const aiocb,
+                nitems: ::c_int,
+                timeout: *const ::timespec,
+            ) -> ::c_int;
+            pub fn aio_cancel(fd: ::c_int, aiocbp: *mut aiocb) -> ::c_int;
+            pub fn lio_listio(
+                mode: ::c_int,
+                aiocb_list: *const *mut aiocb,
+                nitems: ::c_int,
+                sevp: *mut ::sigevent,
+            ) -> ::c_int;
+            pub fn pwritev(
+                fd: ::c_int,
+                iov: *const ::iovec,
+                iovcnt: ::c_int,
+                offset: ::off_t,
+            ) -> ::ssize_t;
+            pub fn preadv(
+                fd: ::c_int,
+                iov: *const ::iovec,
+                iovcnt: ::c_int,
+                offset: ::off_t,
+            ) -> ::ssize_t;
+            pub fn getnameinfo(
+                sa: *const ::sockaddr,
+                salen: ::socklen_t,
+                host: *mut ::c_char,
+                hostlen: ::socklen_t,
+                serv: *mut ::c_char,
+                sevlen: ::socklen_t,
+                flags: ::c_int,
+            ) -> ::c_int;
+            pub fn getloadavg(
+                loadavg: *mut ::c_double,
+                nelem: ::c_int
+            ) -> ::c_int;
+            pub fn process_vm_readv(
+                pid: ::pid_t,
+                local_iov: *const ::iovec,
+                liovcnt: ::c_ulong,
+                remote_iov: *const ::iovec,
+                riovcnt: ::c_ulong,
+                flags: ::c_ulong,
+            ) -> isize;
+            pub fn process_vm_writev(
+                pid: ::pid_t,
+                local_iov: *const ::iovec,
+                liovcnt: ::c_ulong,
+                remote_iov: *const ::iovec,
+                riovcnt: ::c_ulong,
+                flags: ::c_ulong,
+            ) -> isize;
+            pub fn futimes(
+                fd: ::c_int,
+                times: *const ::timeval
+            ) -> ::c_int;
+        }
+    }
+}
+
+extern "C" {
+    #[cfg_attr(not(target_env = "musl"), link_name = "__xpg_strerror_r")]
+    pub fn strerror_r(errnum: ::c_int, buf: *mut c_char, buflen: ::size_t) -> ::c_int;
+
+    pub fn abs(i: ::c_int) -> ::c_int;
+    pub fn atof(s: *const ::c_char) -> ::c_double;
+    pub fn labs(i: ::c_long) -> ::c_long;
+    pub fn rand() -> ::c_int;
+    pub fn srand(seed: ::c_uint);
+
+    pub fn drand48() -> ::c_double;
+    pub fn erand48(xseed: *mut ::c_ushort) -> ::c_double;
+    pub fn lrand48() -> ::c_long;
+    pub fn nrand48(xseed: *mut ::c_ushort) -> ::c_long;
+    pub fn mrand48() -> ::c_long;
+    pub fn jrand48(xseed: *mut ::c_ushort) -> ::c_long;
+    pub fn srand48(seed: ::c_long);
+    pub fn seed48(xseed: *mut ::c_ushort) -> *mut ::c_ushort;
+    pub fn lcong48(p: *mut ::c_ushort);
+
+    pub fn lutimes(file: *const ::c_char, times: *const ::timeval) -> ::c_int;
+
+    pub fn setpwent();
+    pub fn endpwent();
+    pub fn getpwent() -> *mut passwd;
+    pub fn setgrent();
+    pub fn endgrent();
+    pub fn getgrent() -> *mut ::group;
+    pub fn setspent();
+    pub fn endspent();
+    pub fn getspent() -> *mut spwd;
+
+    pub fn getspnam(name: *const ::c_char) -> *mut spwd;
+    // Only `getspnam_r` is implemented for musl, out of all of the reenterant
+    // functions from `shadow.h`.
+    // https://git.musl-libc.org/cgit/musl/tree/include/shadow.h
+    pub fn getspnam_r(
+        name: *const ::c_char,
+        spbuf: *mut spwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        spbufp: *mut *mut spwd,
+    ) -> ::c_int;
+
+    pub fn shm_open(name: *const c_char, oflag: ::c_int, mode: mode_t) -> ::c_int;
+
+    // System V IPC
+    pub fn shmget(key: ::key_t, size: ::size_t, shmflg: ::c_int) -> ::c_int;
+    pub fn shmat(shmid: ::c_int, shmaddr: *const ::c_void, shmflg: ::c_int) -> *mut ::c_void;
+    pub fn shmdt(shmaddr: *const ::c_void) -> ::c_int;
+    pub fn shmctl(shmid: ::c_int, cmd: ::c_int, buf: *mut ::shmid_ds) -> ::c_int;
+    pub fn ftok(pathname: *const ::c_char, proj_id: ::c_int) -> ::key_t;
+    pub fn semget(key: ::key_t, nsems: ::c_int, semflag: ::c_int) -> ::c_int;
+    pub fn semop(semid: ::c_int, sops: *mut ::sembuf, nsops: ::size_t) -> ::c_int;
+    pub fn semctl(semid: ::c_int, semnum: ::c_int, cmd: ::c_int, ...) -> ::c_int;
+    pub fn msgctl(msqid: ::c_int, cmd: ::c_int, buf: *mut msqid_ds) -> ::c_int;
+    pub fn msgget(key: ::key_t, msgflg: ::c_int) -> ::c_int;
+    pub fn msgrcv(
+        msqid: ::c_int,
+        msgp: *mut ::c_void,
+        msgsz: ::size_t,
+        msgtyp: ::c_long,
+        msgflg: ::c_int,
+    ) -> ::ssize_t;
+    pub fn msgsnd(
+        msqid: ::c_int,
+        msgp: *const ::c_void,
+        msgsz: ::size_t,
+        msgflg: ::c_int,
+    ) -> ::c_int;
+
+    pub fn mprotect(addr: *mut ::c_void, len: ::size_t, prot: ::c_int) -> ::c_int;
+    pub fn __errno_location() -> *mut ::c_int;
+
+    pub fn fopen64(filename: *const c_char, mode: *const c_char) -> *mut ::FILE;
+    pub fn freopen64(
+        filename: *const c_char,
+        mode: *const c_char,
+        file: *mut ::FILE,
+    ) -> *mut ::FILE;
+    pub fn tmpfile64() -> *mut ::FILE;
+    pub fn fgetpos64(stream: *mut ::FILE, ptr: *mut fpos64_t) -> ::c_int;
+    pub fn fsetpos64(stream: *mut ::FILE, ptr: *const fpos64_t) -> ::c_int;
+    pub fn fseeko64(stream: *mut ::FILE, offset: ::off64_t, whence: ::c_int) -> ::c_int;
+    pub fn ftello64(stream: *mut ::FILE) -> ::off64_t;
+    pub fn fallocate(fd: ::c_int, mode: ::c_int, offset: ::off_t, len: ::off_t) -> ::c_int;
+    pub fn fallocate64(fd: ::c_int, mode: ::c_int, offset: ::off64_t, len: ::off64_t) -> ::c_int;
+    pub fn posix_fallocate(fd: ::c_int, offset: ::off_t, len: ::off_t) -> ::c_int;
+    pub fn posix_fallocate64(fd: ::c_int, offset: ::off64_t, len: ::off64_t) -> ::c_int;
+    pub fn readahead(fd: ::c_int, offset: ::off64_t, count: ::size_t) -> ::ssize_t;
+    pub fn getxattr(
+        path: *const c_char,
+        name: *const c_char,
+        value: *mut ::c_void,
+        size: ::size_t,
+    ) -> ::ssize_t;
+    pub fn lgetxattr(
+        path: *const c_char,
+        name: *const c_char,
+        value: *mut ::c_void,
+        size: ::size_t,
+    ) -> ::ssize_t;
+    pub fn fgetxattr(
+        filedes: ::c_int,
+        name: *const c_char,
+        value: *mut ::c_void,
+        size: ::size_t,
+    ) -> ::ssize_t;
+    pub fn setxattr(
+        path: *const c_char,
+        name: *const c_char,
+        value: *const ::c_void,
+        size: ::size_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn lsetxattr(
+        path: *const c_char,
+        name: *const c_char,
+        value: *const ::c_void,
+        size: ::size_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn fsetxattr(
+        filedes: ::c_int,
+        name: *const c_char,
+        value: *const ::c_void,
+        size: ::size_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn listxattr(path: *const c_char, list: *mut c_char, size: ::size_t) -> ::ssize_t;
+    pub fn llistxattr(path: *const c_char, list: *mut c_char, size: ::size_t) -> ::ssize_t;
+    pub fn flistxattr(filedes: ::c_int, list: *mut c_char, size: ::size_t) -> ::ssize_t;
+    pub fn removexattr(path: *const c_char, name: *const c_char) -> ::c_int;
+    pub fn lremovexattr(path: *const c_char, name: *const c_char) -> ::c_int;
+    pub fn fremovexattr(filedes: ::c_int, name: *const c_char) -> ::c_int;
+    pub fn signalfd(fd: ::c_int, mask: *const ::sigset_t, flags: ::c_int) -> ::c_int;
+    pub fn timerfd_create(clockid: ::clockid_t, flags: ::c_int) -> ::c_int;
+    pub fn timerfd_gettime(fd: ::c_int, curr_value: *mut itimerspec) -> ::c_int;
+    pub fn timerfd_settime(
+        fd: ::c_int,
+        flags: ::c_int,
+        new_value: *const itimerspec,
+        old_value: *mut itimerspec,
+    ) -> ::c_int;
+    pub fn quotactl(
+        cmd: ::c_int,
+        special: *const ::c_char,
+        id: ::c_int,
+        data: *mut ::c_char,
+    ) -> ::c_int;
+    pub fn mq_open(name: *const ::c_char, oflag: ::c_int, ...) -> ::mqd_t;
+    pub fn mq_close(mqd: ::mqd_t) -> ::c_int;
+    pub fn mq_unlink(name: *const ::c_char) -> ::c_int;
+    pub fn mq_receive(
+        mqd: ::mqd_t,
+        msg_ptr: *mut ::c_char,
+        msg_len: ::size_t,
+        msg_prio: *mut ::c_uint,
+    ) -> ::ssize_t;
+    pub fn mq_timedreceive(
+        mqd: ::mqd_t,
+        msg_ptr: *mut ::c_char,
+        msg_len: ::size_t,
+        msg_prio: *mut ::c_uint,
+        abs_timeout: *const ::timespec,
+    ) -> ::ssize_t;
+    pub fn mq_send(
+        mqd: ::mqd_t,
+        msg_ptr: *const ::c_char,
+        msg_len: ::size_t,
+        msg_prio: ::c_uint,
+    ) -> ::c_int;
+    pub fn mq_timedsend(
+        mqd: ::mqd_t,
+        msg_ptr: *const ::c_char,
+        msg_len: ::size_t,
+        msg_prio: ::c_uint,
+        abs_timeout: *const ::timespec,
+    ) -> ::c_int;
+    pub fn mq_getattr(mqd: ::mqd_t, attr: *mut ::mq_attr) -> ::c_int;
+    pub fn mq_setattr(mqd: ::mqd_t, newattr: *const ::mq_attr, oldattr: *mut ::mq_attr) -> ::c_int;
+    pub fn epoll_pwait(
+        epfd: ::c_int,
+        events: *mut ::epoll_event,
+        maxevents: ::c_int,
+        timeout: ::c_int,
+        sigmask: *const ::sigset_t,
+    ) -> ::c_int;
+    pub fn dup3(oldfd: ::c_int, newfd: ::c_int, flags: ::c_int) -> ::c_int;
+    pub fn mkostemp(template: *mut ::c_char, flags: ::c_int) -> ::c_int;
+    pub fn mkostemps(template: *mut ::c_char, suffixlen: ::c_int, flags: ::c_int) -> ::c_int;
+    pub fn sigtimedwait(
+        set: *const sigset_t,
+        info: *mut siginfo_t,
+        timeout: *const ::timespec,
+    ) -> ::c_int;
+    pub fn sigwaitinfo(set: *const sigset_t, info: *mut siginfo_t) -> ::c_int;
+    pub fn nl_langinfo_l(item: ::nl_item, locale: ::locale_t) -> *mut ::c_char;
+    pub fn accept4(
+        fd: ::c_int,
+        addr: *mut ::sockaddr,
+        len: *mut ::socklen_t,
+        flg: ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_getaffinity_np(
+        thread: ::pthread_t,
+        cpusetsize: ::size_t,
+        cpuset: *mut ::cpu_set_t,
+    ) -> ::c_int;
+    pub fn pthread_setaffinity_np(
+        thread: ::pthread_t,
+        cpusetsize: ::size_t,
+        cpuset: *const ::cpu_set_t,
+    ) -> ::c_int;
+    pub fn pthread_setschedprio(native: ::pthread_t, priority: ::c_int) -> ::c_int;
+    pub fn reboot(how_to: ::c_int) -> ::c_int;
+    pub fn setfsgid(gid: ::gid_t) -> ::c_int;
+    pub fn setfsuid(uid: ::uid_t) -> ::c_int;
+
+    // Not available now on Android
+    pub fn mkfifoat(dirfd: ::c_int, pathname: *const ::c_char, mode: ::mode_t) -> ::c_int;
+    pub fn if_nameindex() -> *mut if_nameindex;
+    pub fn if_freenameindex(ptr: *mut if_nameindex);
+    pub fn sync_file_range(
+        fd: ::c_int,
+        offset: ::off64_t,
+        nbytes: ::off64_t,
+        flags: ::c_uint,
+    ) -> ::c_int;
+    pub fn mremap(
+        addr: *mut ::c_void,
+        len: ::size_t,
+        new_len: ::size_t,
+        flags: ::c_int,
+        ...
+    ) -> *mut ::c_void;
+
+    pub fn glob(
+        pattern: *const c_char,
+        flags: ::c_int,
+        errfunc: ::Option<extern "C" fn(epath: *const c_char, errno: ::c_int) -> ::c_int>,
+        pglob: *mut ::glob_t,
+    ) -> ::c_int;
+    pub fn globfree(pglob: *mut ::glob_t);
+
+    pub fn posix_madvise(addr: *mut ::c_void, len: ::size_t, advice: ::c_int) -> ::c_int;
+
+    pub fn shm_unlink(name: *const ::c_char) -> ::c_int;
+
+    pub fn seekdir(dirp: *mut ::DIR, loc: ::c_long);
+
+    pub fn telldir(dirp: *mut ::DIR) -> ::c_long;
+    pub fn madvise(addr: *mut ::c_void, len: ::size_t, advice: ::c_int) -> ::c_int;
+
+    pub fn msync(addr: *mut ::c_void, len: ::size_t, flags: ::c_int) -> ::c_int;
+    pub fn remap_file_pages(
+        addr: *mut ::c_void,
+        size: ::size_t,
+        prot: ::c_int,
+        pgoff: ::size_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn recvfrom(
+        socket: ::c_int,
+        buf: *mut ::c_void,
+        len: ::size_t,
+        flags: ::c_int,
+        addr: *mut ::sockaddr,
+        addrlen: *mut ::socklen_t,
+    ) -> ::ssize_t;
+    pub fn mkstemps(template: *mut ::c_char, suffixlen: ::c_int) -> ::c_int;
+
+    pub fn nl_langinfo(item: ::nl_item) -> *mut ::c_char;
+
+    pub fn getdomainname(name: *mut ::c_char, len: ::size_t) -> ::c_int;
+    pub fn setdomainname(name: *const ::c_char, len: ::size_t) -> ::c_int;
+    pub fn vhangup() -> ::c_int;
+    pub fn sync();
+    pub fn syncfs(fd: ::c_int) -> ::c_int;
+    pub fn syscall(num: ::c_long, ...) -> ::c_long;
+    pub fn sched_getaffinity(pid: ::pid_t, cpusetsize: ::size_t, cpuset: *mut cpu_set_t)
+        -> ::c_int;
+    pub fn sched_setaffinity(
+        pid: ::pid_t,
+        cpusetsize: ::size_t,
+        cpuset: *const cpu_set_t,
+    ) -> ::c_int;
+    pub fn epoll_create(size: ::c_int) -> ::c_int;
+    pub fn epoll_create1(flags: ::c_int) -> ::c_int;
+    pub fn epoll_wait(
+        epfd: ::c_int,
+        events: *mut ::epoll_event,
+        maxevents: ::c_int,
+        timeout: ::c_int,
+    ) -> ::c_int;
+    pub fn epoll_ctl(epfd: ::c_int, op: ::c_int, fd: ::c_int, event: *mut ::epoll_event)
+        -> ::c_int;
+    pub fn pthread_getschedparam(
+        native: ::pthread_t,
+        policy: *mut ::c_int,
+        param: *mut ::sched_param,
+    ) -> ::c_int;
+    pub fn unshare(flags: ::c_int) -> ::c_int;
+    pub fn umount(target: *const ::c_char) -> ::c_int;
+    pub fn sched_get_priority_max(policy: ::c_int) -> ::c_int;
+    pub fn tee(fd_in: ::c_int, fd_out: ::c_int, len: ::size_t, flags: ::c_uint) -> ::ssize_t;
+    pub fn settimeofday(tv: *const ::timeval, tz: *const ::timezone) -> ::c_int;
+    pub fn splice(
+        fd_in: ::c_int,
+        off_in: *mut ::loff_t,
+        fd_out: ::c_int,
+        off_out: *mut ::loff_t,
+        len: ::size_t,
+        flags: ::c_uint,
+    ) -> ::ssize_t;
+    pub fn eventfd(init: ::c_uint, flags: ::c_int) -> ::c_int;
+    pub fn sched_rr_get_interval(pid: ::pid_t, tp: *mut ::timespec) -> ::c_int;
+    pub fn sem_timedwait(sem: *mut sem_t, abstime: *const ::timespec) -> ::c_int;
+    pub fn sem_getvalue(sem: *mut sem_t, sval: *mut ::c_int) -> ::c_int;
+    pub fn sched_setparam(pid: ::pid_t, param: *const ::sched_param) -> ::c_int;
+    pub fn setns(fd: ::c_int, nstype: ::c_int) -> ::c_int;
+    pub fn swapoff(path: *const ::c_char) -> ::c_int;
+    pub fn vmsplice(
+        fd: ::c_int,
+        iov: *const ::iovec,
+        nr_segs: ::size_t,
+        flags: ::c_uint,
+    ) -> ::ssize_t;
+    pub fn mount(
+        src: *const ::c_char,
+        target: *const ::c_char,
+        fstype: *const ::c_char,
+        flags: ::c_ulong,
+        data: *const ::c_void,
+    ) -> ::c_int;
+    pub fn personality(persona: ::c_ulong) -> ::c_int;
+    pub fn prctl(option: ::c_int, ...) -> ::c_int;
+    pub fn sched_getparam(pid: ::pid_t, param: *mut ::sched_param) -> ::c_int;
+    pub fn ppoll(
+        fds: *mut ::pollfd,
+        nfds: nfds_t,
+        timeout: *const ::timespec,
+        sigmask: *const sigset_t,
+    ) -> ::c_int;
+    pub fn pthread_mutexattr_getprotocol(
+        attr: *const pthread_mutexattr_t,
+        protocol: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_mutexattr_setprotocol(
+        attr: *mut pthread_mutexattr_t,
+        protocol: ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_mutex_consistent(mutex: *mut pthread_mutex_t) -> ::c_int;
+    pub fn pthread_mutex_timedlock(
+        lock: *mut pthread_mutex_t,
+        abstime: *const ::timespec,
+    ) -> ::c_int;
+    pub fn pthread_spin_init(lock: *mut ::pthread_spinlock_t, pshared: ::c_int) -> ::c_int;
+    pub fn pthread_spin_destroy(lock: *mut ::pthread_spinlock_t) -> ::c_int;
+    pub fn pthread_spin_lock(lock: *mut ::pthread_spinlock_t) -> ::c_int;
+    pub fn pthread_spin_trylock(lock: *mut ::pthread_spinlock_t) -> ::c_int;
+    pub fn pthread_spin_unlock(lock: *mut ::pthread_spinlock_t) -> ::c_int;
+    pub fn clone(
+        cb: extern "C" fn(*mut ::c_void) -> ::c_int,
+        child_stack: *mut ::c_void,
+        flags: ::c_int,
+        arg: *mut ::c_void,
+        ...
+    ) -> ::c_int;
+    pub fn sched_getscheduler(pid: ::pid_t) -> ::c_int;
+    pub fn clock_nanosleep(
+        clk_id: ::clockid_t,
+        flags: ::c_int,
+        rqtp: *const ::timespec,
+        rmtp: *mut ::timespec,
+    ) -> ::c_int;
+    pub fn pthread_attr_getguardsize(
+        attr: *const ::pthread_attr_t,
+        guardsize: *mut ::size_t,
+    ) -> ::c_int;
+    pub fn sethostname(name: *const ::c_char, len: ::size_t) -> ::c_int;
+    pub fn sched_get_priority_min(policy: ::c_int) -> ::c_int;
+    pub fn pthread_condattr_getpshared(
+        attr: *const pthread_condattr_t,
+        pshared: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn sysinfo(info: *mut ::sysinfo) -> ::c_int;
+    pub fn umount2(target: *const ::c_char, flags: ::c_int) -> ::c_int;
+    pub fn pthread_setschedparam(
+        native: ::pthread_t,
+        policy: ::c_int,
+        param: *const ::sched_param,
+    ) -> ::c_int;
+    pub fn swapon(path: *const ::c_char, swapflags: ::c_int) -> ::c_int;
+    pub fn sched_setscheduler(
+        pid: ::pid_t,
+        policy: ::c_int,
+        param: *const ::sched_param,
+    ) -> ::c_int;
+    pub fn sendfile(
+        out_fd: ::c_int,
+        in_fd: ::c_int,
+        offset: *mut off_t,
+        count: ::size_t,
+    ) -> ::ssize_t;
+    pub fn sendfile64(
+        out_fd: ::c_int,
+        in_fd: ::c_int,
+        offset: *mut off64_t,
+        count: ::size_t,
+    ) -> ::ssize_t;
+    pub fn sigsuspend(mask: *const ::sigset_t) -> ::c_int;
+    pub fn getgrgid_r(
+        gid: ::gid_t,
+        grp: *mut ::group,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::group,
+    ) -> ::c_int;
+    pub fn sigaltstack(ss: *const stack_t, oss: *mut stack_t) -> ::c_int;
+    pub fn sem_close(sem: *mut sem_t) -> ::c_int;
+    pub fn getdtablesize() -> ::c_int;
+    pub fn getgrnam_r(
+        name: *const ::c_char,
+        grp: *mut ::group,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut ::group,
+    ) -> ::c_int;
+    pub fn initgroups(user: *const ::c_char, group: ::gid_t) -> ::c_int;
+    pub fn pthread_sigmask(how: ::c_int, set: *const sigset_t, oldset: *mut sigset_t) -> ::c_int;
+    pub fn sem_open(name: *const ::c_char, oflag: ::c_int, ...) -> *mut sem_t;
+    pub fn getgrnam(name: *const ::c_char) -> *mut ::group;
+    pub fn pthread_cancel(thread: ::pthread_t) -> ::c_int;
+    pub fn pthread_kill(thread: ::pthread_t, sig: ::c_int) -> ::c_int;
+    pub fn sem_unlink(name: *const ::c_char) -> ::c_int;
+    pub fn daemon(nochdir: ::c_int, noclose: ::c_int) -> ::c_int;
+    pub fn getpwnam_r(
+        name: *const ::c_char,
+        pwd: *mut passwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut passwd,
+    ) -> ::c_int;
+    pub fn getpwuid_r(
+        uid: ::uid_t,
+        pwd: *mut passwd,
+        buf: *mut ::c_char,
+        buflen: ::size_t,
+        result: *mut *mut passwd,
+    ) -> ::c_int;
+    pub fn sigwait(set: *const sigset_t, sig: *mut ::c_int) -> ::c_int;
+    pub fn pthread_atfork(
+        prepare: ::Option<unsafe extern "C" fn()>,
+        parent: ::Option<unsafe extern "C" fn()>,
+        child: ::Option<unsafe extern "C" fn()>,
+    ) -> ::c_int;
+    pub fn getgrgid(gid: ::gid_t) -> *mut ::group;
+    pub fn getgrouplist(
+        user: *const ::c_char,
+        group: ::gid_t,
+        groups: *mut ::gid_t,
+        ngroups: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_mutexattr_getpshared(
+        attr: *const pthread_mutexattr_t,
+        pshared: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_mutexattr_getrobust(
+        attr: *const pthread_mutexattr_t,
+        robustness: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_mutexattr_setrobust(
+        attr: *mut pthread_mutexattr_t,
+        robustness: ::c_int,
+    ) -> ::c_int;
+    pub fn popen(command: *const c_char, mode: *const c_char) -> *mut ::FILE;
+    pub fn faccessat(
+        dirfd: ::c_int,
+        pathname: *const ::c_char,
+        mode: ::c_int,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_create(
+        native: *mut ::pthread_t,
+        attr: *const ::pthread_attr_t,
+        f: extern "C" fn(*mut ::c_void) -> *mut ::c_void,
+        value: *mut ::c_void,
+    ) -> ::c_int;
+    pub fn dl_iterate_phdr(
+        callback: ::Option<
+            unsafe extern "C" fn(
+                info: *mut ::dl_phdr_info,
+                size: ::size_t,
+                data: *mut ::c_void,
+            ) -> ::c_int,
+        >,
+        data: *mut ::c_void,
+    ) -> ::c_int;
+
+    pub fn setmntent(filename: *const ::c_char, ty: *const ::c_char) -> *mut ::FILE;
+    pub fn getmntent(stream: *mut ::FILE) -> *mut ::mntent;
+    pub fn addmntent(stream: *mut ::FILE, mnt: *const ::mntent) -> ::c_int;
+    pub fn endmntent(streamp: *mut ::FILE) -> ::c_int;
+    pub fn hasmntopt(mnt: *const ::mntent, opt: *const ::c_char) -> *mut ::c_char;
+
+    pub fn posix_spawn(
+        pid: *mut ::pid_t,
+        path: *const ::c_char,
+        file_actions: *const ::posix_spawn_file_actions_t,
+        attrp: *const ::posix_spawnattr_t,
+        argv: *const *mut ::c_char,
+        envp: *const *mut ::c_char,
+    ) -> ::c_int;
+    pub fn posix_spawnp(
+        pid: *mut ::pid_t,
+        file: *const ::c_char,
+        file_actions: *const ::posix_spawn_file_actions_t,
+        attrp: *const ::posix_spawnattr_t,
+        argv: *const *mut ::c_char,
+        envp: *const *mut ::c_char,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_init(attr: *mut posix_spawnattr_t) -> ::c_int;
+    pub fn posix_spawnattr_destroy(attr: *mut posix_spawnattr_t) -> ::c_int;
+    pub fn posix_spawnattr_getsigdefault(
+        attr: *const posix_spawnattr_t,
+        default: *mut ::sigset_t,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setsigdefault(
+        attr: *mut posix_spawnattr_t,
+        default: *const ::sigset_t,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_getsigmask(
+        attr: *const posix_spawnattr_t,
+        default: *mut ::sigset_t,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setsigmask(
+        attr: *mut posix_spawnattr_t,
+        default: *const ::sigset_t,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_getflags(
+        attr: *const posix_spawnattr_t,
+        flags: *mut ::c_short,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setflags(attr: *mut posix_spawnattr_t, flags: ::c_short) -> ::c_int;
+    pub fn posix_spawnattr_getpgroup(
+        attr: *const posix_spawnattr_t,
+        flags: *mut ::pid_t,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setpgroup(attr: *mut posix_spawnattr_t, flags: ::pid_t) -> ::c_int;
+    pub fn posix_spawnattr_getschedpolicy(
+        attr: *const posix_spawnattr_t,
+        flags: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setschedpolicy(attr: *mut posix_spawnattr_t, flags: ::c_int) -> ::c_int;
+    pub fn posix_spawnattr_getschedparam(
+        attr: *const posix_spawnattr_t,
+        param: *mut ::sched_param,
+    ) -> ::c_int;
+    pub fn posix_spawnattr_setschedparam(
+        attr: *mut posix_spawnattr_t,
+        param: *const ::sched_param,
+    ) -> ::c_int;
+
+    pub fn posix_spawn_file_actions_init(actions: *mut posix_spawn_file_actions_t) -> ::c_int;
+    pub fn posix_spawn_file_actions_destroy(actions: *mut posix_spawn_file_actions_t) -> ::c_int;
+    pub fn posix_spawn_file_actions_addopen(
+        actions: *mut posix_spawn_file_actions_t,
+        fd: ::c_int,
+        path: *const ::c_char,
+        oflag: ::c_int,
+        mode: ::mode_t,
+    ) -> ::c_int;
+    pub fn posix_spawn_file_actions_addclose(
+        actions: *mut posix_spawn_file_actions_t,
+        fd: ::c_int,
+    ) -> ::c_int;
+    pub fn posix_spawn_file_actions_adddup2(
+        actions: *mut posix_spawn_file_actions_t,
+        fd: ::c_int,
+        newfd: ::c_int,
+    ) -> ::c_int;
+    pub fn fread_unlocked(
+        ptr: *mut ::c_void,
+        size: ::size_t,
+        nobj: ::size_t,
+        stream: *mut ::FILE,
+    ) -> ::size_t;
+    pub fn inotify_rm_watch(fd: ::c_int, wd: ::c_int) -> ::c_int;
+    pub fn inotify_init() -> ::c_int;
+    pub fn inotify_init1(flags: ::c_int) -> ::c_int;
+    pub fn inotify_add_watch(fd: ::c_int, path: *const ::c_char, mask: u32) -> ::c_int;
+    pub fn fanotify_init(flags: ::c_uint, event_f_flags: ::c_uint) -> ::c_int;
+
+    pub fn regcomp(preg: *mut ::regex_t, pattern: *const ::c_char, cflags: ::c_int) -> ::c_int;
+
+    pub fn regexec(
+        preg: *const ::regex_t,
+        input: *const ::c_char,
+        nmatch: ::size_t,
+        pmatch: *mut regmatch_t,
+        eflags: ::c_int,
+    ) -> ::c_int;
+
+    pub fn regerror(
+        errcode: ::c_int,
+        preg: *const ::regex_t,
+        errbuf: *mut ::c_char,
+        errbuf_size: ::size_t,
+    ) -> ::size_t;
+
+    pub fn regfree(preg: *mut ::regex_t);
+
+    pub fn iconv_open(tocode: *const ::c_char, fromcode: *const ::c_char) -> iconv_t;
+    pub fn iconv(
+        cd: iconv_t,
+        inbuf: *mut *mut ::c_char,
+        inbytesleft: *mut ::size_t,
+        outbuf: *mut *mut ::c_char,
+        outbytesleft: *mut ::size_t,
+    ) -> ::size_t;
+    pub fn iconv_close(cd: iconv_t) -> ::c_int;
+
+    pub fn gettid() -> ::pid_t;
+
+    pub fn timer_create(
+        clockid: ::clockid_t,
+        sevp: *mut ::sigevent,
+        timerid: *mut ::timer_t,
+    ) -> ::c_int;
+    pub fn timer_delete(timerid: ::timer_t) -> ::c_int;
+    pub fn timer_getoverrun(timerid: ::timer_t) -> ::c_int;
+    pub fn timer_gettime(timerid: ::timer_t, curr_value: *mut ::itimerspec) -> ::c_int;
+    pub fn timer_settime(
+        timerid: ::timer_t,
+        flags: ::c_int,
+        new_value: *const ::itimerspec,
+        old_value: *mut ::itimerspec,
+    ) -> ::c_int;
+
+    pub fn gethostid() -> ::c_long;
+
+    pub fn pthread_getcpuclockid(thread: ::pthread_t, clk_id: *mut ::clockid_t) -> ::c_int;
+    pub fn memmem(
+        haystack: *const ::c_void,
+        haystacklen: ::size_t,
+        needle: *const ::c_void,
+        needlelen: ::size_t,
+    ) -> *mut ::c_void;
+    pub fn sched_getcpu() -> ::c_int;
+
+    pub fn pthread_getname_np(thread: ::pthread_t, name: *mut ::c_char, len: ::size_t) -> ::c_int;
+    pub fn pthread_setname_np(thread: ::pthread_t, name: *const ::c_char) -> ::c_int;
+    pub fn getopt_long(
+        argc: ::c_int,
+        argv: *const *mut c_char,
+        optstring: *const c_char,
+        longopts: *const option,
+        longindex: *mut ::c_int,
+    ) -> ::c_int;
+}
+
+cfg_if! {
+    if #[cfg(target_env = "uclibc")] {
+        mod uclibc;
+        pub use self::uclibc::*;
+    } else if #[cfg(target_env = "musl")] {
+        mod musl;
+        pub use self::musl::*;
+    } else if #[cfg(target_env = "gnu")] {
+        mod gnu;
+        pub use self::gnu::*;
+    }
+}
+
+mod arch;
+pub use self::arch::*;
+
+cfg_if! {
+    if #[cfg(libc_align)] {
+        #[macro_use]
+        mod align;
+    } else {
+        #[macro_use]
+        mod no_align;
+    }
+}
+expand_align!();
+
+cfg_if! {
+    if #[cfg(libc_non_exhaustive)] {
+        mod non_exhaustive;
+        pub use self::non_exhaustive::*;
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/non_exhaustive.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/non_exhaustive.rs.html new file mode 100644 index 0000000..d6ab775 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/linux/non_exhaustive.rs.html @@ -0,0 +1,20 @@ +non_exhaustive.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+
s! {
+    // linux/openat2.h
+    #[non_exhaustive]
+    pub struct open_how {
+        pub flags: ::__u64,
+        pub mode: ::__u64,
+        pub resolve: ::__u64,
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/mod.rs.html new file mode 100644 index 0000000..c838ce4 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/linux_like/mod.rs.html @@ -0,0 +1,3660 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+1410
+1411
+1412
+1413
+1414
+1415
+1416
+1417
+1418
+1419
+1420
+1421
+1422
+1423
+1424
+1425
+1426
+1427
+1428
+1429
+1430
+1431
+1432
+1433
+1434
+1435
+1436
+1437
+1438
+1439
+1440
+1441
+1442
+1443
+1444
+1445
+1446
+1447
+1448
+1449
+1450
+1451
+1452
+1453
+1454
+1455
+1456
+1457
+1458
+1459
+1460
+1461
+1462
+1463
+1464
+1465
+1466
+1467
+1468
+1469
+1470
+1471
+1472
+1473
+1474
+1475
+1476
+1477
+1478
+1479
+1480
+1481
+1482
+1483
+1484
+1485
+1486
+1487
+1488
+1489
+1490
+1491
+1492
+1493
+1494
+1495
+1496
+1497
+1498
+1499
+1500
+1501
+1502
+1503
+1504
+1505
+1506
+1507
+1508
+1509
+1510
+1511
+1512
+1513
+1514
+1515
+1516
+1517
+1518
+1519
+1520
+1521
+1522
+1523
+1524
+1525
+1526
+1527
+1528
+1529
+1530
+1531
+1532
+1533
+1534
+1535
+1536
+1537
+1538
+1539
+1540
+1541
+1542
+1543
+1544
+1545
+1546
+1547
+1548
+1549
+1550
+1551
+1552
+1553
+1554
+1555
+1556
+1557
+1558
+1559
+1560
+1561
+1562
+1563
+1564
+1565
+1566
+1567
+1568
+1569
+1570
+1571
+1572
+1573
+1574
+1575
+1576
+1577
+1578
+1579
+1580
+1581
+1582
+1583
+1584
+1585
+1586
+1587
+1588
+1589
+1590
+1591
+1592
+1593
+1594
+1595
+1596
+1597
+1598
+1599
+1600
+1601
+1602
+1603
+1604
+1605
+1606
+1607
+1608
+1609
+1610
+1611
+1612
+1613
+1614
+1615
+1616
+1617
+1618
+1619
+1620
+1621
+1622
+1623
+1624
+1625
+1626
+1627
+1628
+1629
+1630
+1631
+1632
+1633
+1634
+1635
+1636
+1637
+1638
+1639
+1640
+1641
+1642
+1643
+1644
+1645
+1646
+1647
+1648
+1649
+1650
+1651
+1652
+1653
+1654
+1655
+1656
+1657
+1658
+1659
+1660
+1661
+1662
+1663
+1664
+1665
+1666
+1667
+1668
+1669
+1670
+1671
+1672
+1673
+1674
+1675
+1676
+1677
+1678
+1679
+1680
+1681
+1682
+1683
+1684
+1685
+1686
+1687
+1688
+1689
+1690
+1691
+1692
+1693
+1694
+1695
+1696
+1697
+1698
+1699
+1700
+1701
+1702
+1703
+1704
+1705
+1706
+1707
+1708
+1709
+1710
+1711
+1712
+1713
+1714
+1715
+1716
+1717
+1718
+1719
+1720
+1721
+1722
+1723
+1724
+1725
+1726
+1727
+1728
+1729
+1730
+1731
+1732
+1733
+1734
+1735
+1736
+1737
+1738
+1739
+1740
+1741
+1742
+1743
+1744
+1745
+1746
+1747
+1748
+1749
+1750
+1751
+1752
+1753
+1754
+1755
+1756
+1757
+1758
+1759
+1760
+1761
+1762
+1763
+1764
+1765
+1766
+1767
+1768
+1769
+1770
+1771
+1772
+1773
+1774
+1775
+1776
+1777
+1778
+1779
+1780
+1781
+1782
+1783
+1784
+1785
+1786
+1787
+1788
+1789
+1790
+1791
+1792
+1793
+1794
+1795
+1796
+1797
+1798
+1799
+1800
+1801
+1802
+1803
+1804
+1805
+1806
+1807
+1808
+1809
+1810
+1811
+1812
+1813
+1814
+1815
+1816
+1817
+1818
+1819
+1820
+1821
+1822
+1823
+1824
+1825
+1826
+1827
+1828
+1829
+
pub type sa_family_t = u16;
+pub type speed_t = ::c_uint;
+pub type tcflag_t = ::c_uint;
+pub type clockid_t = ::c_int;
+pub type timer_t = *mut ::c_void;
+pub type key_t = ::c_int;
+pub type id_t = ::c_uint;
+
+#[cfg_attr(feature = "extra_traits", derive(Debug))]
+pub enum timezone {}
+impl ::Copy for timezone {}
+impl ::Clone for timezone {
+    fn clone(&self) -> timezone {
+        *self
+    }
+}
+
+s! {
+    pub struct in_addr {
+        pub s_addr: ::in_addr_t,
+    }
+
+    pub struct ip_mreq {
+        pub imr_multiaddr: in_addr,
+        pub imr_interface: in_addr,
+    }
+
+    pub struct ip_mreqn {
+        pub imr_multiaddr: in_addr,
+        pub imr_address: in_addr,
+        pub imr_ifindex: ::c_int,
+    }
+
+    pub struct ip_mreq_source {
+        pub imr_multiaddr: in_addr,
+        pub imr_interface: in_addr,
+        pub imr_sourceaddr: in_addr,
+    }
+
+    pub struct sockaddr {
+        pub sa_family: sa_family_t,
+        pub sa_data: [::c_char; 14],
+    }
+
+    pub struct sockaddr_in {
+        pub sin_family: sa_family_t,
+        pub sin_port: ::in_port_t,
+        pub sin_addr: ::in_addr,
+        pub sin_zero: [u8; 8],
+    }
+
+    pub struct sockaddr_in6 {
+        pub sin6_family: sa_family_t,
+        pub sin6_port: ::in_port_t,
+        pub sin6_flowinfo: u32,
+        pub sin6_addr: ::in6_addr,
+        pub sin6_scope_id: u32,
+    }
+
+    // The order of the `ai_addr` field in this struct is crucial
+    // for converting between the Rust and C types.
+    pub struct addrinfo {
+        pub ai_flags: ::c_int,
+        pub ai_family: ::c_int,
+        pub ai_socktype: ::c_int,
+        pub ai_protocol: ::c_int,
+        pub ai_addrlen: socklen_t,
+
+        #[cfg(any(target_os = "linux",
+                  target_os = "emscripten"))]
+        pub ai_addr: *mut ::sockaddr,
+
+        pub ai_canonname: *mut c_char,
+
+        #[cfg(target_os = "android")]
+        pub ai_addr: *mut ::sockaddr,
+
+        pub ai_next: *mut addrinfo,
+    }
+
+    pub struct sockaddr_ll {
+        pub sll_family: ::c_ushort,
+        pub sll_protocol: ::c_ushort,
+        pub sll_ifindex: ::c_int,
+        pub sll_hatype: ::c_ushort,
+        pub sll_pkttype: ::c_uchar,
+        pub sll_halen: ::c_uchar,
+        pub sll_addr: [::c_uchar; 8]
+    }
+
+    pub struct fd_set {
+        fds_bits: [::c_ulong; FD_SETSIZE / ULONG_SIZE],
+    }
+
+    pub struct tm {
+        pub tm_sec: ::c_int,
+        pub tm_min: ::c_int,
+        pub tm_hour: ::c_int,
+        pub tm_mday: ::c_int,
+        pub tm_mon: ::c_int,
+        pub tm_year: ::c_int,
+        pub tm_wday: ::c_int,
+        pub tm_yday: ::c_int,
+        pub tm_isdst: ::c_int,
+        pub tm_gmtoff: ::c_long,
+        pub tm_zone: *const ::c_char,
+    }
+
+    pub struct sched_param {
+        pub sched_priority: ::c_int,
+        #[cfg(any(target_env = "musl", target_os = "emscripten"))]
+        pub sched_ss_low_priority: ::c_int,
+        #[cfg(any(target_env = "musl", target_os = "emscripten"))]
+        pub sched_ss_repl_period: ::timespec,
+        #[cfg(any(target_env = "musl", target_os = "emscripten"))]
+        pub sched_ss_init_budget: ::timespec,
+        #[cfg(any(target_env = "musl", target_os = "emscripten"))]
+        pub sched_ss_max_repl: ::c_int,
+    }
+
+    pub struct Dl_info {
+        pub dli_fname: *const ::c_char,
+        pub dli_fbase: *mut ::c_void,
+        pub dli_sname: *const ::c_char,
+        pub dli_saddr: *mut ::c_void,
+    }
+
+    pub struct lconv {
+        pub decimal_point: *mut ::c_char,
+        pub thousands_sep: *mut ::c_char,
+        pub grouping: *mut ::c_char,
+        pub int_curr_symbol: *mut ::c_char,
+        pub currency_symbol: *mut ::c_char,
+        pub mon_decimal_point: *mut ::c_char,
+        pub mon_thousands_sep: *mut ::c_char,
+        pub mon_grouping: *mut ::c_char,
+        pub positive_sign: *mut ::c_char,
+        pub negative_sign: *mut ::c_char,
+        pub int_frac_digits: ::c_char,
+        pub frac_digits: ::c_char,
+        pub p_cs_precedes: ::c_char,
+        pub p_sep_by_space: ::c_char,
+        pub n_cs_precedes: ::c_char,
+        pub n_sep_by_space: ::c_char,
+        pub p_sign_posn: ::c_char,
+        pub n_sign_posn: ::c_char,
+        pub int_p_cs_precedes: ::c_char,
+        pub int_p_sep_by_space: ::c_char,
+        pub int_n_cs_precedes: ::c_char,
+        pub int_n_sep_by_space: ::c_char,
+        pub int_p_sign_posn: ::c_char,
+        pub int_n_sign_posn: ::c_char,
+    }
+
+    pub struct in_pktinfo {
+        pub ipi_ifindex: ::c_int,
+        pub ipi_spec_dst: ::in_addr,
+        pub ipi_addr: ::in_addr,
+    }
+
+    pub struct ifaddrs {
+        pub ifa_next: *mut ifaddrs,
+        pub ifa_name: *mut c_char,
+        pub ifa_flags: ::c_uint,
+        pub ifa_addr: *mut ::sockaddr,
+        pub ifa_netmask: *mut ::sockaddr,
+        pub ifa_ifu: *mut ::sockaddr, // FIXME This should be a union
+        pub ifa_data: *mut ::c_void
+    }
+
+    pub struct in6_rtmsg {
+        rtmsg_dst: ::in6_addr,
+        rtmsg_src: ::in6_addr,
+        rtmsg_gateway: ::in6_addr,
+        rtmsg_type: u32,
+        rtmsg_dst_len: u16,
+        rtmsg_src_len: u16,
+        rtmsg_metric: u32,
+        rtmsg_info: ::c_ulong,
+        rtmsg_flags: u32,
+        rtmsg_ifindex: ::c_int,
+    }
+
+    pub struct arpreq {
+        pub arp_pa: ::sockaddr,
+        pub arp_ha: ::sockaddr,
+        pub arp_flags: ::c_int,
+        pub arp_netmask: ::sockaddr,
+        pub arp_dev: [::c_char; 16],
+    }
+
+    pub struct arpreq_old {
+        pub arp_pa: ::sockaddr,
+        pub arp_ha: ::sockaddr,
+        pub arp_flags: ::c_int,
+        pub arp_netmask: ::sockaddr,
+    }
+
+    pub struct arphdr {
+        pub ar_hrd: u16,
+        pub ar_pro: u16,
+        pub ar_hln: u8,
+        pub ar_pln: u8,
+        pub ar_op: u16,
+    }
+
+    pub struct mmsghdr {
+        pub msg_hdr: ::msghdr,
+        pub msg_len: ::c_uint,
+    }
+}
+
+s_no_extra_traits! {
+    #[cfg_attr(
+        any(
+            all(
+                target_arch = "x86",
+                not(target_env = "musl"),
+                not(target_os = "android")),
+            target_arch = "x86_64"),
+        repr(packed))]
+    pub struct epoll_event {
+        pub events: u32,
+        pub u64: u64,
+    }
+
+    pub struct sockaddr_un {
+        pub sun_family: sa_family_t,
+        pub sun_path: [::c_char; 108]
+    }
+
+    pub struct sockaddr_storage {
+        pub ss_family: sa_family_t,
+        #[cfg(target_pointer_width = "32")]
+        __ss_pad2: [u8; 128 - 2 - 4],
+        #[cfg(target_pointer_width = "64")]
+        __ss_pad2: [u8; 128 - 2 - 8],
+        __ss_align: ::size_t,
+    }
+
+    pub struct utsname {
+        pub sysname: [::c_char; 65],
+        pub nodename: [::c_char; 65],
+        pub release: [::c_char; 65],
+        pub version: [::c_char; 65],
+        pub machine: [::c_char; 65],
+        pub domainname: [::c_char; 65]
+    }
+
+    pub struct sigevent {
+        pub sigev_value: ::sigval,
+        pub sigev_signo: ::c_int,
+        pub sigev_notify: ::c_int,
+        // Actually a union.  We only expose sigev_notify_thread_id because it's
+        // the most useful member
+        pub sigev_notify_thread_id: ::c_int,
+        #[cfg(target_pointer_width = "64")]
+        __unused1: [::c_int; 11],
+        #[cfg(target_pointer_width = "32")]
+        __unused1: [::c_int; 12]
+    }
+}
+
+cfg_if! {
+    if #[cfg(feature = "extra_traits")] {
+        impl PartialEq for epoll_event {
+            fn eq(&self, other: &epoll_event) -> bool {
+                self.events == other.events
+                    && self.u64 == other.u64
+            }
+        }
+        impl Eq for epoll_event {}
+        impl ::fmt::Debug for epoll_event {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                let events = self.events;
+                let u64 = self.u64;
+                f.debug_struct("epoll_event")
+                    .field("events", &events)
+                    .field("u64", &u64)
+                    .finish()
+            }
+        }
+        impl ::hash::Hash for epoll_event {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                let events = self.events;
+                let u64 = self.u64;
+                events.hash(state);
+                u64.hash(state);
+            }
+        }
+
+        impl PartialEq for sockaddr_un {
+            fn eq(&self, other: &sockaddr_un) -> bool {
+                self.sun_family == other.sun_family
+                    && self
+                    .sun_path
+                    .iter()
+                    .zip(other.sun_path.iter())
+                    .all(|(a, b)| a == b)
+            }
+        }
+        impl Eq for sockaddr_un {}
+        impl ::fmt::Debug for sockaddr_un {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("sockaddr_un")
+                    .field("sun_family", &self.sun_family)
+                // FIXME: .field("sun_path", &self.sun_path)
+                    .finish()
+            }
+        }
+        impl ::hash::Hash for sockaddr_un {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.sun_family.hash(state);
+                self.sun_path.hash(state);
+            }
+        }
+
+        impl PartialEq for sockaddr_storage {
+            fn eq(&self, other: &sockaddr_storage) -> bool {
+                self.ss_family == other.ss_family
+                    && self
+                    .__ss_pad2
+                    .iter()
+                    .zip(other.__ss_pad2.iter())
+                    .all(|(a, b)| a == b)
+            }
+        }
+
+        impl Eq for sockaddr_storage {}
+
+        impl ::fmt::Debug for sockaddr_storage {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("sockaddr_storage")
+                    .field("ss_family", &self.ss_family)
+                    .field("__ss_align", &self.__ss_align)
+                // FIXME: .field("__ss_pad2", &self.__ss_pad2)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for sockaddr_storage {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.ss_family.hash(state);
+                self.__ss_pad2.hash(state);
+            }
+        }
+
+        impl PartialEq for utsname {
+            fn eq(&self, other: &utsname) -> bool {
+                self.sysname
+                    .iter()
+                    .zip(other.sysname.iter())
+                    .all(|(a, b)| a == b)
+                    && self
+                    .nodename
+                    .iter()
+                    .zip(other.nodename.iter())
+                    .all(|(a, b)| a == b)
+                    && self
+                    .release
+                    .iter()
+                    .zip(other.release.iter())
+                    .all(|(a, b)| a == b)
+                    && self
+                    .version
+                    .iter()
+                    .zip(other.version.iter())
+                    .all(|(a, b)| a == b)
+                    && self
+                    .machine
+                    .iter()
+                    .zip(other.machine.iter())
+                    .all(|(a, b)| a == b)
+                    && self
+                    .domainname
+                    .iter()
+                    .zip(other.domainname.iter())
+                    .all(|(a, b)| a == b)
+            }
+        }
+
+        impl Eq for utsname {}
+
+        impl ::fmt::Debug for utsname {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("utsname")
+                // FIXME: .field("sysname", &self.sysname)
+                // FIXME: .field("nodename", &self.nodename)
+                // FIXME: .field("release", &self.release)
+                // FIXME: .field("version", &self.version)
+                // FIXME: .field("machine", &self.machine)
+                // FIXME: .field("domainname", &self.domainname)
+                    .finish()
+            }
+        }
+
+        impl ::hash::Hash for utsname {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.sysname.hash(state);
+                self.nodename.hash(state);
+                self.release.hash(state);
+                self.version.hash(state);
+                self.machine.hash(state);
+                self.domainname.hash(state);
+            }
+        }
+
+        impl PartialEq for sigevent {
+            fn eq(&self, other: &sigevent) -> bool {
+                self.sigev_value == other.sigev_value
+                    && self.sigev_signo == other.sigev_signo
+                    && self.sigev_notify == other.sigev_notify
+                    && self.sigev_notify_thread_id
+                        == other.sigev_notify_thread_id
+            }
+        }
+        impl Eq for sigevent {}
+        impl ::fmt::Debug for sigevent {
+            fn fmt(&self, f: &mut ::fmt::Formatter) -> ::fmt::Result {
+                f.debug_struct("sigevent")
+                    .field("sigev_value", &self.sigev_value)
+                    .field("sigev_signo", &self.sigev_signo)
+                    .field("sigev_notify", &self.sigev_notify)
+                    .field("sigev_notify_thread_id",
+                           &self.sigev_notify_thread_id)
+                    .finish()
+            }
+        }
+        impl ::hash::Hash for sigevent {
+            fn hash<H: ::hash::Hasher>(&self, state: &mut H) {
+                self.sigev_value.hash(state);
+                self.sigev_signo.hash(state);
+                self.sigev_notify.hash(state);
+                self.sigev_notify_thread_id.hash(state);
+            }
+        }
+    }
+}
+
+// intentionally not public, only used for fd_set
+cfg_if! {
+    if #[cfg(target_pointer_width = "32")] {
+        const ULONG_SIZE: usize = 32;
+    } else if #[cfg(target_pointer_width = "64")] {
+        const ULONG_SIZE: usize = 64;
+    } else {
+        // Unknown target_pointer_width
+    }
+}
+
+pub const EXIT_FAILURE: ::c_int = 1;
+pub const EXIT_SUCCESS: ::c_int = 0;
+pub const RAND_MAX: ::c_int = 2147483647;
+pub const EOF: ::c_int = -1;
+pub const SEEK_SET: ::c_int = 0;
+pub const SEEK_CUR: ::c_int = 1;
+pub const SEEK_END: ::c_int = 2;
+pub const _IOFBF: ::c_int = 0;
+pub const _IONBF: ::c_int = 2;
+pub const _IOLBF: ::c_int = 1;
+
+pub const F_DUPFD: ::c_int = 0;
+pub const F_GETFD: ::c_int = 1;
+pub const F_SETFD: ::c_int = 2;
+pub const F_GETFL: ::c_int = 3;
+pub const F_SETFL: ::c_int = 4;
+
+// Linux-specific fcntls
+pub const F_SETLEASE: ::c_int = 1024;
+pub const F_GETLEASE: ::c_int = 1025;
+pub const F_NOTIFY: ::c_int = 1026;
+pub const F_CANCELLK: ::c_int = 1029;
+pub const F_DUPFD_CLOEXEC: ::c_int = 1030;
+pub const F_SETPIPE_SZ: ::c_int = 1031;
+pub const F_GETPIPE_SZ: ::c_int = 1032;
+pub const F_ADD_SEALS: ::c_int = 1033;
+pub const F_GET_SEALS: ::c_int = 1034;
+
+pub const F_SEAL_SEAL: ::c_int = 0x0001;
+pub const F_SEAL_SHRINK: ::c_int = 0x0002;
+pub const F_SEAL_GROW: ::c_int = 0x0004;
+pub const F_SEAL_WRITE: ::c_int = 0x0008;
+
+// FIXME(#235): Include file sealing fcntls once we have a way to verify them.
+
+pub const SIGTRAP: ::c_int = 5;
+
+pub const PTHREAD_CREATE_JOINABLE: ::c_int = 0;
+pub const PTHREAD_CREATE_DETACHED: ::c_int = 1;
+
+pub const CLOCK_REALTIME: ::clockid_t = 0;
+pub const CLOCK_MONOTONIC: ::clockid_t = 1;
+pub const CLOCK_PROCESS_CPUTIME_ID: ::clockid_t = 2;
+pub const CLOCK_THREAD_CPUTIME_ID: ::clockid_t = 3;
+pub const CLOCK_MONOTONIC_RAW: ::clockid_t = 4;
+pub const CLOCK_REALTIME_COARSE: ::clockid_t = 5;
+pub const CLOCK_MONOTONIC_COARSE: ::clockid_t = 6;
+pub const CLOCK_BOOTTIME: ::clockid_t = 7;
+pub const CLOCK_REALTIME_ALARM: ::clockid_t = 8;
+pub const CLOCK_BOOTTIME_ALARM: ::clockid_t = 9;
+pub const CLOCK_TAI: ::clockid_t = 11;
+pub const TIMER_ABSTIME: ::c_int = 1;
+
+pub const RUSAGE_SELF: ::c_int = 0;
+
+pub const O_RDONLY: ::c_int = 0;
+pub const O_WRONLY: ::c_int = 1;
+pub const O_RDWR: ::c_int = 2;
+
+pub const SOCK_CLOEXEC: ::c_int = O_CLOEXEC;
+
+pub const S_IFIFO: ::mode_t = 4096;
+pub const S_IFCHR: ::mode_t = 8192;
+pub const S_IFBLK: ::mode_t = 24576;
+pub const S_IFDIR: ::mode_t = 16384;
+pub const S_IFREG: ::mode_t = 32768;
+pub const S_IFLNK: ::mode_t = 40960;
+pub const S_IFSOCK: ::mode_t = 49152;
+pub const S_IFMT: ::mode_t = 61440;
+pub const S_IRWXU: ::mode_t = 448;
+pub const S_IXUSR: ::mode_t = 64;
+pub const S_IWUSR: ::mode_t = 128;
+pub const S_IRUSR: ::mode_t = 256;
+pub const S_IRWXG: ::mode_t = 56;
+pub const S_IXGRP: ::mode_t = 8;
+pub const S_IWGRP: ::mode_t = 16;
+pub const S_IRGRP: ::mode_t = 32;
+pub const S_IRWXO: ::mode_t = 7;
+pub const S_IXOTH: ::mode_t = 1;
+pub const S_IWOTH: ::mode_t = 2;
+pub const S_IROTH: ::mode_t = 4;
+pub const F_OK: ::c_int = 0;
+pub const R_OK: ::c_int = 4;
+pub const W_OK: ::c_int = 2;
+pub const X_OK: ::c_int = 1;
+pub const STDIN_FILENO: ::c_int = 0;
+pub const STDOUT_FILENO: ::c_int = 1;
+pub const STDERR_FILENO: ::c_int = 2;
+pub const SIGHUP: ::c_int = 1;
+pub const SIGINT: ::c_int = 2;
+pub const SIGQUIT: ::c_int = 3;
+pub const SIGILL: ::c_int = 4;
+pub const SIGABRT: ::c_int = 6;
+pub const SIGFPE: ::c_int = 8;
+pub const SIGKILL: ::c_int = 9;
+pub const SIGSEGV: ::c_int = 11;
+pub const SIGPIPE: ::c_int = 13;
+pub const SIGALRM: ::c_int = 14;
+pub const SIGTERM: ::c_int = 15;
+
+pub const PROT_NONE: ::c_int = 0;
+pub const PROT_READ: ::c_int = 1;
+pub const PROT_WRITE: ::c_int = 2;
+pub const PROT_EXEC: ::c_int = 4;
+
+pub const XATTR_CREATE: ::c_int = 0x1;
+pub const XATTR_REPLACE: ::c_int = 0x2;
+
+cfg_if! {
+    if #[cfg(not(target_env = "uclibc"))] {
+        pub const LC_CTYPE: ::c_int = 0;
+        pub const LC_NUMERIC: ::c_int = 1;
+        pub const LC_TIME: ::c_int = 2;
+        pub const LC_COLLATE: ::c_int = 3;
+        pub const LC_MONETARY: ::c_int = 4;
+        pub const LC_MESSAGES: ::c_int = 5;
+        pub const LC_ALL: ::c_int = 6;
+    }
+}
+
+pub const LC_CTYPE_MASK: ::c_int = 1 << LC_CTYPE;
+pub const LC_NUMERIC_MASK: ::c_int = 1 << LC_NUMERIC;
+pub const LC_TIME_MASK: ::c_int = 1 << LC_TIME;
+pub const LC_COLLATE_MASK: ::c_int = 1 << LC_COLLATE;
+pub const LC_MONETARY_MASK: ::c_int = 1 << LC_MONETARY;
+pub const LC_MESSAGES_MASK: ::c_int = 1 << LC_MESSAGES;
+// LC_ALL_MASK defined per platform
+
+pub const MAP_FILE: ::c_int = 0x0000;
+pub const MAP_SHARED: ::c_int = 0x0001;
+pub const MAP_PRIVATE: ::c_int = 0x0002;
+pub const MAP_FIXED: ::c_int = 0x0010;
+
+pub const MAP_FAILED: *mut ::c_void = !0 as *mut ::c_void;
+
+// MS_ flags for msync(2)
+pub const MS_ASYNC: ::c_int = 0x0001;
+pub const MS_INVALIDATE: ::c_int = 0x0002;
+pub const MS_SYNC: ::c_int = 0x0004;
+
+// MS_ flags for mount(2)
+pub const MS_RDONLY: ::c_ulong = 0x01;
+pub const MS_NOSUID: ::c_ulong = 0x02;
+pub const MS_NODEV: ::c_ulong = 0x04;
+pub const MS_NOEXEC: ::c_ulong = 0x08;
+pub const MS_SYNCHRONOUS: ::c_ulong = 0x10;
+pub const MS_REMOUNT: ::c_ulong = 0x20;
+pub const MS_MANDLOCK: ::c_ulong = 0x40;
+pub const MS_DIRSYNC: ::c_ulong = 0x80;
+pub const MS_NOATIME: ::c_ulong = 0x0400;
+pub const MS_NODIRATIME: ::c_ulong = 0x0800;
+pub const MS_BIND: ::c_ulong = 0x1000;
+pub const MS_MOVE: ::c_ulong = 0x2000;
+pub const MS_REC: ::c_ulong = 0x4000;
+pub const MS_SILENT: ::c_ulong = 0x8000;
+pub const MS_POSIXACL: ::c_ulong = 0x010000;
+pub const MS_UNBINDABLE: ::c_ulong = 0x020000;
+pub const MS_PRIVATE: ::c_ulong = 0x040000;
+pub const MS_SLAVE: ::c_ulong = 0x080000;
+pub const MS_SHARED: ::c_ulong = 0x100000;
+pub const MS_RELATIME: ::c_ulong = 0x200000;
+pub const MS_KERNMOUNT: ::c_ulong = 0x400000;
+pub const MS_I_VERSION: ::c_ulong = 0x800000;
+pub const MS_STRICTATIME: ::c_ulong = 0x1000000;
+pub const MS_LAZYTIME: ::c_ulong = 0x2000000;
+pub const MS_ACTIVE: ::c_ulong = 0x40000000;
+pub const MS_MGC_VAL: ::c_ulong = 0xc0ed0000;
+pub const MS_MGC_MSK: ::c_ulong = 0xffff0000;
+
+pub const SCM_RIGHTS: ::c_int = 0x01;
+pub const SCM_CREDENTIALS: ::c_int = 0x02;
+
+pub const PROT_GROWSDOWN: ::c_int = 0x1000000;
+pub const PROT_GROWSUP: ::c_int = 0x2000000;
+
+pub const MAP_TYPE: ::c_int = 0x000f;
+
+pub const MADV_NORMAL: ::c_int = 0;
+pub const MADV_RANDOM: ::c_int = 1;
+pub const MADV_SEQUENTIAL: ::c_int = 2;
+pub const MADV_WILLNEED: ::c_int = 3;
+pub const MADV_DONTNEED: ::c_int = 4;
+pub const MADV_FREE: ::c_int = 8;
+pub const MADV_REMOVE: ::c_int = 9;
+pub const MADV_DONTFORK: ::c_int = 10;
+pub const MADV_DOFORK: ::c_int = 11;
+pub const MADV_MERGEABLE: ::c_int = 12;
+pub const MADV_UNMERGEABLE: ::c_int = 13;
+pub const MADV_HUGEPAGE: ::c_int = 14;
+pub const MADV_NOHUGEPAGE: ::c_int = 15;
+pub const MADV_DONTDUMP: ::c_int = 16;
+pub const MADV_DODUMP: ::c_int = 17;
+pub const MADV_HWPOISON: ::c_int = 100;
+
+pub const IFF_UP: ::c_int = 0x1;
+pub const IFF_BROADCAST: ::c_int = 0x2;
+pub const IFF_DEBUG: ::c_int = 0x4;
+pub const IFF_LOOPBACK: ::c_int = 0x8;
+pub const IFF_POINTOPOINT: ::c_int = 0x10;
+pub const IFF_NOTRAILERS: ::c_int = 0x20;
+pub const IFF_RUNNING: ::c_int = 0x40;
+pub const IFF_NOARP: ::c_int = 0x80;
+pub const IFF_PROMISC: ::c_int = 0x100;
+pub const IFF_ALLMULTI: ::c_int = 0x200;
+pub const IFF_MASTER: ::c_int = 0x400;
+pub const IFF_SLAVE: ::c_int = 0x800;
+pub const IFF_MULTICAST: ::c_int = 0x1000;
+pub const IFF_PORTSEL: ::c_int = 0x2000;
+pub const IFF_AUTOMEDIA: ::c_int = 0x4000;
+pub const IFF_DYNAMIC: ::c_int = 0x8000;
+
+pub const SOL_IP: ::c_int = 0;
+pub const SOL_TCP: ::c_int = 6;
+pub const SOL_UDP: ::c_int = 17;
+pub const SOL_IPV6: ::c_int = 41;
+pub const SOL_ICMPV6: ::c_int = 58;
+pub const SOL_RAW: ::c_int = 255;
+pub const SOL_DECNET: ::c_int = 261;
+pub const SOL_X25: ::c_int = 262;
+pub const SOL_PACKET: ::c_int = 263;
+pub const SOL_ATM: ::c_int = 264;
+pub const SOL_AAL: ::c_int = 265;
+pub const SOL_IRDA: ::c_int = 266;
+pub const SOL_NETBEUI: ::c_int = 267;
+pub const SOL_LLC: ::c_int = 268;
+pub const SOL_DCCP: ::c_int = 269;
+pub const SOL_NETLINK: ::c_int = 270;
+pub const SOL_TIPC: ::c_int = 271;
+pub const SOL_BLUETOOTH: ::c_int = 274;
+pub const SOL_ALG: ::c_int = 279;
+
+pub const AF_UNSPEC: ::c_int = 0;
+pub const AF_UNIX: ::c_int = 1;
+pub const AF_LOCAL: ::c_int = 1;
+pub const AF_INET: ::c_int = 2;
+pub const AF_AX25: ::c_int = 3;
+pub const AF_IPX: ::c_int = 4;
+pub const AF_APPLETALK: ::c_int = 5;
+pub const AF_NETROM: ::c_int = 6;
+pub const AF_BRIDGE: ::c_int = 7;
+pub const AF_ATMPVC: ::c_int = 8;
+pub const AF_X25: ::c_int = 9;
+pub const AF_INET6: ::c_int = 10;
+pub const AF_ROSE: ::c_int = 11;
+pub const AF_DECnet: ::c_int = 12;
+pub const AF_NETBEUI: ::c_int = 13;
+pub const AF_SECURITY: ::c_int = 14;
+pub const AF_KEY: ::c_int = 15;
+pub const AF_NETLINK: ::c_int = 16;
+pub const AF_ROUTE: ::c_int = AF_NETLINK;
+pub const AF_PACKET: ::c_int = 17;
+pub const AF_ASH: ::c_int = 18;
+pub const AF_ECONET: ::c_int = 19;
+pub const AF_ATMSVC: ::c_int = 20;
+pub const AF_RDS: ::c_int = 21;
+pub const AF_SNA: ::c_int = 22;
+pub const AF_IRDA: ::c_int = 23;
+pub const AF_PPPOX: ::c_int = 24;
+pub const AF_WANPIPE: ::c_int = 25;
+pub const AF_LLC: ::c_int = 26;
+pub const AF_CAN: ::c_int = 29;
+pub const AF_TIPC: ::c_int = 30;
+pub const AF_BLUETOOTH: ::c_int = 31;
+pub const AF_IUCV: ::c_int = 32;
+pub const AF_RXRPC: ::c_int = 33;
+pub const AF_ISDN: ::c_int = 34;
+pub const AF_PHONET: ::c_int = 35;
+pub const AF_IEEE802154: ::c_int = 36;
+pub const AF_CAIF: ::c_int = 37;
+pub const AF_ALG: ::c_int = 38;
+
+pub const PF_UNSPEC: ::c_int = AF_UNSPEC;
+pub const PF_UNIX: ::c_int = AF_UNIX;
+pub const PF_LOCAL: ::c_int = AF_LOCAL;
+pub const PF_INET: ::c_int = AF_INET;
+pub const PF_AX25: ::c_int = AF_AX25;
+pub const PF_IPX: ::c_int = AF_IPX;
+pub const PF_APPLETALK: ::c_int = AF_APPLETALK;
+pub const PF_NETROM: ::c_int = AF_NETROM;
+pub const PF_BRIDGE: ::c_int = AF_BRIDGE;
+pub const PF_ATMPVC: ::c_int = AF_ATMPVC;
+pub const PF_X25: ::c_int = AF_X25;
+pub const PF_INET6: ::c_int = AF_INET6;
+pub const PF_ROSE: ::c_int = AF_ROSE;
+pub const PF_DECnet: ::c_int = AF_DECnet;
+pub const PF_NETBEUI: ::c_int = AF_NETBEUI;
+pub const PF_SECURITY: ::c_int = AF_SECURITY;
+pub const PF_KEY: ::c_int = AF_KEY;
+pub const PF_NETLINK: ::c_int = AF_NETLINK;
+pub const PF_ROUTE: ::c_int = AF_ROUTE;
+pub const PF_PACKET: ::c_int = AF_PACKET;
+pub const PF_ASH: ::c_int = AF_ASH;
+pub const PF_ECONET: ::c_int = AF_ECONET;
+pub const PF_ATMSVC: ::c_int = AF_ATMSVC;
+pub const PF_RDS: ::c_int = AF_RDS;
+pub const PF_SNA: ::c_int = AF_SNA;
+pub const PF_IRDA: ::c_int = AF_IRDA;
+pub const PF_PPPOX: ::c_int = AF_PPPOX;
+pub const PF_WANPIPE: ::c_int = AF_WANPIPE;
+pub const PF_LLC: ::c_int = AF_LLC;
+pub const PF_CAN: ::c_int = AF_CAN;
+pub const PF_TIPC: ::c_int = AF_TIPC;
+pub const PF_BLUETOOTH: ::c_int = AF_BLUETOOTH;
+pub const PF_IUCV: ::c_int = AF_IUCV;
+pub const PF_RXRPC: ::c_int = AF_RXRPC;
+pub const PF_ISDN: ::c_int = AF_ISDN;
+pub const PF_PHONET: ::c_int = AF_PHONET;
+pub const PF_IEEE802154: ::c_int = AF_IEEE802154;
+pub const PF_CAIF: ::c_int = AF_CAIF;
+pub const PF_ALG: ::c_int = AF_ALG;
+
+pub const MSG_OOB: ::c_int = 1;
+pub const MSG_PEEK: ::c_int = 2;
+pub const MSG_DONTROUTE: ::c_int = 4;
+pub const MSG_CTRUNC: ::c_int = 8;
+pub const MSG_TRUNC: ::c_int = 0x20;
+pub const MSG_DONTWAIT: ::c_int = 0x40;
+pub const MSG_EOR: ::c_int = 0x80;
+pub const MSG_WAITALL: ::c_int = 0x100;
+pub const MSG_FIN: ::c_int = 0x200;
+pub const MSG_SYN: ::c_int = 0x400;
+pub const MSG_CONFIRM: ::c_int = 0x800;
+pub const MSG_RST: ::c_int = 0x1000;
+pub const MSG_ERRQUEUE: ::c_int = 0x2000;
+pub const MSG_NOSIGNAL: ::c_int = 0x4000;
+pub const MSG_MORE: ::c_int = 0x8000;
+pub const MSG_WAITFORONE: ::c_int = 0x10000;
+pub const MSG_FASTOPEN: ::c_int = 0x20000000;
+pub const MSG_CMSG_CLOEXEC: ::c_int = 0x40000000;
+
+pub const SCM_TIMESTAMP: ::c_int = SO_TIMESTAMP;
+
+pub const SOCK_RAW: ::c_int = 3;
+pub const SOCK_RDM: ::c_int = 4;
+pub const IP_TOS: ::c_int = 1;
+pub const IP_TTL: ::c_int = 2;
+pub const IP_HDRINCL: ::c_int = 3;
+pub const IP_OPTIONS: ::c_int = 4;
+pub const IP_ROUTER_ALERT: ::c_int = 5;
+pub const IP_RECVOPTS: ::c_int = 6;
+pub const IP_RETOPTS: ::c_int = 7;
+pub const IP_PKTINFO: ::c_int = 8;
+pub const IP_PKTOPTIONS: ::c_int = 9;
+pub const IP_MTU_DISCOVER: ::c_int = 10;
+pub const IP_RECVERR: ::c_int = 11;
+pub const IP_RECVTTL: ::c_int = 12;
+pub const IP_RECVTOS: ::c_int = 13;
+pub const IP_MTU: ::c_int = 14;
+pub const IP_FREEBIND: ::c_int = 15;
+pub const IP_IPSEC_POLICY: ::c_int = 16;
+pub const IP_XFRM_POLICY: ::c_int = 17;
+pub const IP_PASSSEC: ::c_int = 18;
+pub const IP_TRANSPARENT: ::c_int = 19;
+pub const IP_ORIGDSTADDR: ::c_int = 20;
+pub const IP_RECVORIGDSTADDR: ::c_int = IP_ORIGDSTADDR;
+pub const IP_MINTTL: ::c_int = 21;
+pub const IP_NODEFRAG: ::c_int = 22;
+pub const IP_CHECKSUM: ::c_int = 23;
+pub const IP_BIND_ADDRESS_NO_PORT: ::c_int = 24;
+pub const IP_MULTICAST_IF: ::c_int = 32;
+pub const IP_MULTICAST_TTL: ::c_int = 33;
+pub const IP_MULTICAST_LOOP: ::c_int = 34;
+pub const IP_ADD_MEMBERSHIP: ::c_int = 35;
+pub const IP_DROP_MEMBERSHIP: ::c_int = 36;
+pub const IP_UNBLOCK_SOURCE: ::c_int = 37;
+pub const IP_BLOCK_SOURCE: ::c_int = 38;
+pub const IP_ADD_SOURCE_MEMBERSHIP: ::c_int = 39;
+pub const IP_DROP_SOURCE_MEMBERSHIP: ::c_int = 40;
+pub const IP_MSFILTER: ::c_int = 41;
+pub const IP_MULTICAST_ALL: ::c_int = 49;
+pub const IP_UNICAST_IF: ::c_int = 50;
+
+pub const IP_DEFAULT_MULTICAST_TTL: ::c_int = 1;
+pub const IP_DEFAULT_MULTICAST_LOOP: ::c_int = 1;
+
+pub const IP_PMTUDISC_DONT: ::c_int = 0;
+pub const IP_PMTUDISC_WANT: ::c_int = 1;
+pub const IP_PMTUDISC_DO: ::c_int = 2;
+pub const IP_PMTUDISC_PROBE: ::c_int = 3;
+pub const IP_PMTUDISC_INTERFACE: ::c_int = 4;
+pub const IP_PMTUDISC_OMIT: ::c_int = 5;
+
+// IPPROTO_IP defined in src/unix/mod.rs
+/// Hop-by-hop option header
+pub const IPPROTO_HOPOPTS: ::c_int = 0;
+// IPPROTO_ICMP defined in src/unix/mod.rs
+/// group mgmt protocol
+pub const IPPROTO_IGMP: ::c_int = 2;
+/// for compatibility
+pub const IPPROTO_IPIP: ::c_int = 4;
+// IPPROTO_TCP defined in src/unix/mod.rs
+/// exterior gateway protocol
+pub const IPPROTO_EGP: ::c_int = 8;
+/// pup
+pub const IPPROTO_PUP: ::c_int = 12;
+// IPPROTO_UDP defined in src/unix/mod.rs
+/// xns idp
+pub const IPPROTO_IDP: ::c_int = 22;
+/// tp-4 w/ class negotiation
+pub const IPPROTO_TP: ::c_int = 29;
+/// DCCP
+pub const IPPROTO_DCCP: ::c_int = 33;
+// IPPROTO_IPV6 defined in src/unix/mod.rs
+/// IP6 routing header
+pub const IPPROTO_ROUTING: ::c_int = 43;
+/// IP6 fragmentation header
+pub const IPPROTO_FRAGMENT: ::c_int = 44;
+/// resource reservation
+pub const IPPROTO_RSVP: ::c_int = 46;
+/// General Routing Encap.
+pub const IPPROTO_GRE: ::c_int = 47;
+/// IP6 Encap Sec. Payload
+pub const IPPROTO_ESP: ::c_int = 50;
+/// IP6 Auth Header
+pub const IPPROTO_AH: ::c_int = 51;
+// IPPROTO_ICMPV6 defined in src/unix/mod.rs
+/// IP6 no next header
+pub const IPPROTO_NONE: ::c_int = 59;
+/// IP6 destination option
+pub const IPPROTO_DSTOPTS: ::c_int = 60;
+pub const IPPROTO_MTP: ::c_int = 92;
+/// encapsulation header
+pub const IPPROTO_ENCAP: ::c_int = 98;
+/// Protocol indep. multicast
+pub const IPPROTO_PIM: ::c_int = 103;
+/// IP Payload Comp. Protocol
+pub const IPPROTO_COMP: ::c_int = 108;
+/// SCTP
+pub const IPPROTO_SCTP: ::c_int = 132;
+pub const IPPROTO_MH: ::c_int = 135;
+pub const IPPROTO_UDPLITE: ::c_int = 136;
+/// raw IP packet
+pub const IPPROTO_RAW: ::c_int = 255;
+pub const IPPROTO_BEETPH: ::c_int = 94;
+pub const IPPROTO_MPLS: ::c_int = 137;
+
+pub const MCAST_EXCLUDE: ::c_int = 0;
+pub const MCAST_INCLUDE: ::c_int = 1;
+pub const MCAST_JOIN_GROUP: ::c_int = 42;
+pub const MCAST_BLOCK_SOURCE: ::c_int = 43;
+pub const MCAST_UNBLOCK_SOURCE: ::c_int = 44;
+pub const MCAST_LEAVE_GROUP: ::c_int = 45;
+pub const MCAST_JOIN_SOURCE_GROUP: ::c_int = 46;
+pub const MCAST_LEAVE_SOURCE_GROUP: ::c_int = 47;
+pub const MCAST_MSFILTER: ::c_int = 48;
+
+pub const IPV6_ADDRFORM: ::c_int = 1;
+pub const IPV6_2292PKTINFO: ::c_int = 2;
+pub const IPV6_2292HOPOPTS: ::c_int = 3;
+pub const IPV6_2292DSTOPTS: ::c_int = 4;
+pub const IPV6_2292RTHDR: ::c_int = 5;
+pub const IPV6_2292PKTOPTIONS: ::c_int = 6;
+pub const IPV6_CHECKSUM: ::c_int = 7;
+pub const IPV6_2292HOPLIMIT: ::c_int = 8;
+pub const IPV6_NEXTHOP: ::c_int = 9;
+pub const IPV6_AUTHHDR: ::c_int = 10;
+pub const IPV6_UNICAST_HOPS: ::c_int = 16;
+pub const IPV6_MULTICAST_IF: ::c_int = 17;
+pub const IPV6_MULTICAST_HOPS: ::c_int = 18;
+pub const IPV6_MULTICAST_LOOP: ::c_int = 19;
+pub const IPV6_ADD_MEMBERSHIP: ::c_int = 20;
+pub const IPV6_DROP_MEMBERSHIP: ::c_int = 21;
+pub const IPV6_ROUTER_ALERT: ::c_int = 22;
+pub const IPV6_MTU_DISCOVER: ::c_int = 23;
+pub const IPV6_MTU: ::c_int = 24;
+pub const IPV6_RECVERR: ::c_int = 25;
+pub const IPV6_V6ONLY: ::c_int = 26;
+pub const IPV6_JOIN_ANYCAST: ::c_int = 27;
+pub const IPV6_LEAVE_ANYCAST: ::c_int = 28;
+pub const IPV6_IPSEC_POLICY: ::c_int = 34;
+pub const IPV6_XFRM_POLICY: ::c_int = 35;
+pub const IPV6_HDRINCL: ::c_int = 36;
+pub const IPV6_RECVPKTINFO: ::c_int = 49;
+pub const IPV6_PKTINFO: ::c_int = 50;
+pub const IPV6_RECVHOPLIMIT: ::c_int = 51;
+pub const IPV6_HOPLIMIT: ::c_int = 52;
+pub const IPV6_RECVHOPOPTS: ::c_int = 53;
+pub const IPV6_HOPOPTS: ::c_int = 54;
+pub const IPV6_RTHDRDSTOPTS: ::c_int = 55;
+pub const IPV6_RECVRTHDR: ::c_int = 56;
+pub const IPV6_RTHDR: ::c_int = 57;
+pub const IPV6_RECVDSTOPTS: ::c_int = 58;
+pub const IPV6_DSTOPTS: ::c_int = 59;
+pub const IPV6_RECVPATHMTU: ::c_int = 60;
+pub const IPV6_PATHMTU: ::c_int = 61;
+pub const IPV6_DONTFRAG: ::c_int = 62;
+pub const IPV6_RECVTCLASS: ::c_int = 66;
+pub const IPV6_TCLASS: ::c_int = 67;
+pub const IPV6_AUTOFLOWLABEL: ::c_int = 70;
+pub const IPV6_ADDR_PREFERENCES: ::c_int = 72;
+pub const IPV6_MINHOPCOUNT: ::c_int = 73;
+pub const IPV6_ORIGDSTADDR: ::c_int = 74;
+pub const IPV6_RECVORIGDSTADDR: ::c_int = IPV6_ORIGDSTADDR;
+pub const IPV6_TRANSPARENT: ::c_int = 75;
+pub const IPV6_UNICAST_IF: ::c_int = 76;
+pub const IPV6_PREFER_SRC_TMP: ::c_int = 0x0001;
+pub const IPV6_PREFER_SRC_PUBLIC: ::c_int = 0x0002;
+pub const IPV6_PREFER_SRC_PUBTMP_DEFAULT: ::c_int = 0x0100;
+pub const IPV6_PREFER_SRC_COA: ::c_int = 0x0004;
+pub const IPV6_PREFER_SRC_HOME: ::c_int = 0x0400;
+pub const IPV6_PREFER_SRC_CGA: ::c_int = 0x0008;
+pub const IPV6_PREFER_SRC_NONCGA: ::c_int = 0x0800;
+
+pub const IPV6_PMTUDISC_DONT: ::c_int = 0;
+pub const IPV6_PMTUDISC_WANT: ::c_int = 1;
+pub const IPV6_PMTUDISC_DO: ::c_int = 2;
+pub const IPV6_PMTUDISC_PROBE: ::c_int = 3;
+pub const IPV6_PMTUDISC_INTERFACE: ::c_int = 4;
+pub const IPV6_PMTUDISC_OMIT: ::c_int = 5;
+
+pub const TCP_NODELAY: ::c_int = 1;
+pub const TCP_MAXSEG: ::c_int = 2;
+pub const TCP_CORK: ::c_int = 3;
+pub const TCP_KEEPIDLE: ::c_int = 4;
+pub const TCP_KEEPINTVL: ::c_int = 5;
+pub const TCP_KEEPCNT: ::c_int = 6;
+pub const TCP_SYNCNT: ::c_int = 7;
+pub const TCP_LINGER2: ::c_int = 8;
+pub const TCP_DEFER_ACCEPT: ::c_int = 9;
+pub const TCP_WINDOW_CLAMP: ::c_int = 10;
+pub const TCP_INFO: ::c_int = 11;
+pub const TCP_QUICKACK: ::c_int = 12;
+pub const TCP_CONGESTION: ::c_int = 13;
+pub const TCP_MD5SIG: ::c_int = 14;
+cfg_if! {
+    if #[cfg(all(target_os = "linux", any(target_env = "gnu", target_env = "musl")))] {
+        // WARN: deprecated
+        pub const TCP_COOKIE_TRANSACTIONS: ::c_int = 15;
+    }
+}
+pub const TCP_THIN_LINEAR_TIMEOUTS: ::c_int = 16;
+pub const TCP_THIN_DUPACK: ::c_int = 17;
+pub const TCP_USER_TIMEOUT: ::c_int = 18;
+pub const TCP_REPAIR: ::c_int = 19;
+pub const TCP_REPAIR_QUEUE: ::c_int = 20;
+pub const TCP_QUEUE_SEQ: ::c_int = 21;
+pub const TCP_REPAIR_OPTIONS: ::c_int = 22;
+pub const TCP_FASTOPEN: ::c_int = 23;
+pub const TCP_TIMESTAMP: ::c_int = 24;
+pub const TCP_NOTSENT_LOWAT: ::c_int = 25;
+pub const TCP_CC_INFO: ::c_int = 26;
+pub const TCP_SAVE_SYN: ::c_int = 27;
+pub const TCP_SAVED_SYN: ::c_int = 28;
+cfg_if! {
+    if #[cfg(not(target_os = "emscripten"))] {
+        // NOTE: emscripten doesn't support these options yet.
+
+        pub const TCP_REPAIR_WINDOW: ::c_int = 29;
+        pub const TCP_FASTOPEN_CONNECT: ::c_int = 30;
+        pub const TCP_ULP: ::c_int = 31;
+        pub const TCP_MD5SIG_EXT: ::c_int = 32;
+        pub const TCP_FASTOPEN_KEY: ::c_int = 33;
+        pub const TCP_FASTOPEN_NO_COOKIE: ::c_int = 34;
+        pub const TCP_ZEROCOPY_RECEIVE: ::c_int = 35;
+        pub const TCP_INQ: ::c_int = 36;
+        pub const TCP_CM_INQ: ::c_int = TCP_INQ;
+        // NOTE: Some CI images doesn't have this option yet.
+        // pub const TCP_TX_DELAY: ::c_int = 37;
+    }
+}
+
+pub const SO_DEBUG: ::c_int = 1;
+
+pub const SHUT_RD: ::c_int = 0;
+pub const SHUT_WR: ::c_int = 1;
+pub const SHUT_RDWR: ::c_int = 2;
+
+pub const LOCK_SH: ::c_int = 1;
+pub const LOCK_EX: ::c_int = 2;
+pub const LOCK_NB: ::c_int = 4;
+pub const LOCK_UN: ::c_int = 8;
+
+pub const SS_ONSTACK: ::c_int = 1;
+pub const SS_DISABLE: ::c_int = 2;
+
+pub const PATH_MAX: ::c_int = 4096;
+
+pub const UIO_MAXIOV: ::c_int = 1024;
+
+pub const FD_SETSIZE: usize = 1024;
+
+pub const EPOLLIN: ::c_int = 0x1;
+pub const EPOLLPRI: ::c_int = 0x2;
+pub const EPOLLOUT: ::c_int = 0x4;
+pub const EPOLLERR: ::c_int = 0x8;
+pub const EPOLLHUP: ::c_int = 0x10;
+pub const EPOLLRDNORM: ::c_int = 0x40;
+pub const EPOLLRDBAND: ::c_int = 0x80;
+pub const EPOLLWRNORM: ::c_int = 0x100;
+pub const EPOLLWRBAND: ::c_int = 0x200;
+pub const EPOLLMSG: ::c_int = 0x400;
+pub const EPOLLRDHUP: ::c_int = 0x2000;
+pub const EPOLLEXCLUSIVE: ::c_int = 0x10000000;
+pub const EPOLLWAKEUP: ::c_int = 0x20000000;
+pub const EPOLLONESHOT: ::c_int = 0x40000000;
+pub const EPOLLET: ::c_int = 0x80000000;
+
+pub const EPOLL_CTL_ADD: ::c_int = 1;
+pub const EPOLL_CTL_MOD: ::c_int = 3;
+pub const EPOLL_CTL_DEL: ::c_int = 2;
+
+pub const MNT_FORCE: ::c_int = 0x1;
+pub const MNT_DETACH: ::c_int = 0x2;
+pub const MNT_EXPIRE: ::c_int = 0x4;
+pub const UMOUNT_NOFOLLOW: ::c_int = 0x8;
+
+pub const Q_GETFMT: ::c_int = 0x800004;
+pub const Q_GETINFO: ::c_int = 0x800005;
+pub const Q_SETINFO: ::c_int = 0x800006;
+pub const QIF_BLIMITS: u32 = 1;
+pub const QIF_SPACE: u32 = 2;
+pub const QIF_ILIMITS: u32 = 4;
+pub const QIF_INODES: u32 = 8;
+pub const QIF_BTIME: u32 = 16;
+pub const QIF_ITIME: u32 = 32;
+pub const QIF_LIMITS: u32 = 5;
+pub const QIF_USAGE: u32 = 10;
+pub const QIF_TIMES: u32 = 48;
+pub const QIF_ALL: u32 = 63;
+
+pub const Q_SYNC: ::c_int = 0x800001;
+pub const Q_QUOTAON: ::c_int = 0x800002;
+pub const Q_QUOTAOFF: ::c_int = 0x800003;
+pub const Q_GETQUOTA: ::c_int = 0x800007;
+pub const Q_SETQUOTA: ::c_int = 0x800008;
+
+pub const TCIOFF: ::c_int = 2;
+pub const TCION: ::c_int = 3;
+pub const TCOOFF: ::c_int = 0;
+pub const TCOON: ::c_int = 1;
+pub const TCIFLUSH: ::c_int = 0;
+pub const TCOFLUSH: ::c_int = 1;
+pub const TCIOFLUSH: ::c_int = 2;
+pub const NL0: ::tcflag_t = 0x00000000;
+pub const NL1: ::tcflag_t = 0x00000100;
+pub const TAB0: ::tcflag_t = 0x00000000;
+pub const CR0: ::tcflag_t = 0x00000000;
+pub const FF0: ::tcflag_t = 0x00000000;
+pub const BS0: ::tcflag_t = 0x00000000;
+pub const VT0: ::tcflag_t = 0x00000000;
+pub const VERASE: usize = 2;
+pub const VKILL: usize = 3;
+pub const VINTR: usize = 0;
+pub const VQUIT: usize = 1;
+pub const VLNEXT: usize = 15;
+pub const IGNBRK: ::tcflag_t = 0x00000001;
+pub const BRKINT: ::tcflag_t = 0x00000002;
+pub const IGNPAR: ::tcflag_t = 0x00000004;
+pub const PARMRK: ::tcflag_t = 0x00000008;
+pub const INPCK: ::tcflag_t = 0x00000010;
+pub const ISTRIP: ::tcflag_t = 0x00000020;
+pub const INLCR: ::tcflag_t = 0x00000040;
+pub const IGNCR: ::tcflag_t = 0x00000080;
+pub const ICRNL: ::tcflag_t = 0x00000100;
+pub const IXANY: ::tcflag_t = 0x00000800;
+pub const IMAXBEL: ::tcflag_t = 0x00002000;
+pub const OPOST: ::tcflag_t = 0x1;
+pub const CS5: ::tcflag_t = 0x00000000;
+pub const CRTSCTS: ::tcflag_t = 0x80000000;
+pub const ECHO: ::tcflag_t = 0x00000008;
+pub const OCRNL: ::tcflag_t = 0o000010;
+pub const ONOCR: ::tcflag_t = 0o000020;
+pub const ONLRET: ::tcflag_t = 0o000040;
+pub const OFILL: ::tcflag_t = 0o000100;
+pub const OFDEL: ::tcflag_t = 0o000200;
+
+pub const CLONE_VM: ::c_int = 0x100;
+pub const CLONE_FS: ::c_int = 0x200;
+pub const CLONE_FILES: ::c_int = 0x400;
+pub const CLONE_SIGHAND: ::c_int = 0x800;
+pub const CLONE_PTRACE: ::c_int = 0x2000;
+pub const CLONE_VFORK: ::c_int = 0x4000;
+pub const CLONE_PARENT: ::c_int = 0x8000;
+pub const CLONE_THREAD: ::c_int = 0x10000;
+pub const CLONE_NEWNS: ::c_int = 0x20000;
+pub const CLONE_SYSVSEM: ::c_int = 0x40000;
+pub const CLONE_SETTLS: ::c_int = 0x80000;
+pub const CLONE_PARENT_SETTID: ::c_int = 0x100000;
+pub const CLONE_CHILD_CLEARTID: ::c_int = 0x200000;
+pub const CLONE_DETACHED: ::c_int = 0x400000;
+pub const CLONE_UNTRACED: ::c_int = 0x800000;
+pub const CLONE_CHILD_SETTID: ::c_int = 0x01000000;
+pub const CLONE_NEWCGROUP: ::c_int = 0x02000000;
+pub const CLONE_NEWUTS: ::c_int = 0x04000000;
+pub const CLONE_NEWIPC: ::c_int = 0x08000000;
+pub const CLONE_NEWUSER: ::c_int = 0x10000000;
+pub const CLONE_NEWPID: ::c_int = 0x20000000;
+pub const CLONE_NEWNET: ::c_int = 0x40000000;
+pub const CLONE_IO: ::c_int = 0x80000000;
+
+pub const WNOHANG: ::c_int = 0x00000001;
+pub const WUNTRACED: ::c_int = 0x00000002;
+pub const WSTOPPED: ::c_int = WUNTRACED;
+pub const WEXITED: ::c_int = 0x00000004;
+pub const WCONTINUED: ::c_int = 0x00000008;
+pub const WNOWAIT: ::c_int = 0x01000000;
+
+// Options for personality(2).
+pub const ADDR_NO_RANDOMIZE: ::c_int = 0x0040000;
+pub const MMAP_PAGE_ZERO: ::c_int = 0x0100000;
+pub const ADDR_COMPAT_LAYOUT: ::c_int = 0x0200000;
+pub const READ_IMPLIES_EXEC: ::c_int = 0x0400000;
+pub const ADDR_LIMIT_32BIT: ::c_int = 0x0800000;
+pub const SHORT_INODE: ::c_int = 0x1000000;
+pub const WHOLE_SECONDS: ::c_int = 0x2000000;
+pub const STICKY_TIMEOUTS: ::c_int = 0x4000000;
+pub const ADDR_LIMIT_3GB: ::c_int = 0x8000000;
+
+// Options set using PTRACE_SETOPTIONS.
+pub const PTRACE_O_TRACESYSGOOD: ::c_int = 0x00000001;
+pub const PTRACE_O_TRACEFORK: ::c_int = 0x00000002;
+pub const PTRACE_O_TRACEVFORK: ::c_int = 0x00000004;
+pub const PTRACE_O_TRACECLONE: ::c_int = 0x00000008;
+pub const PTRACE_O_TRACEEXEC: ::c_int = 0x00000010;
+pub const PTRACE_O_TRACEVFORKDONE: ::c_int = 0x00000020;
+pub const PTRACE_O_TRACEEXIT: ::c_int = 0x00000040;
+pub const PTRACE_O_TRACESECCOMP: ::c_int = 0x00000080;
+pub const PTRACE_O_SUSPEND_SECCOMP: ::c_int = 0x00200000;
+pub const PTRACE_O_EXITKILL: ::c_int = 0x00100000;
+pub const PTRACE_O_MASK: ::c_int = 0x003000ff;
+
+// Wait extended result codes for the above trace options.
+pub const PTRACE_EVENT_FORK: ::c_int = 1;
+pub const PTRACE_EVENT_VFORK: ::c_int = 2;
+pub const PTRACE_EVENT_CLONE: ::c_int = 3;
+pub const PTRACE_EVENT_EXEC: ::c_int = 4;
+pub const PTRACE_EVENT_VFORK_DONE: ::c_int = 5;
+pub const PTRACE_EVENT_EXIT: ::c_int = 6;
+pub const PTRACE_EVENT_SECCOMP: ::c_int = 7;
+
+pub const __WNOTHREAD: ::c_int = 0x20000000;
+pub const __WALL: ::c_int = 0x40000000;
+pub const __WCLONE: ::c_int = 0x80000000;
+
+pub const SPLICE_F_MOVE: ::c_uint = 0x01;
+pub const SPLICE_F_NONBLOCK: ::c_uint = 0x02;
+pub const SPLICE_F_MORE: ::c_uint = 0x04;
+pub const SPLICE_F_GIFT: ::c_uint = 0x08;
+
+pub const RTLD_LOCAL: ::c_int = 0;
+pub const RTLD_LAZY: ::c_int = 1;
+
+pub const POSIX_FADV_NORMAL: ::c_int = 0;
+pub const POSIX_FADV_RANDOM: ::c_int = 1;
+pub const POSIX_FADV_SEQUENTIAL: ::c_int = 2;
+pub const POSIX_FADV_WILLNEED: ::c_int = 3;
+
+pub const AT_FDCWD: ::c_int = -100;
+pub const AT_SYMLINK_NOFOLLOW: ::c_int = 0x100;
+pub const AT_REMOVEDIR: ::c_int = 0x200;
+pub const AT_SYMLINK_FOLLOW: ::c_int = 0x400;
+pub const AT_NO_AUTOMOUNT: ::c_int = 0x800;
+pub const AT_EMPTY_PATH: ::c_int = 0x1000;
+
+pub const LOG_CRON: ::c_int = 9 << 3;
+pub const LOG_AUTHPRIV: ::c_int = 10 << 3;
+pub const LOG_FTP: ::c_int = 11 << 3;
+pub const LOG_PERROR: ::c_int = 0x20;
+
+pub const PIPE_BUF: usize = 4096;
+
+pub const SI_LOAD_SHIFT: ::c_uint = 16;
+
+// si_code values for SIGBUS signal
+pub const BUS_ADRALN: ::c_int = 1;
+pub const BUS_ADRERR: ::c_int = 2;
+pub const BUS_OBJERR: ::c_int = 3;
+// Linux-specific si_code values for SIGBUS signal
+pub const BUS_MCEERR_AR: ::c_int = 4;
+pub const BUS_MCEERR_AO: ::c_int = 5;
+
+// si_code values for SIGCHLD signal
+pub const CLD_EXITED: ::c_int = 1;
+pub const CLD_KILLED: ::c_int = 2;
+pub const CLD_DUMPED: ::c_int = 3;
+pub const CLD_TRAPPED: ::c_int = 4;
+pub const CLD_STOPPED: ::c_int = 5;
+pub const CLD_CONTINUED: ::c_int = 6;
+
+pub const SIGEV_SIGNAL: ::c_int = 0;
+pub const SIGEV_NONE: ::c_int = 1;
+pub const SIGEV_THREAD: ::c_int = 2;
+
+pub const P_ALL: idtype_t = 0;
+pub const P_PID: idtype_t = 1;
+pub const P_PGID: idtype_t = 2;
+cfg_if! {
+    if #[cfg(not(target_os = "emscripten"))] {
+        pub const P_PIDFD: idtype_t = 3;
+    }
+}
+
+pub const UTIME_OMIT: c_long = 1073741822;
+pub const UTIME_NOW: c_long = 1073741823;
+
+pub const POLLIN: ::c_short = 0x1;
+pub const POLLPRI: ::c_short = 0x2;
+pub const POLLOUT: ::c_short = 0x4;
+pub const POLLERR: ::c_short = 0x8;
+pub const POLLHUP: ::c_short = 0x10;
+pub const POLLNVAL: ::c_short = 0x20;
+pub const POLLRDNORM: ::c_short = 0x040;
+pub const POLLRDBAND: ::c_short = 0x080;
+#[cfg(not(any(target_arch = "sparc", target_arch = "sparc64")))]
+pub const POLLRDHUP: ::c_short = 0x2000;
+#[cfg(any(target_arch = "sparc", target_arch = "sparc64"))]
+pub const POLLRDHUP: ::c_short = 0x800;
+
+pub const IPTOS_LOWDELAY: u8 = 0x10;
+pub const IPTOS_THROUGHPUT: u8 = 0x08;
+pub const IPTOS_RELIABILITY: u8 = 0x04;
+pub const IPTOS_MINCOST: u8 = 0x02;
+
+pub const IPTOS_PREC_NETCONTROL: u8 = 0xe0;
+pub const IPTOS_PREC_INTERNETCONTROL: u8 = 0xc0;
+pub const IPTOS_PREC_CRITIC_ECP: u8 = 0xa0;
+pub const IPTOS_PREC_FLASHOVERRIDE: u8 = 0x80;
+pub const IPTOS_PREC_FLASH: u8 = 0x60;
+pub const IPTOS_PREC_IMMEDIATE: u8 = 0x40;
+pub const IPTOS_PREC_PRIORITY: u8 = 0x20;
+pub const IPTOS_PREC_ROUTINE: u8 = 0x00;
+
+pub const IPTOS_ECN_MASK: u8 = 0x03;
+pub const IPTOS_ECN_ECT1: u8 = 0x01;
+pub const IPTOS_ECN_ECT0: u8 = 0x02;
+pub const IPTOS_ECN_CE: u8 = 0x03;
+
+pub const IPOPT_COPY: u8 = 0x80;
+pub const IPOPT_CLASS_MASK: u8 = 0x60;
+pub const IPOPT_NUMBER_MASK: u8 = 0x1f;
+
+pub const IPOPT_CONTROL: u8 = 0x00;
+pub const IPOPT_RESERVED1: u8 = 0x20;
+pub const IPOPT_MEASUREMENT: u8 = 0x40;
+pub const IPOPT_RESERVED2: u8 = 0x60;
+pub const IPOPT_END: u8 = 0 | IPOPT_CONTROL;
+pub const IPOPT_NOOP: u8 = 1 | IPOPT_CONTROL;
+pub const IPOPT_SEC: u8 = 2 | IPOPT_CONTROL | IPOPT_COPY;
+pub const IPOPT_LSRR: u8 = 3 | IPOPT_CONTROL | IPOPT_COPY;
+pub const IPOPT_TIMESTAMP: u8 = 4 | IPOPT_MEASUREMENT;
+pub const IPOPT_RR: u8 = 7 | IPOPT_CONTROL;
+pub const IPOPT_SID: u8 = 8 | IPOPT_CONTROL | IPOPT_COPY;
+pub const IPOPT_SSRR: u8 = 9 | IPOPT_CONTROL | IPOPT_COPY;
+pub const IPOPT_RA: u8 = 20 | IPOPT_CONTROL | IPOPT_COPY;
+pub const IPVERSION: u8 = 4;
+pub const MAXTTL: u8 = 255;
+pub const IPDEFTTL: u8 = 64;
+pub const IPOPT_OPTVAL: u8 = 0;
+pub const IPOPT_OLEN: u8 = 1;
+pub const IPOPT_OFFSET: u8 = 2;
+pub const IPOPT_MINOFF: u8 = 4;
+pub const MAX_IPOPTLEN: u8 = 40;
+pub const IPOPT_NOP: u8 = IPOPT_NOOP;
+pub const IPOPT_EOL: u8 = IPOPT_END;
+pub const IPOPT_TS: u8 = IPOPT_TIMESTAMP;
+pub const IPOPT_TS_TSONLY: u8 = 0;
+pub const IPOPT_TS_TSANDADDR: u8 = 1;
+pub const IPOPT_TS_PRESPEC: u8 = 3;
+
+pub const ARPOP_RREQUEST: u16 = 3;
+pub const ARPOP_RREPLY: u16 = 4;
+pub const ARPOP_InREQUEST: u16 = 8;
+pub const ARPOP_InREPLY: u16 = 9;
+pub const ARPOP_NAK: u16 = 10;
+
+pub const ATF_NETMASK: ::c_int = 0x20;
+pub const ATF_DONTPUB: ::c_int = 0x40;
+
+pub const ARPHRD_NETROM: u16 = 0;
+pub const ARPHRD_ETHER: u16 = 1;
+pub const ARPHRD_EETHER: u16 = 2;
+pub const ARPHRD_AX25: u16 = 3;
+pub const ARPHRD_PRONET: u16 = 4;
+pub const ARPHRD_CHAOS: u16 = 5;
+pub const ARPHRD_IEEE802: u16 = 6;
+pub const ARPHRD_ARCNET: u16 = 7;
+pub const ARPHRD_APPLETLK: u16 = 8;
+pub const ARPHRD_DLCI: u16 = 15;
+pub const ARPHRD_ATM: u16 = 19;
+pub const ARPHRD_METRICOM: u16 = 23;
+pub const ARPHRD_IEEE1394: u16 = 24;
+pub const ARPHRD_EUI64: u16 = 27;
+pub const ARPHRD_INFINIBAND: u16 = 32;
+
+pub const ARPHRD_SLIP: u16 = 256;
+pub const ARPHRD_CSLIP: u16 = 257;
+pub const ARPHRD_SLIP6: u16 = 258;
+pub const ARPHRD_CSLIP6: u16 = 259;
+pub const ARPHRD_RSRVD: u16 = 260;
+pub const ARPHRD_ADAPT: u16 = 264;
+pub const ARPHRD_ROSE: u16 = 270;
+pub const ARPHRD_X25: u16 = 271;
+pub const ARPHRD_HWX25: u16 = 272;
+pub const ARPHRD_CAN: u16 = 280;
+pub const ARPHRD_PPP: u16 = 512;
+pub const ARPHRD_CISCO: u16 = 513;
+pub const ARPHRD_HDLC: u16 = ARPHRD_CISCO;
+pub const ARPHRD_LAPB: u16 = 516;
+pub const ARPHRD_DDCMP: u16 = 517;
+pub const ARPHRD_RAWHDLC: u16 = 518;
+
+pub const ARPHRD_TUNNEL: u16 = 768;
+pub const ARPHRD_TUNNEL6: u16 = 769;
+pub const ARPHRD_FRAD: u16 = 770;
+pub const ARPHRD_SKIP: u16 = 771;
+pub const ARPHRD_LOOPBACK: u16 = 772;
+pub const ARPHRD_LOCALTLK: u16 = 773;
+pub const ARPHRD_FDDI: u16 = 774;
+pub const ARPHRD_BIF: u16 = 775;
+pub const ARPHRD_SIT: u16 = 776;
+pub const ARPHRD_IPDDP: u16 = 777;
+pub const ARPHRD_IPGRE: u16 = 778;
+pub const ARPHRD_PIMREG: u16 = 779;
+pub const ARPHRD_HIPPI: u16 = 780;
+pub const ARPHRD_ASH: u16 = 781;
+pub const ARPHRD_ECONET: u16 = 782;
+pub const ARPHRD_IRDA: u16 = 783;
+pub const ARPHRD_FCPP: u16 = 784;
+pub const ARPHRD_FCAL: u16 = 785;
+pub const ARPHRD_FCPL: u16 = 786;
+pub const ARPHRD_FCFABRIC: u16 = 787;
+pub const ARPHRD_IEEE802_TR: u16 = 800;
+pub const ARPHRD_IEEE80211: u16 = 801;
+pub const ARPHRD_IEEE80211_PRISM: u16 = 802;
+pub const ARPHRD_IEEE80211_RADIOTAP: u16 = 803;
+pub const ARPHRD_IEEE802154: u16 = 804;
+
+pub const ARPHRD_VOID: u16 = 0xFFFF;
+pub const ARPHRD_NONE: u16 = 0xFFFE;
+
+cfg_if! {
+    if #[cfg(target_os = "emscripten")] {
+        // Emscripten does not define any `*_SUPER_MAGIC` constants.
+    } else if #[cfg(not(target_arch = "s390x"))] {
+        pub const ADFS_SUPER_MAGIC: ::c_long = 0x0000adf5;
+        pub const AFFS_SUPER_MAGIC: ::c_long = 0x0000adff;
+        pub const AFS_SUPER_MAGIC: ::c_long = 0x5346414f;
+        pub const AUTOFS_SUPER_MAGIC: ::c_long = 0x0187;
+        pub const BPF_FS_MAGIC: ::c_long = 0xcafe4a11;
+        pub const BTRFS_SUPER_MAGIC: ::c_long = 0x9123683e;
+        pub const CGROUP2_SUPER_MAGIC: ::c_long = 0x63677270;
+        pub const CGROUP_SUPER_MAGIC: ::c_long = 0x27e0eb;
+        pub const CODA_SUPER_MAGIC: ::c_long = 0x73757245;
+        pub const CRAMFS_MAGIC: ::c_long = 0x28cd3d45;
+        pub const DEBUGFS_MAGIC: ::c_long = 0x64626720;
+        pub const DEVPTS_SUPER_MAGIC: ::c_long = 0x1cd1;
+        pub const ECRYPTFS_SUPER_MAGIC: ::c_long = 0xf15f;
+        pub const EFS_SUPER_MAGIC: ::c_long = 0x00414a53;
+        pub const EXT2_SUPER_MAGIC: ::c_long = 0x0000ef53;
+        pub const EXT3_SUPER_MAGIC: ::c_long = 0x0000ef53;
+        pub const EXT4_SUPER_MAGIC: ::c_long = 0x0000ef53;
+        pub const F2FS_SUPER_MAGIC: ::c_long = 0xf2f52010;
+        pub const FUSE_SUPER_MAGIC: ::c_long = 0x65735546;
+        pub const FUTEXFS_SUPER_MAGIC: ::c_long = 0xbad1dea;
+        pub const HOSTFS_SUPER_MAGIC: ::c_long = 0x00c0ffee;
+        pub const HPFS_SUPER_MAGIC: ::c_long = 0xf995e849;
+        pub const HUGETLBFS_MAGIC: ::c_long = 0x958458f6;
+        pub const ISOFS_SUPER_MAGIC: ::c_long = 0x00009660;
+        pub const JFFS2_SUPER_MAGIC: ::c_long = 0x000072b6;
+        pub const MINIX2_SUPER_MAGIC2: ::c_long = 0x00002478;
+        pub const MINIX2_SUPER_MAGIC: ::c_long = 0x00002468;
+        pub const MINIX3_SUPER_MAGIC: ::c_long = 0x4d5a;
+        pub const MINIX_SUPER_MAGIC2: ::c_long = 0x0000138f;
+        pub const MINIX_SUPER_MAGIC: ::c_long = 0x0000137f;
+        pub const MSDOS_SUPER_MAGIC: ::c_long = 0x00004d44;
+        pub const NCP_SUPER_MAGIC: ::c_long = 0x0000564c;
+        pub const NFS_SUPER_MAGIC: ::c_long = 0x00006969;
+        pub const NILFS_SUPER_MAGIC: ::c_long = 0x3434;
+        pub const OCFS2_SUPER_MAGIC: ::c_long = 0x7461636f;
+        pub const OPENPROM_SUPER_MAGIC: ::c_long = 0x00009fa1;
+        pub const OVERLAYFS_SUPER_MAGIC: ::c_long = 0x794c7630;
+        pub const PROC_SUPER_MAGIC: ::c_long = 0x00009fa0;
+        pub const QNX4_SUPER_MAGIC: ::c_long = 0x0000002f;
+        pub const QNX6_SUPER_MAGIC: ::c_long = 0x68191122;
+        pub const RDTGROUP_SUPER_MAGIC: ::c_long = 0x7655821;
+        pub const REISERFS_SUPER_MAGIC: ::c_long = 0x52654973;
+        pub const SECURITYFS_MAGIC: ::c_long = 0x73636673;
+        pub const SELINUX_MAGIC: ::c_long = 0xf97cff8c;
+        pub const SMACK_MAGIC: ::c_long = 0x43415d53;
+        pub const SMB_SUPER_MAGIC: ::c_long = 0x0000517b;
+        pub const SYSFS_MAGIC: ::c_long = 0x62656572;
+        pub const TMPFS_MAGIC: ::c_long = 0x01021994;
+        pub const TRACEFS_MAGIC: ::c_long = 0x74726163;
+        pub const UDF_SUPER_MAGIC: ::c_long = 0x15013346;
+        pub const USBDEVICE_SUPER_MAGIC: ::c_long = 0x00009fa2;
+        pub const XENFS_SUPER_MAGIC: ::c_long = 0xabba1974;
+        pub const NSFS_MAGIC: ::c_long = 0x6e736673;
+    } else if #[cfg(target_arch = "s390x")] {
+        pub const ADFS_SUPER_MAGIC: ::c_uint = 0x0000adf5;
+        pub const AFFS_SUPER_MAGIC: ::c_uint = 0x0000adff;
+        pub const AFS_SUPER_MAGIC: ::c_uint = 0x5346414f;
+        pub const AUTOFS_SUPER_MAGIC: ::c_uint = 0x0187;
+        pub const BPF_FS_MAGIC: ::c_uint = 0xcafe4a11;
+        pub const BTRFS_SUPER_MAGIC: ::c_uint = 0x9123683e;
+        pub const CGROUP2_SUPER_MAGIC: ::c_uint = 0x63677270;
+        pub const CGROUP_SUPER_MAGIC: ::c_uint = 0x27e0eb;
+        pub const CODA_SUPER_MAGIC: ::c_uint = 0x73757245;
+        pub const CRAMFS_MAGIC: ::c_uint = 0x28cd3d45;
+        pub const DEBUGFS_MAGIC: ::c_uint = 0x64626720;
+        pub const DEVPTS_SUPER_MAGIC: ::c_uint = 0x1cd1;
+        pub const ECRYPTFS_SUPER_MAGIC: ::c_uint = 0xf15f;
+        pub const EFS_SUPER_MAGIC: ::c_uint = 0x00414a53;
+        pub const EXT2_SUPER_MAGIC: ::c_uint = 0x0000ef53;
+        pub const EXT3_SUPER_MAGIC: ::c_uint = 0x0000ef53;
+        pub const EXT4_SUPER_MAGIC: ::c_uint = 0x0000ef53;
+        pub const F2FS_SUPER_MAGIC: ::c_uint = 0xf2f52010;
+        pub const FUSE_SUPER_MAGIC: ::c_uint = 0x65735546;
+        pub const FUTEXFS_SUPER_MAGIC: ::c_uint = 0xbad1dea;
+        pub const HOSTFS_SUPER_MAGIC: ::c_uint = 0x00c0ffee;
+        pub const HPFS_SUPER_MAGIC: ::c_uint = 0xf995e849;
+        pub const HUGETLBFS_MAGIC: ::c_uint = 0x958458f6;
+        pub const ISOFS_SUPER_MAGIC: ::c_uint = 0x00009660;
+        pub const JFFS2_SUPER_MAGIC: ::c_uint = 0x000072b6;
+        pub const MINIX2_SUPER_MAGIC2: ::c_uint = 0x00002478;
+        pub const MINIX2_SUPER_MAGIC: ::c_uint = 0x00002468;
+        pub const MINIX3_SUPER_MAGIC: ::c_uint = 0x4d5a;
+        pub const MINIX_SUPER_MAGIC2: ::c_uint = 0x0000138f;
+        pub const MINIX_SUPER_MAGIC: ::c_uint = 0x0000137f;
+        pub const MSDOS_SUPER_MAGIC: ::c_uint = 0x00004d44;
+        pub const NCP_SUPER_MAGIC: ::c_uint = 0x0000564c;
+        pub const NFS_SUPER_MAGIC: ::c_uint = 0x00006969;
+        pub const NILFS_SUPER_MAGIC: ::c_uint = 0x3434;
+        pub const OCFS2_SUPER_MAGIC: ::c_uint = 0x7461636f;
+        pub const OPENPROM_SUPER_MAGIC: ::c_uint = 0x00009fa1;
+        pub const OVERLAYFS_SUPER_MAGIC: ::c_uint = 0x794c7630;
+        pub const PROC_SUPER_MAGIC: ::c_uint = 0x00009fa0;
+        pub const QNX4_SUPER_MAGIC: ::c_uint = 0x0000002f;
+        pub const QNX6_SUPER_MAGIC: ::c_uint = 0x68191122;
+        pub const RDTGROUP_SUPER_MAGIC: ::c_uint = 0x7655821;
+        pub const REISERFS_SUPER_MAGIC: ::c_uint = 0x52654973;
+        pub const SECURITYFS_MAGIC: ::c_uint = 0x73636673;
+        pub const SELINUX_MAGIC: ::c_uint = 0xf97cff8c;
+        pub const SMACK_MAGIC: ::c_uint = 0x43415d53;
+        pub const SMB_SUPER_MAGIC: ::c_uint = 0x0000517b;
+        pub const SYSFS_MAGIC: ::c_uint = 0x62656572;
+        pub const TMPFS_MAGIC: ::c_uint = 0x01021994;
+        pub const TRACEFS_MAGIC: ::c_uint = 0x74726163;
+        pub const UDF_SUPER_MAGIC: ::c_uint = 0x15013346;
+        pub const USBDEVICE_SUPER_MAGIC: ::c_uint = 0x00009fa2;
+        pub const XENFS_SUPER_MAGIC: ::c_uint = 0xabba1974;
+        pub const NSFS_MAGIC: ::c_uint = 0x6e736673;
+    }
+}
+
+const_fn! {
+    {const} fn CMSG_ALIGN(len: usize) -> usize {
+        len + ::mem::size_of::<usize>() - 1 & !(::mem::size_of::<usize>() - 1)
+    }
+}
+
+f! {
+    pub fn CMSG_FIRSTHDR(mhdr: *const msghdr) -> *mut cmsghdr {
+        if (*mhdr).msg_controllen as usize >= ::mem::size_of::<cmsghdr>() {
+            (*mhdr).msg_control as *mut cmsghdr
+        } else {
+            0 as *mut cmsghdr
+        }
+    }
+
+    pub fn CMSG_DATA(cmsg: *const cmsghdr) -> *mut ::c_uchar {
+        cmsg.offset(1) as *mut ::c_uchar
+    }
+
+    pub {const} fn CMSG_SPACE(length: ::c_uint) -> ::c_uint {
+        (CMSG_ALIGN(length as usize) + CMSG_ALIGN(::mem::size_of::<cmsghdr>()))
+            as ::c_uint
+    }
+
+    pub fn CMSG_LEN(length: ::c_uint) -> ::c_uint {
+        CMSG_ALIGN(::mem::size_of::<cmsghdr>()) as ::c_uint + length
+    }
+
+    pub fn FD_CLR(fd: ::c_int, set: *mut fd_set) -> () {
+        let fd = fd as usize;
+        let size = ::mem::size_of_val(&(*set).fds_bits[0]) * 8;
+        (*set).fds_bits[fd / size] &= !(1 << (fd % size));
+        return
+    }
+
+    pub fn FD_ISSET(fd: ::c_int, set: *const fd_set) -> bool {
+        let fd = fd as usize;
+        let size = ::mem::size_of_val(&(*set).fds_bits[0]) * 8;
+        return ((*set).fds_bits[fd / size] & (1 << (fd % size))) != 0
+    }
+
+    pub fn FD_SET(fd: ::c_int, set: *mut fd_set) -> () {
+        let fd = fd as usize;
+        let size = ::mem::size_of_val(&(*set).fds_bits[0]) * 8;
+        (*set).fds_bits[fd / size] |= 1 << (fd % size);
+        return
+    }
+
+    pub fn FD_ZERO(set: *mut fd_set) -> () {
+        for slot in (*set).fds_bits.iter_mut() {
+            *slot = 0;
+        }
+    }
+}
+
+safe_f! {
+    pub fn SIGRTMAX() -> ::c_int {
+        unsafe { __libc_current_sigrtmax() }
+    }
+
+    pub fn SIGRTMIN() -> ::c_int {
+        unsafe { __libc_current_sigrtmin() }
+    }
+
+    pub {const} fn WIFSTOPPED(status: ::c_int) -> bool {
+        (status & 0xff) == 0x7f
+    }
+
+    pub {const} fn WSTOPSIG(status: ::c_int) -> ::c_int {
+        (status >> 8) & 0xff
+    }
+
+    pub {const} fn WIFCONTINUED(status: ::c_int) -> bool {
+        status == 0xffff
+    }
+
+    pub {const} fn WIFSIGNALED(status: ::c_int) -> bool {
+        ((status & 0x7f) + 1) as i8 >= 2
+    }
+
+    pub {const} fn WTERMSIG(status: ::c_int) -> ::c_int {
+        status & 0x7f
+    }
+
+    pub {const} fn WIFEXITED(status: ::c_int) -> bool {
+        (status & 0x7f) == 0
+    }
+
+    pub {const} fn WEXITSTATUS(status: ::c_int) -> ::c_int {
+        (status >> 8) & 0xff
+    }
+
+    pub {const} fn WCOREDUMP(status: ::c_int) -> bool {
+        (status & 0x80) != 0
+    }
+
+    pub {const} fn W_EXITCODE(ret: ::c_int, sig: ::c_int) -> ::c_int {
+        (ret << 8) | sig
+    }
+
+    pub {const} fn W_STOPCODE(sig: ::c_int) -> ::c_int {
+        (sig << 8) | 0x7f
+    }
+
+    pub {const} fn QCMD(cmd: ::c_int, type_: ::c_int) -> ::c_int {
+        (cmd << 8) | (type_ & 0x00ff)
+    }
+
+    pub {const} fn IPOPT_COPIED(o: u8) -> u8 {
+        o & IPOPT_COPY
+    }
+
+    pub {const} fn IPOPT_CLASS(o: u8) -> u8 {
+        o & IPOPT_CLASS_MASK
+    }
+
+    pub {const} fn IPOPT_NUMBER(o: u8) -> u8 {
+        o & IPOPT_NUMBER_MASK
+    }
+
+    pub {const} fn IPTOS_ECN(x: u8) -> u8 {
+        x & ::IPTOS_ECN_MASK
+    }
+}
+
+extern "C" {
+    #[doc(hidden)]
+    pub fn __libc_current_sigrtmax() -> ::c_int;
+    #[doc(hidden)]
+    pub fn __libc_current_sigrtmin() -> ::c_int;
+
+    pub fn sem_destroy(sem: *mut sem_t) -> ::c_int;
+    pub fn sem_init(sem: *mut sem_t, pshared: ::c_int, value: ::c_uint) -> ::c_int;
+    pub fn fdatasync(fd: ::c_int) -> ::c_int;
+    pub fn mincore(addr: *mut ::c_void, len: ::size_t, vec: *mut ::c_uchar) -> ::c_int;
+
+    pub fn clock_getres(clk_id: ::clockid_t, tp: *mut ::timespec) -> ::c_int;
+    pub fn clock_gettime(clk_id: ::clockid_t, tp: *mut ::timespec) -> ::c_int;
+    pub fn clock_settime(clk_id: ::clockid_t, tp: *const ::timespec) -> ::c_int;
+    pub fn clock_getcpuclockid(pid: ::pid_t, clk_id: *mut ::clockid_t) -> ::c_int;
+
+    pub fn dirfd(dirp: *mut ::DIR) -> ::c_int;
+
+    pub fn pthread_getattr_np(native: ::pthread_t, attr: *mut ::pthread_attr_t) -> ::c_int;
+    pub fn pthread_attr_getstack(
+        attr: *const ::pthread_attr_t,
+        stackaddr: *mut *mut ::c_void,
+        stacksize: *mut ::size_t,
+    ) -> ::c_int;
+    pub fn memalign(align: ::size_t, size: ::size_t) -> *mut ::c_void;
+    pub fn setgroups(ngroups: ::size_t, ptr: *const ::gid_t) -> ::c_int;
+    pub fn pipe2(fds: *mut ::c_int, flags: ::c_int) -> ::c_int;
+    pub fn statfs(path: *const ::c_char, buf: *mut statfs) -> ::c_int;
+    pub fn statfs64(path: *const ::c_char, buf: *mut statfs64) -> ::c_int;
+    pub fn fstatfs(fd: ::c_int, buf: *mut statfs) -> ::c_int;
+    pub fn fstatfs64(fd: ::c_int, buf: *mut statfs64) -> ::c_int;
+    pub fn statvfs64(path: *const ::c_char, buf: *mut statvfs64) -> ::c_int;
+    pub fn fstatvfs64(fd: ::c_int, buf: *mut statvfs64) -> ::c_int;
+    pub fn memrchr(cx: *const ::c_void, c: ::c_int, n: ::size_t) -> *mut ::c_void;
+
+    pub fn posix_fadvise(fd: ::c_int, offset: ::off_t, len: ::off_t, advise: ::c_int) -> ::c_int;
+    pub fn posix_fadvise64(
+        fd: ::c_int,
+        offset: ::off64_t,
+        len: ::off64_t,
+        advise: ::c_int,
+    ) -> ::c_int;
+    pub fn futimens(fd: ::c_int, times: *const ::timespec) -> ::c_int;
+    pub fn utimensat(
+        dirfd: ::c_int,
+        path: *const ::c_char,
+        times: *const ::timespec,
+        flag: ::c_int,
+    ) -> ::c_int;
+    pub fn duplocale(base: ::locale_t) -> ::locale_t;
+    pub fn freelocale(loc: ::locale_t);
+    pub fn newlocale(mask: ::c_int, locale: *const ::c_char, base: ::locale_t) -> ::locale_t;
+    pub fn uselocale(loc: ::locale_t) -> ::locale_t;
+    pub fn creat64(path: *const c_char, mode: mode_t) -> ::c_int;
+    pub fn fstat64(fildes: ::c_int, buf: *mut stat64) -> ::c_int;
+    pub fn fstatat64(
+        dirfd: ::c_int,
+        pathname: *const c_char,
+        buf: *mut stat64,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn ftruncate64(fd: ::c_int, length: off64_t) -> ::c_int;
+    pub fn lseek64(fd: ::c_int, offset: off64_t, whence: ::c_int) -> off64_t;
+    pub fn lstat64(path: *const c_char, buf: *mut stat64) -> ::c_int;
+    pub fn mmap64(
+        addr: *mut ::c_void,
+        len: ::size_t,
+        prot: ::c_int,
+        flags: ::c_int,
+        fd: ::c_int,
+        offset: off64_t,
+    ) -> *mut ::c_void;
+    pub fn open64(path: *const c_char, oflag: ::c_int, ...) -> ::c_int;
+    pub fn openat64(fd: ::c_int, path: *const c_char, oflag: ::c_int, ...) -> ::c_int;
+    pub fn pread64(fd: ::c_int, buf: *mut ::c_void, count: ::size_t, offset: off64_t) -> ::ssize_t;
+    pub fn pwrite64(
+        fd: ::c_int,
+        buf: *const ::c_void,
+        count: ::size_t,
+        offset: off64_t,
+    ) -> ::ssize_t;
+    pub fn readdir64(dirp: *mut ::DIR) -> *mut ::dirent64;
+    pub fn readdir64_r(
+        dirp: *mut ::DIR,
+        entry: *mut ::dirent64,
+        result: *mut *mut ::dirent64,
+    ) -> ::c_int;
+    pub fn stat64(path: *const c_char, buf: *mut stat64) -> ::c_int;
+    pub fn truncate64(path: *const c_char, length: off64_t) -> ::c_int;
+
+    pub fn mknodat(
+        dirfd: ::c_int,
+        pathname: *const ::c_char,
+        mode: ::mode_t,
+        dev: dev_t,
+    ) -> ::c_int;
+    pub fn pthread_condattr_getclock(
+        attr: *const pthread_condattr_t,
+        clock_id: *mut clockid_t,
+    ) -> ::c_int;
+    pub fn pthread_condattr_setclock(
+        attr: *mut pthread_condattr_t,
+        clock_id: ::clockid_t,
+    ) -> ::c_int;
+    pub fn pthread_condattr_setpshared(attr: *mut pthread_condattr_t, pshared: ::c_int) -> ::c_int;
+    pub fn pthread_mutexattr_setpshared(
+        attr: *mut pthread_mutexattr_t,
+        pshared: ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_rwlockattr_getpshared(
+        attr: *const pthread_rwlockattr_t,
+        val: *mut ::c_int,
+    ) -> ::c_int;
+    pub fn pthread_rwlockattr_setpshared(attr: *mut pthread_rwlockattr_t, val: ::c_int) -> ::c_int;
+    pub fn ptsname_r(fd: ::c_int, buf: *mut ::c_char, buflen: ::size_t) -> ::c_int;
+    pub fn clearenv() -> ::c_int;
+    pub fn waitid(idtype: idtype_t, id: id_t, infop: *mut ::siginfo_t, options: ::c_int)
+        -> ::c_int;
+    pub fn getresuid(ruid: *mut ::uid_t, euid: *mut ::uid_t, suid: *mut ::uid_t) -> ::c_int;
+    pub fn getresgid(rgid: *mut ::gid_t, egid: *mut ::gid_t, sgid: *mut ::gid_t) -> ::c_int;
+    pub fn acct(filename: *const ::c_char) -> ::c_int;
+    pub fn brk(addr: *mut ::c_void) -> ::c_int;
+    pub fn sbrk(increment: ::intptr_t) -> *mut ::c_void;
+    #[deprecated(
+        since = "0.2.66",
+        note = "causes memory corruption, see rust-lang/libc#1596"
+    )]
+    pub fn vfork() -> ::pid_t;
+    pub fn setresgid(rgid: ::gid_t, egid: ::gid_t, sgid: ::gid_t) -> ::c_int;
+    pub fn setresuid(ruid: ::uid_t, euid: ::uid_t, suid: ::uid_t) -> ::c_int;
+    pub fn wait4(
+        pid: ::pid_t,
+        status: *mut ::c_int,
+        options: ::c_int,
+        rusage: *mut ::rusage,
+    ) -> ::pid_t;
+    pub fn login_tty(fd: ::c_int) -> ::c_int;
+    pub fn execvpe(
+        file: *const ::c_char,
+        argv: *const *const ::c_char,
+        envp: *const *const ::c_char,
+    ) -> ::c_int;
+    pub fn fexecve(
+        fd: ::c_int,
+        argv: *const *const ::c_char,
+        envp: *const *const ::c_char,
+    ) -> ::c_int;
+    pub fn getifaddrs(ifap: *mut *mut ::ifaddrs) -> ::c_int;
+    pub fn freeifaddrs(ifa: *mut ::ifaddrs);
+    pub fn bind(socket: ::c_int, address: *const ::sockaddr, address_len: ::socklen_t) -> ::c_int;
+
+    pub fn writev(fd: ::c_int, iov: *const ::iovec, iovcnt: ::c_int) -> ::ssize_t;
+    pub fn readv(fd: ::c_int, iov: *const ::iovec, iovcnt: ::c_int) -> ::ssize_t;
+
+    pub fn sendmsg(fd: ::c_int, msg: *const ::msghdr, flags: ::c_int) -> ::ssize_t;
+    pub fn recvmsg(fd: ::c_int, msg: *mut ::msghdr, flags: ::c_int) -> ::ssize_t;
+    pub fn uname(buf: *mut ::utsname) -> ::c_int;
+}
+
+cfg_if! {
+    if #[cfg(not(target_env = "uclibc"))] {
+        extern "C" {
+            pub fn preadv64(
+                fd: ::c_int,
+                iov: *const ::iovec,
+                iovcnt: ::c_int,
+                offset: ::off64_t,
+            ) -> ::ssize_t;
+            pub fn pwritev64(
+                fd: ::c_int,
+                iov: *const ::iovec,
+                iovcnt: ::c_int,
+                offset: ::off64_t,
+            ) -> ::ssize_t;
+            // uclibc has separate non-const version of this function
+            pub fn forkpty(
+                amaster: *mut ::c_int,
+                name: *mut ::c_char,
+                termp: *const termios,
+                winp: *const ::winsize,
+            ) -> ::pid_t;
+            // uclibc has separate non-const version of this function
+            pub fn openpty(
+                amaster: *mut ::c_int,
+                aslave: *mut ::c_int,
+                name: *mut ::c_char,
+                termp: *const termios,
+                winp: *const ::winsize,
+            ) -> ::c_int;
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(target_os = "emscripten")] {
+        mod emscripten;
+        pub use self::emscripten::*;
+    } else if #[cfg(target_os = "linux")] {
+        mod linux;
+        pub use self::linux::*;
+    } else if #[cfg(target_os = "l4re")] {
+        mod linux;
+        pub use self::linux::*;
+    } else if #[cfg(target_os = "android")] {
+        mod android;
+        pub use self::android::*;
+    } else {
+        // Unknown target_os
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/mod.rs.html new file mode 100644 index 0000000..b6a435c --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/libc/unix/mod.rs.html @@ -0,0 +1,3108 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+1410
+1411
+1412
+1413
+1414
+1415
+1416
+1417
+1418
+1419
+1420
+1421
+1422
+1423
+1424
+1425
+1426
+1427
+1428
+1429
+1430
+1431
+1432
+1433
+1434
+1435
+1436
+1437
+1438
+1439
+1440
+1441
+1442
+1443
+1444
+1445
+1446
+1447
+1448
+1449
+1450
+1451
+1452
+1453
+1454
+1455
+1456
+1457
+1458
+1459
+1460
+1461
+1462
+1463
+1464
+1465
+1466
+1467
+1468
+1469
+1470
+1471
+1472
+1473
+1474
+1475
+1476
+1477
+1478
+1479
+1480
+1481
+1482
+1483
+1484
+1485
+1486
+1487
+1488
+1489
+1490
+1491
+1492
+1493
+1494
+1495
+1496
+1497
+1498
+1499
+1500
+1501
+1502
+1503
+1504
+1505
+1506
+1507
+1508
+1509
+1510
+1511
+1512
+1513
+1514
+1515
+1516
+1517
+1518
+1519
+1520
+1521
+1522
+1523
+1524
+1525
+1526
+1527
+1528
+1529
+1530
+1531
+1532
+1533
+1534
+1535
+1536
+1537
+1538
+1539
+1540
+1541
+1542
+1543
+1544
+1545
+1546
+1547
+1548
+1549
+1550
+1551
+1552
+1553
+
//! Definitions found commonly among almost all Unix derivatives
+//!
+//! More functions and definitions can be found in the more specific modules
+//! according to the platform in question.
+
+pub type c_schar = i8;
+pub type c_uchar = u8;
+pub type c_short = i16;
+pub type c_ushort = u16;
+pub type c_int = i32;
+pub type c_uint = u32;
+pub type c_float = f32;
+pub type c_double = f64;
+pub type c_longlong = i64;
+pub type c_ulonglong = u64;
+pub type intmax_t = i64;
+pub type uintmax_t = u64;
+
+pub type size_t = usize;
+pub type ptrdiff_t = isize;
+pub type intptr_t = isize;
+pub type uintptr_t = usize;
+pub type ssize_t = isize;
+
+pub type pid_t = i32;
+pub type in_addr_t = u32;
+pub type in_port_t = u16;
+pub type sighandler_t = ::size_t;
+pub type cc_t = ::c_uchar;
+
+cfg_if! {
+    if #[cfg(any(target_os = "espidf", target_os = "horizon"))] {
+        pub type uid_t = ::c_ushort;
+        pub type gid_t = ::c_ushort;
+    } else {
+        pub type uid_t = u32;
+        pub type gid_t = u32;
+    }
+}
+
+#[cfg_attr(feature = "extra_traits", derive(Debug))]
+pub enum DIR {}
+impl ::Copy for DIR {}
+impl ::Clone for DIR {
+    fn clone(&self) -> DIR {
+        *self
+    }
+}
+pub type locale_t = *mut ::c_void;
+
+s! {
+    pub struct group {
+        pub gr_name: *mut ::c_char,
+        pub gr_passwd: *mut ::c_char,
+        pub gr_gid: ::gid_t,
+        pub gr_mem: *mut *mut ::c_char,
+    }
+
+    pub struct utimbuf {
+        pub actime: time_t,
+        pub modtime: time_t,
+    }
+
+    pub struct timeval {
+        pub tv_sec: time_t,
+        pub tv_usec: suseconds_t,
+    }
+
+    // linux x32 compatibility
+    // See https://sourceware.org/bugzilla/show_bug.cgi?id=16437
+    pub struct timespec {
+        pub tv_sec: time_t,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        pub tv_nsec: i64,
+        #[cfg(not(all(target_arch = "x86_64", target_pointer_width = "32")))]
+        pub tv_nsec: ::c_long,
+    }
+
+    pub struct rlimit {
+        pub rlim_cur: rlim_t,
+        pub rlim_max: rlim_t,
+    }
+
+    pub struct rusage {
+        pub ru_utime: timeval,
+        pub ru_stime: timeval,
+        pub ru_maxrss: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad1: u32,
+        pub ru_ixrss: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad2: u32,
+        pub ru_idrss: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad3: u32,
+        pub ru_isrss: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad4: u32,
+        pub ru_minflt: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad5: u32,
+        pub ru_majflt: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad6: u32,
+        pub ru_nswap: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad7: u32,
+        pub ru_inblock: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad8: u32,
+        pub ru_oublock: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad9: u32,
+        pub ru_msgsnd: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad10: u32,
+        pub ru_msgrcv: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad11: u32,
+        pub ru_nsignals: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad12: u32,
+        pub ru_nvcsw: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad13: u32,
+        pub ru_nivcsw: c_long,
+        #[cfg(all(target_arch = "x86_64", target_pointer_width = "32"))]
+        __pad14: u32,
+
+        #[cfg(any(target_env = "musl", target_os = "emscripten"))]
+        __reserved: [c_long; 16],
+    }
+
+    pub struct ipv6_mreq {
+        pub ipv6mr_multiaddr: in6_addr,
+        #[cfg(target_os = "android")]
+        pub ipv6mr_interface: ::c_int,
+        #[cfg(not(target_os = "android"))]
+        pub ipv6mr_interface: ::c_uint,
+    }
+
+    pub struct hostent {
+        pub h_name: *mut ::c_char,
+        pub h_aliases: *mut *mut ::c_char,
+        pub h_addrtype: ::c_int,
+        pub h_length: ::c_int,
+        pub h_addr_list: *mut *mut ::c_char,
+    }
+
+    pub struct iovec {
+        pub iov_base: *mut ::c_void,
+        pub iov_len: ::size_t,
+    }
+
+    pub struct pollfd {
+        pub fd: ::c_int,
+        pub events: ::c_short,
+        pub revents: ::c_short,
+    }
+
+    pub struct winsize {
+        pub ws_row: ::c_ushort,
+        pub ws_col: ::c_ushort,
+        pub ws_xpixel: ::c_ushort,
+        pub ws_ypixel: ::c_ushort,
+    }
+
+    pub struct linger {
+        pub l_onoff: ::c_int,
+        pub l_linger: ::c_int,
+    }
+
+    pub struct sigval {
+        // Actually a union of an int and a void*
+        pub sival_ptr: *mut ::c_void
+    }
+
+    // <sys/time.h>
+    pub struct itimerval {
+        pub it_interval: ::timeval,
+        pub it_value: ::timeval,
+    }
+
+    // <sys/times.h>
+    pub struct tms {
+        pub tms_utime: ::clock_t,
+        pub tms_stime: ::clock_t,
+        pub tms_cutime: ::clock_t,
+        pub tms_cstime: ::clock_t,
+    }
+
+    pub struct servent {
+        pub s_name: *mut ::c_char,
+        pub s_aliases: *mut *mut ::c_char,
+        pub s_port: ::c_int,
+        pub s_proto: *mut ::c_char,
+    }
+
+    pub struct protoent {
+        pub p_name: *mut ::c_char,
+        pub p_aliases: *mut *mut ::c_char,
+        pub p_proto: ::c_int,
+    }
+}
+
+pub const INT_MIN: c_int = -2147483648;
+pub const INT_MAX: c_int = 2147483647;
+
+pub const SIG_DFL: sighandler_t = 0 as sighandler_t;
+pub const SIG_IGN: sighandler_t = 1 as sighandler_t;
+pub const SIG_ERR: sighandler_t = !0 as sighandler_t;
+
+pub const DT_UNKNOWN: u8 = 0;
+pub const DT_FIFO: u8 = 1;
+pub const DT_CHR: u8 = 2;
+pub const DT_DIR: u8 = 4;
+pub const DT_BLK: u8 = 6;
+pub const DT_REG: u8 = 8;
+pub const DT_LNK: u8 = 10;
+pub const DT_SOCK: u8 = 12;
+
+cfg_if! {
+    if #[cfg(not(target_os = "redox"))] {
+        pub const FD_CLOEXEC: ::c_int = 0x1;
+    }
+}
+
+pub const USRQUOTA: ::c_int = 0;
+pub const GRPQUOTA: ::c_int = 1;
+
+pub const SIGIOT: ::c_int = 6;
+
+pub const S_ISUID: ::mode_t = 0x800;
+pub const S_ISGID: ::mode_t = 0x400;
+pub const S_ISVTX: ::mode_t = 0x200;
+
+cfg_if! {
+    if #[cfg(not(any(target_os = "haiku", target_os = "illumos",
+                     target_os = "solaris")))] {
+        pub const IF_NAMESIZE: ::size_t = 16;
+        pub const IFNAMSIZ: ::size_t = IF_NAMESIZE;
+    }
+}
+
+pub const LOG_EMERG: ::c_int = 0;
+pub const LOG_ALERT: ::c_int = 1;
+pub const LOG_CRIT: ::c_int = 2;
+pub const LOG_ERR: ::c_int = 3;
+pub const LOG_WARNING: ::c_int = 4;
+pub const LOG_NOTICE: ::c_int = 5;
+pub const LOG_INFO: ::c_int = 6;
+pub const LOG_DEBUG: ::c_int = 7;
+
+pub const LOG_KERN: ::c_int = 0;
+pub const LOG_USER: ::c_int = 1 << 3;
+pub const LOG_MAIL: ::c_int = 2 << 3;
+pub const LOG_DAEMON: ::c_int = 3 << 3;
+pub const LOG_AUTH: ::c_int = 4 << 3;
+pub const LOG_SYSLOG: ::c_int = 5 << 3;
+pub const LOG_LPR: ::c_int = 6 << 3;
+pub const LOG_NEWS: ::c_int = 7 << 3;
+pub const LOG_UUCP: ::c_int = 8 << 3;
+pub const LOG_LOCAL0: ::c_int = 16 << 3;
+pub const LOG_LOCAL1: ::c_int = 17 << 3;
+pub const LOG_LOCAL2: ::c_int = 18 << 3;
+pub const LOG_LOCAL3: ::c_int = 19 << 3;
+pub const LOG_LOCAL4: ::c_int = 20 << 3;
+pub const LOG_LOCAL5: ::c_int = 21 << 3;
+pub const LOG_LOCAL6: ::c_int = 22 << 3;
+pub const LOG_LOCAL7: ::c_int = 23 << 3;
+
+cfg_if! {
+    if #[cfg(not(target_os = "haiku"))] {
+        pub const LOG_PID: ::c_int = 0x01;
+        pub const LOG_CONS: ::c_int = 0x02;
+        pub const LOG_ODELAY: ::c_int = 0x04;
+        pub const LOG_NDELAY: ::c_int = 0x08;
+        pub const LOG_NOWAIT: ::c_int = 0x10;
+    }
+}
+pub const LOG_PRIMASK: ::c_int = 7;
+pub const LOG_FACMASK: ::c_int = 0x3f8;
+
+pub const PRIO_MIN: ::c_int = -20;
+pub const PRIO_MAX: ::c_int = 20;
+
+pub const IPPROTO_ICMP: ::c_int = 1;
+pub const IPPROTO_ICMPV6: ::c_int = 58;
+pub const IPPROTO_TCP: ::c_int = 6;
+pub const IPPROTO_UDP: ::c_int = 17;
+pub const IPPROTO_IP: ::c_int = 0;
+pub const IPPROTO_IPV6: ::c_int = 41;
+
+pub const INADDR_LOOPBACK: in_addr_t = 2130706433;
+pub const INADDR_ANY: in_addr_t = 0;
+pub const INADDR_BROADCAST: in_addr_t = 4294967295;
+pub const INADDR_NONE: in_addr_t = 4294967295;
+
+pub const ARPOP_REQUEST: u16 = 1;
+pub const ARPOP_REPLY: u16 = 2;
+
+pub const ATF_COM: ::c_int = 0x02;
+pub const ATF_PERM: ::c_int = 0x04;
+pub const ATF_PUBL: ::c_int = 0x08;
+pub const ATF_USETRAILERS: ::c_int = 0x10;
+
+cfg_if! {
+    if #[cfg(any(target_os = "l4re", target_os = "espidf"))] {
+        // required libraries for L4Re and the ESP-IDF framework are linked externally, ATM
+    } else if #[cfg(feature = "std")] {
+        // cargo build, don't pull in anything extra as the libstd dep
+        // already pulls in all libs.
+    } else if #[cfg(all(target_os = "linux",
+                        any(target_env = "gnu", target_env = "uclibc"),
+                        feature = "rustc-dep-of-std"))] {
+        #[link(name = "util", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "rt", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "pthread", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "m", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "dl", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "c", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "gcc_eh", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "gcc", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "c", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "util", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "rt", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "pthread", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "m", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "dl", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "c", cfg(not(target_feature = "crt-static")))]
+        extern {}
+    } else if #[cfg(target_env = "musl")] {
+        #[cfg_attr(feature = "rustc-dep-of-std",
+                   link(name = "c", kind = "static", modifiers = "-bundle",
+                        cfg(target_feature = "crt-static")))]
+        #[cfg_attr(feature = "rustc-dep-of-std",
+                   link(name = "c", cfg(not(target_feature = "crt-static"))))]
+        extern {}
+    } else if #[cfg(target_os = "emscripten")] {
+        #[link(name = "c")]
+        extern {}
+    } else if #[cfg(all(target_os = "android", feature = "rustc-dep-of-std"))] {
+        #[link(name = "c", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "m", kind = "static", modifiers = "-bundle",
+            cfg(target_feature = "crt-static"))]
+        #[link(name = "m", cfg(not(target_feature = "crt-static")))]
+        #[link(name = "c", cfg(not(target_feature = "crt-static")))]
+        extern {}
+    } else if #[cfg(any(target_os = "macos",
+                        target_os = "ios",
+                        target_os = "tvos",
+                        target_os = "watchos",
+                        target_os = "android",
+                        target_os = "openbsd"))] {
+        #[link(name = "c")]
+        #[link(name = "m")]
+        extern {}
+    } else if #[cfg(target_os = "haiku")] {
+        #[link(name = "root")]
+        #[link(name = "network")]
+        extern {}
+    } else if #[cfg(target_env = "newlib")] {
+        #[link(name = "c")]
+        #[link(name = "m")]
+        extern {}
+    } else if #[cfg(target_os = "hermit")] {
+        // no_default_libraries is set to false for HermitCore, so only a link
+        // to "pthread" needs to be added.
+        #[link(name = "pthread")]
+        extern {}
+    } else if #[cfg(target_env = "illumos")] {
+        #[link(name = "c")]
+        #[link(name = "m")]
+        extern {}
+    } else if #[cfg(target_os = "redox")] {
+        #[cfg_attr(feature = "rustc-dep-of-std",
+                   link(name = "c", kind = "static", modifiers = "-bundle",
+                        cfg(target_feature = "crt-static")))]
+        #[cfg_attr(feature = "rustc-dep-of-std",
+                   link(name = "c", cfg(not(target_feature = "crt-static"))))]
+        extern {}
+    } else {
+        #[link(name = "c")]
+        #[link(name = "m")]
+        #[link(name = "rt")]
+        #[link(name = "pthread")]
+        extern {}
+    }
+}
+
+#[cfg_attr(feature = "extra_traits", derive(Debug))]
+pub enum FILE {}
+impl ::Copy for FILE {}
+impl ::Clone for FILE {
+    fn clone(&self) -> FILE {
+        *self
+    }
+}
+#[cfg_attr(feature = "extra_traits", derive(Debug))]
+pub enum fpos_t {} // FIXME: fill this out with a struct
+impl ::Copy for fpos_t {}
+impl ::Clone for fpos_t {
+    fn clone(&self) -> fpos_t {
+        *self
+    }
+}
+
+extern "C" {
+    pub fn isalnum(c: c_int) -> c_int;
+    pub fn isalpha(c: c_int) -> c_int;
+    pub fn iscntrl(c: c_int) -> c_int;
+    pub fn isdigit(c: c_int) -> c_int;
+    pub fn isgraph(c: c_int) -> c_int;
+    pub fn islower(c: c_int) -> c_int;
+    pub fn isprint(c: c_int) -> c_int;
+    pub fn ispunct(c: c_int) -> c_int;
+    pub fn isspace(c: c_int) -> c_int;
+    pub fn isupper(c: c_int) -> c_int;
+    pub fn isxdigit(c: c_int) -> c_int;
+    pub fn isblank(c: c_int) -> c_int;
+    pub fn tolower(c: c_int) -> c_int;
+    pub fn toupper(c: c_int) -> c_int;
+    pub fn qsort(
+        base: *mut c_void,
+        num: size_t,
+        size: size_t,
+        compar: ::Option<unsafe extern "C" fn(*const c_void, *const c_void) -> c_int>,
+    );
+    pub fn bsearch(
+        key: *const c_void,
+        base: *const c_void,
+        num: size_t,
+        size: size_t,
+        compar: ::Option<unsafe extern "C" fn(*const c_void, *const c_void) -> c_int>,
+    ) -> *mut c_void;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fopen$UNIX2003"
+    )]
+    pub fn fopen(filename: *const c_char, mode: *const c_char) -> *mut FILE;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "freopen$UNIX2003"
+    )]
+    pub fn freopen(filename: *const c_char, mode: *const c_char, file: *mut FILE) -> *mut FILE;
+    pub fn fmemopen(buf: *mut c_void, size: size_t, mode: *const c_char) -> *mut FILE;
+    pub fn open_memstream(ptr: *mut *mut c_char, sizeloc: *mut size_t) -> *mut FILE;
+
+    pub fn fflush(file: *mut FILE) -> c_int;
+    pub fn fclose(file: *mut FILE) -> c_int;
+    pub fn remove(filename: *const c_char) -> c_int;
+    pub fn rename(oldname: *const c_char, newname: *const c_char) -> c_int;
+    pub fn tmpfile() -> *mut FILE;
+    pub fn setvbuf(stream: *mut FILE, buffer: *mut c_char, mode: c_int, size: size_t) -> c_int;
+    pub fn setbuf(stream: *mut FILE, buf: *mut c_char);
+    pub fn getchar() -> c_int;
+    pub fn putchar(c: c_int) -> c_int;
+    pub fn fgetc(stream: *mut FILE) -> c_int;
+    pub fn fgets(buf: *mut c_char, n: c_int, stream: *mut FILE) -> *mut c_char;
+    pub fn fputc(c: c_int, stream: *mut FILE) -> c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fputs$UNIX2003"
+    )]
+    pub fn fputs(s: *const c_char, stream: *mut FILE) -> c_int;
+    pub fn puts(s: *const c_char) -> c_int;
+    pub fn ungetc(c: c_int, stream: *mut FILE) -> c_int;
+    pub fn fread(ptr: *mut c_void, size: size_t, nobj: size_t, stream: *mut FILE) -> size_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fwrite$UNIX2003"
+    )]
+    pub fn fwrite(ptr: *const c_void, size: size_t, nobj: size_t, stream: *mut FILE) -> size_t;
+    pub fn fseek(stream: *mut FILE, offset: c_long, whence: c_int) -> c_int;
+    pub fn ftell(stream: *mut FILE) -> c_long;
+    pub fn rewind(stream: *mut FILE);
+    #[cfg_attr(target_os = "netbsd", link_name = "__fgetpos50")]
+    pub fn fgetpos(stream: *mut FILE, ptr: *mut fpos_t) -> c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__fsetpos50")]
+    pub fn fsetpos(stream: *mut FILE, ptr: *const fpos_t) -> c_int;
+    pub fn feof(stream: *mut FILE) -> c_int;
+    pub fn ferror(stream: *mut FILE) -> c_int;
+    pub fn clearerr(stream: *mut FILE);
+    pub fn perror(s: *const c_char);
+    pub fn atoi(s: *const c_char) -> c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "strtod$UNIX2003"
+    )]
+    pub fn strtod(s: *const c_char, endp: *mut *mut c_char) -> c_double;
+    pub fn strtof(s: *const c_char, endp: *mut *mut c_char) -> c_float;
+    pub fn strtol(s: *const c_char, endp: *mut *mut c_char, base: c_int) -> c_long;
+    pub fn strtoul(s: *const c_char, endp: *mut *mut c_char, base: c_int) -> c_ulong;
+    pub fn calloc(nobj: size_t, size: size_t) -> *mut c_void;
+    pub fn malloc(size: size_t) -> *mut c_void;
+    pub fn realloc(p: *mut c_void, size: size_t) -> *mut c_void;
+    pub fn free(p: *mut c_void);
+    pub fn abort() -> !;
+    pub fn exit(status: c_int) -> !;
+    pub fn _exit(status: c_int) -> !;
+    pub fn atexit(cb: extern "C" fn()) -> c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "system$UNIX2003"
+    )]
+    pub fn system(s: *const c_char) -> c_int;
+    pub fn getenv(s: *const c_char) -> *mut c_char;
+
+    pub fn strcpy(dst: *mut c_char, src: *const c_char) -> *mut c_char;
+    pub fn strncpy(dst: *mut c_char, src: *const c_char, n: size_t) -> *mut c_char;
+    pub fn stpcpy(dst: *mut c_char, src: *const c_char) -> *mut c_char;
+    pub fn strcat(s: *mut c_char, ct: *const c_char) -> *mut c_char;
+    pub fn strncat(s: *mut c_char, ct: *const c_char, n: size_t) -> *mut c_char;
+    pub fn strcmp(cs: *const c_char, ct: *const c_char) -> c_int;
+    pub fn strncmp(cs: *const c_char, ct: *const c_char, n: size_t) -> c_int;
+    pub fn strcoll(cs: *const c_char, ct: *const c_char) -> c_int;
+    pub fn strchr(cs: *const c_char, c: c_int) -> *mut c_char;
+    pub fn strrchr(cs: *const c_char, c: c_int) -> *mut c_char;
+    pub fn strspn(cs: *const c_char, ct: *const c_char) -> size_t;
+    pub fn strcspn(cs: *const c_char, ct: *const c_char) -> size_t;
+    pub fn strdup(cs: *const c_char) -> *mut c_char;
+    pub fn strndup(cs: *const c_char, n: size_t) -> *mut c_char;
+    pub fn strpbrk(cs: *const c_char, ct: *const c_char) -> *mut c_char;
+    pub fn strstr(cs: *const c_char, ct: *const c_char) -> *mut c_char;
+    pub fn strcasecmp(s1: *const c_char, s2: *const c_char) -> c_int;
+    pub fn strncasecmp(s1: *const c_char, s2: *const c_char, n: size_t) -> c_int;
+    pub fn strlen(cs: *const c_char) -> size_t;
+    pub fn strnlen(cs: *const c_char, maxlen: size_t) -> size_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "strerror$UNIX2003"
+    )]
+    pub fn strerror(n: c_int) -> *mut c_char;
+    pub fn strtok(s: *mut c_char, t: *const c_char) -> *mut c_char;
+    pub fn strtok_r(s: *mut c_char, t: *const c_char, p: *mut *mut c_char) -> *mut c_char;
+    pub fn strxfrm(s: *mut c_char, ct: *const c_char, n: size_t) -> size_t;
+    pub fn strsignal(sig: c_int) -> *mut c_char;
+    pub fn wcslen(buf: *const wchar_t) -> size_t;
+    pub fn wcstombs(dest: *mut c_char, src: *const wchar_t, n: size_t) -> ::size_t;
+
+    pub fn memchr(cx: *const c_void, c: c_int, n: size_t) -> *mut c_void;
+    pub fn wmemchr(cx: *const wchar_t, c: wchar_t, n: size_t) -> *mut wchar_t;
+    pub fn memcmp(cx: *const c_void, ct: *const c_void, n: size_t) -> c_int;
+    pub fn memcpy(dest: *mut c_void, src: *const c_void, n: size_t) -> *mut c_void;
+    pub fn memmove(dest: *mut c_void, src: *const c_void, n: size_t) -> *mut c_void;
+    pub fn memset(dest: *mut c_void, c: c_int, n: size_t) -> *mut c_void;
+}
+
+extern "C" {
+    #[cfg_attr(target_os = "netbsd", link_name = "__getpwnam50")]
+    pub fn getpwnam(name: *const ::c_char) -> *mut passwd;
+    #[cfg_attr(target_os = "netbsd", link_name = "__getpwuid50")]
+    pub fn getpwuid(uid: ::uid_t) -> *mut passwd;
+
+    pub fn fprintf(stream: *mut ::FILE, format: *const ::c_char, ...) -> ::c_int;
+    pub fn printf(format: *const ::c_char, ...) -> ::c_int;
+    pub fn snprintf(s: *mut ::c_char, n: ::size_t, format: *const ::c_char, ...) -> ::c_int;
+    pub fn sprintf(s: *mut ::c_char, format: *const ::c_char, ...) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "linux", not(target_env = "uclibc")),
+        link_name = "__isoc99_fscanf"
+    )]
+    pub fn fscanf(stream: *mut ::FILE, format: *const ::c_char, ...) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "linux", not(target_env = "uclibc")),
+        link_name = "__isoc99_scanf"
+    )]
+    pub fn scanf(format: *const ::c_char, ...) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "linux", not(target_env = "uclibc")),
+        link_name = "__isoc99_sscanf"
+    )]
+    pub fn sscanf(s: *const ::c_char, format: *const ::c_char, ...) -> ::c_int;
+    pub fn getchar_unlocked() -> ::c_int;
+    pub fn putchar_unlocked(c: ::c_int) -> ::c_int;
+
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(target_os = "netbsd", link_name = "__socket30")]
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_socket")]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_socket")]
+    pub fn socket(domain: ::c_int, ty: ::c_int, protocol: ::c_int) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "connect$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_connect")]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_connect")]
+    pub fn connect(socket: ::c_int, address: *const sockaddr, len: socklen_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "listen$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_listen")]
+    pub fn listen(socket: ::c_int, backlog: ::c_int) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "accept$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_accept")]
+    pub fn accept(socket: ::c_int, address: *mut sockaddr, address_len: *mut socklen_t) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "getpeername$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_getpeername")]
+    pub fn getpeername(
+        socket: ::c_int,
+        address: *mut sockaddr,
+        address_len: *mut socklen_t,
+    ) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "getsockname$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_getsockname")]
+    pub fn getsockname(
+        socket: ::c_int,
+        address: *mut sockaddr,
+        address_len: *mut socklen_t,
+    ) -> ::c_int;
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_setsockopt")]
+    pub fn setsockopt(
+        socket: ::c_int,
+        level: ::c_int,
+        name: ::c_int,
+        value: *const ::c_void,
+        option_len: socklen_t,
+    ) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "socketpair$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_socketpair")]
+    pub fn socketpair(
+        domain: ::c_int,
+        type_: ::c_int,
+        protocol: ::c_int,
+        socket_vector: *mut ::c_int,
+    ) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "sendto$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_sendto")]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_sendto")]
+    pub fn sendto(
+        socket: ::c_int,
+        buf: *const ::c_void,
+        len: ::size_t,
+        flags: ::c_int,
+        addr: *const sockaddr,
+        addrlen: socklen_t,
+    ) -> ::ssize_t;
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_shutdown")]
+    pub fn shutdown(socket: ::c_int, how: ::c_int) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "chmod$UNIX2003"
+    )]
+    pub fn chmod(path: *const c_char, mode: mode_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fchmod$UNIX2003"
+    )]
+    pub fn fchmod(fd: ::c_int, mode: mode_t) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", not(target_arch = "aarch64")),
+        link_name = "fstat$INODE64"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__fstat50")]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "fstat@FBSD_1.0"
+    )]
+    pub fn fstat(fildes: ::c_int, buf: *mut stat) -> ::c_int;
+
+    pub fn mkdir(path: *const c_char, mode: mode_t) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", not(target_arch = "aarch64")),
+        link_name = "stat$INODE64"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__stat50")]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "stat@FBSD_1.0"
+    )]
+    pub fn stat(path: *const c_char, buf: *mut stat) -> ::c_int;
+
+    pub fn pclose(stream: *mut ::FILE) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fdopen$UNIX2003"
+    )]
+    pub fn fdopen(fd: ::c_int, mode: *const c_char) -> *mut ::FILE;
+    pub fn fileno(stream: *mut ::FILE) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "open$UNIX2003"
+    )]
+    pub fn open(path: *const c_char, oflag: ::c_int, ...) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "creat$UNIX2003"
+    )]
+    pub fn creat(path: *const c_char, mode: mode_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fcntl$UNIX2003"
+    )]
+    pub fn fcntl(fd: ::c_int, cmd: ::c_int, ...) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86_64"),
+        link_name = "opendir$INODE64"
+    )]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "opendir$INODE64$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__opendir30")]
+    pub fn opendir(dirname: *const c_char) -> *mut ::DIR;
+
+    #[cfg_attr(
+        all(target_os = "macos", not(target_arch = "aarch64")),
+        link_name = "readdir$INODE64"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__readdir30")]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "readdir@FBSD_1.0"
+    )]
+    pub fn readdir(dirp: *mut ::DIR) -> *mut ::dirent;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "closedir$UNIX2003"
+    )]
+    pub fn closedir(dirp: *mut ::DIR) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86_64"),
+        link_name = "rewinddir$INODE64"
+    )]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "rewinddir$INODE64$UNIX2003"
+    )]
+    pub fn rewinddir(dirp: *mut ::DIR);
+
+    pub fn fchmodat(
+        dirfd: ::c_int,
+        pathname: *const ::c_char,
+        mode: ::mode_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn fchown(fd: ::c_int, owner: ::uid_t, group: ::gid_t) -> ::c_int;
+    pub fn fchownat(
+        dirfd: ::c_int,
+        pathname: *const ::c_char,
+        owner: ::uid_t,
+        group: ::gid_t,
+        flags: ::c_int,
+    ) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", not(target_arch = "aarch64")),
+        link_name = "fstatat$INODE64"
+    )]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "fstatat@FBSD_1.1"
+    )]
+    pub fn fstatat(
+        dirfd: ::c_int,
+        pathname: *const ::c_char,
+        buf: *mut stat,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn linkat(
+        olddirfd: ::c_int,
+        oldpath: *const ::c_char,
+        newdirfd: ::c_int,
+        newpath: *const ::c_char,
+        flags: ::c_int,
+    ) -> ::c_int;
+    pub fn renameat(
+        olddirfd: ::c_int,
+        oldpath: *const ::c_char,
+        newdirfd: ::c_int,
+        newpath: *const ::c_char,
+    ) -> ::c_int;
+    pub fn symlinkat(
+        target: *const ::c_char,
+        newdirfd: ::c_int,
+        linkpath: *const ::c_char,
+    ) -> ::c_int;
+    pub fn unlinkat(dirfd: ::c_int, pathname: *const ::c_char, flags: ::c_int) -> ::c_int;
+
+    pub fn access(path: *const c_char, amode: ::c_int) -> ::c_int;
+    pub fn alarm(seconds: ::c_uint) -> ::c_uint;
+    pub fn chdir(dir: *const c_char) -> ::c_int;
+    pub fn fchdir(dirfd: ::c_int) -> ::c_int;
+    pub fn chown(path: *const c_char, uid: uid_t, gid: gid_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "lchown$UNIX2003"
+    )]
+    pub fn lchown(path: *const c_char, uid: uid_t, gid: gid_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "close$NOCANCEL$UNIX2003"
+    )]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86_64"),
+        link_name = "close$NOCANCEL"
+    )]
+    pub fn close(fd: ::c_int) -> ::c_int;
+    pub fn dup(fd: ::c_int) -> ::c_int;
+    pub fn dup2(src: ::c_int, dst: ::c_int) -> ::c_int;
+    pub fn execl(path: *const c_char, arg0: *const c_char, ...) -> ::c_int;
+    pub fn execle(path: *const ::c_char, arg0: *const ::c_char, ...) -> ::c_int;
+    pub fn execlp(file: *const ::c_char, arg0: *const ::c_char, ...) -> ::c_int;
+    pub fn execv(prog: *const c_char, argv: *const *const c_char) -> ::c_int;
+    pub fn execve(
+        prog: *const c_char,
+        argv: *const *const c_char,
+        envp: *const *const c_char,
+    ) -> ::c_int;
+    pub fn execvp(c: *const c_char, argv: *const *const c_char) -> ::c_int;
+    pub fn fork() -> pid_t;
+    pub fn fpathconf(filedes: ::c_int, name: ::c_int) -> c_long;
+    pub fn getcwd(buf: *mut c_char, size: ::size_t) -> *mut c_char;
+    pub fn getegid() -> gid_t;
+    pub fn geteuid() -> uid_t;
+    pub fn getgid() -> gid_t;
+    pub fn getgroups(ngroups_max: ::c_int, groups: *mut gid_t) -> ::c_int;
+    #[cfg_attr(target_os = "illumos", link_name = "getloginx")]
+    pub fn getlogin() -> *mut c_char;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "getopt$UNIX2003"
+    )]
+    pub fn getopt(argc: ::c_int, argv: *const *mut c_char, optstr: *const c_char) -> ::c_int;
+    pub fn getpgid(pid: pid_t) -> pid_t;
+    pub fn getpgrp() -> pid_t;
+    pub fn getpid() -> pid_t;
+    pub fn getppid() -> pid_t;
+    pub fn getuid() -> uid_t;
+    pub fn isatty(fd: ::c_int) -> ::c_int;
+    pub fn link(src: *const c_char, dst: *const c_char) -> ::c_int;
+    pub fn lseek(fd: ::c_int, offset: off_t, whence: ::c_int) -> off_t;
+    pub fn pathconf(path: *const c_char, name: ::c_int) -> c_long;
+    pub fn pipe(fds: *mut ::c_int) -> ::c_int;
+    pub fn posix_memalign(memptr: *mut *mut ::c_void, align: ::size_t, size: ::size_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "read$UNIX2003"
+    )]
+    pub fn read(fd: ::c_int, buf: *mut ::c_void, count: ::size_t) -> ::ssize_t;
+    pub fn rmdir(path: *const c_char) -> ::c_int;
+    pub fn seteuid(uid: uid_t) -> ::c_int;
+    pub fn setegid(gid: gid_t) -> ::c_int;
+    pub fn setgid(gid: gid_t) -> ::c_int;
+    pub fn setpgid(pid: pid_t, pgid: pid_t) -> ::c_int;
+    pub fn setsid() -> pid_t;
+    pub fn setuid(uid: uid_t) -> ::c_int;
+    pub fn setreuid(ruid: uid_t, euid: uid_t) -> ::c_int;
+    pub fn setregid(rgid: gid_t, egid: gid_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "sleep$UNIX2003"
+    )]
+    pub fn sleep(secs: ::c_uint) -> ::c_uint;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "nanosleep$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__nanosleep50")]
+    pub fn nanosleep(rqtp: *const timespec, rmtp: *mut timespec) -> ::c_int;
+    pub fn tcgetpgrp(fd: ::c_int) -> pid_t;
+    pub fn tcsetpgrp(fd: ::c_int, pgrp: ::pid_t) -> ::c_int;
+    pub fn ttyname(fd: ::c_int) -> *mut c_char;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "ttyname_r$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "illumos", link_name = "__posix_ttyname_r")]
+    pub fn ttyname_r(fd: ::c_int, buf: *mut c_char, buflen: ::size_t) -> ::c_int;
+    pub fn unlink(c: *const c_char) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "wait$UNIX2003"
+    )]
+    pub fn wait(status: *mut ::c_int) -> pid_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "waitpid$UNIX2003"
+    )]
+    pub fn waitpid(pid: pid_t, status: *mut ::c_int, options: ::c_int) -> pid_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "write$UNIX2003"
+    )]
+    pub fn write(fd: ::c_int, buf: *const ::c_void, count: ::size_t) -> ::ssize_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pread$UNIX2003"
+    )]
+    pub fn pread(fd: ::c_int, buf: *mut ::c_void, count: ::size_t, offset: off_t) -> ::ssize_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pwrite$UNIX2003"
+    )]
+    pub fn pwrite(fd: ::c_int, buf: *const ::c_void, count: ::size_t, offset: off_t) -> ::ssize_t;
+    pub fn umask(mask: mode_t) -> mode_t;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__utime50")]
+    pub fn utime(file: *const c_char, buf: *const utimbuf) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "kill$UNIX2003"
+    )]
+    pub fn kill(pid: pid_t, sig: ::c_int) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "killpg$UNIX2003"
+    )]
+    pub fn killpg(pgrp: pid_t, sig: ::c_int) -> ::c_int;
+
+    pub fn mlock(addr: *const ::c_void, len: ::size_t) -> ::c_int;
+    pub fn munlock(addr: *const ::c_void, len: ::size_t) -> ::c_int;
+    pub fn mlockall(flags: ::c_int) -> ::c_int;
+    pub fn munlockall() -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "mmap$UNIX2003"
+    )]
+    pub fn mmap(
+        addr: *mut ::c_void,
+        len: ::size_t,
+        prot: ::c_int,
+        flags: ::c_int,
+        fd: ::c_int,
+        offset: off_t,
+    ) -> *mut ::c_void;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "munmap$UNIX2003"
+    )]
+    pub fn munmap(addr: *mut ::c_void, len: ::size_t) -> ::c_int;
+
+    pub fn if_nametoindex(ifname: *const c_char) -> ::c_uint;
+    pub fn if_indextoname(ifindex: ::c_uint, ifname: *mut ::c_char) -> *mut ::c_char;
+
+    #[cfg_attr(
+        all(target_os = "macos", not(target_arch = "aarch64")),
+        link_name = "lstat$INODE64"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__lstat50")]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "lstat@FBSD_1.0"
+    )]
+    pub fn lstat(path: *const c_char, buf: *mut stat) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "fsync$UNIX2003"
+    )]
+    pub fn fsync(fd: ::c_int) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "setenv$UNIX2003"
+    )]
+    pub fn setenv(name: *const c_char, val: *const c_char, overwrite: ::c_int) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "unsetenv$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__unsetenv13")]
+    pub fn unsetenv(name: *const c_char) -> ::c_int;
+
+    pub fn symlink(path1: *const c_char, path2: *const c_char) -> ::c_int;
+
+    pub fn ftruncate(fd: ::c_int, length: off_t) -> ::c_int;
+
+    pub fn signal(signum: ::c_int, handler: sighandler_t) -> sighandler_t;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__getrusage50")]
+    pub fn getrusage(resource: ::c_int, usage: *mut rusage) -> ::c_int;
+
+    #[cfg_attr(
+        any(
+            target_os = "macos",
+            target_os = "ios",
+            target_os = "tvos",
+            target_os = "watchos"
+        ),
+        link_name = "realpath$DARWIN_EXTSN"
+    )]
+    pub fn realpath(pathname: *const ::c_char, resolved: *mut ::c_char) -> *mut ::c_char;
+
+    pub fn flock(fd: ::c_int, operation: ::c_int) -> ::c_int;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__times13")]
+    pub fn times(buf: *mut ::tms) -> ::clock_t;
+
+    pub fn pthread_self() -> ::pthread_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_join$UNIX2003"
+    )]
+    pub fn pthread_join(native: ::pthread_t, value: *mut *mut ::c_void) -> ::c_int;
+    pub fn pthread_exit(value: *mut ::c_void) -> !;
+    pub fn pthread_attr_init(attr: *mut ::pthread_attr_t) -> ::c_int;
+    pub fn pthread_attr_destroy(attr: *mut ::pthread_attr_t) -> ::c_int;
+    pub fn pthread_attr_setstacksize(attr: *mut ::pthread_attr_t, stack_size: ::size_t) -> ::c_int;
+    pub fn pthread_attr_setdetachstate(attr: *mut ::pthread_attr_t, state: ::c_int) -> ::c_int;
+    pub fn pthread_detach(thread: ::pthread_t) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__libc_thr_yield")]
+    pub fn sched_yield() -> ::c_int;
+    pub fn pthread_key_create(
+        key: *mut pthread_key_t,
+        dtor: ::Option<unsafe extern "C" fn(*mut ::c_void)>,
+    ) -> ::c_int;
+    pub fn pthread_key_delete(key: pthread_key_t) -> ::c_int;
+    pub fn pthread_getspecific(key: pthread_key_t) -> *mut ::c_void;
+    pub fn pthread_setspecific(key: pthread_key_t, value: *const ::c_void) -> ::c_int;
+    pub fn pthread_mutex_init(
+        lock: *mut pthread_mutex_t,
+        attr: *const pthread_mutexattr_t,
+    ) -> ::c_int;
+    pub fn pthread_mutex_destroy(lock: *mut pthread_mutex_t) -> ::c_int;
+    pub fn pthread_mutex_lock(lock: *mut pthread_mutex_t) -> ::c_int;
+    pub fn pthread_mutex_trylock(lock: *mut pthread_mutex_t) -> ::c_int;
+    pub fn pthread_mutex_unlock(lock: *mut pthread_mutex_t) -> ::c_int;
+
+    pub fn pthread_mutexattr_init(attr: *mut pthread_mutexattr_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_mutexattr_destroy$UNIX2003"
+    )]
+    pub fn pthread_mutexattr_destroy(attr: *mut pthread_mutexattr_t) -> ::c_int;
+    pub fn pthread_mutexattr_settype(attr: *mut pthread_mutexattr_t, _type: ::c_int) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_cond_init$UNIX2003"
+    )]
+    pub fn pthread_cond_init(cond: *mut pthread_cond_t, attr: *const pthread_condattr_t)
+        -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_cond_wait$UNIX2003"
+    )]
+    pub fn pthread_cond_wait(cond: *mut pthread_cond_t, lock: *mut pthread_mutex_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_cond_timedwait$UNIX2003"
+    )]
+    pub fn pthread_cond_timedwait(
+        cond: *mut pthread_cond_t,
+        lock: *mut pthread_mutex_t,
+        abstime: *const ::timespec,
+    ) -> ::c_int;
+    pub fn pthread_cond_signal(cond: *mut pthread_cond_t) -> ::c_int;
+    pub fn pthread_cond_broadcast(cond: *mut pthread_cond_t) -> ::c_int;
+    pub fn pthread_cond_destroy(cond: *mut pthread_cond_t) -> ::c_int;
+    pub fn pthread_condattr_init(attr: *mut pthread_condattr_t) -> ::c_int;
+    pub fn pthread_condattr_destroy(attr: *mut pthread_condattr_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_init$UNIX2003"
+    )]
+    pub fn pthread_rwlock_init(
+        lock: *mut pthread_rwlock_t,
+        attr: *const pthread_rwlockattr_t,
+    ) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_destroy$UNIX2003"
+    )]
+    pub fn pthread_rwlock_destroy(lock: *mut pthread_rwlock_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_rdlock$UNIX2003"
+    )]
+    pub fn pthread_rwlock_rdlock(lock: *mut pthread_rwlock_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_tryrdlock$UNIX2003"
+    )]
+    pub fn pthread_rwlock_tryrdlock(lock: *mut pthread_rwlock_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_wrlock$UNIX2003"
+    )]
+    pub fn pthread_rwlock_wrlock(lock: *mut pthread_rwlock_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_trywrlock$UNIX2003"
+    )]
+    pub fn pthread_rwlock_trywrlock(lock: *mut pthread_rwlock_t) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pthread_rwlock_unlock$UNIX2003"
+    )]
+    pub fn pthread_rwlock_unlock(lock: *mut pthread_rwlock_t) -> ::c_int;
+    pub fn pthread_rwlockattr_init(attr: *mut pthread_rwlockattr_t) -> ::c_int;
+    pub fn pthread_rwlockattr_destroy(attr: *mut pthread_rwlockattr_t) -> ::c_int;
+
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_getsockopt")]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_getsockopt")]
+    pub fn getsockopt(
+        sockfd: ::c_int,
+        level: ::c_int,
+        optname: ::c_int,
+        optval: *mut ::c_void,
+        optlen: *mut ::socklen_t,
+    ) -> ::c_int;
+    pub fn raise(signum: ::c_int) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigaction14")]
+    pub fn sigaction(signum: ::c_int, act: *const sigaction, oldact: *mut sigaction) -> ::c_int;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__utimes50")]
+    pub fn utimes(filename: *const ::c_char, times: *const ::timeval) -> ::c_int;
+    pub fn dlopen(filename: *const ::c_char, flag: ::c_int) -> *mut ::c_void;
+    pub fn dlerror() -> *mut ::c_char;
+    pub fn dlsym(handle: *mut ::c_void, symbol: *const ::c_char) -> *mut ::c_void;
+    pub fn dlclose(handle: *mut ::c_void) -> ::c_int;
+    pub fn dladdr(addr: *const ::c_void, info: *mut Dl_info) -> ::c_int;
+
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(target_os = "illumos", link_name = "__xnet_getaddrinfo")]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_getaddrinfo")]
+    pub fn getaddrinfo(
+        node: *const c_char,
+        service: *const c_char,
+        hints: *const addrinfo,
+        res: *mut *mut addrinfo,
+    ) -> ::c_int;
+    #[cfg(not(all(
+        libc_cfg_target_vendor,
+        target_arch = "powerpc",
+        target_vendor = "nintendo"
+    )))]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_freeaddrinfo")]
+    pub fn freeaddrinfo(res: *mut addrinfo);
+    pub fn hstrerror(errcode: ::c_int) -> *const ::c_char;
+    pub fn gai_strerror(errcode: ::c_int) -> *const ::c_char;
+    #[cfg_attr(
+        any(
+            all(target_os = "linux", not(target_env = "musl")),
+            target_os = "freebsd",
+            target_os = "dragonfly",
+            target_os = "haiku"
+        ),
+        link_name = "__res_init"
+    )]
+    #[cfg_attr(
+        any(
+            target_os = "macos",
+            target_os = "ios",
+            target_os = "tvos",
+            target_os = "watchos"
+        ),
+        link_name = "res_9_init"
+    )]
+    pub fn res_init() -> ::c_int;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__gmtime_r50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn gmtime_r(time_p: *const time_t, result: *mut tm) -> *mut tm;
+    #[cfg_attr(target_os = "netbsd", link_name = "__localtime_r50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn localtime_r(time_p: *const time_t, result: *mut tm) -> *mut tm;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "mktime$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__mktime50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn mktime(tm: *mut tm) -> time_t;
+    #[cfg_attr(target_os = "netbsd", link_name = "__time50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn time(time: *mut time_t) -> time_t;
+    #[cfg_attr(target_os = "netbsd", link_name = "__gmtime50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn gmtime(time_p: *const time_t) -> *mut tm;
+    #[cfg_attr(target_os = "netbsd", link_name = "__locatime50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn localtime(time_p: *const time_t) -> *mut tm;
+    #[cfg_attr(target_os = "netbsd", link_name = "__difftime50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn difftime(time1: time_t, time0: time_t) -> ::c_double;
+    #[cfg_attr(target_os = "netbsd", link_name = "__timegm50")]
+    #[cfg_attr(target_env = "musl", allow(deprecated))]
+    // FIXME: for `time_t`
+    pub fn timegm(tm: *mut ::tm) -> time_t;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__mknod50")]
+    #[cfg_attr(
+        all(target_os = "freebsd", any(freebsd11, freebsd10)),
+        link_name = "mknod@FBSD_1.0"
+    )]
+    pub fn mknod(pathname: *const ::c_char, mode: ::mode_t, dev: ::dev_t) -> ::c_int;
+    pub fn gethostname(name: *mut ::c_char, len: ::size_t) -> ::c_int;
+    pub fn endservent();
+    pub fn getservbyname(name: *const ::c_char, proto: *const ::c_char) -> *mut servent;
+    pub fn getservbyport(port: ::c_int, proto: *const ::c_char) -> *mut servent;
+    pub fn getservent() -> *mut servent;
+    pub fn setservent(stayopen: ::c_int);
+    pub fn getprotobyname(name: *const ::c_char) -> *mut protoent;
+    pub fn getprotobynumber(proto: ::c_int) -> *mut protoent;
+    pub fn chroot(name: *const ::c_char) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "usleep$UNIX2003"
+    )]
+    pub fn usleep(secs: ::c_uint) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "send$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_send")]
+    pub fn send(socket: ::c_int, buf: *const ::c_void, len: ::size_t, flags: ::c_int) -> ::ssize_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "recv$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "espidf", link_name = "lwip_recv")]
+    pub fn recv(socket: ::c_int, buf: *mut ::c_void, len: ::size_t, flags: ::c_int) -> ::ssize_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "putenv$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__putenv50")]
+    pub fn putenv(string: *mut c_char) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "poll$UNIX2003"
+    )]
+    pub fn poll(fds: *mut pollfd, nfds: nfds_t, timeout: ::c_int) -> ::c_int;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86_64"),
+        link_name = "select$1050"
+    )]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "select$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__select50")]
+    pub fn select(
+        nfds: ::c_int,
+        readfds: *mut fd_set,
+        writefds: *mut fd_set,
+        errorfds: *mut fd_set,
+        timeout: *mut timeval,
+    ) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__setlocale50")]
+    pub fn setlocale(category: ::c_int, locale: *const ::c_char) -> *mut ::c_char;
+    pub fn localeconv() -> *mut lconv;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "sem_wait$UNIX2003"
+    )]
+    pub fn sem_wait(sem: *mut sem_t) -> ::c_int;
+    pub fn sem_trywait(sem: *mut sem_t) -> ::c_int;
+    pub fn sem_post(sem: *mut sem_t) -> ::c_int;
+    pub fn statvfs(path: *const c_char, buf: *mut statvfs) -> ::c_int;
+    pub fn fstatvfs(fd: ::c_int, buf: *mut statvfs) -> ::c_int;
+
+    pub fn readlink(path: *const c_char, buf: *mut c_char, bufsz: ::size_t) -> ::ssize_t;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigemptyset14")]
+    pub fn sigemptyset(set: *mut sigset_t) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigaddset14")]
+    pub fn sigaddset(set: *mut sigset_t, signum: ::c_int) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigfillset14")]
+    pub fn sigfillset(set: *mut sigset_t) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigdelset14")]
+    pub fn sigdelset(set: *mut sigset_t, signum: ::c_int) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigismember14")]
+    pub fn sigismember(set: *const sigset_t, signum: ::c_int) -> ::c_int;
+
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigprocmask14")]
+    pub fn sigprocmask(how: ::c_int, set: *const sigset_t, oldset: *mut sigset_t) -> ::c_int;
+    #[cfg_attr(target_os = "netbsd", link_name = "__sigpending14")]
+    pub fn sigpending(set: *mut sigset_t) -> ::c_int;
+
+    pub fn sysconf(name: ::c_int) -> ::c_long;
+
+    pub fn mkfifo(path: *const c_char, mode: mode_t) -> ::c_int;
+
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86_64"),
+        link_name = "pselect$1050"
+    )]
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "pselect$UNIX2003"
+    )]
+    #[cfg_attr(target_os = "netbsd", link_name = "__pselect50")]
+    pub fn pselect(
+        nfds: ::c_int,
+        readfds: *mut fd_set,
+        writefds: *mut fd_set,
+        errorfds: *mut fd_set,
+        timeout: *const timespec,
+        sigmask: *const sigset_t,
+    ) -> ::c_int;
+    pub fn fseeko(stream: *mut ::FILE, offset: ::off_t, whence: ::c_int) -> ::c_int;
+    pub fn ftello(stream: *mut ::FILE) -> ::off_t;
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "tcdrain$UNIX2003"
+    )]
+    pub fn tcdrain(fd: ::c_int) -> ::c_int;
+    pub fn cfgetispeed(termios: *const ::termios) -> ::speed_t;
+    pub fn cfgetospeed(termios: *const ::termios) -> ::speed_t;
+    pub fn cfsetispeed(termios: *mut ::termios, speed: ::speed_t) -> ::c_int;
+    pub fn cfsetospeed(termios: *mut ::termios, speed: ::speed_t) -> ::c_int;
+    pub fn tcgetattr(fd: ::c_int, termios: *mut ::termios) -> ::c_int;
+    pub fn tcsetattr(fd: ::c_int, optional_actions: ::c_int, termios: *const ::termios) -> ::c_int;
+    pub fn tcflow(fd: ::c_int, action: ::c_int) -> ::c_int;
+    pub fn tcflush(fd: ::c_int, action: ::c_int) -> ::c_int;
+    pub fn tcgetsid(fd: ::c_int) -> ::pid_t;
+    pub fn tcsendbreak(fd: ::c_int, duration: ::c_int) -> ::c_int;
+    pub fn mkstemp(template: *mut ::c_char) -> ::c_int;
+    pub fn mkdtemp(template: *mut ::c_char) -> *mut ::c_char;
+
+    pub fn tmpnam(ptr: *mut ::c_char) -> *mut ::c_char;
+
+    pub fn openlog(ident: *const ::c_char, logopt: ::c_int, facility: ::c_int);
+    pub fn closelog();
+    pub fn setlogmask(maskpri: ::c_int) -> ::c_int;
+    #[cfg_attr(target_os = "macos", link_name = "syslog$DARWIN_EXTSN")]
+    pub fn syslog(priority: ::c_int, message: *const ::c_char, ...);
+    #[cfg_attr(
+        all(target_os = "macos", target_arch = "x86"),
+        link_name = "nice$UNIX2003"
+    )]
+    pub fn nice(incr: ::c_int) -> ::c_int;
+
+    pub fn grantpt(fd: ::c_int) -> ::c_int;
+    pub fn posix_openpt(flags: ::c_int) -> ::c_int;
+    pub fn ptsname(fd: ::c_int) -> *mut ::c_char;
+    pub fn unlockpt(fd: ::c_int) -> ::c_int;
+
+    pub fn strcasestr(cs: *const c_char, ct: *const c_char) -> *mut c_char;
+    pub fn getline(lineptr: *mut *mut c_char, n: *mut size_t, stream: *mut FILE) -> ssize_t;
+
+    pub fn lockf(fd: ::c_int, cmd: ::c_int, len: ::off_t) -> ::c_int;
+
+}
+cfg_if! {
+    if #[cfg(not(any(target_os = "emscripten",
+                     target_os = "android",
+                     target_os = "haiku")))] {
+        extern "C" {
+            pub fn adjtime(delta: *const timeval, olddelta: *mut timeval) -> ::c_int;
+            pub fn stpncpy(dst: *mut c_char, src: *const c_char, n: size_t) -> *mut c_char;
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(not(target_env = "uclibc"))] {
+        extern "C" {
+            pub fn open_wmemstream(
+                ptr: *mut *mut wchar_t,
+                sizeloc: *mut size_t,
+            ) -> *mut FILE;
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(not(target_os = "redox"))] {
+        extern {
+            pub fn getsid(pid: pid_t) -> pid_t;
+            pub fn truncate(path: *const c_char, length: off_t) -> ::c_int;
+            #[cfg_attr(all(target_os = "macos", target_arch = "x86"),
+                       link_name = "pause$UNIX2003")]
+            pub fn pause() -> ::c_int;
+
+            pub fn readlinkat(dirfd: ::c_int,
+                              pathname: *const ::c_char,
+                              buf: *mut ::c_char,
+                              bufsiz: ::size_t) -> ::ssize_t;
+            pub fn mkdirat(dirfd: ::c_int, pathname: *const ::c_char,
+                           mode: ::mode_t) -> ::c_int;
+            pub fn openat(dirfd: ::c_int, pathname: *const ::c_char,
+                          flags: ::c_int, ...) -> ::c_int;
+
+            #[cfg_attr(all(target_os = "macos", target_arch = "x86_64"),
+                       link_name = "fdopendir$INODE64")]
+            #[cfg_attr(all(target_os = "macos", target_arch = "x86"),
+                       link_name = "fdopendir$INODE64$UNIX2003")]
+            pub fn fdopendir(fd: ::c_int) -> *mut ::DIR;
+
+            #[cfg_attr(all(target_os = "macos", not(target_arch = "aarch64")),
+                       link_name = "readdir_r$INODE64")]
+            #[cfg_attr(target_os = "netbsd", link_name = "__readdir_r30")]
+            #[cfg_attr(
+                all(target_os = "freebsd", any(freebsd11, freebsd10)),
+                link_name = "readdir_r@FBSD_1.0"
+            )]
+            #[allow(non_autolinks)] // FIXME: `<>` breaks line length limit.
+            /// The 64-bit libc on Solaris and illumos only has readdir_r. If a
+            /// 32-bit Solaris or illumos target is ever created, it should use
+            /// __posix_readdir_r. See libc(3LIB) on Solaris or illumos:
+            /// https://illumos.org/man/3lib/libc
+            /// https://docs.oracle.com/cd/E36784_01/html/E36873/libc-3lib.html
+            /// https://www.unix.com/man-page/opensolaris/3LIB/libc/
+            pub fn readdir_r(dirp: *mut ::DIR, entry: *mut ::dirent,
+                             result: *mut *mut ::dirent) -> ::c_int;
+        }
+    }
+}
+
+cfg_if! {
+   if #[cfg(not(any(target_os = "solaris", target_os = "illumos")))] {
+        extern {
+            pub fn cfmakeraw(termios: *mut ::termios);
+            pub fn cfsetspeed(termios: *mut ::termios,
+                              speed: ::speed_t) -> ::c_int;
+        }
+   }
+}
+
+cfg_if! {
+    if #[cfg(target_env = "newlib")] {
+        mod newlib;
+        pub use self::newlib::*;
+    } else if #[cfg(any(target_os = "linux",
+                        target_os = "l4re",
+                        target_os = "android",
+                        target_os = "emscripten"))] {
+        mod linux_like;
+        pub use self::linux_like::*;
+    } else if #[cfg(any(target_os = "macos",
+                        target_os = "ios",
+                        target_os = "tvos",
+                        target_os = "watchos",
+                        target_os = "freebsd",
+                        target_os = "dragonfly",
+                        target_os = "openbsd",
+                        target_os = "netbsd"))] {
+        mod bsd;
+        pub use self::bsd::*;
+    } else if #[cfg(any(target_os = "solaris",
+                        target_os = "illumos"))] {
+        mod solarish;
+        pub use self::solarish::*;
+    } else if #[cfg(target_os = "haiku")] {
+        mod haiku;
+        pub use self::haiku::*;
+    } else if #[cfg(target_os = "hermit")] {
+        mod hermit;
+        pub use self::hermit::*;
+    } else if #[cfg(target_os = "redox")] {
+        mod redox;
+        pub use self::redox::*;
+    } else {
+        // Unknown target_os
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_core_cvoid)] {
+        pub use ::ffi::c_void;
+    } else {
+        // Use repr(u8) as LLVM expects `void*` to be the same as `i8*` to help
+        // enable more optimization opportunities around it recognizing things
+        // like malloc/free.
+        #[repr(u8)]
+        #[allow(missing_copy_implementations)]
+        #[allow(missing_debug_implementations)]
+        pub enum c_void {
+            // Two dummy variants so the #[repr] attribute can be used.
+            #[doc(hidden)]
+            __variant1,
+            #[doc(hidden)]
+            __variant2,
+        }
+    }
+}
+
+cfg_if! {
+    if #[cfg(libc_align)] {
+        mod align;
+        pub use self::align::*;
+    } else {
+        mod no_align;
+        pub use self::no_align::*;
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/lib.rs.html new file mode 100644 index 0000000..8188dea --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/lib.rs.html @@ -0,0 +1,46 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+
#![no_std]
+
+// Design:
+// - safety: safe creation of any machine type is done only by instance methods of a
+//   Machine (which is a ZST + Copy type), which can only by created unsafely or safely
+//   through feature detection (e.g. fn AVX2::try_get() -> Option<Machine>).
+
+mod soft;
+mod types;
+pub use self::types::*;
+
+#[cfg(all(target_arch = "x86_64", target_feature = "sse2", not(feature = "no_simd"), not(miri)))]
+pub mod x86_64;
+#[cfg(all(target_arch = "x86_64", target_feature = "sse2", not(feature = "no_simd"), not(miri)))]
+use self::x86_64 as arch;
+
+#[cfg(any(feature = "no_simd", miri, not(target_arch = "x86_64"), all(target_arch = "x86_64", not(target_feature = "sse2"))))]
+pub mod generic;
+#[cfg(any(feature = "no_simd", miri, not(target_arch = "x86_64"), all(target_arch = "x86_64", not(target_feature = "sse2"))))]
+use self::generic as arch;
+
+pub use self::arch::{vec128_storage, vec256_storage, vec512_storage};
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/soft.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/soft.rs.html new file mode 100644 index 0000000..15a524c --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/soft.rs.html @@ -0,0 +1,946 @@ +soft.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+
//! Implement 256- and 512- bit in terms of 128-bit, for machines without native wide SIMD.
+
+use crate::types::*;
+use crate::{vec128_storage, vec256_storage, vec512_storage};
+use core::marker::PhantomData;
+use core::ops::*;
+
+#[derive(Copy, Clone, Default)]
+#[allow(non_camel_case_types)]
+pub struct x2<W, G>(pub [W; 2], PhantomData<G>);
+impl<W, G> x2<W, G> {
+    #[inline(always)]
+    pub fn new(xs: [W; 2]) -> Self {
+        x2(xs, PhantomData)
+    }
+}
+macro_rules! fwd_binop_x2 {
+    ($trait:ident, $fn:ident) => {
+        impl<W: $trait + Copy, G> $trait for x2<W, G> {
+            type Output = x2<W::Output, G>;
+            #[inline(always)]
+            fn $fn(self, rhs: Self) -> Self::Output {
+                x2::new([self.0[0].$fn(rhs.0[0]), self.0[1].$fn(rhs.0[1])])
+            }
+        }
+    };
+}
+macro_rules! fwd_binop_assign_x2 {
+    ($trait:ident, $fn_assign:ident) => {
+        impl<W: $trait + Copy, G> $trait for x2<W, G> {
+            #[inline(always)]
+            fn $fn_assign(&mut self, rhs: Self) {
+                (self.0[0]).$fn_assign(rhs.0[0]);
+                (self.0[1]).$fn_assign(rhs.0[1]);
+            }
+        }
+    };
+}
+macro_rules! fwd_unop_x2 {
+    ($fn:ident) => {
+        #[inline(always)]
+        fn $fn(self) -> Self {
+            x2::new([self.0[0].$fn(), self.0[1].$fn()])
+        }
+    };
+}
+impl<W, G> RotateEachWord32 for x2<W, G>
+where
+    W: Copy + RotateEachWord32,
+{
+    fwd_unop_x2!(rotate_each_word_right7);
+    fwd_unop_x2!(rotate_each_word_right8);
+    fwd_unop_x2!(rotate_each_word_right11);
+    fwd_unop_x2!(rotate_each_word_right12);
+    fwd_unop_x2!(rotate_each_word_right16);
+    fwd_unop_x2!(rotate_each_word_right20);
+    fwd_unop_x2!(rotate_each_word_right24);
+    fwd_unop_x2!(rotate_each_word_right25);
+}
+impl<W, G> RotateEachWord64 for x2<W, G>
+where
+    W: Copy + RotateEachWord64,
+{
+    fwd_unop_x2!(rotate_each_word_right32);
+}
+impl<W, G> RotateEachWord128 for x2<W, G> where W: RotateEachWord128 {}
+impl<W, G> BitOps0 for x2<W, G>
+where
+    W: BitOps0,
+    G: Copy,
+{
+}
+impl<W, G> BitOps32 for x2<W, G>
+where
+    W: BitOps32 + BitOps0,
+    G: Copy,
+{
+}
+impl<W, G> BitOps64 for x2<W, G>
+where
+    W: BitOps64 + BitOps0,
+    G: Copy,
+{
+}
+impl<W, G> BitOps128 for x2<W, G>
+where
+    W: BitOps128 + BitOps0,
+    G: Copy,
+{
+}
+fwd_binop_x2!(BitAnd, bitand);
+fwd_binop_x2!(BitOr, bitor);
+fwd_binop_x2!(BitXor, bitxor);
+fwd_binop_x2!(AndNot, andnot);
+fwd_binop_assign_x2!(BitAndAssign, bitand_assign);
+fwd_binop_assign_x2!(BitOrAssign, bitor_assign);
+fwd_binop_assign_x2!(BitXorAssign, bitxor_assign);
+impl<W, G> ArithOps for x2<W, G>
+where
+    W: ArithOps,
+    G: Copy,
+{
+}
+fwd_binop_x2!(Add, add);
+fwd_binop_assign_x2!(AddAssign, add_assign);
+impl<W: Not + Copy, G> Not for x2<W, G> {
+    type Output = x2<W::Output, G>;
+    #[inline(always)]
+    fn not(self) -> Self::Output {
+        x2::new([self.0[0].not(), self.0[1].not()])
+    }
+}
+impl<W, G> UnsafeFrom<[W; 2]> for x2<W, G> {
+    #[inline(always)]
+    unsafe fn unsafe_from(xs: [W; 2]) -> Self {
+        x2::new(xs)
+    }
+}
+impl<W: Copy, G> Vec2<W> for x2<W, G> {
+    #[inline(always)]
+    fn extract(self, i: u32) -> W {
+        self.0[i as usize]
+    }
+    #[inline(always)]
+    fn insert(mut self, w: W, i: u32) -> Self {
+        self.0[i as usize] = w;
+        self
+    }
+}
+impl<W: Copy + Store<vec128_storage>, G> Store<vec256_storage> for x2<W, G> {
+    #[inline(always)]
+    unsafe fn unpack(p: vec256_storage) -> Self {
+        let p = p.split128();
+        x2::new([W::unpack(p[0]), W::unpack(p[1])])
+    }
+}
+impl<W, G> From<x2<W, G>> for vec256_storage
+where
+    W: Copy,
+    vec128_storage: From<W>,
+{
+    #[inline(always)]
+    fn from(x: x2<W, G>) -> Self {
+        vec256_storage::new128([x.0[0].into(), x.0[1].into()])
+    }
+}
+impl<W, G> Swap64 for x2<W, G>
+where
+    W: Swap64 + Copy,
+{
+    fwd_unop_x2!(swap1);
+    fwd_unop_x2!(swap2);
+    fwd_unop_x2!(swap4);
+    fwd_unop_x2!(swap8);
+    fwd_unop_x2!(swap16);
+    fwd_unop_x2!(swap32);
+    fwd_unop_x2!(swap64);
+}
+impl<W: Copy, G> MultiLane<[W; 2]> for x2<W, G> {
+    #[inline(always)]
+    fn to_lanes(self) -> [W; 2] {
+        self.0
+    }
+    #[inline(always)]
+    fn from_lanes(lanes: [W; 2]) -> Self {
+        x2::new(lanes)
+    }
+}
+impl<W: BSwap + Copy, G> BSwap for x2<W, G> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        x2::new([self.0[0].bswap(), self.0[1].bswap()])
+    }
+}
+impl<W: StoreBytes + BSwap + Copy, G> StoreBytes for x2<W, G> {
+    #[inline(always)]
+    unsafe fn unsafe_read_le(input: &[u8]) -> Self {
+        let input = input.split_at(input.len() / 2);
+        x2::new([W::unsafe_read_le(input.0), W::unsafe_read_le(input.1)])
+    }
+    #[inline(always)]
+    unsafe fn unsafe_read_be(input: &[u8]) -> Self {
+        let input = input.split_at(input.len() / 2);
+        x2::new([W::unsafe_read_be(input.0), W::unsafe_read_be(input.1)])
+    }
+    #[inline(always)]
+    fn write_le(self, out: &mut [u8]) {
+        let out = out.split_at_mut(out.len() / 2);
+        self.0[0].write_le(out.0);
+        self.0[1].write_le(out.1);
+    }
+    #[inline(always)]
+    fn write_be(self, out: &mut [u8]) {
+        let out = out.split_at_mut(out.len() / 2);
+        self.0[0].write_be(out.0);
+        self.0[1].write_be(out.1);
+    }
+}
+impl<W: Copy + LaneWords4, G: Copy> LaneWords4 for x2<W, G> {
+    #[inline(always)]
+    fn shuffle_lane_words2301(self) -> Self {
+        Self::new([
+            self.0[0].shuffle_lane_words2301(),
+            self.0[1].shuffle_lane_words2301(),
+        ])
+    }
+    #[inline(always)]
+    fn shuffle_lane_words1230(self) -> Self {
+        Self::new([
+            self.0[0].shuffle_lane_words1230(),
+            self.0[1].shuffle_lane_words1230(),
+        ])
+    }
+    #[inline(always)]
+    fn shuffle_lane_words3012(self) -> Self {
+        Self::new([
+            self.0[0].shuffle_lane_words3012(),
+            self.0[1].shuffle_lane_words3012(),
+        ])
+    }
+}
+
+#[derive(Copy, Clone, Default)]
+#[allow(non_camel_case_types)]
+pub struct x4<W>(pub [W; 4]);
+impl<W> x4<W> {
+    #[inline(always)]
+    pub fn new(xs: [W; 4]) -> Self {
+        x4(xs)
+    }
+}
+macro_rules! fwd_binop_x4 {
+    ($trait:ident, $fn:ident) => {
+        impl<W: $trait + Copy> $trait for x4<W> {
+            type Output = x4<W::Output>;
+            #[inline(always)]
+            fn $fn(self, rhs: Self) -> Self::Output {
+                x4([
+                    self.0[0].$fn(rhs.0[0]),
+                    self.0[1].$fn(rhs.0[1]),
+                    self.0[2].$fn(rhs.0[2]),
+                    self.0[3].$fn(rhs.0[3]),
+                ])
+            }
+        }
+    };
+}
+macro_rules! fwd_binop_assign_x4 {
+    ($trait:ident, $fn_assign:ident) => {
+        impl<W: $trait + Copy> $trait for x4<W> {
+            #[inline(always)]
+            fn $fn_assign(&mut self, rhs: Self) {
+                self.0[0].$fn_assign(rhs.0[0]);
+                self.0[1].$fn_assign(rhs.0[1]);
+                self.0[2].$fn_assign(rhs.0[2]);
+                self.0[3].$fn_assign(rhs.0[3]);
+            }
+        }
+    };
+}
+macro_rules! fwd_unop_x4 {
+    ($fn:ident) => {
+        #[inline(always)]
+        fn $fn(self) -> Self {
+            x4([
+                self.0[0].$fn(),
+                self.0[1].$fn(),
+                self.0[2].$fn(),
+                self.0[3].$fn(),
+            ])
+        }
+    };
+}
+impl<W> RotateEachWord32 for x4<W>
+where
+    W: Copy + RotateEachWord32,
+{
+    fwd_unop_x4!(rotate_each_word_right7);
+    fwd_unop_x4!(rotate_each_word_right8);
+    fwd_unop_x4!(rotate_each_word_right11);
+    fwd_unop_x4!(rotate_each_word_right12);
+    fwd_unop_x4!(rotate_each_word_right16);
+    fwd_unop_x4!(rotate_each_word_right20);
+    fwd_unop_x4!(rotate_each_word_right24);
+    fwd_unop_x4!(rotate_each_word_right25);
+}
+impl<W> RotateEachWord64 for x4<W>
+where
+    W: Copy + RotateEachWord64,
+{
+    fwd_unop_x4!(rotate_each_word_right32);
+}
+impl<W> RotateEachWord128 for x4<W> where W: RotateEachWord128 {}
+impl<W> BitOps0 for x4<W> where W: BitOps0 {}
+impl<W> BitOps32 for x4<W> where W: BitOps32 + BitOps0 {}
+impl<W> BitOps64 for x4<W> where W: BitOps64 + BitOps0 {}
+impl<W> BitOps128 for x4<W> where W: BitOps128 + BitOps0 {}
+fwd_binop_x4!(BitAnd, bitand);
+fwd_binop_x4!(BitOr, bitor);
+fwd_binop_x4!(BitXor, bitxor);
+fwd_binop_x4!(AndNot, andnot);
+fwd_binop_assign_x4!(BitAndAssign, bitand_assign);
+fwd_binop_assign_x4!(BitOrAssign, bitor_assign);
+fwd_binop_assign_x4!(BitXorAssign, bitxor_assign);
+impl<W> ArithOps for x4<W> where W: ArithOps {}
+fwd_binop_x4!(Add, add);
+fwd_binop_assign_x4!(AddAssign, add_assign);
+impl<W: Not + Copy> Not for x4<W> {
+    type Output = x4<W::Output>;
+    #[inline(always)]
+    fn not(self) -> Self::Output {
+        x4([
+            self.0[0].not(),
+            self.0[1].not(),
+            self.0[2].not(),
+            self.0[3].not(),
+        ])
+    }
+}
+impl<W> UnsafeFrom<[W; 4]> for x4<W> {
+    #[inline(always)]
+    unsafe fn unsafe_from(xs: [W; 4]) -> Self {
+        x4(xs)
+    }
+}
+impl<W: Copy> Vec4<W> for x4<W> {
+    #[inline(always)]
+    fn extract(self, i: u32) -> W {
+        self.0[i as usize]
+    }
+    #[inline(always)]
+    fn insert(mut self, w: W, i: u32) -> Self {
+        self.0[i as usize] = w;
+        self
+    }
+}
+impl<W: Copy> Vec4Ext<W> for x4<W> {
+    #[inline(always)]
+    fn transpose4(a: Self, b: Self, c: Self, d: Self) -> (Self, Self, Self, Self)
+    where
+        Self: Sized,
+    {
+        (
+            x4([a.0[0], b.0[0], c.0[0], d.0[0]]),
+            x4([a.0[1], b.0[1], c.0[1], d.0[1]]),
+            x4([a.0[2], b.0[2], c.0[2], d.0[2]]),
+            x4([a.0[3], b.0[3], c.0[3], d.0[3]]),
+        )
+    }
+}
+impl<W: Copy + Store<vec128_storage>> Store<vec512_storage> for x4<W> {
+    #[inline(always)]
+    unsafe fn unpack(p: vec512_storage) -> Self {
+        let p = p.split128();
+        x4([
+            W::unpack(p[0]),
+            W::unpack(p[1]),
+            W::unpack(p[2]),
+            W::unpack(p[3]),
+        ])
+    }
+}
+impl<W> From<x4<W>> for vec512_storage
+where
+    W: Copy,
+    vec128_storage: From<W>,
+{
+    #[inline(always)]
+    fn from(x: x4<W>) -> Self {
+        vec512_storage::new128([x.0[0].into(), x.0[1].into(), x.0[2].into(), x.0[3].into()])
+    }
+}
+impl<W> Swap64 for x4<W>
+where
+    W: Swap64 + Copy,
+{
+    fwd_unop_x4!(swap1);
+    fwd_unop_x4!(swap2);
+    fwd_unop_x4!(swap4);
+    fwd_unop_x4!(swap8);
+    fwd_unop_x4!(swap16);
+    fwd_unop_x4!(swap32);
+    fwd_unop_x4!(swap64);
+}
+impl<W: Copy> MultiLane<[W; 4]> for x4<W> {
+    #[inline(always)]
+    fn to_lanes(self) -> [W; 4] {
+        self.0
+    }
+    #[inline(always)]
+    fn from_lanes(lanes: [W; 4]) -> Self {
+        x4(lanes)
+    }
+}
+impl<W: BSwap + Copy> BSwap for x4<W> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        x4([
+            self.0[0].bswap(),
+            self.0[1].bswap(),
+            self.0[2].bswap(),
+            self.0[3].bswap(),
+        ])
+    }
+}
+impl<W: StoreBytes + BSwap + Copy> StoreBytes for x4<W> {
+    #[inline(always)]
+    unsafe fn unsafe_read_le(input: &[u8]) -> Self {
+        let n = input.len() / 4;
+        x4([
+            W::unsafe_read_le(&input[..n]),
+            W::unsafe_read_le(&input[n..n * 2]),
+            W::unsafe_read_le(&input[n * 2..n * 3]),
+            W::unsafe_read_le(&input[n * 3..]),
+        ])
+    }
+    #[inline(always)]
+    unsafe fn unsafe_read_be(input: &[u8]) -> Self {
+        let n = input.len() / 4;
+        x4([
+            W::unsafe_read_be(&input[..n]),
+            W::unsafe_read_be(&input[n..n * 2]),
+            W::unsafe_read_be(&input[n * 2..n * 3]),
+            W::unsafe_read_be(&input[n * 3..]),
+        ])
+    }
+    #[inline(always)]
+    fn write_le(self, out: &mut [u8]) {
+        let n = out.len() / 4;
+        self.0[0].write_le(&mut out[..n]);
+        self.0[1].write_le(&mut out[n..n * 2]);
+        self.0[2].write_le(&mut out[n * 2..n * 3]);
+        self.0[3].write_le(&mut out[n * 3..]);
+    }
+    #[inline(always)]
+    fn write_be(self, out: &mut [u8]) {
+        let n = out.len() / 4;
+        self.0[0].write_be(&mut out[..n]);
+        self.0[1].write_be(&mut out[n..n * 2]);
+        self.0[2].write_be(&mut out[n * 2..n * 3]);
+        self.0[3].write_be(&mut out[n * 3..]);
+    }
+}
+impl<W: Copy + LaneWords4> LaneWords4 for x4<W> {
+    #[inline(always)]
+    fn shuffle_lane_words2301(self) -> Self {
+        x4([
+            self.0[0].shuffle_lane_words2301(),
+            self.0[1].shuffle_lane_words2301(),
+            self.0[2].shuffle_lane_words2301(),
+            self.0[3].shuffle_lane_words2301(),
+        ])
+    }
+    #[inline(always)]
+    fn shuffle_lane_words1230(self) -> Self {
+        x4([
+            self.0[0].shuffle_lane_words1230(),
+            self.0[1].shuffle_lane_words1230(),
+            self.0[2].shuffle_lane_words1230(),
+            self.0[3].shuffle_lane_words1230(),
+        ])
+    }
+    #[inline(always)]
+    fn shuffle_lane_words3012(self) -> Self {
+        x4([
+            self.0[0].shuffle_lane_words3012(),
+            self.0[1].shuffle_lane_words3012(),
+            self.0[2].shuffle_lane_words3012(),
+            self.0[3].shuffle_lane_words3012(),
+        ])
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/types.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/types.rs.html new file mode 100644 index 0000000..40e2382 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/types.rs.html @@ -0,0 +1,598 @@ +types.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+
#![allow(non_camel_case_types)]
+use core::ops::{Add, AddAssign, BitAnd, BitOr, BitXor, BitXorAssign, Not};
+
+pub trait AndNot {
+    type Output;
+    fn andnot(self, rhs: Self) -> Self::Output;
+}
+pub trait BSwap {
+    fn bswap(self) -> Self;
+}
+/// Ops that depend on word size
+pub trait ArithOps: Add<Output = Self> + AddAssign + Sized + Copy + Clone + BSwap {}
+/// Ops that are independent of word size and endian
+pub trait BitOps0:
+    BitAnd<Output = Self>
+    + BitOr<Output = Self>
+    + BitXor<Output = Self>
+    + BitXorAssign
+    + Not<Output = Self>
+    + AndNot<Output = Self>
+    + Sized
+    + Copy
+    + Clone
+{
+}
+
+pub trait BitOps32: BitOps0 + RotateEachWord32 {}
+pub trait BitOps64: BitOps32 + RotateEachWord64 {}
+pub trait BitOps128: BitOps64 + RotateEachWord128 {}
+
+pub trait RotateEachWord32 {
+    fn rotate_each_word_right7(self) -> Self;
+    fn rotate_each_word_right8(self) -> Self;
+    fn rotate_each_word_right11(self) -> Self;
+    fn rotate_each_word_right12(self) -> Self;
+    fn rotate_each_word_right16(self) -> Self;
+    fn rotate_each_word_right20(self) -> Self;
+    fn rotate_each_word_right24(self) -> Self;
+    fn rotate_each_word_right25(self) -> Self;
+}
+
+pub trait RotateEachWord64 {
+    fn rotate_each_word_right32(self) -> Self;
+}
+
+pub trait RotateEachWord128 {}
+
+// Vector type naming scheme:
+// uN[xP]xL
+// Unsigned; N-bit words * P bits per lane * L lanes
+//
+// A lane is always 128-bits, chosen because common SIMD architectures treat 128-bit units of
+// wide vectors specially (supporting e.g. intra-lane shuffles), and tend to have limited and
+// slow inter-lane operations.
+
+use crate::arch::{vec128_storage, vec256_storage, vec512_storage};
+
+#[allow(clippy::missing_safety_doc)]
+pub trait UnsafeFrom<T> {
+    unsafe fn unsafe_from(t: T) -> Self;
+}
+
+/// A vector composed of two elements, which may be words or themselves vectors.
+pub trait Vec2<W> {
+    fn extract(self, i: u32) -> W;
+    fn insert(self, w: W, i: u32) -> Self;
+}
+
+/// A vector composed of four elements, which may be words or themselves vectors.
+pub trait Vec4<W> {
+    fn extract(self, i: u32) -> W;
+    fn insert(self, w: W, i: u32) -> Self;
+}
+/// Vec4 functions which may not be implemented yet for all Vec4 types.
+/// NOTE: functions in this trait may be moved to Vec4 in any patch release. To avoid breakage,
+/// import Vec4Ext only together with Vec4, and don't qualify its methods.
+pub trait Vec4Ext<W> {
+    fn transpose4(a: Self, b: Self, c: Self, d: Self) -> (Self, Self, Self, Self)
+    where
+        Self: Sized;
+}
+pub trait Vector<T> {
+    fn to_scalars(self) -> T;
+}
+
+// TODO: multiples of 4 should inherit this
+/// A vector composed of four words; depending on their size, operations may cross lanes.
+pub trait Words4 {
+    fn shuffle1230(self) -> Self;
+    fn shuffle2301(self) -> Self;
+    fn shuffle3012(self) -> Self;
+}
+
+/// A vector composed one or more lanes each composed of four words.
+pub trait LaneWords4 {
+    fn shuffle_lane_words1230(self) -> Self;
+    fn shuffle_lane_words2301(self) -> Self;
+    fn shuffle_lane_words3012(self) -> Self;
+}
+
+// TODO: make this a part of BitOps
+/// Exchange neigboring ranges of bits of the specified size
+pub trait Swap64 {
+    fn swap1(self) -> Self;
+    fn swap2(self) -> Self;
+    fn swap4(self) -> Self;
+    fn swap8(self) -> Self;
+    fn swap16(self) -> Self;
+    fn swap32(self) -> Self;
+    fn swap64(self) -> Self;
+}
+
+pub trait u32x4<M: Machine>:
+    BitOps32
+    + Store<vec128_storage>
+    + ArithOps
+    + Vec4<u32>
+    + Words4
+    + LaneWords4
+    + StoreBytes
+    + MultiLane<[u32; 4]>
+    + Into<vec128_storage>
+{
+}
+pub trait u64x2<M: Machine>:
+    BitOps64 + Store<vec128_storage> + ArithOps + Vec2<u64> + MultiLane<[u64; 2]> + Into<vec128_storage>
+{
+}
+pub trait u128x1<M: Machine>:
+    BitOps128 + Store<vec128_storage> + Swap64 + MultiLane<[u128; 1]> + Into<vec128_storage>
+{
+}
+
+pub trait u32x4x2<M: Machine>:
+    BitOps32
+    + Store<vec256_storage>
+    + Vec2<M::u32x4>
+    + MultiLane<[M::u32x4; 2]>
+    + ArithOps
+    + Into<vec256_storage>
+    + StoreBytes
+{
+}
+pub trait u64x2x2<M: Machine>:
+    BitOps64
+    + Store<vec256_storage>
+    + Vec2<M::u64x2>
+    + MultiLane<[M::u64x2; 2]>
+    + ArithOps
+    + StoreBytes
+    + Into<vec256_storage>
+{
+}
+pub trait u64x4<M: Machine>:
+    BitOps64
+    + Store<vec256_storage>
+    + Vec4<u64>
+    + MultiLane<[u64; 4]>
+    + ArithOps
+    + Words4
+    + StoreBytes
+    + Into<vec256_storage>
+{
+}
+pub trait u128x2<M: Machine>:
+    BitOps128
+    + Store<vec256_storage>
+    + Vec2<M::u128x1>
+    + MultiLane<[M::u128x1; 2]>
+    + Swap64
+    + Into<vec256_storage>
+{
+}
+
+pub trait u32x4x4<M: Machine>:
+    BitOps32
+    + Store<vec512_storage>
+    + Vec4<M::u32x4>
+    + Vec4Ext<M::u32x4>
+    + Vector<[u32; 16]>
+    + MultiLane<[M::u32x4; 4]>
+    + ArithOps
+    + LaneWords4
+    + Into<vec512_storage>
+    + StoreBytes
+{
+}
+pub trait u64x2x4<M: Machine>:
+    BitOps64
+    + Store<vec512_storage>
+    + Vec4<M::u64x2>
+    + MultiLane<[M::u64x2; 4]>
+    + ArithOps
+    + Into<vec512_storage>
+{
+}
+// TODO: Words4
+pub trait u128x4<M: Machine>:
+    BitOps128
+    + Store<vec512_storage>
+    + Vec4<M::u128x1>
+    + MultiLane<[M::u128x1; 4]>
+    + Swap64
+    + Into<vec512_storage>
+{
+}
+
+/// A vector composed of multiple 128-bit lanes.
+pub trait MultiLane<Lanes> {
+    /// Split a multi-lane vector into single-lane vectors.
+    fn to_lanes(self) -> Lanes;
+    /// Build a multi-lane vector from individual lanes.
+    fn from_lanes(lanes: Lanes) -> Self;
+}
+
+/// Combine single vectors into a multi-lane vector.
+pub trait VZip<V> {
+    fn vzip(self) -> V;
+}
+
+impl<V, T> VZip<V> for T
+where
+    V: MultiLane<T>,
+{
+    #[inline(always)]
+    fn vzip(self) -> V {
+        V::from_lanes(self)
+    }
+}
+
+pub trait Machine: Sized + Copy {
+    type u32x4: u32x4<Self>;
+    type u64x2: u64x2<Self>;
+    type u128x1: u128x1<Self>;
+
+    type u32x4x2: u32x4x2<Self>;
+    type u64x2x2: u64x2x2<Self>;
+    type u64x4: u64x4<Self>;
+    type u128x2: u128x2<Self>;
+
+    type u32x4x4: u32x4x4<Self>;
+    type u64x2x4: u64x2x4<Self>;
+    type u128x4: u128x4<Self>;
+
+    #[inline(always)]
+    fn unpack<S, V: Store<S>>(self, s: S) -> V {
+        unsafe { V::unpack(s) }
+    }
+
+    #[inline(always)]
+    fn vec<V, A>(self, a: A) -> V
+    where
+        V: MultiLane<A>,
+    {
+        V::from_lanes(a)
+    }
+
+    #[inline(always)]
+    fn read_le<V>(self, input: &[u8]) -> V
+    where
+        V: StoreBytes,
+    {
+        unsafe { V::unsafe_read_le(input) }
+    }
+
+    #[inline(always)]
+    fn read_be<V>(self, input: &[u8]) -> V
+    where
+        V: StoreBytes,
+    {
+        unsafe { V::unsafe_read_be(input) }
+    }
+
+    /// # Safety
+    /// Caller must ensure the type of Self is appropriate for the hardware of the execution
+    /// environment.
+    unsafe fn instance() -> Self;
+}
+
+pub trait Store<S> {
+    /// # Safety
+    /// Caller must ensure the type of Self is appropriate for the hardware of the execution
+    /// environment.
+    unsafe fn unpack(p: S) -> Self;
+}
+
+pub trait StoreBytes {
+    /// # Safety
+    /// Caller must ensure the type of Self is appropriate for the hardware of the execution
+    /// environment.
+    unsafe fn unsafe_read_le(input: &[u8]) -> Self;
+    /// # Safety
+    /// Caller must ensure the type of Self is appropriate for the hardware of the execution
+    /// environment.
+    unsafe fn unsafe_read_be(input: &[u8]) -> Self;
+    fn write_le(self, out: &mut [u8]);
+    fn write_be(self, out: &mut [u8]);
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/mod.rs.html new file mode 100644 index 0000000..c649c50 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/mod.rs.html @@ -0,0 +1,876 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+
// crate minimums: sse2, x86_64
+
+use crate::types::*;
+use core::arch::x86_64::{__m128i, __m256i};
+
+mod sse2;
+
+#[derive(Copy, Clone)]
+pub struct YesS3;
+#[derive(Copy, Clone)]
+pub struct NoS3;
+
+#[derive(Copy, Clone)]
+pub struct YesS4;
+#[derive(Copy, Clone)]
+pub struct NoS4;
+
+#[derive(Copy, Clone)]
+pub struct YesA1;
+#[derive(Copy, Clone)]
+pub struct NoA1;
+
+#[derive(Copy, Clone)]
+pub struct YesA2;
+#[derive(Copy, Clone)]
+pub struct NoA2;
+
+#[derive(Copy, Clone)]
+pub struct YesNI;
+#[derive(Copy, Clone)]
+pub struct NoNI;
+
+use core::marker::PhantomData;
+
+#[derive(Copy, Clone)]
+pub struct SseMachine<S3, S4, NI>(PhantomData<(S3, S4, NI)>);
+impl<S3: Copy, S4: Copy, NI: Copy> Machine for SseMachine<S3, S4, NI>
+where
+    sse2::u128x1_sse2<S3, S4, NI>: Swap64,
+    sse2::u64x2_sse2<S3, S4, NI>: BSwap + RotateEachWord32 + MultiLane<[u64; 2]> + Vec2<u64>,
+    sse2::u32x4_sse2<S3, S4, NI>: BSwap + RotateEachWord32 + MultiLane<[u32; 4]> + Vec4<u32>,
+    sse2::u64x4_sse2<S3, S4, NI>: BSwap + Words4,
+    sse2::u128x1_sse2<S3, S4, NI>: BSwap,
+    sse2::u128x2_sse2<S3, S4, NI>: Into<sse2::u64x2x2_sse2<S3, S4, NI>>,
+    sse2::u128x2_sse2<S3, S4, NI>: Into<sse2::u64x4_sse2<S3, S4, NI>>,
+    sse2::u128x2_sse2<S3, S4, NI>: Into<sse2::u32x4x2_sse2<S3, S4, NI>>,
+    sse2::u128x4_sse2<S3, S4, NI>: Into<sse2::u64x2x4_sse2<S3, S4, NI>>,
+    sse2::u128x4_sse2<S3, S4, NI>: Into<sse2::u32x4x4_sse2<S3, S4, NI>>,
+{
+    type u32x4 = sse2::u32x4_sse2<S3, S4, NI>;
+    type u64x2 = sse2::u64x2_sse2<S3, S4, NI>;
+    type u128x1 = sse2::u128x1_sse2<S3, S4, NI>;
+
+    type u32x4x2 = sse2::u32x4x2_sse2<S3, S4, NI>;
+    type u64x2x2 = sse2::u64x2x2_sse2<S3, S4, NI>;
+    type u64x4 = sse2::u64x4_sse2<S3, S4, NI>;
+    type u128x2 = sse2::u128x2_sse2<S3, S4, NI>;
+
+    type u32x4x4 = sse2::u32x4x4_sse2<S3, S4, NI>;
+    type u64x2x4 = sse2::u64x2x4_sse2<S3, S4, NI>;
+    type u128x4 = sse2::u128x4_sse2<S3, S4, NI>;
+
+    #[inline(always)]
+    unsafe fn instance() -> Self {
+        SseMachine(PhantomData)
+    }
+}
+
+#[derive(Copy, Clone)]
+pub struct Avx2Machine<NI>(PhantomData<NI>);
+impl<NI: Copy> Machine for Avx2Machine<NI>
+where
+    sse2::u128x1_sse2<YesS3, YesS4, NI>: BSwap + Swap64,
+    sse2::u64x2_sse2<YesS3, YesS4, NI>: BSwap + RotateEachWord32 + MultiLane<[u64; 2]> + Vec2<u64>,
+    sse2::u32x4_sse2<YesS3, YesS4, NI>: BSwap + RotateEachWord32 + MultiLane<[u32; 4]> + Vec4<u32>,
+    sse2::u64x4_sse2<YesS3, YesS4, NI>: BSwap + Words4,
+{
+    type u32x4 = sse2::u32x4_sse2<YesS3, YesS4, NI>;
+    type u64x2 = sse2::u64x2_sse2<YesS3, YesS4, NI>;
+    type u128x1 = sse2::u128x1_sse2<YesS3, YesS4, NI>;
+
+    type u32x4x2 = sse2::avx2::u32x4x2_avx2<NI>;
+    type u64x2x2 = sse2::u64x2x2_sse2<YesS3, YesS4, NI>;
+    type u64x4 = sse2::u64x4_sse2<YesS3, YesS4, NI>;
+    type u128x2 = sse2::u128x2_sse2<YesS3, YesS4, NI>;
+
+    type u32x4x4 = sse2::avx2::u32x4x4_avx2<NI>;
+    type u64x2x4 = sse2::u64x2x4_sse2<YesS3, YesS4, NI>;
+    type u128x4 = sse2::u128x4_sse2<YesS3, YesS4, NI>;
+
+    #[inline(always)]
+    unsafe fn instance() -> Self {
+        Avx2Machine(PhantomData)
+    }
+}
+
+pub type SSE2 = SseMachine<NoS3, NoS4, NoNI>;
+pub type SSSE3 = SseMachine<YesS3, NoS4, NoNI>;
+pub type SSE41 = SseMachine<YesS3, YesS4, NoNI>;
+/// AVX but not AVX2: only 128-bit integer operations, but use VEX versions of everything
+/// to avoid expensive SSE/VEX conflicts.
+pub type AVX = SseMachine<YesS3, YesS4, NoNI>;
+pub type AVX2 = Avx2Machine<NoNI>;
+
+/// Generic wrapper for unparameterized storage of any of the possible impls.
+/// Converting into and out of this type should be essentially free, although it may be more
+/// aligned than a particular impl requires.
+#[allow(non_camel_case_types)]
+#[derive(Copy, Clone)]
+pub union vec128_storage {
+    u32x4: [u32; 4],
+    u64x2: [u64; 2],
+    u128x1: [u128; 1],
+    sse2: __m128i,
+}
+impl Store<vec128_storage> for vec128_storage {
+    #[inline(always)]
+    unsafe fn unpack(p: vec128_storage) -> Self {
+        p
+    }
+}
+impl<'a> From<&'a vec128_storage> for &'a [u32; 4] {
+    #[inline(always)]
+    fn from(x: &'a vec128_storage) -> Self {
+        unsafe { &x.u32x4 }
+    }
+}
+impl From<[u32; 4]> for vec128_storage {
+    #[inline(always)]
+    fn from(u32x4: [u32; 4]) -> Self {
+        vec128_storage { u32x4 }
+    }
+}
+impl Default for vec128_storage {
+    #[inline(always)]
+    fn default() -> Self {
+        vec128_storage { u128x1: [0] }
+    }
+}
+impl Eq for vec128_storage {}
+impl PartialEq for vec128_storage {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        unsafe { self.u128x1 == rhs.u128x1 }
+    }
+}
+
+#[allow(non_camel_case_types)]
+#[derive(Copy, Clone)]
+pub union vec256_storage {
+    u32x8: [u32; 8],
+    u64x4: [u64; 4],
+    u128x2: [u128; 2],
+    sse2: [vec128_storage; 2],
+    avx: __m256i,
+}
+impl From<[u64; 4]> for vec256_storage {
+    #[inline(always)]
+    fn from(u64x4: [u64; 4]) -> Self {
+        vec256_storage { u64x4 }
+    }
+}
+impl Default for vec256_storage {
+    #[inline(always)]
+    fn default() -> Self {
+        vec256_storage { u128x2: [0, 0] }
+    }
+}
+impl vec256_storage {
+    #[inline(always)]
+    pub fn new128(xs: [vec128_storage; 2]) -> Self {
+        Self { sse2: xs }
+    }
+    #[inline(always)]
+    pub fn split128(self) -> [vec128_storage; 2] {
+        unsafe { self.sse2 }
+    }
+}
+impl Eq for vec256_storage {}
+impl PartialEq for vec256_storage {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        unsafe { self.sse2 == rhs.sse2 }
+    }
+}
+
+#[allow(non_camel_case_types)]
+#[derive(Copy, Clone)]
+pub union vec512_storage {
+    u32x16: [u32; 16],
+    u64x8: [u64; 8],
+    u128x4: [u128; 4],
+    sse2: [vec128_storage; 4],
+    avx: [vec256_storage; 2],
+}
+impl Default for vec512_storage {
+    #[inline(always)]
+    fn default() -> Self {
+        vec512_storage {
+            u128x4: [0, 0, 0, 0],
+        }
+    }
+}
+impl vec512_storage {
+    #[inline(always)]
+    pub fn new128(xs: [vec128_storage; 4]) -> Self {
+        Self { sse2: xs }
+    }
+    #[inline(always)]
+    pub fn split128(self) -> [vec128_storage; 4] {
+        unsafe { self.sse2 }
+    }
+}
+impl Eq for vec512_storage {}
+impl PartialEq for vec512_storage {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        unsafe { self.avx == rhs.avx }
+    }
+}
+
+macro_rules! impl_into {
+    ($storage:ident, $array:ty, $name:ident) => {
+        impl From<$storage> for $array {
+            #[inline(always)]
+            fn from(vec: $storage) -> Self {
+                unsafe { vec.$name }
+            }
+        }
+    };
+}
+impl_into!(vec128_storage, [u32; 4], u32x4);
+impl_into!(vec128_storage, [u64; 2], u64x2);
+impl_into!(vec128_storage, [u128; 1], u128x1);
+impl_into!(vec256_storage, [u32; 8], u32x8);
+impl_into!(vec256_storage, [u64; 4], u64x4);
+impl_into!(vec256_storage, [u128; 2], u128x2);
+impl_into!(vec512_storage, [u32; 16], u32x16);
+impl_into!(vec512_storage, [u64; 8], u64x8);
+impl_into!(vec512_storage, [u128; 4], u128x4);
+
+/// Generate the full set of optimized implementations to take advantage of the most important
+/// hardware feature sets.
+///
+/// This dispatcher is suitable for maximizing throughput.
+#[macro_export]
+macro_rules! dispatch {
+    ($mach:ident, $MTy:ident, { $([$pub:tt$(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) -> $ret:ty $body:block }) => {
+        #[cfg(feature = "std")]
+        $($pub$(($krate))*)* fn $name($($arg: $argty),*) -> $ret {
+            #[inline(always)]
+            fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            use std::arch::x86_64::*;
+            #[target_feature(enable = "avx2")]
+            unsafe fn impl_avx2($($arg: $argty),*) -> $ret {
+                let ret = fn_impl($crate::x86_64::AVX2::instance(), $($arg),*);
+                _mm256_zeroupper();
+                ret
+            }
+            #[target_feature(enable = "avx")]
+            #[target_feature(enable = "sse4.1")]
+            #[target_feature(enable = "ssse3")]
+            unsafe fn impl_avx($($arg: $argty),*) -> $ret {
+                let ret = fn_impl($crate::x86_64::AVX::instance(), $($arg),*);
+                _mm256_zeroupper();
+                ret
+            }
+            #[target_feature(enable = "sse4.1")]
+            #[target_feature(enable = "ssse3")]
+            unsafe fn impl_sse41($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::SSE41::instance(), $($arg),*)
+            }
+            #[target_feature(enable = "ssse3")]
+            unsafe fn impl_ssse3($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::SSSE3::instance(), $($arg),*)
+            }
+            #[target_feature(enable = "sse2")]
+            unsafe fn impl_sse2($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+            }
+            unsafe {
+                if is_x86_feature_detected!("avx2") {
+                    impl_avx2($($arg),*)
+                } else if is_x86_feature_detected!("avx") {
+                    impl_avx($($arg),*)
+                } else if is_x86_feature_detected!("sse4.1") {
+                    impl_sse41($($arg),*)
+                } else if is_x86_feature_detected!("ssse3") {
+                    impl_ssse3($($arg),*)
+                } else if is_x86_feature_detected!("sse2") {
+                    impl_sse2($($arg),*)
+                } else {
+                    unimplemented!()
+                }
+            }
+        }
+        #[cfg(not(feature = "std"))]
+        #[inline(always)]
+        $($pub$(($krate))*)* fn $name($($arg: $argty),*) -> $ret {
+            unsafe fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            unsafe {
+                if cfg!(target_feature = "avx2") {
+                    fn_impl($crate::x86_64::AVX2::instance(), $($arg),*)
+                } else if cfg!(target_feature = "avx") {
+                    fn_impl($crate::x86_64::AVX::instance(), $($arg),*)
+                } else if cfg!(target_feature = "sse4.1") {
+                    fn_impl($crate::x86_64::SSE41::instance(), $($arg),*)
+                } else if cfg!(target_feature = "ssse3") {
+                    fn_impl($crate::x86_64::SSSE3::instance(), $($arg),*)
+                } else {
+                    fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+                }
+            }
+        }
+    };
+    ($mach:ident, $MTy:ident, { $([$pub:tt $(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) $body:block }) => {
+        dispatch!($mach, $MTy, {
+            $([$pub $(($krate))*])* fn $name($($arg: $argty),*) -> () $body
+        });
+    }
+}
+
+/// Generate only the basic implementations necessary to be able to operate efficiently on 128-bit
+/// vectors on this platfrom. For x86-64, that would mean SSE2 and AVX.
+///
+/// This dispatcher is suitable for vector operations that do not benefit from advanced hardware
+/// features (e.g. because they are done infrequently), so minimizing their contribution to code
+/// size is more important.
+#[macro_export]
+macro_rules! dispatch_light128 {
+    ($mach:ident, $MTy:ident, { $([$pub:tt$(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) -> $ret:ty $body:block }) => {
+        #[cfg(feature = "std")]
+        $($pub $(($krate))*)* fn $name($($arg: $argty),*) -> $ret {
+            #[inline(always)]
+            fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            use std::arch::x86_64::*;
+            #[target_feature(enable = "avx")]
+            unsafe fn impl_avx($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::AVX::instance(), $($arg),*)
+            }
+            #[target_feature(enable = "sse2")]
+            unsafe fn impl_sse2($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+            }
+            unsafe {
+                if is_x86_feature_detected!("avx") {
+                    impl_avx($($arg),*)
+                } else if is_x86_feature_detected!("sse2") {
+                    impl_sse2($($arg),*)
+                } else {
+                    unimplemented!()
+                }
+            }
+        }
+        #[cfg(not(feature = "std"))]
+        #[inline(always)]
+        $($pub$(($krate))*)* fn $name($($arg: $argty),*) -> $ret {
+            unsafe fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            unsafe {
+                if cfg!(target_feature = "avx2") {
+                    fn_impl($crate::x86_64::AVX2::instance(), $($arg),*)
+                } else if cfg!(target_feature = "avx") {
+                    fn_impl($crate::x86_64::AVX::instance(), $($arg),*)
+                } else if cfg!(target_feature = "sse4.1") {
+                    fn_impl($crate::x86_64::SSE41::instance(), $($arg),*)
+                } else if cfg!(target_feature = "ssse3") {
+                    fn_impl($crate::x86_64::SSSE3::instance(), $($arg),*)
+                } else {
+                    fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+                }
+            }
+        }
+    };
+    ($mach:ident, $MTy:ident, { $([$pub:tt$(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) $body:block }) => {
+        dispatch_light128!($mach, $MTy, {
+            $([$pub $(($krate))*])* fn $name($($arg: $argty),*) -> () $body
+        });
+    }
+}
+
+/// Generate only the basic implementations necessary to be able to operate efficiently on 256-bit
+/// vectors on this platfrom. For x86-64, that would mean SSE2, AVX, and AVX2.
+///
+/// This dispatcher is suitable for vector operations that do not benefit from advanced hardware
+/// features (e.g. because they are done infrequently), so minimizing their contribution to code
+/// size is more important.
+#[macro_export]
+macro_rules! dispatch_light256 {
+    ($mach:ident, $MTy:ident, { $([$pub:tt$(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) -> $ret:ty $body:block }) => {
+        #[cfg(feature = "std")]
+        $([$pub $(($krate))*])* fn $name($($arg: $argty),*) -> $ret {
+            #[inline(always)]
+            fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            use std::arch::x86_64::*;
+            #[target_feature(enable = "avx")]
+            unsafe fn impl_avx($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::AVX::instance(), $($arg),*)
+            }
+            #[target_feature(enable = "sse2")]
+            unsafe fn impl_sse2($($arg: $argty),*) -> $ret {
+                fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+            }
+            unsafe {
+                if is_x86_feature_detected!("avx") {
+                    impl_avx($($arg),*)
+                } else if is_x86_feature_detected!("sse2") {
+                    impl_sse2($($arg),*)
+                } else {
+                    unimplemented!()
+                }
+            }
+        }
+        #[cfg(not(feature = "std"))]
+        #[inline(always)]
+        $($pub$(($krate))*)* fn $name($($arg: $argty),*) -> $ret {
+            unsafe fn fn_impl<$MTy: $crate::Machine>($mach: $MTy, $($arg: $argty),*) -> $ret $body
+            unsafe {
+                if cfg!(target_feature = "avx2") {
+                    fn_impl($crate::x86_64::AVX2::instance(), $($arg),*)
+                } else if cfg!(target_feature = "avx") {
+                    fn_impl($crate::x86_64::AVX::instance(), $($arg),*)
+                } else if cfg!(target_feature = "sse4.1") {
+                    fn_impl($crate::x86_64::SSE41::instance(), $($arg),*)
+                } else if cfg!(target_feature = "ssse3") {
+                    fn_impl($crate::x86_64::SSSE3::instance(), $($arg),*)
+                } else {
+                    fn_impl($crate::x86_64::SSE2::instance(), $($arg),*)
+                }
+            }
+        }
+    };
+    ($mach:ident, $MTy:ident, { $([$pub:tt$(($krate:tt))*])* fn $name:ident($($arg:ident: $argty:ty),* $(,)*) $body:block }) => {
+        dispatch_light256!($mach, $MTy, {
+            $([$pub $(($krate))*])* fn $name($($arg: $argty),*) -> () $body
+        });
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/sse2.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/sse2.rs.html new file mode 100644 index 0000000..609cf09 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/ppv_lite86/x86_64/sse2.rs.html @@ -0,0 +1,3408 @@ +sse2.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+1410
+1411
+1412
+1413
+1414
+1415
+1416
+1417
+1418
+1419
+1420
+1421
+1422
+1423
+1424
+1425
+1426
+1427
+1428
+1429
+1430
+1431
+1432
+1433
+1434
+1435
+1436
+1437
+1438
+1439
+1440
+1441
+1442
+1443
+1444
+1445
+1446
+1447
+1448
+1449
+1450
+1451
+1452
+1453
+1454
+1455
+1456
+1457
+1458
+1459
+1460
+1461
+1462
+1463
+1464
+1465
+1466
+1467
+1468
+1469
+1470
+1471
+1472
+1473
+1474
+1475
+1476
+1477
+1478
+1479
+1480
+1481
+1482
+1483
+1484
+1485
+1486
+1487
+1488
+1489
+1490
+1491
+1492
+1493
+1494
+1495
+1496
+1497
+1498
+1499
+1500
+1501
+1502
+1503
+1504
+1505
+1506
+1507
+1508
+1509
+1510
+1511
+1512
+1513
+1514
+1515
+1516
+1517
+1518
+1519
+1520
+1521
+1522
+1523
+1524
+1525
+1526
+1527
+1528
+1529
+1530
+1531
+1532
+1533
+1534
+1535
+1536
+1537
+1538
+1539
+1540
+1541
+1542
+1543
+1544
+1545
+1546
+1547
+1548
+1549
+1550
+1551
+1552
+1553
+1554
+1555
+1556
+1557
+1558
+1559
+1560
+1561
+1562
+1563
+1564
+1565
+1566
+1567
+1568
+1569
+1570
+1571
+1572
+1573
+1574
+1575
+1576
+1577
+1578
+1579
+1580
+1581
+1582
+1583
+1584
+1585
+1586
+1587
+1588
+1589
+1590
+1591
+1592
+1593
+1594
+1595
+1596
+1597
+1598
+1599
+1600
+1601
+1602
+1603
+1604
+1605
+1606
+1607
+1608
+1609
+1610
+1611
+1612
+1613
+1614
+1615
+1616
+1617
+1618
+1619
+1620
+1621
+1622
+1623
+1624
+1625
+1626
+1627
+1628
+1629
+1630
+1631
+1632
+1633
+1634
+1635
+1636
+1637
+1638
+1639
+1640
+1641
+1642
+1643
+1644
+1645
+1646
+1647
+1648
+1649
+1650
+1651
+1652
+1653
+1654
+1655
+1656
+1657
+1658
+1659
+1660
+1661
+1662
+1663
+1664
+1665
+1666
+1667
+1668
+1669
+1670
+1671
+1672
+1673
+1674
+1675
+1676
+1677
+1678
+1679
+1680
+1681
+1682
+1683
+1684
+1685
+1686
+1687
+1688
+1689
+1690
+1691
+1692
+1693
+1694
+1695
+1696
+1697
+1698
+1699
+1700
+1701
+1702
+1703
+
use crate::soft::{x2, x4};
+use crate::types::*;
+use crate::vec128_storage;
+use crate::x86_64::Avx2Machine;
+use crate::x86_64::SseMachine as Machine86;
+use crate::x86_64::{NoS3, NoS4, YesS3, YesS4};
+use core::arch::x86_64::*;
+use core::marker::PhantomData;
+use core::ops::{
+    Add, AddAssign, BitAnd, BitAndAssign, BitOr, BitOrAssign, BitXor, BitXorAssign, Not,
+};
+
+macro_rules! impl_binop {
+    ($vec:ident, $trait:ident, $fn:ident, $impl_fn:ident) => {
+        impl<S3, S4, NI> $trait for $vec<S3, S4, NI> {
+            type Output = Self;
+            #[inline(always)]
+            fn $fn(self, rhs: Self) -> Self::Output {
+                Self::new(unsafe { $impl_fn(self.x, rhs.x) })
+            }
+        }
+    };
+}
+
+macro_rules! impl_binop_assign {
+    ($vec:ident, $trait:ident, $fn_assign:ident, $fn:ident) => {
+        impl<S3, S4, NI> $trait for $vec<S3, S4, NI>
+        where
+            $vec<S3, S4, NI>: Copy,
+        {
+            #[inline(always)]
+            fn $fn_assign(&mut self, rhs: Self) {
+                *self = self.$fn(rhs);
+            }
+        }
+    };
+}
+
+macro_rules! def_vec {
+    ($vec:ident, $word:ident) => {
+        #[allow(non_camel_case_types)]
+        #[derive(Copy, Clone)]
+        pub struct $vec<S3, S4, NI> {
+            x: __m128i,
+            s3: PhantomData<S3>,
+            s4: PhantomData<S4>,
+            ni: PhantomData<NI>,
+        }
+
+        impl<S3, S4, NI> Store<vec128_storage> for $vec<S3, S4, NI> {
+            #[inline(always)]
+            unsafe fn unpack(x: vec128_storage) -> Self {
+                Self::new(x.sse2)
+            }
+        }
+        impl<S3, S4, NI> From<$vec<S3, S4, NI>> for vec128_storage {
+            #[inline(always)]
+            fn from(x: $vec<S3, S4, NI>) -> Self {
+                vec128_storage { sse2: x.x }
+            }
+        }
+        impl<S3, S4, NI> $vec<S3, S4, NI> {
+            #[inline(always)]
+            fn new(x: __m128i) -> Self {
+                $vec {
+                    x,
+                    s3: PhantomData,
+                    s4: PhantomData,
+                    ni: PhantomData,
+                }
+            }
+        }
+
+        impl<S3, S4, NI> StoreBytes for $vec<S3, S4, NI>
+        where
+            Self: BSwap,
+        {
+            #[inline(always)]
+            unsafe fn unsafe_read_le(input: &[u8]) -> Self {
+                assert_eq!(input.len(), 16);
+                Self::new(_mm_loadu_si128(input.as_ptr() as *const _))
+            }
+            #[inline(always)]
+            unsafe fn unsafe_read_be(input: &[u8]) -> Self {
+                assert_eq!(input.len(), 16);
+                Self::new(_mm_loadu_si128(input.as_ptr() as *const _)).bswap()
+            }
+            #[inline(always)]
+            fn write_le(self, out: &mut [u8]) {
+                assert_eq!(out.len(), 16);
+                unsafe { _mm_storeu_si128(out.as_mut_ptr() as *mut _, self.x) }
+            }
+            #[inline(always)]
+            fn write_be(self, out: &mut [u8]) {
+                assert_eq!(out.len(), 16);
+                let x = self.bswap().x;
+                unsafe {
+                    _mm_storeu_si128(out.as_mut_ptr() as *mut _, x);
+                }
+            }
+        }
+
+        impl<S3, S4, NI> Default for $vec<S3, S4, NI> {
+            #[inline(always)]
+            fn default() -> Self {
+                Self::new(unsafe { _mm_setzero_si128() })
+            }
+        }
+
+        impl<S3, S4, NI> Not for $vec<S3, S4, NI> {
+            type Output = Self;
+            #[inline(always)]
+            fn not(self) -> Self::Output {
+                unsafe {
+                    let ff = _mm_set1_epi64x(-1i64);
+                    self ^ Self::new(ff)
+                }
+            }
+        }
+
+        impl<S3: Copy, S4: Copy, NI: Copy> BitOps0 for $vec<S3, S4, NI> {}
+        impl_binop!($vec, BitAnd, bitand, _mm_and_si128);
+        impl_binop!($vec, BitOr, bitor, _mm_or_si128);
+        impl_binop!($vec, BitXor, bitxor, _mm_xor_si128);
+        impl_binop_assign!($vec, BitAndAssign, bitand_assign, bitand);
+        impl_binop_assign!($vec, BitOrAssign, bitor_assign, bitor);
+        impl_binop_assign!($vec, BitXorAssign, bitxor_assign, bitxor);
+        impl<S3: Copy, S4: Copy, NI: Copy> AndNot for $vec<S3, S4, NI> {
+            type Output = Self;
+            #[inline(always)]
+            fn andnot(self, rhs: Self) -> Self {
+                Self::new(unsafe { _mm_andnot_si128(self.x, rhs.x) })
+            }
+        }
+    };
+}
+
+macro_rules! impl_bitops32 {
+    ($vec:ident) => {
+        impl<S3: Copy, S4: Copy, NI: Copy> BitOps32 for $vec<S3, S4, NI> where
+            $vec<S3, S4, NI>: RotateEachWord32
+        {
+        }
+    };
+}
+
+macro_rules! impl_bitops64 {
+    ($vec:ident) => {
+        impl_bitops32!($vec);
+        impl<S3: Copy, S4: Copy, NI: Copy> BitOps64 for $vec<S3, S4, NI> where
+            $vec<S3, S4, NI>: RotateEachWord64 + RotateEachWord32
+        {
+        }
+    };
+}
+
+macro_rules! impl_bitops128 {
+    ($vec:ident) => {
+        impl_bitops64!($vec);
+        impl<S3: Copy, S4: Copy, NI: Copy> BitOps128 for $vec<S3, S4, NI> where
+            $vec<S3, S4, NI>: RotateEachWord128
+        {
+        }
+    };
+}
+
+macro_rules! rotr_32_s3 {
+    ($name:ident, $k0:expr, $k1:expr) => {
+        #[inline(always)]
+        fn $name(self) -> Self {
+            Self::new(unsafe { _mm_shuffle_epi8(self.x, _mm_set_epi64x($k0, $k1)) })
+        }
+    };
+}
+macro_rules! rotr_32 {
+    ($name:ident, $i:expr) => {
+        #[inline(always)]
+        fn $name(self) -> Self {
+            Self::new(unsafe {
+                _mm_or_si128(
+                    _mm_srli_epi32(self.x, $i as i32),
+                    _mm_slli_epi32(self.x, 32 - $i as i32),
+                )
+            })
+        }
+    };
+}
+impl<S4: Copy, NI: Copy> RotateEachWord32 for u32x4_sse2<YesS3, S4, NI> {
+    rotr_32!(rotate_each_word_right7, 7);
+    rotr_32_s3!(
+        rotate_each_word_right8,
+        0x0c0f_0e0d_080b_0a09,
+        0x0407_0605_0003_0201
+    );
+    rotr_32!(rotate_each_word_right11, 11);
+    rotr_32!(rotate_each_word_right12, 12);
+    rotr_32_s3!(
+        rotate_each_word_right16,
+        0x0d0c_0f0e_0908_0b0a,
+        0x0504_0706_0100_0302
+    );
+    rotr_32!(rotate_each_word_right20, 20);
+    rotr_32_s3!(
+        rotate_each_word_right24,
+        0x0e0d_0c0f_0a09_080b,
+        0x0605_0407_0201_0003
+    );
+    rotr_32!(rotate_each_word_right25, 25);
+}
+impl<S4: Copy, NI: Copy> RotateEachWord32 for u32x4_sse2<NoS3, S4, NI> {
+    rotr_32!(rotate_each_word_right7, 7);
+    rotr_32!(rotate_each_word_right8, 8);
+    rotr_32!(rotate_each_word_right11, 11);
+    rotr_32!(rotate_each_word_right12, 12);
+    #[inline(always)]
+    fn rotate_each_word_right16(self) -> Self {
+        Self::new(swap16_s2(self.x))
+    }
+    rotr_32!(rotate_each_word_right20, 20);
+    rotr_32!(rotate_each_word_right24, 24);
+    rotr_32!(rotate_each_word_right25, 25);
+}
+
+macro_rules! rotr_64_s3 {
+    ($name:ident, $k0:expr, $k1:expr) => {
+        #[inline(always)]
+        fn $name(self) -> Self {
+            Self::new(unsafe { _mm_shuffle_epi8(self.x, _mm_set_epi64x($k0, $k1)) })
+        }
+    };
+}
+macro_rules! rotr_64 {
+    ($name:ident, $i:expr) => {
+        #[inline(always)]
+        fn $name(self) -> Self {
+            Self::new(unsafe {
+                _mm_or_si128(
+                    _mm_srli_epi64(self.x, $i as i32),
+                    _mm_slli_epi64(self.x, 64 - $i as i32),
+                )
+            })
+        }
+    };
+}
+impl<S4: Copy, NI: Copy> RotateEachWord32 for u64x2_sse2<YesS3, S4, NI> {
+    rotr_64!(rotate_each_word_right7, 7);
+    rotr_64_s3!(
+        rotate_each_word_right8,
+        0x080f_0e0d_0c0b_0a09,
+        0x0007_0605_0403_0201
+    );
+    rotr_64!(rotate_each_word_right11, 11);
+    rotr_64!(rotate_each_word_right12, 12);
+    rotr_64_s3!(
+        rotate_each_word_right16,
+        0x0908_0f0e_0d0c_0b0a,
+        0x0100_0706_0504_0302
+    );
+    rotr_64!(rotate_each_word_right20, 20);
+    rotr_64_s3!(
+        rotate_each_word_right24,
+        0x0a09_080f_0e0d_0c0b,
+        0x0201_0007_0605_0403
+    );
+    rotr_64!(rotate_each_word_right25, 25);
+}
+impl<S4: Copy, NI: Copy> RotateEachWord32 for u64x2_sse2<NoS3, S4, NI> {
+    rotr_64!(rotate_each_word_right7, 7);
+    rotr_64!(rotate_each_word_right8, 8);
+    rotr_64!(rotate_each_word_right11, 11);
+    rotr_64!(rotate_each_word_right12, 12);
+    #[inline(always)]
+    fn rotate_each_word_right16(self) -> Self {
+        Self::new(swap16_s2(self.x))
+    }
+    rotr_64!(rotate_each_word_right20, 20);
+    rotr_64!(rotate_each_word_right24, 24);
+    rotr_64!(rotate_each_word_right25, 25);
+}
+impl<S3: Copy, S4: Copy, NI: Copy> RotateEachWord64 for u64x2_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn rotate_each_word_right32(self) -> Self {
+        Self::new(unsafe { _mm_shuffle_epi32(self.x, 0b10110001) })
+    }
+}
+
+macro_rules! rotr_128 {
+    ($name:ident, $i:expr) => {
+        #[inline(always)]
+        fn $name(self) -> Self {
+            Self::new(unsafe {
+                _mm_or_si128(
+                    _mm_srli_si128(self.x, $i as i32),
+                    _mm_slli_si128(self.x, 128 - $i as i32),
+                )
+            })
+        }
+    };
+}
+// TODO: completely unoptimized
+impl<S3: Copy, S4: Copy, NI: Copy> RotateEachWord32 for u128x1_sse2<S3, S4, NI> {
+    rotr_128!(rotate_each_word_right7, 7);
+    rotr_128!(rotate_each_word_right8, 8);
+    rotr_128!(rotate_each_word_right11, 11);
+    rotr_128!(rotate_each_word_right12, 12);
+    rotr_128!(rotate_each_word_right16, 16);
+    rotr_128!(rotate_each_word_right20, 20);
+    rotr_128!(rotate_each_word_right24, 24);
+    rotr_128!(rotate_each_word_right25, 25);
+}
+// TODO: completely unoptimized
+impl<S3: Copy, S4: Copy, NI: Copy> RotateEachWord64 for u128x1_sse2<S3, S4, NI> {
+    rotr_128!(rotate_each_word_right32, 32);
+}
+impl<S3: Copy, S4: Copy, NI: Copy> RotateEachWord128 for u128x1_sse2<S3, S4, NI> {}
+
+def_vec!(u32x4_sse2, u32);
+def_vec!(u64x2_sse2, u64);
+def_vec!(u128x1_sse2, u128);
+
+impl<S3, NI> MultiLane<[u32; 4]> for u32x4_sse2<S3, YesS4, NI> {
+    #[inline(always)]
+    fn to_lanes(self) -> [u32; 4] {
+        unsafe {
+            let x = _mm_cvtsi128_si64(self.x) as u64;
+            let y = _mm_extract_epi64(self.x, 1) as u64;
+            [x as u32, (x >> 32) as u32, y as u32, (y >> 32) as u32]
+        }
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u32; 4]) -> Self {
+        unsafe {
+            let mut x = _mm_cvtsi64_si128((xs[0] as u64 | ((xs[1] as u64) << 32)) as i64);
+            x = _mm_insert_epi64(x, (xs[2] as u64 | ((xs[3] as u64) << 32)) as i64, 1);
+            Self::new(x)
+        }
+    }
+}
+impl<S3, NI> MultiLane<[u32; 4]> for u32x4_sse2<S3, NoS4, NI> {
+    #[inline(always)]
+    fn to_lanes(self) -> [u32; 4] {
+        unsafe {
+            let x = _mm_cvtsi128_si64(self.x) as u64;
+            let y = _mm_cvtsi128_si64(_mm_shuffle_epi32(self.x, 0b11101110)) as u64;
+            [x as u32, (x >> 32) as u32, y as u32, (y >> 32) as u32]
+        }
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u32; 4]) -> Self {
+        unsafe {
+            let x = (xs[0] as u64 | ((xs[1] as u64) << 32)) as i64;
+            let y = (xs[2] as u64 | ((xs[3] as u64) << 32)) as i64;
+            let x = _mm_cvtsi64_si128(x);
+            let y = _mm_slli_si128(_mm_cvtsi64_si128(y), 8);
+            Self::new(_mm_or_si128(x, y))
+        }
+    }
+}
+impl<S3, NI> MultiLane<[u64; 2]> for u64x2_sse2<S3, YesS4, NI> {
+    #[inline(always)]
+    fn to_lanes(self) -> [u64; 2] {
+        unsafe {
+            [
+                _mm_cvtsi128_si64(self.x) as u64,
+                _mm_extract_epi64(self.x, 1) as u64,
+            ]
+        }
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u64; 2]) -> Self {
+        unsafe {
+            let mut x = _mm_cvtsi64_si128(xs[0] as i64);
+            x = _mm_insert_epi64(x, xs[1] as i64, 1);
+            Self::new(x)
+        }
+    }
+}
+impl<S3, NI> MultiLane<[u64; 2]> for u64x2_sse2<S3, NoS4, NI> {
+    #[inline(always)]
+    fn to_lanes(self) -> [u64; 2] {
+        unsafe {
+            [
+                _mm_cvtsi128_si64(self.x) as u64,
+                _mm_cvtsi128_si64(_mm_srli_si128(self.x, 8)) as u64,
+            ]
+        }
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u64; 2]) -> Self {
+        unsafe {
+            let x = _mm_cvtsi64_si128(xs[0] as i64);
+            let y = _mm_slli_si128(_mm_cvtsi64_si128(xs[1] as i64), 8);
+            Self::new(_mm_or_si128(x, y))
+        }
+    }
+}
+impl<S3, S4, NI> MultiLane<[u128; 1]> for u128x1_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn to_lanes(self) -> [u128; 1] {
+        unimplemented!()
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u128; 1]) -> Self {
+        unimplemented!("{:?}", xs)
+    }
+}
+
+impl<S3, S4, NI> MultiLane<[u64; 4]> for u64x4_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: MultiLane<[u64; 2]> + Copy,
+{
+    #[inline(always)]
+    fn to_lanes(self) -> [u64; 4] {
+        let (a, b) = (self.0[0].to_lanes(), self.0[1].to_lanes());
+        [a[0], a[1], b[0], b[1]]
+    }
+    #[inline(always)]
+    fn from_lanes(xs: [u64; 4]) -> Self {
+        let (a, b) = (
+            u64x2_sse2::from_lanes([xs[0], xs[1]]),
+            u64x2_sse2::from_lanes([xs[2], xs[3]]),
+        );
+        x2::new([a, b])
+    }
+}
+
+macro_rules! impl_into {
+    ($from:ident, $to:ident) => {
+        impl<S3, S4, NI> From<$from<S3, S4, NI>> for $to<S3, S4, NI> {
+            #[inline(always)]
+            fn from(x: $from<S3, S4, NI>) -> Self {
+                $to::new(x.x)
+            }
+        }
+    };
+}
+
+impl_into!(u128x1_sse2, u32x4_sse2);
+impl_into!(u128x1_sse2, u64x2_sse2);
+
+impl_bitops32!(u32x4_sse2);
+impl_bitops64!(u64x2_sse2);
+impl_bitops128!(u128x1_sse2);
+
+impl<S3: Copy, S4: Copy, NI: Copy> ArithOps for u32x4_sse2<S3, S4, NI> where
+    u32x4_sse2<S3, S4, NI>: BSwap
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> ArithOps for u64x2_sse2<S3, S4, NI> where
+    u64x2_sse2<S3, S4, NI>: BSwap
+{
+}
+impl_binop!(u32x4_sse2, Add, add, _mm_add_epi32);
+impl_binop!(u64x2_sse2, Add, add, _mm_add_epi64);
+impl_binop_assign!(u32x4_sse2, AddAssign, add_assign, add);
+impl_binop_assign!(u64x2_sse2, AddAssign, add_assign, add);
+
+impl<S3: Copy, S4: Copy, NI: Copy> u32x4<Machine86<S3, S4, NI>> for u32x4_sse2<S3, S4, NI>
+where
+    u32x4_sse2<S3, S4, NI>: RotateEachWord32 + BSwap + MultiLane<[u32; 4]> + Vec4<u32>,
+    Machine86<S3, S4, NI>: Machine,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u64x2<Machine86<S3, S4, NI>> for u64x2_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>:
+        RotateEachWord64 + RotateEachWord32 + BSwap + MultiLane<[u64; 2]> + Vec2<u64>,
+    Machine86<S3, S4, NI>: Machine,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u128x1<Machine86<S3, S4, NI>> for u128x1_sse2<S3, S4, NI>
+where
+    u128x1_sse2<S3, S4, NI>: Swap64 + RotateEachWord64 + RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u128x1_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u32x4>,
+    u128x1_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u64x2>,
+{
+}
+
+impl<NI: Copy> u32x4<Avx2Machine<NI>> for u32x4_sse2<YesS3, YesS4, NI>
+where
+    u32x4_sse2<YesS3, YesS4, NI>: RotateEachWord32 + BSwap + MultiLane<[u32; 4]> + Vec4<u32>,
+    Machine86<YesS3, YesS4, NI>: Machine,
+{
+}
+impl<NI: Copy> u64x2<Avx2Machine<NI>> for u64x2_sse2<YesS3, YesS4, NI>
+where
+    u64x2_sse2<YesS3, YesS4, NI>:
+        RotateEachWord64 + RotateEachWord32 + BSwap + MultiLane<[u64; 2]> + Vec2<u64>,
+    Machine86<YesS3, YesS4, NI>: Machine,
+{
+}
+impl<NI: Copy> u128x1<Avx2Machine<NI>> for u128x1_sse2<YesS3, YesS4, NI>
+where
+    u128x1_sse2<YesS3, YesS4, NI>: Swap64 + RotateEachWord64 + RotateEachWord32 + BSwap,
+    Machine86<YesS3, YesS4, NI>: Machine,
+    u128x1_sse2<YesS3, YesS4, NI>: Into<<Machine86<YesS3, YesS4, NI> as Machine>::u32x4>,
+    u128x1_sse2<YesS3, YesS4, NI>: Into<<Machine86<YesS3, YesS4, NI> as Machine>::u64x2>,
+{
+}
+
+impl<S3, S4, NI> UnsafeFrom<[u32; 4]> for u32x4_sse2<S3, S4, NI> {
+    #[inline(always)]
+    unsafe fn unsafe_from(xs: [u32; 4]) -> Self {
+        Self::new(_mm_set_epi32(
+            xs[3] as i32,
+            xs[2] as i32,
+            xs[1] as i32,
+            xs[0] as i32,
+        ))
+    }
+}
+
+impl<S3, NI> Vec4<u32> for u32x4_sse2<S3, YesS4, NI>
+where
+    Self: MultiLane<[u32; 4]>,
+{
+    #[inline(always)]
+    fn extract(self, i: u32) -> u32 {
+        self.to_lanes()[i as usize]
+    }
+    #[inline(always)]
+    fn insert(self, v: u32, i: u32) -> Self {
+        Self::new(unsafe {
+            match i {
+                0 => _mm_insert_epi32(self.x, v as i32, 0),
+                1 => _mm_insert_epi32(self.x, v as i32, 1),
+                2 => _mm_insert_epi32(self.x, v as i32, 2),
+                3 => _mm_insert_epi32(self.x, v as i32, 3),
+                _ => unreachable!(),
+            }
+        })
+    }
+}
+impl<S3, NI> Vec4<u32> for u32x4_sse2<S3, NoS4, NI>
+where
+    Self: MultiLane<[u32; 4]>,
+{
+    #[inline(always)]
+    fn extract(self, i: u32) -> u32 {
+        self.to_lanes()[i as usize]
+    }
+    #[inline(always)]
+    fn insert(self, v: u32, i: u32) -> Self {
+        Self::new(unsafe {
+            match i {
+                0 => {
+                    let x = _mm_andnot_si128(_mm_cvtsi32_si128(-1), self.x);
+                    _mm_or_si128(x, _mm_cvtsi32_si128(v as i32))
+                }
+                1 => {
+                    let mut x = _mm_shuffle_epi32(self.x, 0b0111_1000);
+                    x = _mm_slli_si128(x, 4);
+                    x = _mm_or_si128(x, _mm_cvtsi32_si128(v as i32));
+                    _mm_shuffle_epi32(x, 0b1110_0001)
+                }
+                2 => {
+                    let mut x = _mm_shuffle_epi32(self.x, 0b1011_0100);
+                    x = _mm_slli_si128(x, 4);
+                    x = _mm_or_si128(x, _mm_cvtsi32_si128(v as i32));
+                    _mm_shuffle_epi32(x, 0b1100_1001)
+                }
+                3 => {
+                    let mut x = _mm_slli_si128(self.x, 4);
+                    x = _mm_or_si128(x, _mm_cvtsi32_si128(v as i32));
+                    _mm_shuffle_epi32(x, 0b0011_1001)
+                }
+                _ => unreachable!(),
+            }
+        })
+    }
+}
+
+impl<S3, S4, NI> LaneWords4 for u32x4_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn shuffle_lane_words2301(self) -> Self {
+        self.shuffle2301()
+    }
+    #[inline(always)]
+    fn shuffle_lane_words1230(self) -> Self {
+        self.shuffle1230()
+    }
+    #[inline(always)]
+    fn shuffle_lane_words3012(self) -> Self {
+        self.shuffle3012()
+    }
+}
+
+impl<S3, S4, NI> Words4 for u32x4_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn shuffle2301(self) -> Self {
+        Self::new(unsafe { _mm_shuffle_epi32(self.x, 0b0100_1110) })
+    }
+    #[inline(always)]
+    fn shuffle1230(self) -> Self {
+        Self::new(unsafe { _mm_shuffle_epi32(self.x, 0b1001_0011) })
+    }
+    #[inline(always)]
+    fn shuffle3012(self) -> Self {
+        Self::new(unsafe { _mm_shuffle_epi32(self.x, 0b0011_1001) })
+    }
+}
+
+impl<S4, NI> Words4 for u64x4_sse2<YesS3, S4, NI> {
+    #[inline(always)]
+    fn shuffle2301(self) -> Self {
+        x2::new([u64x2_sse2::new(self.0[1].x), u64x2_sse2::new(self.0[0].x)])
+    }
+    #[inline(always)]
+    fn shuffle3012(self) -> Self {
+        unsafe {
+            x2::new([
+                u64x2_sse2::new(_mm_alignr_epi8(self.0[1].x, self.0[0].x, 8)),
+                u64x2_sse2::new(_mm_alignr_epi8(self.0[0].x, self.0[1].x, 8)),
+            ])
+        }
+    }
+    #[inline(always)]
+    fn shuffle1230(self) -> Self {
+        unsafe {
+            x2::new([
+                u64x2_sse2::new(_mm_alignr_epi8(self.0[0].x, self.0[1].x, 8)),
+                u64x2_sse2::new(_mm_alignr_epi8(self.0[1].x, self.0[0].x, 8)),
+            ])
+        }
+    }
+}
+impl<S4, NI> Words4 for u64x4_sse2<NoS3, S4, NI> {
+    #[inline(always)]
+    fn shuffle2301(self) -> Self {
+        x2::new([u64x2_sse2::new(self.0[1].x), u64x2_sse2::new(self.0[0].x)])
+    }
+    #[inline(always)]
+    fn shuffle3012(self) -> Self {
+        unsafe {
+            let a = _mm_srli_si128(self.0[0].x, 8);
+            let b = _mm_slli_si128(self.0[0].x, 8);
+            let c = _mm_srli_si128(self.0[1].x, 8);
+            let d = _mm_slli_si128(self.0[1].x, 8);
+            let da = _mm_or_si128(d, a);
+            let bc = _mm_or_si128(b, c);
+            x2::new([u64x2_sse2::new(da), u64x2_sse2::new(bc)])
+        }
+    }
+    #[inline(always)]
+    fn shuffle1230(self) -> Self {
+        unsafe {
+            let a = _mm_srli_si128(self.0[0].x, 8);
+            let b = _mm_slli_si128(self.0[0].x, 8);
+            let c = _mm_srli_si128(self.0[1].x, 8);
+            let d = _mm_slli_si128(self.0[1].x, 8);
+            let da = _mm_or_si128(d, a);
+            let bc = _mm_or_si128(b, c);
+            x2::new([u64x2_sse2::new(bc), u64x2_sse2::new(da)])
+        }
+    }
+}
+
+impl<S3, S4, NI> UnsafeFrom<[u64; 2]> for u64x2_sse2<S3, S4, NI> {
+    #[inline(always)]
+    unsafe fn unsafe_from(xs: [u64; 2]) -> Self {
+        Self::new(_mm_set_epi64x(xs[1] as i64, xs[0] as i64))
+    }
+}
+
+impl<S3, NI> Vec2<u64> for u64x2_sse2<S3, YesS4, NI> {
+    #[inline(always)]
+    fn extract(self, i: u32) -> u64 {
+        unsafe {
+            match i {
+                0 => _mm_cvtsi128_si64(self.x) as u64,
+                1 => _mm_extract_epi64(self.x, 1) as u64,
+                _ => unreachable!(),
+            }
+        }
+    }
+    #[inline(always)]
+    fn insert(self, x: u64, i: u32) -> Self {
+        Self::new(unsafe {
+            match i {
+                0 => _mm_insert_epi64(self.x, x as i64, 0),
+                1 => _mm_insert_epi64(self.x, x as i64, 1),
+                _ => unreachable!(),
+            }
+        })
+    }
+}
+impl<S3, NI> Vec2<u64> for u64x2_sse2<S3, NoS4, NI> {
+    #[inline(always)]
+    fn extract(self, i: u32) -> u64 {
+        unsafe {
+            match i {
+                0 => _mm_cvtsi128_si64(self.x) as u64,
+                1 => _mm_cvtsi128_si64(_mm_shuffle_epi32(self.x, 0b11101110)) as u64,
+                _ => unreachable!(),
+            }
+        }
+    }
+    #[inline(always)]
+    fn insert(self, x: u64, i: u32) -> Self {
+        Self::new(unsafe {
+            match i {
+                0 => _mm_or_si128(
+                    _mm_andnot_si128(_mm_cvtsi64_si128(-1), self.x),
+                    _mm_cvtsi64_si128(x as i64),
+                ),
+                1 => _mm_or_si128(
+                    _mm_move_epi64(self.x),
+                    _mm_slli_si128(_mm_cvtsi64_si128(x as i64), 8),
+                ),
+                _ => unreachable!(),
+            }
+        })
+    }
+}
+
+impl<S4, NI> BSwap for u32x4_sse2<YesS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        Self::new(unsafe {
+            let k = _mm_set_epi64x(0x0c0d_0e0f_0809_0a0b, 0x0405_0607_0001_0203);
+            _mm_shuffle_epi8(self.x, k)
+        })
+    }
+}
+#[inline(always)]
+fn bswap32_s2(x: __m128i) -> __m128i {
+    unsafe {
+        let mut y = _mm_unpacklo_epi8(x, _mm_setzero_si128());
+        y = _mm_shufflehi_epi16(y, 0b0001_1011);
+        y = _mm_shufflelo_epi16(y, 0b0001_1011);
+        let mut z = _mm_unpackhi_epi8(x, _mm_setzero_si128());
+        z = _mm_shufflehi_epi16(z, 0b0001_1011);
+        z = _mm_shufflelo_epi16(z, 0b0001_1011);
+        _mm_packus_epi16(y, z)
+    }
+}
+impl<S4, NI> BSwap for u32x4_sse2<NoS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        Self::new(bswap32_s2(self.x))
+    }
+}
+
+impl<S4, NI> BSwap for u64x2_sse2<YesS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        Self::new(unsafe {
+            let k = _mm_set_epi64x(0x0809_0a0b_0c0d_0e0f, 0x0001_0203_0405_0607);
+            _mm_shuffle_epi8(self.x, k)
+        })
+    }
+}
+impl<S4, NI> BSwap for u64x2_sse2<NoS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        Self::new(unsafe { bswap32_s2(_mm_shuffle_epi32(self.x, 0b1011_0001)) })
+    }
+}
+
+impl<S4, NI> BSwap for u128x1_sse2<YesS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        Self::new(unsafe {
+            let k = _mm_set_epi64x(0x0f0e_0d0c_0b0a_0908, 0x0706_0504_0302_0100);
+            _mm_shuffle_epi8(self.x, k)
+        })
+    }
+}
+impl<S4, NI> BSwap for u128x1_sse2<NoS3, S4, NI> {
+    #[inline(always)]
+    fn bswap(self) -> Self {
+        unimplemented!()
+    }
+}
+
+macro_rules! swapi {
+    ($x:expr, $i:expr, $k:expr) => {
+        unsafe {
+            const K: u8 = $k;
+            let k = _mm_set1_epi8(K as i8);
+            u128x1_sse2::new(_mm_or_si128(
+                _mm_srli_epi16(_mm_and_si128($x.x, k), $i),
+                _mm_and_si128(_mm_slli_epi16($x.x, $i), k),
+            ))
+        }
+    };
+}
+#[inline(always)]
+fn swap16_s2(x: __m128i) -> __m128i {
+    unsafe { _mm_shufflehi_epi16(_mm_shufflelo_epi16(x, 0b1011_0001), 0b1011_0001) }
+}
+impl<S4, NI> Swap64 for u128x1_sse2<YesS3, S4, NI> {
+    #[inline(always)]
+    fn swap1(self) -> Self {
+        swapi!(self, 1, 0xaa)
+    }
+    #[inline(always)]
+    fn swap2(self) -> Self {
+        swapi!(self, 2, 0xcc)
+    }
+    #[inline(always)]
+    fn swap4(self) -> Self {
+        swapi!(self, 4, 0xf0)
+    }
+    #[inline(always)]
+    fn swap8(self) -> Self {
+        u128x1_sse2::new(unsafe {
+            let k = _mm_set_epi64x(0x0e0f_0c0d_0a0b_0809, 0x0607_0405_0203_0001);
+            _mm_shuffle_epi8(self.x, k)
+        })
+    }
+    #[inline(always)]
+    fn swap16(self) -> Self {
+        u128x1_sse2::new(unsafe {
+            let k = _mm_set_epi64x(0x0d0c_0f0e_0908_0b0a, 0x0504_0706_0100_0302);
+            _mm_shuffle_epi8(self.x, k)
+        })
+    }
+    #[inline(always)]
+    fn swap32(self) -> Self {
+        u128x1_sse2::new(unsafe { _mm_shuffle_epi32(self.x, 0b1011_0001) })
+    }
+    #[inline(always)]
+    fn swap64(self) -> Self {
+        u128x1_sse2::new(unsafe { _mm_shuffle_epi32(self.x, 0b0100_1110) })
+    }
+}
+impl<S4, NI> Swap64 for u128x1_sse2<NoS3, S4, NI> {
+    #[inline(always)]
+    fn swap1(self) -> Self {
+        swapi!(self, 1, 0xaa)
+    }
+    #[inline(always)]
+    fn swap2(self) -> Self {
+        swapi!(self, 2, 0xcc)
+    }
+    #[inline(always)]
+    fn swap4(self) -> Self {
+        swapi!(self, 4, 0xf0)
+    }
+    #[inline(always)]
+    fn swap8(self) -> Self {
+        u128x1_sse2::new(unsafe {
+            _mm_or_si128(_mm_slli_epi16(self.x, 8), _mm_srli_epi16(self.x, 8))
+        })
+    }
+    #[inline(always)]
+    fn swap16(self) -> Self {
+        u128x1_sse2::new(swap16_s2(self.x))
+    }
+    #[inline(always)]
+    fn swap32(self) -> Self {
+        u128x1_sse2::new(unsafe { _mm_shuffle_epi32(self.x, 0b1011_0001) })
+    }
+    #[inline(always)]
+    fn swap64(self) -> Self {
+        u128x1_sse2::new(unsafe { _mm_shuffle_epi32(self.x, 0b0100_1110) })
+    }
+}
+
+#[derive(Copy, Clone)]
+pub struct G0;
+#[derive(Copy, Clone)]
+pub struct G1;
+
+#[allow(non_camel_case_types)]
+pub type u32x4x2_sse2<S3, S4, NI> = x2<u32x4_sse2<S3, S4, NI>, G0>;
+#[allow(non_camel_case_types)]
+pub type u64x2x2_sse2<S3, S4, NI> = x2<u64x2_sse2<S3, S4, NI>, G0>;
+#[allow(non_camel_case_types)]
+pub type u64x4_sse2<S3, S4, NI> = x2<u64x2_sse2<S3, S4, NI>, G1>;
+#[allow(non_camel_case_types)]
+pub type u128x2_sse2<S3, S4, NI> = x2<u128x1_sse2<S3, S4, NI>, G0>;
+
+#[allow(non_camel_case_types)]
+pub type u32x4x4_sse2<S3, S4, NI> = x4<u32x4_sse2<S3, S4, NI>>;
+#[allow(non_camel_case_types)]
+pub type u64x2x4_sse2<S3, S4, NI> = x4<u64x2_sse2<S3, S4, NI>>;
+#[allow(non_camel_case_types)]
+pub type u128x4_sse2<S3, S4, NI> = x4<u128x1_sse2<S3, S4, NI>>;
+
+impl<S3, S4, NI> Vector<[u32; 16]> for u32x4x4_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn to_scalars(self) -> [u32; 16] {
+        unsafe { core::mem::transmute(self) }
+    }
+}
+
+impl<S3: Copy, S4: Copy, NI: Copy> u32x4x2<Machine86<S3, S4, NI>> for u32x4x2_sse2<S3, S4, NI>
+where
+    u32x4_sse2<S3, S4, NI>: RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u32x4x2_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u32x4; 2]>,
+    u32x4x2_sse2<S3, S4, NI>: Vec2<<Machine86<S3, S4, NI> as Machine>::u32x4>,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u64x2x2<Machine86<S3, S4, NI>> for u64x2x2_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u64x2x2_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u64x2; 2]>,
+    u64x2x2_sse2<S3, S4, NI>: Vec2<<Machine86<S3, S4, NI> as Machine>::u64x2>,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u64x4<Machine86<S3, S4, NI>> for u64x4_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u64x4_sse2<S3, S4, NI>: MultiLane<[u64; 4]> + Vec4<u64> + Words4,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u128x2<Machine86<S3, S4, NI>> for u128x2_sse2<S3, S4, NI>
+where
+    u128x1_sse2<S3, S4, NI>: Swap64 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u128x2_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u128x1; 2]>,
+    u128x2_sse2<S3, S4, NI>: Vec2<<Machine86<S3, S4, NI> as Machine>::u128x1>,
+    u128x2_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u32x4x2>,
+    u128x2_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u64x2x2>,
+    u128x2_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u64x4>,
+{
+}
+
+impl<NI: Copy> u32x4x2<Avx2Machine<NI>> for u32x4x2_sse2<YesS3, YesS4, NI>
+where
+    u32x4_sse2<YesS3, YesS4, NI>: RotateEachWord32 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u32x4x2_sse2<YesS3, YesS4, NI>: MultiLane<[<Avx2Machine<NI> as Machine>::u32x4; 2]>,
+    u32x4x2_sse2<YesS3, YesS4, NI>: Vec2<<Avx2Machine<NI> as Machine>::u32x4>,
+{
+}
+impl<NI: Copy> u64x2x2<Avx2Machine<NI>> for u64x2x2_sse2<YesS3, YesS4, NI>
+where
+    u64x2_sse2<YesS3, YesS4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u64x2x2_sse2<YesS3, YesS4, NI>: MultiLane<[<Avx2Machine<NI> as Machine>::u64x2; 2]>,
+    u64x2x2_sse2<YesS3, YesS4, NI>: Vec2<<Avx2Machine<NI> as Machine>::u64x2>,
+{
+}
+impl<NI: Copy> u64x4<Avx2Machine<NI>> for u64x4_sse2<YesS3, YesS4, NI>
+where
+    u64x2_sse2<YesS3, YesS4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u64x4_sse2<YesS3, YesS4, NI>: MultiLane<[u64; 4]> + Vec4<u64> + Words4,
+{
+}
+impl<NI: Copy> u128x2<Avx2Machine<NI>> for u128x2_sse2<YesS3, YesS4, NI>
+where
+    u128x1_sse2<YesS3, YesS4, NI>: Swap64 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u128x2_sse2<YesS3, YesS4, NI>: MultiLane<[<Avx2Machine<NI> as Machine>::u128x1; 2]>,
+    u128x2_sse2<YesS3, YesS4, NI>: Vec2<<Avx2Machine<NI> as Machine>::u128x1>,
+    u128x2_sse2<YesS3, YesS4, NI>: Into<<Avx2Machine<NI> as Machine>::u32x4x2>,
+    u128x2_sse2<YesS3, YesS4, NI>: Into<<Avx2Machine<NI> as Machine>::u64x2x2>,
+    u128x2_sse2<YesS3, YesS4, NI>: Into<<Avx2Machine<NI> as Machine>::u64x4>,
+{
+}
+
+impl<S3, S4, NI> Vec4<u64> for u64x4_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: Copy + Vec2<u64>,
+{
+    #[inline(always)]
+    fn extract(self, i: u32) -> u64 {
+        match i {
+            0 => self.0[0].extract(0),
+            1 => self.0[0].extract(1),
+            2 => self.0[1].extract(0),
+            3 => self.0[1].extract(1),
+            _ => panic!(),
+        }
+    }
+    #[inline(always)]
+    fn insert(mut self, w: u64, i: u32) -> Self {
+        match i {
+            0 => self.0[0] = self.0[0].insert(w, 0),
+            1 => self.0[0] = self.0[0].insert(w, 1),
+            2 => self.0[1] = self.0[1].insert(w, 0),
+            3 => self.0[1] = self.0[1].insert(w, 1),
+            _ => panic!(),
+        };
+        self
+    }
+}
+
+impl<S3: Copy, S4: Copy, NI: Copy> u32x4x4<Machine86<S3, S4, NI>> for u32x4x4_sse2<S3, S4, NI>
+where
+    u32x4_sse2<S3, S4, NI>: RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u32x4x4_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u32x4; 4]>,
+    u32x4x4_sse2<S3, S4, NI>: Vec4<<Machine86<S3, S4, NI> as Machine>::u32x4>,
+    u32x4x4_sse2<S3, S4, NI>: Vec4Ext<<Machine86<S3, S4, NI> as Machine>::u32x4>,
+    u32x4x4_sse2<S3, S4, NI>: Vector<[u32; 16]>,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u64x2x4<Machine86<S3, S4, NI>> for u64x2x4_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u64x2x4_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u64x2; 4]>,
+    u64x2x4_sse2<S3, S4, NI>: Vec4<<Machine86<S3, S4, NI> as Machine>::u64x2>,
+{
+}
+impl<S3: Copy, S4: Copy, NI: Copy> u128x4<Machine86<S3, S4, NI>> for u128x4_sse2<S3, S4, NI>
+where
+    u128x1_sse2<S3, S4, NI>: Swap64 + BSwap,
+    Machine86<S3, S4, NI>: Machine,
+    u128x4_sse2<S3, S4, NI>: MultiLane<[<Machine86<S3, S4, NI> as Machine>::u128x1; 4]>,
+    u128x4_sse2<S3, S4, NI>: Vec4<<Machine86<S3, S4, NI> as Machine>::u128x1>,
+    u128x4_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u32x4x4>,
+    u128x4_sse2<S3, S4, NI>: Into<<Machine86<S3, S4, NI> as Machine>::u64x2x4>,
+{
+}
+
+impl<NI: Copy> u64x2x4<Avx2Machine<NI>> for u64x2x4_sse2<YesS3, YesS4, NI>
+where
+    u64x2_sse2<YesS3, YesS4, NI>: RotateEachWord64 + RotateEachWord32 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u64x2x4_sse2<YesS3, YesS4, NI>: MultiLane<[<Avx2Machine<NI> as Machine>::u64x2; 4]>,
+    u64x2x4_sse2<YesS3, YesS4, NI>: Vec4<<Avx2Machine<NI> as Machine>::u64x2>,
+{
+}
+impl<NI: Copy> u128x4<Avx2Machine<NI>> for u128x4_sse2<YesS3, YesS4, NI>
+where
+    u128x1_sse2<YesS3, YesS4, NI>: Swap64 + BSwap,
+    Avx2Machine<NI>: Machine,
+    u128x4_sse2<YesS3, YesS4, NI>: MultiLane<[<Avx2Machine<NI> as Machine>::u128x1; 4]>,
+    u128x4_sse2<YesS3, YesS4, NI>: Vec4<<Avx2Machine<NI> as Machine>::u128x1>,
+    u128x4_sse2<YesS3, YesS4, NI>: Into<<Avx2Machine<NI> as Machine>::u32x4x4>,
+    u128x4_sse2<YesS3, YesS4, NI>: Into<<Avx2Machine<NI> as Machine>::u64x2x4>,
+{
+}
+
+macro_rules! impl_into_x {
+    ($from:ident, $to:ident) => {
+        impl<S3: Copy, S4: Copy, NI: Copy, Gf, Gt> From<x2<$from<S3, S4, NI>, Gf>>
+            for x2<$to<S3, S4, NI>, Gt>
+        {
+            #[inline(always)]
+            fn from(x: x2<$from<S3, S4, NI>, Gf>) -> Self {
+                x2::new([$to::from(x.0[0]), $to::from(x.0[1])])
+            }
+        }
+        impl<S3: Copy, S4: Copy, NI: Copy> From<x4<$from<S3, S4, NI>>> for x4<$to<S3, S4, NI>> {
+            #[inline(always)]
+            fn from(x: x4<$from<S3, S4, NI>>) -> Self {
+                x4::new([
+                    $to::from(x.0[0]),
+                    $to::from(x.0[1]),
+                    $to::from(x.0[2]),
+                    $to::from(x.0[3]),
+                ])
+            }
+        }
+    };
+}
+impl_into_x!(u128x1_sse2, u64x2_sse2);
+impl_into_x!(u128x1_sse2, u32x4_sse2);
+
+///// Debugging
+
+use core::fmt::{Debug, Formatter, Result};
+
+impl<W: PartialEq, G> PartialEq for x2<W, G> {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        self.0[0] == rhs.0[0] && self.0[1] == rhs.0[1]
+    }
+}
+
+#[allow(unused)]
+#[inline(always)]
+unsafe fn eq128_s4(x: __m128i, y: __m128i) -> bool {
+    let q = _mm_shuffle_epi32(_mm_cmpeq_epi64(x, y), 0b1100_0110);
+    _mm_cvtsi128_si64(q) == -1
+}
+
+#[inline(always)]
+unsafe fn eq128_s2(x: __m128i, y: __m128i) -> bool {
+    let q = _mm_cmpeq_epi32(x, y);
+    let p = _mm_cvtsi128_si64(_mm_srli_si128(q, 8));
+    let q = _mm_cvtsi128_si64(q);
+    (p & q) == -1
+}
+
+impl<S3, S4, NI> PartialEq for u32x4_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        unsafe { eq128_s2(self.x, rhs.x) }
+    }
+}
+impl<S3, S4, NI> Debug for u32x4_sse2<S3, S4, NI>
+where
+    Self: Copy + MultiLane<[u32; 4]>,
+{
+    #[cold]
+    fn fmt(&self, fmt: &mut Formatter) -> Result {
+        fmt.write_fmt(format_args!("{:08x?}", &self.to_lanes()))
+    }
+}
+
+impl<S3, S4, NI> PartialEq for u64x2_sse2<S3, S4, NI> {
+    #[inline(always)]
+    fn eq(&self, rhs: &Self) -> bool {
+        unsafe { eq128_s2(self.x, rhs.x) }
+    }
+}
+impl<S3, S4, NI> Debug for u64x2_sse2<S3, S4, NI>
+where
+    Self: Copy + MultiLane<[u64; 2]>,
+{
+    #[cold]
+    fn fmt(&self, fmt: &mut Formatter) -> Result {
+        fmt.write_fmt(format_args!("{:016x?}", &self.to_lanes()))
+    }
+}
+
+impl<S3, S4, NI> Debug for u64x4_sse2<S3, S4, NI>
+where
+    u64x2_sse2<S3, S4, NI>: Copy + MultiLane<[u64; 2]>,
+{
+    #[cold]
+    fn fmt(&self, fmt: &mut Formatter) -> Result {
+        let (a, b) = (self.0[0].to_lanes(), self.0[1].to_lanes());
+        fmt.write_fmt(format_args!("{:016x?}", &[a[0], a[1], b[0], b[1]]))
+    }
+}
+
+#[cfg(test)]
+#[cfg(target_arch = "x86_64")]
+mod test {
+    use super::*;
+    use crate::x86_64::{SSE2, SSE41, SSSE3};
+    use crate::Machine;
+
+    #[test]
+    #[cfg_attr(not(target_feature = "ssse3"), ignore)]
+    fn test_bswap32_s2_vs_s3() {
+        let xs = [0x0f0e_0d0c, 0x0b0a_0908, 0x0706_0504, 0x0302_0100];
+        let ys = [0x0c0d_0e0f, 0x0809_0a0b, 0x0405_0607, 0x0001_0203];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u32x4 = s2.vec(xs);
+            x_s2.bswap()
+        };
+
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u32x4 = s3.vec(xs);
+            x_s3.bswap()
+        };
+
+        assert_eq!(x_s2, unsafe { core::mem::transmute(x_s3) });
+        assert_eq!(x_s2, s2.vec(ys));
+    }
+
+    #[test]
+    #[cfg_attr(not(target_feature = "ssse3"), ignore)]
+    fn test_bswap64_s2_vs_s3() {
+        let xs = [0x0f0e_0d0c_0b0a_0908, 0x0706_0504_0302_0100];
+        let ys = [0x0809_0a0b_0c0d_0e0f, 0x0001_0203_0405_0607];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u64x2 = s2.vec(xs);
+            x_s2.bswap()
+        };
+
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u64x2 = s3.vec(xs);
+            x_s3.bswap()
+        };
+
+        assert_eq!(x_s2, s2.vec(ys));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+    }
+
+    #[test]
+    #[cfg_attr(not(target_feature = "ssse3"), ignore)]
+    fn test_shuffle32_s2_vs_s3() {
+        let xs = [0x0, 0x1, 0x2, 0x3];
+        let ys = [0x2, 0x3, 0x0, 0x1];
+        let zs = [0x1, 0x2, 0x3, 0x0];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u32x4 = s2.vec(xs);
+            x_s2.shuffle2301()
+        };
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u32x4 = s3.vec(xs);
+            x_s3.shuffle2301()
+        };
+        assert_eq!(x_s2, s2.vec(ys));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u32x4 = s2.vec(xs);
+            x_s2.shuffle3012()
+        };
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u32x4 = s3.vec(xs);
+            x_s3.shuffle3012()
+        };
+        assert_eq!(x_s2, s2.vec(zs));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+
+        let x_s2 = x_s2.shuffle1230();
+        let x_s3 = x_s3.shuffle1230();
+        assert_eq!(x_s2, s2.vec(xs));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+    }
+
+    #[test]
+    #[cfg_attr(not(target_feature = "ssse3"), ignore)]
+    fn test_shuffle64_s2_vs_s3() {
+        let xs = [0x0, 0x1, 0x2, 0x3];
+        let ys = [0x2, 0x3, 0x0, 0x1];
+        let zs = [0x1, 0x2, 0x3, 0x0];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u64x4 = s2.vec(xs);
+            x_s2.shuffle2301()
+        };
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u64x4 = s3.vec(xs);
+            x_s3.shuffle2301()
+        };
+        assert_eq!(x_s2, s2.vec(ys));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+
+        let x_s2 = {
+            let x_s2: <SSE2 as Machine>::u64x4 = s2.vec(xs);
+            x_s2.shuffle3012()
+        };
+        let x_s3 = {
+            let x_s3: <SSSE3 as Machine>::u64x4 = s3.vec(xs);
+            x_s3.shuffle3012()
+        };
+        assert_eq!(x_s2, s2.vec(zs));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+
+        let x_s2 = x_s2.shuffle1230();
+        let x_s3 = x_s3.shuffle1230();
+        assert_eq!(x_s2, s2.vec(xs));
+        assert_eq!(x_s3, unsafe { core::mem::transmute(x_s3) });
+    }
+
+    #[cfg_attr(not(all(target_feature = "ssse3", target_feature = "sse4.1")), ignore)]
+    #[test]
+    fn test_lanes_u32x4() {
+        let xs = [0x1, 0x2, 0x3, 0x4];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+        let s4 = unsafe { SSE41::instance() };
+
+        {
+            let x_s2: <SSE2 as Machine>::u32x4 = s2.vec(xs);
+            let y_s2 = <SSE2 as Machine>::u32x4::from_lanes(xs);
+            assert_eq!(x_s2, y_s2);
+            assert_eq!(xs, y_s2.to_lanes());
+        }
+
+        {
+            let x_s3: <SSSE3 as Machine>::u32x4 = s3.vec(xs);
+            let y_s3 = <SSSE3 as Machine>::u32x4::from_lanes(xs);
+            assert_eq!(x_s3, y_s3);
+            assert_eq!(xs, y_s3.to_lanes());
+        }
+
+        {
+            let x_s4: <SSE41 as Machine>::u32x4 = s4.vec(xs);
+            let y_s4 = <SSE41 as Machine>::u32x4::from_lanes(xs);
+            assert_eq!(x_s4, y_s4);
+            assert_eq!(xs, y_s4.to_lanes());
+        }
+    }
+
+    #[test]
+    #[cfg_attr(not(all(target_feature = "ssse3", target_feature = "sse4.1")), ignore)]
+    fn test_lanes_u64x2() {
+        let xs = [0x1, 0x2];
+
+        let s2 = unsafe { SSE2::instance() };
+        let s3 = unsafe { SSSE3::instance() };
+        let s4 = unsafe { SSE41::instance() };
+
+        {
+            let x_s2: <SSE2 as Machine>::u64x2 = s2.vec(xs);
+            let y_s2 = <SSE2 as Machine>::u64x2::from_lanes(xs);
+            assert_eq!(x_s2, y_s2);
+            assert_eq!(xs, y_s2.to_lanes());
+        }
+
+        {
+            let x_s3: <SSSE3 as Machine>::u64x2 = s3.vec(xs);
+            let y_s3 = <SSSE3 as Machine>::u64x2::from_lanes(xs);
+            assert_eq!(x_s3, y_s3);
+            assert_eq!(xs, y_s3.to_lanes());
+        }
+
+        {
+            let x_s4: <SSE41 as Machine>::u64x2 = s4.vec(xs);
+            let y_s4 = <SSE41 as Machine>::u64x2::from_lanes(xs);
+            assert_eq!(x_s4, y_s4);
+            assert_eq!(xs, y_s4.to_lanes());
+        }
+    }
+
+    #[test]
+    fn test_vec4_u32x4_s2() {
+        let xs = [1, 2, 3, 4];
+        let s2 = unsafe { SSE2::instance() };
+        let x_s2: <SSE2 as Machine>::u32x4 = s2.vec(xs);
+        assert_eq!(x_s2.extract(0), 1);
+        assert_eq!(x_s2.extract(1), 2);
+        assert_eq!(x_s2.extract(2), 3);
+        assert_eq!(x_s2.extract(3), 4);
+        assert_eq!(x_s2.insert(0xf, 0), s2.vec([0xf, 2, 3, 4]));
+        assert_eq!(x_s2.insert(0xf, 1), s2.vec([1, 0xf, 3, 4]));
+        assert_eq!(x_s2.insert(0xf, 2), s2.vec([1, 2, 0xf, 4]));
+        assert_eq!(x_s2.insert(0xf, 3), s2.vec([1, 2, 3, 0xf]));
+    }
+
+    #[test]
+    #[cfg_attr(not(all(target_feature = "ssse3", target_feature = "sse4.1")), ignore)]
+    fn test_vec4_u32x4_s4() {
+        let xs = [1, 2, 3, 4];
+        let s4 = unsafe { SSE41::instance() };
+        let x_s4: <SSE41 as Machine>::u32x4 = s4.vec(xs);
+        assert_eq!(x_s4.extract(0), 1);
+        assert_eq!(x_s4.extract(1), 2);
+        assert_eq!(x_s4.extract(2), 3);
+        assert_eq!(x_s4.extract(3), 4);
+        assert_eq!(x_s4.insert(0xf, 0), s4.vec([0xf, 2, 3, 4]));
+        assert_eq!(x_s4.insert(0xf, 1), s4.vec([1, 0xf, 3, 4]));
+        assert_eq!(x_s4.insert(0xf, 2), s4.vec([1, 2, 0xf, 4]));
+        assert_eq!(x_s4.insert(0xf, 3), s4.vec([1, 2, 3, 0xf]));
+    }
+
+    #[test]
+    fn test_vec2_u64x2_s2() {
+        let xs = [0x1, 0x2];
+        let s2 = unsafe { SSE2::instance() };
+        let x_s2: <SSE2 as Machine>::u64x2 = s2.vec(xs);
+        assert_eq!(x_s2.extract(0), 1);
+        assert_eq!(x_s2.extract(1), 2);
+        assert_eq!(x_s2.insert(0xf, 0), s2.vec([0xf, 2]));
+        assert_eq!(x_s2.insert(0xf, 1), s2.vec([1, 0xf]));
+    }
+
+    #[test]
+    #[cfg_attr(not(all(target_feature = "ssse3", target_feature = "sse4.1")), ignore)]
+    fn test_vec4_u64x2_s4() {
+        let xs = [0x1, 0x2];
+        let s4 = unsafe { SSE41::instance() };
+        let x_s4: <SSE41 as Machine>::u64x2 = s4.vec(xs);
+        assert_eq!(x_s4.extract(0), 1);
+        assert_eq!(x_s4.extract(1), 2);
+        assert_eq!(x_s4.insert(0xf, 0), s4.vec([0xf, 2]));
+        assert_eq!(x_s4.insert(0xf, 1), s4.vec([1, 0xf]));
+    }
+}
+
+pub mod avx2 {
+    #![allow(non_camel_case_types)]
+    use crate::soft::{x2, x4};
+    use crate::types::*;
+    use crate::x86_64::sse2::{u128x1_sse2, u32x4_sse2, G0};
+    use crate::x86_64::{vec256_storage, vec512_storage, Avx2Machine, YesS3, YesS4};
+    use core::arch::x86_64::*;
+    use core::marker::PhantomData;
+    use core::ops::*;
+
+    #[derive(Copy, Clone)]
+    pub struct u32x4x2_avx2<NI> {
+        x: __m256i,
+        ni: PhantomData<NI>,
+    }
+
+    impl<NI> u32x4x2_avx2<NI> {
+        #[inline(always)]
+        fn new(x: __m256i) -> Self {
+            Self { x, ni: PhantomData }
+        }
+    }
+
+    impl<NI> u32x4x2<Avx2Machine<NI>> for u32x4x2_avx2<NI> where NI: Copy {}
+    impl<NI> Store<vec256_storage> for u32x4x2_avx2<NI> {
+        #[inline(always)]
+        unsafe fn unpack(p: vec256_storage) -> Self {
+            Self::new(p.avx)
+        }
+    }
+    impl<NI> StoreBytes for u32x4x2_avx2<NI> {
+        #[inline(always)]
+        unsafe fn unsafe_read_le(input: &[u8]) -> Self {
+            assert_eq!(input.len(), 32);
+            Self::new(_mm256_loadu_si256(input.as_ptr() as *const _))
+        }
+        #[inline(always)]
+        unsafe fn unsafe_read_be(input: &[u8]) -> Self {
+            Self::unsafe_read_le(input).bswap()
+        }
+        #[inline(always)]
+        fn write_le(self, out: &mut [u8]) {
+            unsafe {
+                assert_eq!(out.len(), 32);
+                _mm256_storeu_si256(out.as_mut_ptr() as *mut _, self.x)
+            }
+        }
+        #[inline(always)]
+        fn write_be(self, out: &mut [u8]) {
+            self.bswap().write_le(out)
+        }
+    }
+    impl<NI> MultiLane<[u32x4_sse2<YesS3, YesS4, NI>; 2]> for u32x4x2_avx2<NI> {
+        #[inline(always)]
+        fn to_lanes(self) -> [u32x4_sse2<YesS3, YesS4, NI>; 2] {
+            unsafe {
+                [
+                    u32x4_sse2::new(_mm256_extracti128_si256(self.x, 0)),
+                    u32x4_sse2::new(_mm256_extracti128_si256(self.x, 1)),
+                ]
+            }
+        }
+        #[inline(always)]
+        fn from_lanes(x: [u32x4_sse2<YesS3, YesS4, NI>; 2]) -> Self {
+            Self::new(unsafe { _mm256_setr_m128i(x[0].x, x[1].x) })
+        }
+    }
+    impl<NI> Vec2<u32x4_sse2<YesS3, YesS4, NI>> for u32x4x2_avx2<NI> {
+        #[inline(always)]
+        fn extract(self, i: u32) -> u32x4_sse2<YesS3, YesS4, NI> {
+            unsafe {
+                match i {
+                    0 => u32x4_sse2::new(_mm256_extracti128_si256(self.x, 0)),
+                    1 => u32x4_sse2::new(_mm256_extracti128_si256(self.x, 1)),
+                    _ => panic!(),
+                }
+            }
+        }
+        #[inline(always)]
+        fn insert(self, w: u32x4_sse2<YesS3, YesS4, NI>, i: u32) -> Self {
+            Self::new(unsafe {
+                match i {
+                    0 => _mm256_inserti128_si256(self.x, w.x, 0),
+                    1 => _mm256_inserti128_si256(self.x, w.x, 1),
+                    _ => panic!(),
+                }
+            })
+        }
+    }
+    impl<NI> BitOps32 for u32x4x2_avx2<NI> where NI: Copy {}
+    impl<NI> ArithOps for u32x4x2_avx2<NI> where NI: Copy {}
+    macro_rules! shuf_lane_bytes {
+        ($name:ident, $k0:expr, $k1:expr) => {
+            #[inline(always)]
+            fn $name(self) -> Self {
+                Self::new(unsafe {
+                    _mm256_shuffle_epi8(self.x, _mm256_set_epi64x($k0, $k1, $k0, $k1))
+                })
+            }
+        };
+    }
+    macro_rules! rotr_32 {
+        ($name:ident, $i:expr) => {
+            #[inline(always)]
+            fn $name(self) -> Self {
+                Self::new(unsafe {
+                    _mm256_or_si256(
+                        _mm256_srli_epi32(self.x, $i as i32),
+                        _mm256_slli_epi32(self.x, 32 - $i as i32),
+                    )
+                })
+            }
+        };
+    }
+    impl<NI: Copy> RotateEachWord32 for u32x4x2_avx2<NI> {
+        rotr_32!(rotate_each_word_right7, 7);
+        shuf_lane_bytes!(
+            rotate_each_word_right8,
+            0x0c0f_0e0d_080b_0a09,
+            0x0407_0605_0003_0201
+        );
+        rotr_32!(rotate_each_word_right11, 11);
+        rotr_32!(rotate_each_word_right12, 12);
+        shuf_lane_bytes!(
+            rotate_each_word_right16,
+            0x0d0c_0f0e_0908_0b0a,
+            0x0504_0706_0100_0302
+        );
+        rotr_32!(rotate_each_word_right20, 20);
+        shuf_lane_bytes!(
+            rotate_each_word_right24,
+            0x0e0d_0c0f_0a09_080b,
+            0x0605_0407_0201_0003
+        );
+        rotr_32!(rotate_each_word_right25, 25);
+    }
+    impl<NI> BitOps0 for u32x4x2_avx2<NI> where NI: Copy {}
+    impl<NI> From<u32x4x2_avx2<NI>> for vec256_storage {
+        #[inline(always)]
+        fn from(x: u32x4x2_avx2<NI>) -> Self {
+            Self { avx: x.x }
+        }
+    }
+
+    macro_rules! impl_assign {
+        ($vec:ident, $Assign:ident, $assign_fn:ident, $bin_fn:ident) => {
+            impl<NI> $Assign for $vec<NI>
+            where
+                NI: Copy,
+            {
+                #[inline(always)]
+                fn $assign_fn(&mut self, rhs: Self) {
+                    *self = self.$bin_fn(rhs);
+                }
+            }
+        };
+    }
+    impl_assign!(u32x4x2_avx2, BitXorAssign, bitxor_assign, bitxor);
+    impl_assign!(u32x4x2_avx2, BitOrAssign, bitor_assign, bitor);
+    impl_assign!(u32x4x2_avx2, BitAndAssign, bitand_assign, bitand);
+    impl_assign!(u32x4x2_avx2, AddAssign, add_assign, add);
+
+    macro_rules! impl_bitop {
+        ($vec:ident, $Op:ident, $op_fn:ident, $impl_fn:ident) => {
+            impl<NI> $Op for $vec<NI> {
+                type Output = Self;
+                #[inline(always)]
+                fn $op_fn(self, rhs: Self) -> Self::Output {
+                    Self::new(unsafe { $impl_fn(self.x, rhs.x) })
+                }
+            }
+        };
+    }
+    impl_bitop!(u32x4x2_avx2, BitXor, bitxor, _mm256_xor_si256);
+    impl_bitop!(u32x4x2_avx2, BitOr, bitor, _mm256_or_si256);
+    impl_bitop!(u32x4x2_avx2, BitAnd, bitand, _mm256_and_si256);
+    impl_bitop!(u32x4x2_avx2, AndNot, andnot, _mm256_andnot_si256);
+    impl_bitop!(u32x4x2_avx2, Add, add, _mm256_add_epi32);
+
+    impl<NI> Not for u32x4x2_avx2<NI> {
+        type Output = Self;
+        #[inline(always)]
+        fn not(self) -> Self::Output {
+            unsafe {
+                let f = _mm256_set1_epi8(-0x7f);
+                Self::new(f) ^ self
+            }
+        }
+    }
+
+    impl<NI> BSwap for u32x4x2_avx2<NI> {
+        shuf_lane_bytes!(bswap, 0x0c0d_0e0f_0809_0a0b, 0x0405_0607_0001_0203);
+    }
+
+    impl<NI> From<x2<u128x1_sse2<YesS3, YesS4, NI>, G0>> for u32x4x2_avx2<NI>
+    where
+        NI: Copy,
+    {
+        #[inline(always)]
+        fn from(x: x2<u128x1_sse2<YesS3, YesS4, NI>, G0>) -> Self {
+            Self::new(unsafe { _mm256_setr_m128i(x.0[0].x, x.0[1].x) })
+        }
+    }
+
+    impl<NI> LaneWords4 for u32x4x2_avx2<NI> {
+        #[inline(always)]
+        fn shuffle_lane_words1230(self) -> Self {
+            Self::new(unsafe { _mm256_shuffle_epi32(self.x, 0b1001_0011) })
+        }
+        #[inline(always)]
+        fn shuffle_lane_words2301(self) -> Self {
+            Self::new(unsafe { _mm256_shuffle_epi32(self.x, 0b0100_1110) })
+        }
+        #[inline(always)]
+        fn shuffle_lane_words3012(self) -> Self {
+            Self::new(unsafe { _mm256_shuffle_epi32(self.x, 0b0011_1001) })
+        }
+    }
+
+    ///////////////////////////////////////////////////////////////////////////////////////////
+
+    pub type u32x4x4_avx2<NI> = x2<u32x4x2_avx2<NI>, G0>;
+    impl<NI: Copy> u32x4x4<Avx2Machine<NI>> for u32x4x4_avx2<NI> {}
+
+    impl<NI: Copy> Store<vec512_storage> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        unsafe fn unpack(p: vec512_storage) -> Self {
+            Self::new([
+                u32x4x2_avx2::unpack(p.avx[0]),
+                u32x4x2_avx2::unpack(p.avx[1]),
+            ])
+        }
+    }
+    impl<NI: Copy> MultiLane<[u32x4_sse2<YesS3, YesS4, NI>; 4]> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        fn to_lanes(self) -> [u32x4_sse2<YesS3, YesS4, NI>; 4] {
+            let [a, b] = self.0[0].to_lanes();
+            let [c, d] = self.0[1].to_lanes();
+            [a, b, c, d]
+        }
+        #[inline(always)]
+        fn from_lanes(x: [u32x4_sse2<YesS3, YesS4, NI>; 4]) -> Self {
+            let ab = u32x4x2_avx2::from_lanes([x[0], x[1]]);
+            let cd = u32x4x2_avx2::from_lanes([x[2], x[3]]);
+            Self::new([ab, cd])
+        }
+    }
+    impl<NI: Copy> Vec4<u32x4_sse2<YesS3, YesS4, NI>> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        fn extract(self, i: u32) -> u32x4_sse2<YesS3, YesS4, NI> {
+            match i {
+                0 => self.0[0].extract(0),
+                1 => self.0[0].extract(1),
+                2 => self.0[1].extract(0),
+                3 => self.0[1].extract(1),
+                _ => panic!(),
+            }
+        }
+        #[inline(always)]
+        fn insert(self, w: u32x4_sse2<YesS3, YesS4, NI>, i: u32) -> Self {
+            Self::new(match i {
+                0 | 1 => [self.0[0].insert(w, i), self.0[1]],
+                2 | 3 => [self.0[0], self.0[1].insert(w, i - 2)],
+                _ => panic!(),
+            })
+        }
+    }
+    impl<NI: Copy> Vec4Ext<u32x4_sse2<YesS3, YesS4, NI>> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        fn transpose4(a: Self, b: Self, c: Self, d: Self) -> (Self, Self, Self, Self) {
+            /*
+             * a00:a01 a10:a11
+             * b00:b01 b10:b11
+             * c00:c01 c10:c11
+             * d00:d01 d10:d11
+             *       =>
+             * a00:b00 c00:d00
+             * a01:b01 c01:d01
+             * a10:b10 c10:d10
+             * a11:b11 c11:d11
+             */
+            unsafe {
+                let ab00 = u32x4x2_avx2::new(_mm256_permute2x128_si256(a.0[0].x, b.0[0].x, 0x20));
+                let ab01 = u32x4x2_avx2::new(_mm256_permute2x128_si256(a.0[0].x, b.0[0].x, 0x31));
+                let ab10 = u32x4x2_avx2::new(_mm256_permute2x128_si256(a.0[1].x, b.0[1].x, 0x20));
+                let ab11 = u32x4x2_avx2::new(_mm256_permute2x128_si256(a.0[1].x, b.0[1].x, 0x31));
+                let cd00 = u32x4x2_avx2::new(_mm256_permute2x128_si256(c.0[0].x, d.0[0].x, 0x20));
+                let cd01 = u32x4x2_avx2::new(_mm256_permute2x128_si256(c.0[0].x, d.0[0].x, 0x31));
+                let cd10 = u32x4x2_avx2::new(_mm256_permute2x128_si256(c.0[1].x, d.0[1].x, 0x20));
+                let cd11 = u32x4x2_avx2::new(_mm256_permute2x128_si256(c.0[1].x, d.0[1].x, 0x31));
+                (
+                    Self::new([ab00, cd00]),
+                    Self::new([ab01, cd01]),
+                    Self::new([ab10, cd10]),
+                    Self::new([ab11, cd11]),
+                )
+            }
+        }
+    }
+    impl<NI: Copy> Vector<[u32; 16]> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        fn to_scalars(self) -> [u32; 16] {
+            unsafe { core::mem::transmute(self) }
+        }
+    }
+    impl<NI: Copy> From<u32x4x4_avx2<NI>> for vec512_storage {
+        #[inline(always)]
+        fn from(x: u32x4x4_avx2<NI>) -> Self {
+            Self {
+                avx: [
+                    vec256_storage { avx: x.0[0].x },
+                    vec256_storage { avx: x.0[1].x },
+                ],
+            }
+        }
+    }
+    impl<NI: Copy> From<x4<u128x1_sse2<YesS3, YesS4, NI>>> for u32x4x4_avx2<NI> {
+        #[inline(always)]
+        fn from(x: x4<u128x1_sse2<YesS3, YesS4, NI>>) -> Self {
+            Self::new(unsafe {
+                [
+                    u32x4x2_avx2::new(_mm256_setr_m128i(x.0[0].x, x.0[1].x)),
+                    u32x4x2_avx2::new(_mm256_setr_m128i(x.0[2].x, x.0[3].x)),
+                ]
+            })
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/bernoulli.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/bernoulli.rs.html new file mode 100644 index 0000000..8b882e8 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/bernoulli.rs.html @@ -0,0 +1,441 @@ +bernoulli.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The Bernoulli distribution.
+
+use crate::distributions::Distribution;
+use crate::Rng;
+use core::{fmt, u64};
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+/// The Bernoulli distribution.
+///
+/// This is a special case of the Binomial distribution where `n = 1`.
+///
+/// # Example
+///
+/// ```rust
+/// use rand::distributions::{Bernoulli, Distribution};
+///
+/// let d = Bernoulli::new(0.3).unwrap();
+/// let v = d.sample(&mut rand::thread_rng());
+/// println!("{} is from a Bernoulli distribution", v);
+/// ```
+///
+/// # Precision
+///
+/// This `Bernoulli` distribution uses 64 bits from the RNG (a `u64`),
+/// so only probabilities that are multiples of 2<sup>-64</sup> can be
+/// represented.
+#[derive(Clone, Copy, Debug, PartialEq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct Bernoulli {
+    /// Probability of success, relative to the maximal integer.
+    p_int: u64,
+}
+
+// To sample from the Bernoulli distribution we use a method that compares a
+// random `u64` value `v < (p * 2^64)`.
+//
+// If `p == 1.0`, the integer `v` to compare against can not represented as a
+// `u64`. We manually set it to `u64::MAX` instead (2^64 - 1 instead of 2^64).
+// Note that  value of `p < 1.0` can never result in `u64::MAX`, because an
+// `f64` only has 53 bits of precision, and the next largest value of `p` will
+// result in `2^64 - 2048`.
+//
+// Also there is a 100% theoretical concern: if someone consistently wants to
+// generate `true` using the Bernoulli distribution (i.e. by using a probability
+// of `1.0`), just using `u64::MAX` is not enough. On average it would return
+// false once every 2^64 iterations. Some people apparently care about this
+// case.
+//
+// That is why we special-case `u64::MAX` to always return `true`, without using
+// the RNG, and pay the performance price for all uses that *are* reasonable.
+// Luckily, if `new()` and `sample` are close, the compiler can optimize out the
+// extra check.
+const ALWAYS_TRUE: u64 = u64::MAX;
+
+// This is just `2.0.powi(64)`, but written this way because it is not available
+// in `no_std` mode.
+const SCALE: f64 = 2.0 * (1u64 << 63) as f64;
+
+/// Error type returned from `Bernoulli::new`.
+#[derive(Clone, Copy, Debug, PartialEq, Eq)]
+pub enum BernoulliError {
+    /// `p < 0` or `p > 1`.
+    InvalidProbability,
+}
+
+impl fmt::Display for BernoulliError {
+    fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
+        f.write_str(match self {
+            BernoulliError::InvalidProbability => "p is outside [0, 1] in Bernoulli distribution",
+        })
+    }
+}
+
+#[cfg(feature = "std")]
+impl ::std::error::Error for BernoulliError {}
+
+impl Bernoulli {
+    /// Construct a new `Bernoulli` with the given probability of success `p`.
+    ///
+    /// # Precision
+    ///
+    /// For `p = 1.0`, the resulting distribution will always generate true.
+    /// For `p = 0.0`, the resulting distribution will always generate false.
+    ///
+    /// This method is accurate for any input `p` in the range `[0, 1]` which is
+    /// a multiple of 2<sup>-64</sup>. (Note that not all multiples of
+    /// 2<sup>-64</sup> in `[0, 1]` can be represented as a `f64`.)
+    #[inline]
+    pub fn new(p: f64) -> Result<Bernoulli, BernoulliError> {
+        if !(0.0..1.0).contains(&p) {
+            if p == 1.0 {
+                return Ok(Bernoulli { p_int: ALWAYS_TRUE });
+            }
+            return Err(BernoulliError::InvalidProbability);
+        }
+        Ok(Bernoulli {
+            p_int: (p * SCALE) as u64,
+        })
+    }
+
+    /// Construct a new `Bernoulli` with the probability of success of
+    /// `numerator`-in-`denominator`. I.e. `new_ratio(2, 3)` will return
+    /// a `Bernoulli` with a 2-in-3 chance, or about 67%, of returning `true`.
+    ///
+    /// return `true`. If `numerator == 0` it will always return `false`.
+    /// For `numerator > denominator` and `denominator == 0`, this returns an
+    /// error. Otherwise, for `numerator == denominator`, samples are always
+    /// true; for `numerator == 0` samples are always false.
+    #[inline]
+    pub fn from_ratio(numerator: u32, denominator: u32) -> Result<Bernoulli, BernoulliError> {
+        if numerator > denominator || denominator == 0 {
+            return Err(BernoulliError::InvalidProbability);
+        }
+        if numerator == denominator {
+            return Ok(Bernoulli { p_int: ALWAYS_TRUE });
+        }
+        let p_int = ((f64::from(numerator) / f64::from(denominator)) * SCALE) as u64;
+        Ok(Bernoulli { p_int })
+    }
+}
+
+impl Distribution<bool> for Bernoulli {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> bool {
+        // Make sure to always return true for p = 1.0.
+        if self.p_int == ALWAYS_TRUE {
+            return true;
+        }
+        let v: u64 = rng.gen();
+        v < self.p_int
+    }
+}
+
+#[cfg(test)]
+mod test {
+    use super::Bernoulli;
+    use crate::distributions::Distribution;
+    use crate::Rng;
+
+    #[test]
+    #[cfg(feature="serde1")]
+    fn test_serializing_deserializing_bernoulli() {
+        let coin_flip = Bernoulli::new(0.5).unwrap();
+        let de_coin_flip : Bernoulli = bincode::deserialize(&bincode::serialize(&coin_flip).unwrap()).unwrap();
+
+        assert_eq!(coin_flip.p_int, de_coin_flip.p_int);
+    }
+
+    #[test]
+    fn test_trivial() {
+        // We prefer to be explicit here.
+        #![allow(clippy::bool_assert_comparison)]
+
+        let mut r = crate::test::rng(1);
+        let always_false = Bernoulli::new(0.0).unwrap();
+        let always_true = Bernoulli::new(1.0).unwrap();
+        for _ in 0..5 {
+            assert_eq!(r.sample::<bool, _>(&always_false), false);
+            assert_eq!(r.sample::<bool, _>(&always_true), true);
+            assert_eq!(Distribution::<bool>::sample(&always_false, &mut r), false);
+            assert_eq!(Distribution::<bool>::sample(&always_true, &mut r), true);
+        }
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_average() {
+        const P: f64 = 0.3;
+        const NUM: u32 = 3;
+        const DENOM: u32 = 10;
+        let d1 = Bernoulli::new(P).unwrap();
+        let d2 = Bernoulli::from_ratio(NUM, DENOM).unwrap();
+        const N: u32 = 100_000;
+
+        let mut sum1: u32 = 0;
+        let mut sum2: u32 = 0;
+        let mut rng = crate::test::rng(2);
+        for _ in 0..N {
+            if d1.sample(&mut rng) {
+                sum1 += 1;
+            }
+            if d2.sample(&mut rng) {
+                sum2 += 1;
+            }
+        }
+        let avg1 = (sum1 as f64) / (N as f64);
+        assert!((avg1 - P).abs() < 5e-3);
+
+        let avg2 = (sum2 as f64) / (N as f64);
+        assert!((avg2 - (NUM as f64) / (DENOM as f64)).abs() < 5e-3);
+    }
+
+    #[test]
+    fn value_stability() {
+        let mut rng = crate::test::rng(3);
+        let distr = Bernoulli::new(0.4532).unwrap();
+        let mut buf = [false; 10];
+        for x in &mut buf {
+            *x = rng.sample(&distr);
+        }
+        assert_eq!(buf, [
+            true, false, false, true, false, false, true, true, true, true
+        ]);
+    }
+
+    #[test]
+    fn bernoulli_distributions_can_be_compared() {
+        assert_eq!(Bernoulli::new(1.0), Bernoulli::new(1.0));
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/distribution.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/distribution.rs.html new file mode 100644 index 0000000..afc8925 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/distribution.rs.html @@ -0,0 +1,547 @@ +distribution.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013-2017 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Distribution trait and associates
+
+use crate::Rng;
+use core::iter;
+#[cfg(feature = "alloc")]
+use alloc::string::String;
+
+/// Types (distributions) that can be used to create a random instance of `T`.
+///
+/// It is possible to sample from a distribution through both the
+/// `Distribution` and [`Rng`] traits, via `distr.sample(&mut rng)` and
+/// `rng.sample(distr)`. They also both offer the [`sample_iter`] method, which
+/// produces an iterator that samples from the distribution.
+///
+/// All implementations are expected to be immutable; this has the significant
+/// advantage of not needing to consider thread safety, and for most
+/// distributions efficient state-less sampling algorithms are available.
+///
+/// Implementations are typically expected to be portable with reproducible
+/// results when used with a PRNG with fixed seed; see the
+/// [portability chapter](https://rust-random.github.io/book/portability.html)
+/// of The Rust Rand Book. In some cases this does not apply, e.g. the `usize`
+/// type requires different sampling on 32-bit and 64-bit machines.
+///
+/// [`sample_iter`]: Distribution::sample_iter
+pub trait Distribution<T> {
+    /// Generate a random value of `T`, using `rng` as the source of randomness.
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> T;
+
+    /// Create an iterator that generates random values of `T`, using `rng` as
+    /// the source of randomness.
+    ///
+    /// Note that this function takes `self` by value. This works since
+    /// `Distribution<T>` is impl'd for `&D` where `D: Distribution<T>`,
+    /// however borrowing is not automatic hence `distr.sample_iter(...)` may
+    /// need to be replaced with `(&distr).sample_iter(...)` to borrow or
+    /// `(&*distr).sample_iter(...)` to reborrow an existing reference.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::thread_rng;
+    /// use rand::distributions::{Distribution, Alphanumeric, Uniform, Standard};
+    ///
+    /// let mut rng = thread_rng();
+    ///
+    /// // Vec of 16 x f32:
+    /// let v: Vec<f32> = Standard.sample_iter(&mut rng).take(16).collect();
+    ///
+    /// // String:
+    /// let s: String = Alphanumeric
+    ///     .sample_iter(&mut rng)
+    ///     .take(7)
+    ///     .map(char::from)
+    ///     .collect();
+    ///
+    /// // Dice-rolling:
+    /// let die_range = Uniform::new_inclusive(1, 6);
+    /// let mut roll_die = die_range.sample_iter(&mut rng);
+    /// while roll_die.next().unwrap() != 6 {
+    ///     println!("Not a 6; rolling again!");
+    /// }
+    /// ```
+    fn sample_iter<R>(self, rng: R) -> DistIter<Self, R, T>
+    where
+        R: Rng,
+        Self: Sized,
+    {
+        DistIter {
+            distr: self,
+            rng,
+            phantom: ::core::marker::PhantomData,
+        }
+    }
+
+    /// Create a distribution of values of 'S' by mapping the output of `Self`
+    /// through the closure `F`
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::thread_rng;
+    /// use rand::distributions::{Distribution, Uniform};
+    ///
+    /// let mut rng = thread_rng();
+    ///
+    /// let die = Uniform::new_inclusive(1, 6);
+    /// let even_number = die.map(|num| num % 2 == 0);
+    /// while !even_number.sample(&mut rng) {
+    ///     println!("Still odd; rolling again!");
+    /// }
+    /// ```
+    fn map<F, S>(self, func: F) -> DistMap<Self, F, T, S>
+    where
+        F: Fn(T) -> S,
+        Self: Sized,
+    {
+        DistMap {
+            distr: self,
+            func,
+            phantom: ::core::marker::PhantomData,
+        }
+    }
+}
+
+impl<'a, T, D: Distribution<T>> Distribution<T> for &'a D {
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> T {
+        (*self).sample(rng)
+    }
+}
+
+/// An iterator that generates random values of `T` with distribution `D`,
+/// using `R` as the source of randomness.
+///
+/// This `struct` is created by the [`sample_iter`] method on [`Distribution`].
+/// See its documentation for more.
+///
+/// [`sample_iter`]: Distribution::sample_iter
+#[derive(Debug)]
+pub struct DistIter<D, R, T> {
+    distr: D,
+    rng: R,
+    phantom: ::core::marker::PhantomData<T>,
+}
+
+impl<D, R, T> Iterator for DistIter<D, R, T>
+where
+    D: Distribution<T>,
+    R: Rng,
+{
+    type Item = T;
+
+    #[inline(always)]
+    fn next(&mut self) -> Option<T> {
+        // Here, self.rng may be a reference, but we must take &mut anyway.
+        // Even if sample could take an R: Rng by value, we would need to do this
+        // since Rng is not copyable and we cannot enforce that this is "reborrowable".
+        Some(self.distr.sample(&mut self.rng))
+    }
+
+    fn size_hint(&self) -> (usize, Option<usize>) {
+        (usize::max_value(), None)
+    }
+}
+
+impl<D, R, T> iter::FusedIterator for DistIter<D, R, T>
+where
+    D: Distribution<T>,
+    R: Rng,
+{
+}
+
+#[cfg(features = "nightly")]
+impl<D, R, T> iter::TrustedLen for DistIter<D, R, T>
+where
+    D: Distribution<T>,
+    R: Rng,
+{
+}
+
+/// A distribution of values of type `S` derived from the distribution `D`
+/// by mapping its output of type `T` through the closure `F`.
+///
+/// This `struct` is created by the [`Distribution::map`] method.
+/// See its documentation for more.
+#[derive(Debug)]
+pub struct DistMap<D, F, T, S> {
+    distr: D,
+    func: F,
+    phantom: ::core::marker::PhantomData<fn(T) -> S>,
+}
+
+impl<D, F, T, S> Distribution<S> for DistMap<D, F, T, S>
+where
+    D: Distribution<T>,
+    F: Fn(T) -> S,
+{
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> S {
+        (self.func)(self.distr.sample(rng))
+    }
+}
+
+/// `String` sampler
+///
+/// Sampling a `String` of random characters is not quite the same as collecting
+/// a sequence of chars. This trait contains some helpers.
+#[cfg(feature = "alloc")]
+pub trait DistString {
+    /// Append `len` random chars to `string`
+    fn append_string<R: Rng + ?Sized>(&self, rng: &mut R, string: &mut String, len: usize);
+
+    /// Generate a `String` of `len` random chars
+    #[inline]
+    fn sample_string<R: Rng + ?Sized>(&self, rng: &mut R, len: usize) -> String {
+        let mut s = String::new();
+        self.append_string(rng, &mut s, len);
+        s
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use crate::distributions::{Distribution, Uniform};
+    use crate::Rng;
+
+    #[test]
+    fn test_distributions_iter() {
+        use crate::distributions::Open01;
+        let mut rng = crate::test::rng(210);
+        let distr = Open01;
+        let mut iter = Distribution::<f32>::sample_iter(distr, &mut rng);
+        let mut sum: f32 = 0.;
+        for _ in 0..100 {
+            sum += iter.next().unwrap();
+        }
+        assert!(0. < sum && sum < 100.);
+    }
+
+    #[test]
+    fn test_distributions_map() {
+        let dist = Uniform::new_inclusive(0, 5).map(|val| val + 15);
+
+        let mut rng = crate::test::rng(212);
+        let val = dist.sample(&mut rng);
+        assert!((15..=20).contains(&val));
+    }
+
+    #[test]
+    fn test_make_an_iter() {
+        fn ten_dice_rolls_other_than_five<R: Rng>(
+            rng: &mut R,
+        ) -> impl Iterator<Item = i32> + '_ {
+            Uniform::new_inclusive(1, 6)
+                .sample_iter(rng)
+                .filter(|x| *x != 5)
+                .take(10)
+        }
+
+        let mut rng = crate::test::rng(211);
+        let mut count = 0;
+        for val in ten_dice_rolls_other_than_five(&mut rng) {
+            assert!((1..=6).contains(&val) && val != 5);
+            count += 1;
+        }
+        assert_eq!(count, 10);
+    }
+
+    #[test]
+    #[cfg(feature = "alloc")]
+    fn test_dist_string() {
+        use core::str;
+        use crate::distributions::{Alphanumeric, DistString, Standard};
+        let mut rng = crate::test::rng(213);
+
+        let s1 = Alphanumeric.sample_string(&mut rng, 20);
+        assert_eq!(s1.len(), 20);
+        assert_eq!(str::from_utf8(s1.as_bytes()), Ok(s1.as_str()));
+
+        let s2 = Standard.sample_string(&mut rng, 20);
+        assert_eq!(s2.chars().count(), 20);
+        assert_eq!(str::from_utf8(s2.as_bytes()), Ok(s2.as_str()));
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/float.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/float.rs.html new file mode 100644 index 0000000..cba1f5b --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/float.rs.html @@ -0,0 +1,627 @@ +float.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Basic floating-point number distributions
+
+use crate::distributions::utils::FloatSIMDUtils;
+use crate::distributions::{Distribution, Standard};
+use crate::Rng;
+use core::mem;
+#[cfg(feature = "simd_support")] use packed_simd::*;
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+
+/// A distribution to sample floating point numbers uniformly in the half-open
+/// interval `(0, 1]`, i.e. including 1 but not 0.
+///
+/// All values that can be generated are of the form `n * ε/2`. For `f32`
+/// the 24 most significant random bits of a `u32` are used and for `f64` the
+/// 53 most significant bits of a `u64` are used. The conversion uses the
+/// multiplicative method.
+///
+/// See also: [`Standard`] which samples from `[0, 1)`, [`Open01`]
+/// which samples from `(0, 1)` and [`Uniform`] which samples from arbitrary
+/// ranges.
+///
+/// # Example
+/// ```
+/// use rand::{thread_rng, Rng};
+/// use rand::distributions::OpenClosed01;
+///
+/// let val: f32 = thread_rng().sample(OpenClosed01);
+/// println!("f32 from (0, 1): {}", val);
+/// ```
+///
+/// [`Standard`]: crate::distributions::Standard
+/// [`Open01`]: crate::distributions::Open01
+/// [`Uniform`]: crate::distributions::uniform::Uniform
+#[derive(Clone, Copy, Debug)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct OpenClosed01;
+
+/// A distribution to sample floating point numbers uniformly in the open
+/// interval `(0, 1)`, i.e. not including either endpoint.
+///
+/// All values that can be generated are of the form `n * ε + ε/2`. For `f32`
+/// the 23 most significant random bits of an `u32` are used, for `f64` 52 from
+/// an `u64`. The conversion uses a transmute-based method.
+///
+/// See also: [`Standard`] which samples from `[0, 1)`, [`OpenClosed01`]
+/// which samples from `(0, 1]` and [`Uniform`] which samples from arbitrary
+/// ranges.
+///
+/// # Example
+/// ```
+/// use rand::{thread_rng, Rng};
+/// use rand::distributions::Open01;
+///
+/// let val: f32 = thread_rng().sample(Open01);
+/// println!("f32 from (0, 1): {}", val);
+/// ```
+///
+/// [`Standard`]: crate::distributions::Standard
+/// [`OpenClosed01`]: crate::distributions::OpenClosed01
+/// [`Uniform`]: crate::distributions::uniform::Uniform
+#[derive(Clone, Copy, Debug)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct Open01;
+
+
+// This trait is needed by both this lib and rand_distr hence is a hidden export
+#[doc(hidden)]
+pub trait IntoFloat {
+    type F;
+
+    /// Helper method to combine the fraction and a constant exponent into a
+    /// float.
+    ///
+    /// Only the least significant bits of `self` may be set, 23 for `f32` and
+    /// 52 for `f64`.
+    /// The resulting value will fall in a range that depends on the exponent.
+    /// As an example the range with exponent 0 will be
+    /// [2<sup>0</sup>..2<sup>1</sup>), which is [1..2).
+    fn into_float_with_exponent(self, exponent: i32) -> Self::F;
+}
+
+macro_rules! float_impls {
+    ($ty:ident, $uty:ident, $f_scalar:ident, $u_scalar:ty,
+     $fraction_bits:expr, $exponent_bias:expr) => {
+        impl IntoFloat for $uty {
+            type F = $ty;
+            #[inline(always)]
+            fn into_float_with_exponent(self, exponent: i32) -> $ty {
+                // The exponent is encoded using an offset-binary representation
+                let exponent_bits: $u_scalar =
+                    (($exponent_bias + exponent) as $u_scalar) << $fraction_bits;
+                $ty::from_bits(self | exponent_bits)
+            }
+        }
+
+        impl Distribution<$ty> for Standard {
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                // Multiply-based method; 24/53 random bits; [0, 1) interval.
+                // We use the most significant bits because for simple RNGs
+                // those are usually more random.
+                let float_size = mem::size_of::<$f_scalar>() as u32 * 8;
+                let precision = $fraction_bits + 1;
+                let scale = 1.0 / ((1 as $u_scalar << precision) as $f_scalar);
+
+                let value: $uty = rng.gen();
+                let value = value >> (float_size - precision);
+                scale * $ty::cast_from_int(value)
+            }
+        }
+
+        impl Distribution<$ty> for OpenClosed01 {
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                // Multiply-based method; 24/53 random bits; (0, 1] interval.
+                // We use the most significant bits because for simple RNGs
+                // those are usually more random.
+                let float_size = mem::size_of::<$f_scalar>() as u32 * 8;
+                let precision = $fraction_bits + 1;
+                let scale = 1.0 / ((1 as $u_scalar << precision) as $f_scalar);
+
+                let value: $uty = rng.gen();
+                let value = value >> (float_size - precision);
+                // Add 1 to shift up; will not overflow because of right-shift:
+                scale * $ty::cast_from_int(value + 1)
+            }
+        }
+
+        impl Distribution<$ty> for Open01 {
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                // Transmute-based method; 23/52 random bits; (0, 1) interval.
+                // We use the most significant bits because for simple RNGs
+                // those are usually more random.
+                use core::$f_scalar::EPSILON;
+                let float_size = mem::size_of::<$f_scalar>() as u32 * 8;
+
+                let value: $uty = rng.gen();
+                let fraction = value >> (float_size - $fraction_bits);
+                fraction.into_float_with_exponent(0) - (1.0 - EPSILON / 2.0)
+            }
+        }
+    }
+}
+
+float_impls! { f32, u32, f32, u32, 23, 127 }
+float_impls! { f64, u64, f64, u64, 52, 1023 }
+
+#[cfg(feature = "simd_support")]
+float_impls! { f32x2, u32x2, f32, u32, 23, 127 }
+#[cfg(feature = "simd_support")]
+float_impls! { f32x4, u32x4, f32, u32, 23, 127 }
+#[cfg(feature = "simd_support")]
+float_impls! { f32x8, u32x8, f32, u32, 23, 127 }
+#[cfg(feature = "simd_support")]
+float_impls! { f32x16, u32x16, f32, u32, 23, 127 }
+
+#[cfg(feature = "simd_support")]
+float_impls! { f64x2, u64x2, f64, u64, 52, 1023 }
+#[cfg(feature = "simd_support")]
+float_impls! { f64x4, u64x4, f64, u64, 52, 1023 }
+#[cfg(feature = "simd_support")]
+float_impls! { f64x8, u64x8, f64, u64, 52, 1023 }
+
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+    use crate::rngs::mock::StepRng;
+
+    const EPSILON32: f32 = ::core::f32::EPSILON;
+    const EPSILON64: f64 = ::core::f64::EPSILON;
+
+    macro_rules! test_f32 {
+        ($fnn:ident, $ty:ident, $ZERO:expr, $EPSILON:expr) => {
+            #[test]
+            fn $fnn() {
+                // Standard
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.gen::<$ty>(), $ZERO);
+                let mut one = StepRng::new(1 << 8 | 1 << (8 + 32), 0);
+                assert_eq!(one.gen::<$ty>(), $EPSILON / 2.0);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.gen::<$ty>(), 1.0 - $EPSILON / 2.0);
+
+                // OpenClosed01
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.sample::<$ty, _>(OpenClosed01), 0.0 + $EPSILON / 2.0);
+                let mut one = StepRng::new(1 << 8 | 1 << (8 + 32), 0);
+                assert_eq!(one.sample::<$ty, _>(OpenClosed01), $EPSILON);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.sample::<$ty, _>(OpenClosed01), $ZERO + 1.0);
+
+                // Open01
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.sample::<$ty, _>(Open01), 0.0 + $EPSILON / 2.0);
+                let mut one = StepRng::new(1 << 9 | 1 << (9 + 32), 0);
+                assert_eq!(one.sample::<$ty, _>(Open01), $EPSILON / 2.0 * 3.0);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.sample::<$ty, _>(Open01), 1.0 - $EPSILON / 2.0);
+            }
+        };
+    }
+    test_f32! { f32_edge_cases, f32, 0.0, EPSILON32 }
+    #[cfg(feature = "simd_support")]
+    test_f32! { f32x2_edge_cases, f32x2, f32x2::splat(0.0), f32x2::splat(EPSILON32) }
+    #[cfg(feature = "simd_support")]
+    test_f32! { f32x4_edge_cases, f32x4, f32x4::splat(0.0), f32x4::splat(EPSILON32) }
+    #[cfg(feature = "simd_support")]
+    test_f32! { f32x8_edge_cases, f32x8, f32x8::splat(0.0), f32x8::splat(EPSILON32) }
+    #[cfg(feature = "simd_support")]
+    test_f32! { f32x16_edge_cases, f32x16, f32x16::splat(0.0), f32x16::splat(EPSILON32) }
+
+    macro_rules! test_f64 {
+        ($fnn:ident, $ty:ident, $ZERO:expr, $EPSILON:expr) => {
+            #[test]
+            fn $fnn() {
+                // Standard
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.gen::<$ty>(), $ZERO);
+                let mut one = StepRng::new(1 << 11, 0);
+                assert_eq!(one.gen::<$ty>(), $EPSILON / 2.0);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.gen::<$ty>(), 1.0 - $EPSILON / 2.0);
+
+                // OpenClosed01
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.sample::<$ty, _>(OpenClosed01), 0.0 + $EPSILON / 2.0);
+                let mut one = StepRng::new(1 << 11, 0);
+                assert_eq!(one.sample::<$ty, _>(OpenClosed01), $EPSILON);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.sample::<$ty, _>(OpenClosed01), $ZERO + 1.0);
+
+                // Open01
+                let mut zeros = StepRng::new(0, 0);
+                assert_eq!(zeros.sample::<$ty, _>(Open01), 0.0 + $EPSILON / 2.0);
+                let mut one = StepRng::new(1 << 12, 0);
+                assert_eq!(one.sample::<$ty, _>(Open01), $EPSILON / 2.0 * 3.0);
+                let mut max = StepRng::new(!0, 0);
+                assert_eq!(max.sample::<$ty, _>(Open01), 1.0 - $EPSILON / 2.0);
+            }
+        };
+    }
+    test_f64! { f64_edge_cases, f64, 0.0, EPSILON64 }
+    #[cfg(feature = "simd_support")]
+    test_f64! { f64x2_edge_cases, f64x2, f64x2::splat(0.0), f64x2::splat(EPSILON64) }
+    #[cfg(feature = "simd_support")]
+    test_f64! { f64x4_edge_cases, f64x4, f64x4::splat(0.0), f64x4::splat(EPSILON64) }
+    #[cfg(feature = "simd_support")]
+    test_f64! { f64x8_edge_cases, f64x8, f64x8::splat(0.0), f64x8::splat(EPSILON64) }
+
+    #[test]
+    fn value_stability() {
+        fn test_samples<T: Copy + core::fmt::Debug + PartialEq, D: Distribution<T>>(
+            distr: &D, zero: T, expected: &[T],
+        ) {
+            let mut rng = crate::test::rng(0x6f44f5646c2a7334);
+            let mut buf = [zero; 3];
+            for x in &mut buf {
+                *x = rng.sample(&distr);
+            }
+            assert_eq!(&buf, expected);
+        }
+
+        test_samples(&Standard, 0f32, &[0.0035963655, 0.7346052, 0.09778172]);
+        test_samples(&Standard, 0f64, &[
+            0.7346051961657583,
+            0.20298547462974248,
+            0.8166436635290655,
+        ]);
+
+        test_samples(&OpenClosed01, 0f32, &[0.003596425, 0.73460525, 0.09778178]);
+        test_samples(&OpenClosed01, 0f64, &[
+            0.7346051961657584,
+            0.2029854746297426,
+            0.8166436635290656,
+        ]);
+
+        test_samples(&Open01, 0f32, &[0.0035963655, 0.73460525, 0.09778172]);
+        test_samples(&Open01, 0f64, &[
+            0.7346051961657584,
+            0.20298547462974248,
+            0.8166436635290656,
+        ]);
+
+        #[cfg(feature = "simd_support")]
+        {
+            // We only test a sub-set of types here. Values are identical to
+            // non-SIMD types; we assume this pattern continues across all
+            // SIMD types.
+
+            test_samples(&Standard, f32x2::new(0.0, 0.0), &[
+                f32x2::new(0.0035963655, 0.7346052),
+                f32x2::new(0.09778172, 0.20298547),
+                f32x2::new(0.34296435, 0.81664366),
+            ]);
+
+            test_samples(&Standard, f64x2::new(0.0, 0.0), &[
+                f64x2::new(0.7346051961657583, 0.20298547462974248),
+                f64x2::new(0.8166436635290655, 0.7423708925400552),
+                f64x2::new(0.16387782224016323, 0.9087068770169618),
+            ]);
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/integer.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/integer.rs.html new file mode 100644 index 0000000..0fbac64 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/integer.rs.html @@ -0,0 +1,551 @@ +integer.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The implementations of the `Standard` distribution for integer types.
+
+use crate::distributions::{Distribution, Standard};
+use crate::Rng;
+#[cfg(all(target_arch = "x86", feature = "simd_support"))]
+use core::arch::x86::{__m128i, __m256i};
+#[cfg(all(target_arch = "x86_64", feature = "simd_support"))]
+use core::arch::x86_64::{__m128i, __m256i};
+use core::num::{NonZeroU16, NonZeroU32, NonZeroU64, NonZeroU8, NonZeroUsize,
+    NonZeroU128};
+#[cfg(feature = "simd_support")] use packed_simd::*;
+
+impl Distribution<u8> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u8 {
+        rng.next_u32() as u8
+    }
+}
+
+impl Distribution<u16> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u16 {
+        rng.next_u32() as u16
+    }
+}
+
+impl Distribution<u32> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u32 {
+        rng.next_u32()
+    }
+}
+
+impl Distribution<u64> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u64 {
+        rng.next_u64()
+    }
+}
+
+impl Distribution<u128> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u128 {
+        // Use LE; we explicitly generate one value before the next.
+        let x = u128::from(rng.next_u64());
+        let y = u128::from(rng.next_u64());
+        (y << 64) | x
+    }
+}
+
+impl Distribution<usize> for Standard {
+    #[inline]
+    #[cfg(any(target_pointer_width = "32", target_pointer_width = "16"))]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> usize {
+        rng.next_u32() as usize
+    }
+
+    #[inline]
+    #[cfg(target_pointer_width = "64")]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> usize {
+        rng.next_u64() as usize
+    }
+}
+
+macro_rules! impl_int_from_uint {
+    ($ty:ty, $uty:ty) => {
+        impl Distribution<$ty> for Standard {
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                rng.gen::<$uty>() as $ty
+            }
+        }
+    };
+}
+
+impl_int_from_uint! { i8, u8 }
+impl_int_from_uint! { i16, u16 }
+impl_int_from_uint! { i32, u32 }
+impl_int_from_uint! { i64, u64 }
+impl_int_from_uint! { i128, u128 }
+impl_int_from_uint! { isize, usize }
+
+macro_rules! impl_nzint {
+    ($ty:ty, $new:path) => {
+        impl Distribution<$ty> for Standard {
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                loop {
+                    if let Some(nz) = $new(rng.gen()) {
+                        break nz;
+                    }
+                }
+            }
+        }
+    };
+}
+
+impl_nzint!(NonZeroU8, NonZeroU8::new);
+impl_nzint!(NonZeroU16, NonZeroU16::new);
+impl_nzint!(NonZeroU32, NonZeroU32::new);
+impl_nzint!(NonZeroU64, NonZeroU64::new);
+impl_nzint!(NonZeroU128, NonZeroU128::new);
+impl_nzint!(NonZeroUsize, NonZeroUsize::new);
+
+#[cfg(feature = "simd_support")]
+macro_rules! simd_impl {
+    ($(($intrinsic:ident, $vec:ty),)+) => {$(
+        impl Distribution<$intrinsic> for Standard {
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $intrinsic {
+                $intrinsic::from_bits(rng.gen::<$vec>())
+            }
+        }
+    )+};
+
+    ($bits:expr,) => {};
+    ($bits:expr, $ty:ty, $($ty_more:ty,)*) => {
+        simd_impl!($bits, $($ty_more,)*);
+
+        impl Distribution<$ty> for Standard {
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> $ty {
+                let mut vec: $ty = Default::default();
+                unsafe {
+                    let ptr = &mut vec;
+                    let b_ptr = &mut *(ptr as *mut $ty as *mut [u8; $bits/8]);
+                    rng.fill_bytes(b_ptr);
+                }
+                vec.to_le()
+            }
+        }
+    };
+}
+
+#[cfg(feature = "simd_support")]
+simd_impl!(16, u8x2, i8x2,);
+#[cfg(feature = "simd_support")]
+simd_impl!(32, u8x4, i8x4, u16x2, i16x2,);
+#[cfg(feature = "simd_support")]
+simd_impl!(64, u8x8, i8x8, u16x4, i16x4, u32x2, i32x2,);
+#[cfg(feature = "simd_support")]
+simd_impl!(128, u8x16, i8x16, u16x8, i16x8, u32x4, i32x4, u64x2, i64x2,);
+#[cfg(feature = "simd_support")]
+simd_impl!(256, u8x32, i8x32, u16x16, i16x16, u32x8, i32x8, u64x4, i64x4,);
+#[cfg(feature = "simd_support")]
+simd_impl!(512, u8x64, i8x64, u16x32, i16x32, u32x16, i32x16, u64x8, i64x8,);
+#[cfg(all(
+    feature = "simd_support",
+    any(target_arch = "x86", target_arch = "x86_64")
+))]
+simd_impl!((__m128i, u8x16), (__m256i, u8x32),);
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+
+    #[test]
+    fn test_integers() {
+        let mut rng = crate::test::rng(806);
+
+        rng.sample::<isize, _>(Standard);
+        rng.sample::<i8, _>(Standard);
+        rng.sample::<i16, _>(Standard);
+        rng.sample::<i32, _>(Standard);
+        rng.sample::<i64, _>(Standard);
+        rng.sample::<i128, _>(Standard);
+
+        rng.sample::<usize, _>(Standard);
+        rng.sample::<u8, _>(Standard);
+        rng.sample::<u16, _>(Standard);
+        rng.sample::<u32, _>(Standard);
+        rng.sample::<u64, _>(Standard);
+        rng.sample::<u128, _>(Standard);
+    }
+
+    #[test]
+    fn value_stability() {
+        fn test_samples<T: Copy + core::fmt::Debug + PartialEq>(zero: T, expected: &[T])
+        where Standard: Distribution<T> {
+            let mut rng = crate::test::rng(807);
+            let mut buf = [zero; 3];
+            for x in &mut buf {
+                *x = rng.sample(Standard);
+            }
+            assert_eq!(&buf, expected);
+        }
+
+        test_samples(0u8, &[9, 247, 111]);
+        test_samples(0u16, &[32265, 42999, 38255]);
+        test_samples(0u32, &[2220326409, 2575017975, 2018088303]);
+        test_samples(0u64, &[
+            11059617991457472009,
+            16096616328739788143,
+            1487364411147516184,
+        ]);
+        test_samples(0u128, &[
+            296930161868957086625409848350820761097,
+            145644820879247630242265036535529306392,
+            111087889832015897993126088499035356354,
+        ]);
+        #[cfg(any(target_pointer_width = "32", target_pointer_width = "16"))]
+        test_samples(0usize, &[2220326409, 2575017975, 2018088303]);
+        #[cfg(target_pointer_width = "64")]
+        test_samples(0usize, &[
+            11059617991457472009,
+            16096616328739788143,
+            1487364411147516184,
+        ]);
+
+        test_samples(0i8, &[9, -9, 111]);
+        // Skip further i* types: they are simple reinterpretation of u* samples
+
+        #[cfg(feature = "simd_support")]
+        {
+            // We only test a sub-set of types here and make assumptions about the rest.
+
+            test_samples(u8x2::default(), &[
+                u8x2::new(9, 126),
+                u8x2::new(247, 167),
+                u8x2::new(111, 149),
+            ]);
+            test_samples(u8x4::default(), &[
+                u8x4::new(9, 126, 87, 132),
+                u8x4::new(247, 167, 123, 153),
+                u8x4::new(111, 149, 73, 120),
+            ]);
+            test_samples(u8x8::default(), &[
+                u8x8::new(9, 126, 87, 132, 247, 167, 123, 153),
+                u8x8::new(111, 149, 73, 120, 68, 171, 98, 223),
+                u8x8::new(24, 121, 1, 50, 13, 46, 164, 20),
+            ]);
+
+            test_samples(i64x8::default(), &[
+                i64x8::new(
+                    -7387126082252079607,
+                    -2350127744969763473,
+                    1487364411147516184,
+                    7895421560427121838,
+                    602190064936008898,
+                    6022086574635100741,
+                    -5080089175222015595,
+                    -4066367846667249123,
+                ),
+                i64x8::new(
+                    9180885022207963908,
+                    3095981199532211089,
+                    6586075293021332726,
+                    419343203796414657,
+                    3186951873057035255,
+                    5287129228749947252,
+                    444726432079249540,
+                    -1587028029513790706,
+                ),
+                i64x8::new(
+                    6075236523189346388,
+                    1351763722368165432,
+                    -6192309979959753740,
+                    -7697775502176768592,
+                    -4482022114172078123,
+                    7522501477800909500,
+                    -1837258847956201231,
+                    -586926753024886735,
+                ),
+            ]);
+        }
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/mod.rs.html new file mode 100644 index 0000000..8e93c46 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/mod.rs.html @@ -0,0 +1,439 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013-2017 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Generating random samples from probability distributions
+//!
+//! This module is the home of the [`Distribution`] trait and several of its
+//! implementations. It is the workhorse behind some of the convenient
+//! functionality of the [`Rng`] trait, e.g. [`Rng::gen`] and of course
+//! [`Rng::sample`].
+//!
+//! Abstractly, a [probability distribution] describes the probability of
+//! occurrence of each value in its sample space.
+//!
+//! More concretely, an implementation of `Distribution<T>` for type `X` is an
+//! algorithm for choosing values from the sample space (a subset of `T`)
+//! according to the distribution `X` represents, using an external source of
+//! randomness (an RNG supplied to the `sample` function).
+//!
+//! A type `X` may implement `Distribution<T>` for multiple types `T`.
+//! Any type implementing [`Distribution`] is stateless (i.e. immutable),
+//! but it may have internal parameters set at construction time (for example,
+//! [`Uniform`] allows specification of its sample space as a range within `T`).
+//!
+//!
+//! # The `Standard` distribution
+//!
+//! The [`Standard`] distribution is important to mention. This is the
+//! distribution used by [`Rng::gen`] and represents the "default" way to
+//! produce a random value for many different types, including most primitive
+//! types, tuples, arrays, and a few derived types. See the documentation of
+//! [`Standard`] for more details.
+//!
+//! Implementing `Distribution<T>` for [`Standard`] for user types `T` makes it
+//! possible to generate type `T` with [`Rng::gen`], and by extension also
+//! with the [`random`] function.
+//!
+//! ## Random characters
+//!
+//! [`Alphanumeric`] is a simple distribution to sample random letters and
+//! numbers of the `char` type; in contrast [`Standard`] may sample any valid
+//! `char`.
+//!
+//!
+//! # Uniform numeric ranges
+//!
+//! The [`Uniform`] distribution is more flexible than [`Standard`], but also
+//! more specialised: it supports fewer target types, but allows the sample
+//! space to be specified as an arbitrary range within its target type `T`.
+//! Both [`Standard`] and [`Uniform`] are in some sense uniform distributions.
+//!
+//! Values may be sampled from this distribution using [`Rng::sample(Range)`] or
+//! by creating a distribution object with [`Uniform::new`],
+//! [`Uniform::new_inclusive`] or `From<Range>`. When the range limits are not
+//! known at compile time it is typically faster to reuse an existing
+//! `Uniform` object than to call [`Rng::sample(Range)`].
+//!
+//! User types `T` may also implement `Distribution<T>` for [`Uniform`],
+//! although this is less straightforward than for [`Standard`] (see the
+//! documentation in the [`uniform`] module). Doing so enables generation of
+//! values of type `T` with  [`Rng::sample(Range)`].
+//!
+//! ## Open and half-open ranges
+//!
+//! There are surprisingly many ways to uniformly generate random floats. A
+//! range between 0 and 1 is standard, but the exact bounds (open vs closed)
+//! and accuracy differ. In addition to the [`Standard`] distribution Rand offers
+//! [`Open01`] and [`OpenClosed01`]. See "Floating point implementation" section of
+//! [`Standard`] documentation for more details.
+//!
+//! # Non-uniform sampling
+//!
+//! Sampling a simple true/false outcome with a given probability has a name:
+//! the [`Bernoulli`] distribution (this is used by [`Rng::gen_bool`]).
+//!
+//! For weighted sampling from a sequence of discrete values, use the
+//! [`WeightedIndex`] distribution.
+//!
+//! This crate no longer includes other non-uniform distributions; instead
+//! it is recommended that you use either [`rand_distr`] or [`statrs`].
+//!
+//!
+//! [probability distribution]: https://en.wikipedia.org/wiki/Probability_distribution
+//! [`rand_distr`]: https://crates.io/crates/rand_distr
+//! [`statrs`]: https://crates.io/crates/statrs
+
+//! [`random`]: crate::random
+//! [`rand_distr`]: https://crates.io/crates/rand_distr
+//! [`statrs`]: https://crates.io/crates/statrs
+
+mod bernoulli;
+mod distribution;
+mod float;
+mod integer;
+mod other;
+mod slice;
+mod utils;
+#[cfg(feature = "alloc")]
+mod weighted_index;
+
+#[doc(hidden)]
+pub mod hidden_export {
+    pub use super::float::IntoFloat; // used by rand_distr
+}
+pub mod uniform;
+#[deprecated(
+    since = "0.8.0",
+    note = "use rand::distributions::{WeightedIndex, WeightedError} instead"
+)]
+#[cfg(feature = "alloc")]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+pub mod weighted;
+
+pub use self::bernoulli::{Bernoulli, BernoulliError};
+pub use self::distribution::{Distribution, DistIter, DistMap};
+#[cfg(feature = "alloc")]
+pub use self::distribution::DistString;
+pub use self::float::{Open01, OpenClosed01};
+pub use self::other::Alphanumeric;
+pub use self::slice::Slice;
+#[doc(inline)]
+pub use self::uniform::Uniform;
+#[cfg(feature = "alloc")]
+pub use self::weighted_index::{WeightedError, WeightedIndex};
+
+#[allow(unused)]
+use crate::Rng;
+
+/// A generic random value distribution, implemented for many primitive types.
+/// Usually generates values with a numerically uniform distribution, and with a
+/// range appropriate to the type.
+///
+/// ## Provided implementations
+///
+/// Assuming the provided `Rng` is well-behaved, these implementations
+/// generate values with the following ranges and distributions:
+///
+/// * Integers (`i32`, `u32`, `isize`, `usize`, etc.): Uniformly distributed
+///   over all values of the type.
+/// * `char`: Uniformly distributed over all Unicode scalar values, i.e. all
+///   code points in the range `0...0x10_FFFF`, except for the range
+///   `0xD800...0xDFFF` (the surrogate code points). This includes
+///   unassigned/reserved code points.
+/// * `bool`: Generates `false` or `true`, each with probability 0.5.
+/// * Floating point types (`f32` and `f64`): Uniformly distributed in the
+///   half-open range `[0, 1)`. See notes below.
+/// * Wrapping integers (`Wrapping<T>`), besides the type identical to their
+///   normal integer variants.
+///
+/// The `Standard` distribution also supports generation of the following
+/// compound types where all component types are supported:
+///
+/// *   Tuples (up to 12 elements): each element is generated sequentially.
+/// *   Arrays (up to 32 elements): each element is generated sequentially;
+///     see also [`Rng::fill`] which supports arbitrary array length for integer
+///     and float types and tends to be faster for `u32` and smaller types.
+///     When using `rustc` ≥ 1.51, enable the `min_const_gen` feature to support
+///     arrays larger than 32 elements.
+///     Note that [`Rng::fill`] and `Standard`'s array support are *not* equivalent:
+///     the former is optimised for integer types (using fewer RNG calls for
+///     element types smaller than the RNG word size), while the latter supports
+///     any element type supported by `Standard`.
+/// *   `Option<T>` first generates a `bool`, and if true generates and returns
+///     `Some(value)` where `value: T`, otherwise returning `None`.
+///
+/// ## Custom implementations
+///
+/// The [`Standard`] distribution may be implemented for user types as follows:
+///
+/// ```
+/// # #![allow(dead_code)]
+/// use rand::Rng;
+/// use rand::distributions::{Distribution, Standard};
+///
+/// struct MyF32 {
+///     x: f32,
+/// }
+///
+/// impl Distribution<MyF32> for Standard {
+///     fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> MyF32 {
+///         MyF32 { x: rng.gen() }
+///     }
+/// }
+/// ```
+///
+/// ## Example usage
+/// ```
+/// use rand::prelude::*;
+/// use rand::distributions::Standard;
+///
+/// let val: f32 = StdRng::from_entropy().sample(Standard);
+/// println!("f32 from [0, 1): {}", val);
+/// ```
+///
+/// # Floating point implementation
+/// The floating point implementations for `Standard` generate a random value in
+/// the half-open interval `[0, 1)`, i.e. including 0 but not 1.
+///
+/// All values that can be generated are of the form `n * ε/2`. For `f32`
+/// the 24 most significant random bits of a `u32` are used and for `f64` the
+/// 53 most significant bits of a `u64` are used. The conversion uses the
+/// multiplicative method: `(rng.gen::<$uty>() >> N) as $ty * (ε/2)`.
+///
+/// See also: [`Open01`] which samples from `(0, 1)`, [`OpenClosed01`] which
+/// samples from `(0, 1]` and `Rng::gen_range(0..1)` which also samples from
+/// `[0, 1)`. Note that `Open01` uses transmute-based methods which yield 1 bit
+/// less precision but may perform faster on some architectures (on modern Intel
+/// CPUs all methods have approximately equal performance).
+///
+/// [`Uniform`]: uniform::Uniform
+#[derive(Clone, Copy, Debug)]
+#[cfg_attr(feature = "serde1", derive(serde::Serialize, serde::Deserialize))]
+pub struct Standard;
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/other.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/other.rs.html new file mode 100644 index 0000000..415f1da --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/other.rs.html @@ -0,0 +1,733 @@ +other.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The implementations of the `Standard` distribution for other built-in types.
+
+use core::char;
+use core::num::Wrapping;
+#[cfg(feature = "alloc")]
+use alloc::string::String;
+
+use crate::distributions::{Distribution, Standard, Uniform};
+#[cfg(feature = "alloc")]
+use crate::distributions::DistString;
+use crate::Rng;
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+#[cfg(feature = "min_const_gen")]
+use core::mem::{self, MaybeUninit};
+
+
+// ----- Sampling distributions -----
+
+/// Sample a `u8`, uniformly distributed over ASCII letters and numbers:
+/// a-z, A-Z and 0-9.
+///
+/// # Example
+///
+/// ```
+/// use rand::{Rng, thread_rng};
+/// use rand::distributions::Alphanumeric;
+///
+/// let mut rng = thread_rng();
+/// let chars: String = (0..7).map(|_| rng.sample(Alphanumeric) as char).collect();
+/// println!("Random chars: {}", chars);
+/// ```
+///
+/// The [`DistString`] trait provides an easier method of generating
+/// a random `String`, and offers more efficient allocation:
+/// ```
+/// use rand::distributions::{Alphanumeric, DistString};
+/// let string = Alphanumeric.sample_string(&mut rand::thread_rng(), 16);
+/// println!("Random string: {}", string);
+/// ```
+///
+/// # Passwords
+///
+/// Users sometimes ask whether it is safe to use a string of random characters
+/// as a password. In principle, all RNGs in Rand implementing `CryptoRng` are
+/// suitable as a source of randomness for generating passwords (if they are
+/// properly seeded), but it is more conservative to only use randomness
+/// directly from the operating system via the `getrandom` crate, or the
+/// corresponding bindings of a crypto library.
+///
+/// When generating passwords or keys, it is important to consider the threat
+/// model and in some cases the memorability of the password. This is out of
+/// scope of the Rand project, and therefore we defer to the following
+/// references:
+///
+/// - [Wikipedia article on Password Strength](https://en.wikipedia.org/wiki/Password_strength)
+/// - [Diceware for generating memorable passwords](https://en.wikipedia.org/wiki/Diceware)
+#[derive(Debug, Clone, Copy)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct Alphanumeric;
+
+
+// ----- Implementations of distributions -----
+
+impl Distribution<char> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> char {
+        // A valid `char` is either in the interval `[0, 0xD800)` or
+        // `(0xDFFF, 0x11_0000)`. All `char`s must therefore be in
+        // `[0, 0x11_0000)` but not in the "gap" `[0xD800, 0xDFFF]` which is
+        // reserved for surrogates. This is the size of that gap.
+        const GAP_SIZE: u32 = 0xDFFF - 0xD800 + 1;
+
+        // Uniform::new(0, 0x11_0000 - GAP_SIZE) can also be used but it
+        // seemed slower.
+        let range = Uniform::new(GAP_SIZE, 0x11_0000);
+
+        let mut n = range.sample(rng);
+        if n <= 0xDFFF {
+            n -= GAP_SIZE;
+        }
+        unsafe { char::from_u32_unchecked(n) }
+    }
+}
+
+/// Note: the `String` is potentially left with excess capacity; optionally the
+/// user may call `string.shrink_to_fit()` afterwards.
+#[cfg(feature = "alloc")]
+impl DistString for Standard {
+    fn append_string<R: Rng + ?Sized>(&self, rng: &mut R, s: &mut String, len: usize) {
+        // A char is encoded with at most four bytes, thus this reservation is
+        // guaranteed to be sufficient. We do not shrink_to_fit afterwards so
+        // that repeated usage on the same `String` buffer does not reallocate.
+        s.reserve(4 * len);
+        s.extend(Distribution::<char>::sample_iter(self, rng).take(len));
+    }
+}
+
+impl Distribution<u8> for Alphanumeric {
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> u8 {
+        const RANGE: u32 = 26 + 26 + 10;
+        const GEN_ASCII_STR_CHARSET: &[u8] = b"ABCDEFGHIJKLMNOPQRSTUVWXYZ\
+                abcdefghijklmnopqrstuvwxyz\
+                0123456789";
+        // We can pick from 62 characters. This is so close to a power of 2, 64,
+        // that we can do better than `Uniform`. Use a simple bitshift and
+        // rejection sampling. We do not use a bitmask, because for small RNGs
+        // the most significant bits are usually of higher quality.
+        loop {
+            let var = rng.next_u32() >> (32 - 6);
+            if var < RANGE {
+                return GEN_ASCII_STR_CHARSET[var as usize];
+            }
+        }
+    }
+}
+
+#[cfg(feature = "alloc")]
+impl DistString for Alphanumeric {
+    fn append_string<R: Rng + ?Sized>(&self, rng: &mut R, string: &mut String, len: usize) {
+        unsafe {
+            let v = string.as_mut_vec();
+            v.extend(self.sample_iter(rng).take(len));
+        }
+    }
+}
+
+impl Distribution<bool> for Standard {
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> bool {
+        // We can compare against an arbitrary bit of an u32 to get a bool.
+        // Because the least significant bits of a lower quality RNG can have
+        // simple patterns, we compare against the most significant bit. This is
+        // easiest done using a sign test.
+        (rng.next_u32() as i32) < 0
+    }
+}
+
+macro_rules! tuple_impl {
+    // use variables to indicate the arity of the tuple
+    ($($tyvar:ident),* ) => {
+        // the trailing commas are for the 1 tuple
+        impl< $( $tyvar ),* >
+            Distribution<( $( $tyvar ),* , )>
+            for Standard
+            where $( Standard: Distribution<$tyvar> ),*
+        {
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, _rng: &mut R) -> ( $( $tyvar ),* , ) {
+                (
+                    // use the $tyvar's to get the appropriate number of
+                    // repeats (they're not actually needed)
+                    $(
+                        _rng.gen::<$tyvar>()
+                    ),*
+                    ,
+                )
+            }
+        }
+    }
+}
+
+impl Distribution<()> for Standard {
+    #[allow(clippy::unused_unit)]
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, _: &mut R) -> () {
+        ()
+    }
+}
+tuple_impl! {A}
+tuple_impl! {A, B}
+tuple_impl! {A, B, C}
+tuple_impl! {A, B, C, D}
+tuple_impl! {A, B, C, D, E}
+tuple_impl! {A, B, C, D, E, F}
+tuple_impl! {A, B, C, D, E, F, G}
+tuple_impl! {A, B, C, D, E, F, G, H}
+tuple_impl! {A, B, C, D, E, F, G, H, I}
+tuple_impl! {A, B, C, D, E, F, G, H, I, J}
+tuple_impl! {A, B, C, D, E, F, G, H, I, J, K}
+tuple_impl! {A, B, C, D, E, F, G, H, I, J, K, L}
+
+#[cfg(feature = "min_const_gen")]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "min_const_gen")))]
+impl<T, const N: usize> Distribution<[T; N]> for Standard
+where Standard: Distribution<T>
+{
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, _rng: &mut R) -> [T; N] {
+        let mut buff: [MaybeUninit<T>; N] = unsafe { MaybeUninit::uninit().assume_init() };
+
+        for elem in &mut buff {
+            *elem = MaybeUninit::new(_rng.gen());
+        }
+
+        unsafe { mem::transmute_copy::<_, _>(&buff) }
+    }
+}
+
+#[cfg(not(feature = "min_const_gen"))]
+macro_rules! array_impl {
+    // recursive, given at least one type parameter:
+    {$n:expr, $t:ident, $($ts:ident,)*} => {
+        array_impl!{($n - 1), $($ts,)*}
+
+        impl<T> Distribution<[T; $n]> for Standard where Standard: Distribution<T> {
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, _rng: &mut R) -> [T; $n] {
+                [_rng.gen::<$t>(), $(_rng.gen::<$ts>()),*]
+            }
+        }
+    };
+    // empty case:
+    {$n:expr,} => {
+        impl<T> Distribution<[T; $n]> for Standard {
+            fn sample<R: Rng + ?Sized>(&self, _rng: &mut R) -> [T; $n] { [] }
+        }
+    };
+}
+
+#[cfg(not(feature = "min_const_gen"))]
+array_impl! {32, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T, T,}
+
+impl<T> Distribution<Option<T>> for Standard
+where Standard: Distribution<T>
+{
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Option<T> {
+        // UFCS is needed here: https://github.com/rust-lang/rust/issues/24066
+        if rng.gen::<bool>() {
+            Some(rng.gen())
+        } else {
+            None
+        }
+    }
+}
+
+impl<T> Distribution<Wrapping<T>> for Standard
+where Standard: Distribution<T>
+{
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Wrapping<T> {
+        Wrapping(rng.gen())
+    }
+}
+
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+    use crate::RngCore;
+    #[cfg(feature = "alloc")] use alloc::string::String;
+
+    #[test]
+    fn test_misc() {
+        let rng: &mut dyn RngCore = &mut crate::test::rng(820);
+
+        rng.sample::<char, _>(Standard);
+        rng.sample::<bool, _>(Standard);
+    }
+
+    #[cfg(feature = "alloc")]
+    #[test]
+    fn test_chars() {
+        use core::iter;
+        let mut rng = crate::test::rng(805);
+
+        // Test by generating a relatively large number of chars, so we also
+        // take the rejection sampling path.
+        let word: String = iter::repeat(())
+            .map(|()| rng.gen::<char>())
+            .take(1000)
+            .collect();
+        assert!(!word.is_empty());
+    }
+
+    #[test]
+    fn test_alphanumeric() {
+        let mut rng = crate::test::rng(806);
+
+        // Test by generating a relatively large number of chars, so we also
+        // take the rejection sampling path.
+        let mut incorrect = false;
+        for _ in 0..100 {
+            let c: char = rng.sample(Alphanumeric).into();
+            incorrect |= !(('0'..='9').contains(&c) ||
+                           ('A'..='Z').contains(&c) ||
+                           ('a'..='z').contains(&c) );
+        }
+        assert!(!incorrect);
+    }
+
+    #[test]
+    fn value_stability() {
+        fn test_samples<T: Copy + core::fmt::Debug + PartialEq, D: Distribution<T>>(
+            distr: &D, zero: T, expected: &[T],
+        ) {
+            let mut rng = crate::test::rng(807);
+            let mut buf = [zero; 5];
+            for x in &mut buf {
+                *x = rng.sample(&distr);
+            }
+            assert_eq!(&buf, expected);
+        }
+
+        test_samples(&Standard, 'a', &[
+            '\u{8cdac}',
+            '\u{a346a}',
+            '\u{80120}',
+            '\u{ed692}',
+            '\u{35888}',
+        ]);
+        test_samples(&Alphanumeric, 0, &[104, 109, 101, 51, 77]);
+        test_samples(&Standard, false, &[true, true, false, true, false]);
+        test_samples(&Standard, None as Option<bool>, &[
+            Some(true),
+            None,
+            Some(false),
+            None,
+            Some(false),
+        ]);
+        test_samples(&Standard, Wrapping(0i32), &[
+            Wrapping(-2074640887),
+            Wrapping(-1719949321),
+            Wrapping(2018088303),
+            Wrapping(-547181756),
+            Wrapping(838957336),
+        ]);
+
+        // We test only sub-sets of tuple and array impls
+        test_samples(&Standard, (), &[(), (), (), (), ()]);
+        test_samples(&Standard, (false,), &[
+            (true,),
+            (true,),
+            (false,),
+            (true,),
+            (false,),
+        ]);
+        test_samples(&Standard, (false, false), &[
+            (true, true),
+            (false, true),
+            (false, false),
+            (true, false),
+            (false, false),
+        ]);
+
+        test_samples(&Standard, [0u8; 0], &[[], [], [], [], []]);
+        test_samples(&Standard, [0u8; 3], &[
+            [9, 247, 111],
+            [68, 24, 13],
+            [174, 19, 194],
+            [172, 69, 213],
+            [149, 207, 29],
+        ]);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/slice.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/slice.rs.html new file mode 100644 index 0000000..2f43484 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/slice.rs.html @@ -0,0 +1,237 @@ +slice.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+
// Copyright 2021 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+use crate::distributions::{Distribution, Uniform};
+
+/// A distribution to sample items uniformly from a slice.
+///
+/// [`Slice::new`] constructs a distribution referencing a slice and uniformly
+/// samples references from the items in the slice. It may do extra work up
+/// front to make sampling of multiple values faster; if only one sample from
+/// the slice is required, [`SliceRandom::choose`] can be more efficient.
+///
+/// Steps are taken to avoid bias which might be present in naive
+/// implementations; for example `slice[rng.gen() % slice.len()]` samples from
+/// the slice, but may be more likely to select numbers in the low range than
+/// other values.
+///
+/// This distribution samples with replacement; each sample is independent.
+/// Sampling without replacement requires state to be retained, and therefore
+/// cannot be handled by a distribution; you should instead consider methods
+/// on [`SliceRandom`], such as [`SliceRandom::choose_multiple`].
+///
+/// # Example
+///
+/// ```
+/// use rand::Rng;
+/// use rand::distributions::Slice;
+///
+/// let vowels = ['a', 'e', 'i', 'o', 'u'];
+/// let vowels_dist = Slice::new(&vowels).unwrap();
+/// let rng = rand::thread_rng();
+///
+/// // build a string of 10 vowels
+/// let vowel_string: String = rng
+///     .sample_iter(&vowels_dist)
+///     .take(10)
+///     .collect();
+///
+/// println!("{}", vowel_string);
+/// assert_eq!(vowel_string.len(), 10);
+/// assert!(vowel_string.chars().all(|c| vowels.contains(&c)));
+/// ```
+///
+/// For a single sample, [`SliceRandom::choose`][crate::seq::SliceRandom::choose]
+/// may be preferred:
+///
+/// ```
+/// use rand::seq::SliceRandom;
+///
+/// let vowels = ['a', 'e', 'i', 'o', 'u'];
+/// let mut rng = rand::thread_rng();
+///
+/// println!("{}", vowels.choose(&mut rng).unwrap())
+/// ```
+///
+/// [`SliceRandom`]: crate::seq::SliceRandom
+/// [`SliceRandom::choose`]: crate::seq::SliceRandom::choose
+/// [`SliceRandom::choose_multiple`]: crate::seq::SliceRandom::choose_multiple
+#[derive(Debug, Clone, Copy)]
+pub struct Slice<'a, T> {
+    slice: &'a [T],
+    range: Uniform<usize>,
+}
+
+impl<'a, T> Slice<'a, T> {
+    /// Create a new `Slice` instance which samples uniformly from the slice.
+    /// Returns `Err` if the slice is empty.
+    pub fn new(slice: &'a [T]) -> Result<Self, EmptySlice> {
+        match slice.len() {
+            0 => Err(EmptySlice),
+            len => Ok(Self {
+                slice,
+                range: Uniform::new(0, len),
+            }),
+        }
+    }
+}
+
+impl<'a, T> Distribution<&'a T> for Slice<'a, T> {
+    fn sample<R: crate::Rng + ?Sized>(&self, rng: &mut R) -> &'a T {
+        let idx = self.range.sample(rng);
+
+        debug_assert!(
+            idx < self.slice.len(),
+            "Uniform::new(0, {}) somehow returned {}",
+            self.slice.len(),
+            idx
+        );
+
+        // Safety: at construction time, it was ensured that the slice was
+        // non-empty, and that the `Uniform` range produces values in range
+        // for the slice
+        unsafe { self.slice.get_unchecked(idx) }
+    }
+}
+
+/// Error type indicating that a [`Slice`] distribution was improperly
+/// constructed with an empty slice.
+#[derive(Debug, Clone, Copy)]
+pub struct EmptySlice;
+
+impl core::fmt::Display for EmptySlice {
+    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
+        write!(
+            f,
+            "Tried to create a `distributions::Slice` with an empty slice"
+        )
+    }
+}
+
+#[cfg(feature = "std")]
+impl std::error::Error for EmptySlice {}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/uniform.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/uniform.rs.html new file mode 100644 index 0000000..72d0ba1 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/uniform.rs.html @@ -0,0 +1,3319 @@ +uniform.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+1357
+1358
+1359
+1360
+1361
+1362
+1363
+1364
+1365
+1366
+1367
+1368
+1369
+1370
+1371
+1372
+1373
+1374
+1375
+1376
+1377
+1378
+1379
+1380
+1381
+1382
+1383
+1384
+1385
+1386
+1387
+1388
+1389
+1390
+1391
+1392
+1393
+1394
+1395
+1396
+1397
+1398
+1399
+1400
+1401
+1402
+1403
+1404
+1405
+1406
+1407
+1408
+1409
+1410
+1411
+1412
+1413
+1414
+1415
+1416
+1417
+1418
+1419
+1420
+1421
+1422
+1423
+1424
+1425
+1426
+1427
+1428
+1429
+1430
+1431
+1432
+1433
+1434
+1435
+1436
+1437
+1438
+1439
+1440
+1441
+1442
+1443
+1444
+1445
+1446
+1447
+1448
+1449
+1450
+1451
+1452
+1453
+1454
+1455
+1456
+1457
+1458
+1459
+1460
+1461
+1462
+1463
+1464
+1465
+1466
+1467
+1468
+1469
+1470
+1471
+1472
+1473
+1474
+1475
+1476
+1477
+1478
+1479
+1480
+1481
+1482
+1483
+1484
+1485
+1486
+1487
+1488
+1489
+1490
+1491
+1492
+1493
+1494
+1495
+1496
+1497
+1498
+1499
+1500
+1501
+1502
+1503
+1504
+1505
+1506
+1507
+1508
+1509
+1510
+1511
+1512
+1513
+1514
+1515
+1516
+1517
+1518
+1519
+1520
+1521
+1522
+1523
+1524
+1525
+1526
+1527
+1528
+1529
+1530
+1531
+1532
+1533
+1534
+1535
+1536
+1537
+1538
+1539
+1540
+1541
+1542
+1543
+1544
+1545
+1546
+1547
+1548
+1549
+1550
+1551
+1552
+1553
+1554
+1555
+1556
+1557
+1558
+1559
+1560
+1561
+1562
+1563
+1564
+1565
+1566
+1567
+1568
+1569
+1570
+1571
+1572
+1573
+1574
+1575
+1576
+1577
+1578
+1579
+1580
+1581
+1582
+1583
+1584
+1585
+1586
+1587
+1588
+1589
+1590
+1591
+1592
+1593
+1594
+1595
+1596
+1597
+1598
+1599
+1600
+1601
+1602
+1603
+1604
+1605
+1606
+1607
+1608
+1609
+1610
+1611
+1612
+1613
+1614
+1615
+1616
+1617
+1618
+1619
+1620
+1621
+1622
+1623
+1624
+1625
+1626
+1627
+1628
+1629
+1630
+1631
+1632
+1633
+1634
+1635
+1636
+1637
+1638
+1639
+1640
+1641
+1642
+1643
+1644
+1645
+1646
+1647
+1648
+1649
+1650
+1651
+1652
+1653
+1654
+1655
+1656
+1657
+1658
+
// Copyright 2018-2020 Developers of the Rand project.
+// Copyright 2017 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! A distribution uniformly sampling numbers within a given range.
+//!
+//! [`Uniform`] is the standard distribution to sample uniformly from a range;
+//! e.g. `Uniform::new_inclusive(1, 6)` can sample integers from 1 to 6, like a
+//! standard die. [`Rng::gen_range`] supports any type supported by
+//! [`Uniform`].
+//!
+//! This distribution is provided with support for several primitive types
+//! (all integer and floating-point types) as well as [`std::time::Duration`],
+//! and supports extension to user-defined types via a type-specific *back-end*
+//! implementation.
+//!
+//! The types [`UniformInt`], [`UniformFloat`] and [`UniformDuration`] are the
+//! back-ends supporting sampling from primitive integer and floating-point
+//! ranges as well as from [`std::time::Duration`]; these types do not normally
+//! need to be used directly (unless implementing a derived back-end).
+//!
+//! # Example usage
+//!
+//! ```
+//! use rand::{Rng, thread_rng};
+//! use rand::distributions::Uniform;
+//!
+//! let mut rng = thread_rng();
+//! let side = Uniform::new(-10.0, 10.0);
+//!
+//! // sample between 1 and 10 points
+//! for _ in 0..rng.gen_range(1..=10) {
+//!     // sample a point from the square with sides -10 - 10 in two dimensions
+//!     let (x, y) = (rng.sample(side), rng.sample(side));
+//!     println!("Point: {}, {}", x, y);
+//! }
+//! ```
+//!
+//! # Extending `Uniform` to support a custom type
+//!
+//! To extend [`Uniform`] to support your own types, write a back-end which
+//! implements the [`UniformSampler`] trait, then implement the [`SampleUniform`]
+//! helper trait to "register" your back-end. See the `MyF32` example below.
+//!
+//! At a minimum, the back-end needs to store any parameters needed for sampling
+//! (e.g. the target range) and implement `new`, `new_inclusive` and `sample`.
+//! Those methods should include an assert to check the range is valid (i.e.
+//! `low < high`). The example below merely wraps another back-end.
+//!
+//! The `new`, `new_inclusive` and `sample_single` functions use arguments of
+//! type SampleBorrow<X> in order to support passing in values by reference or
+//! by value. In the implementation of these functions, you can choose to
+//! simply use the reference returned by [`SampleBorrow::borrow`], or you can choose
+//! to copy or clone the value, whatever is appropriate for your type.
+//!
+//! ```
+//! use rand::prelude::*;
+//! use rand::distributions::uniform::{Uniform, SampleUniform,
+//!         UniformSampler, UniformFloat, SampleBorrow};
+//!
+//! struct MyF32(f32);
+//!
+//! #[derive(Clone, Copy, Debug)]
+//! struct UniformMyF32(UniformFloat<f32>);
+//!
+//! impl UniformSampler for UniformMyF32 {
+//!     type X = MyF32;
+//!     fn new<B1, B2>(low: B1, high: B2) -> Self
+//!         where B1: SampleBorrow<Self::X> + Sized,
+//!               B2: SampleBorrow<Self::X> + Sized
+//!     {
+//!         UniformMyF32(UniformFloat::<f32>::new(low.borrow().0, high.borrow().0))
+//!     }
+//!     fn new_inclusive<B1, B2>(low: B1, high: B2) -> Self
+//!         where B1: SampleBorrow<Self::X> + Sized,
+//!               B2: SampleBorrow<Self::X> + Sized
+//!     {
+//!         UniformMyF32(UniformFloat::<f32>::new_inclusive(
+//!             low.borrow().0,
+//!             high.borrow().0,
+//!         ))
+//!     }
+//!     fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+//!         MyF32(self.0.sample(rng))
+//!     }
+//! }
+//!
+//! impl SampleUniform for MyF32 {
+//!     type Sampler = UniformMyF32;
+//! }
+//!
+//! let (low, high) = (MyF32(17.0f32), MyF32(22.0f32));
+//! let uniform = Uniform::new(low, high);
+//! let x = uniform.sample(&mut thread_rng());
+//! ```
+//!
+//! [`SampleUniform`]: crate::distributions::uniform::SampleUniform
+//! [`UniformSampler`]: crate::distributions::uniform::UniformSampler
+//! [`UniformInt`]: crate::distributions::uniform::UniformInt
+//! [`UniformFloat`]: crate::distributions::uniform::UniformFloat
+//! [`UniformDuration`]: crate::distributions::uniform::UniformDuration
+//! [`SampleBorrow::borrow`]: crate::distributions::uniform::SampleBorrow::borrow
+
+use core::time::Duration;
+use core::ops::{Range, RangeInclusive};
+
+use crate::distributions::float::IntoFloat;
+use crate::distributions::utils::{BoolAsSIMD, FloatAsSIMD, FloatSIMDUtils, WideningMultiply};
+use crate::distributions::Distribution;
+use crate::{Rng, RngCore};
+
+#[cfg(not(feature = "std"))]
+#[allow(unused_imports)] // rustc doesn't detect that this is actually used
+use crate::distributions::utils::Float;
+
+#[cfg(feature = "simd_support")] use packed_simd::*;
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+
+/// Sample values uniformly between two bounds.
+///
+/// [`Uniform::new`] and [`Uniform::new_inclusive`] construct a uniform
+/// distribution sampling from the given range; these functions may do extra
+/// work up front to make sampling of multiple values faster. If only one sample
+/// from the range is required, [`Rng::gen_range`] can be more efficient.
+///
+/// When sampling from a constant range, many calculations can happen at
+/// compile-time and all methods should be fast; for floating-point ranges and
+/// the full range of integer types this should have comparable performance to
+/// the `Standard` distribution.
+///
+/// Steps are taken to avoid bias which might be present in naive
+/// implementations; for example `rng.gen::<u8>() % 170` samples from the range
+/// `[0, 169]` but is twice as likely to select numbers less than 85 than other
+/// values. Further, the implementations here give more weight to the high-bits
+/// generated by the RNG than the low bits, since with some RNGs the low-bits
+/// are of lower quality than the high bits.
+///
+/// Implementations must sample in `[low, high)` range for
+/// `Uniform::new(low, high)`, i.e., excluding `high`. In particular, care must
+/// be taken to ensure that rounding never results values `< low` or `>= high`.
+///
+/// # Example
+///
+/// ```
+/// use rand::distributions::{Distribution, Uniform};
+///
+/// let between = Uniform::from(10..10000);
+/// let mut rng = rand::thread_rng();
+/// let mut sum = 0;
+/// for _ in 0..1000 {
+///     sum += between.sample(&mut rng);
+/// }
+/// println!("{}", sum);
+/// ```
+///
+/// For a single sample, [`Rng::gen_range`] may be preferred:
+///
+/// ```
+/// use rand::Rng;
+///
+/// let mut rng = rand::thread_rng();
+/// println!("{}", rng.gen_range(0..10));
+/// ```
+///
+/// [`new`]: Uniform::new
+/// [`new_inclusive`]: Uniform::new_inclusive
+/// [`Rng::gen_range`]: Rng::gen_range
+#[derive(Clone, Copy, Debug, PartialEq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+#[cfg_attr(feature = "serde1", serde(bound(serialize = "X::Sampler: Serialize")))]
+#[cfg_attr(feature = "serde1", serde(bound(deserialize = "X::Sampler: Deserialize<'de>")))]
+pub struct Uniform<X: SampleUniform>(X::Sampler);
+
+impl<X: SampleUniform> Uniform<X> {
+    /// Create a new `Uniform` instance which samples uniformly from the half
+    /// open range `[low, high)` (excluding `high`). Panics if `low >= high`.
+    pub fn new<B1, B2>(low: B1, high: B2) -> Uniform<X>
+    where
+        B1: SampleBorrow<X> + Sized,
+        B2: SampleBorrow<X> + Sized,
+    {
+        Uniform(X::Sampler::new(low, high))
+    }
+
+    /// Create a new `Uniform` instance which samples uniformly from the closed
+    /// range `[low, high]` (inclusive). Panics if `low > high`.
+    pub fn new_inclusive<B1, B2>(low: B1, high: B2) -> Uniform<X>
+    where
+        B1: SampleBorrow<X> + Sized,
+        B2: SampleBorrow<X> + Sized,
+    {
+        Uniform(X::Sampler::new_inclusive(low, high))
+    }
+}
+
+impl<X: SampleUniform> Distribution<X> for Uniform<X> {
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> X {
+        self.0.sample(rng)
+    }
+}
+
+/// Helper trait for creating objects using the correct implementation of
+/// [`UniformSampler`] for the sampling type.
+///
+/// See the [module documentation] on how to implement [`Uniform`] range
+/// sampling for a custom type.
+///
+/// [module documentation]: crate::distributions::uniform
+pub trait SampleUniform: Sized {
+    /// The `UniformSampler` implementation supporting type `X`.
+    type Sampler: UniformSampler<X = Self>;
+}
+
+/// Helper trait handling actual uniform sampling.
+///
+/// See the [module documentation] on how to implement [`Uniform`] range
+/// sampling for a custom type.
+///
+/// Implementation of [`sample_single`] is optional, and is only useful when
+/// the implementation can be faster than `Self::new(low, high).sample(rng)`.
+///
+/// [module documentation]: crate::distributions::uniform
+/// [`sample_single`]: UniformSampler::sample_single
+pub trait UniformSampler: Sized {
+    /// The type sampled by this implementation.
+    type X;
+
+    /// Construct self, with inclusive lower bound and exclusive upper bound
+    /// `[low, high)`.
+    ///
+    /// Usually users should not call this directly but instead use
+    /// `Uniform::new`, which asserts that `low < high` before calling this.
+    fn new<B1, B2>(low: B1, high: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized;
+
+    /// Construct self, with inclusive bounds `[low, high]`.
+    ///
+    /// Usually users should not call this directly but instead use
+    /// `Uniform::new_inclusive`, which asserts that `low <= high` before
+    /// calling this.
+    fn new_inclusive<B1, B2>(low: B1, high: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized;
+
+    /// Sample a value.
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X;
+
+    /// Sample a single value uniformly from a range with inclusive lower bound
+    /// and exclusive upper bound `[low, high)`.
+    ///
+    /// By default this is implemented using
+    /// `UniformSampler::new(low, high).sample(rng)`. However, for some types
+    /// more optimal implementations for single usage may be provided via this
+    /// method (which is the case for integers and floats).
+    /// Results may not be identical.
+    ///
+    /// Note that to use this method in a generic context, the type needs to be
+    /// retrieved via `SampleUniform::Sampler` as follows:
+    /// ```
+    /// use rand::{thread_rng, distributions::uniform::{SampleUniform, UniformSampler}};
+    /// # #[allow(unused)]
+    /// fn sample_from_range<T: SampleUniform>(lb: T, ub: T) -> T {
+    ///     let mut rng = thread_rng();
+    ///     <T as SampleUniform>::Sampler::sample_single(lb, ub, &mut rng)
+    /// }
+    /// ```
+    fn sample_single<R: Rng + ?Sized, B1, B2>(low: B1, high: B2, rng: &mut R) -> Self::X
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized,
+    {
+        let uniform: Self = UniformSampler::new(low, high);
+        uniform.sample(rng)
+    }
+
+    /// Sample a single value uniformly from a range with inclusive lower bound
+    /// and inclusive upper bound `[low, high]`.
+    ///
+    /// By default this is implemented using
+    /// `UniformSampler::new_inclusive(low, high).sample(rng)`. However, for
+    /// some types more optimal implementations for single usage may be provided
+    /// via this method.
+    /// Results may not be identical.
+    fn sample_single_inclusive<R: Rng + ?Sized, B1, B2>(low: B1, high: B2, rng: &mut R)
+        -> Self::X
+        where B1: SampleBorrow<Self::X> + Sized,
+              B2: SampleBorrow<Self::X> + Sized
+    {
+        let uniform: Self = UniformSampler::new_inclusive(low, high);
+        uniform.sample(rng)
+    }
+}
+
+impl<X: SampleUniform> From<Range<X>> for Uniform<X> {
+    fn from(r: ::core::ops::Range<X>) -> Uniform<X> {
+        Uniform::new(r.start, r.end)
+    }
+}
+
+impl<X: SampleUniform> From<RangeInclusive<X>> for Uniform<X> {
+    fn from(r: ::core::ops::RangeInclusive<X>) -> Uniform<X> {
+        Uniform::new_inclusive(r.start(), r.end())
+    }
+}
+
+
+/// Helper trait similar to [`Borrow`] but implemented
+/// only for SampleUniform and references to SampleUniform in
+/// order to resolve ambiguity issues.
+///
+/// [`Borrow`]: std::borrow::Borrow
+pub trait SampleBorrow<Borrowed> {
+    /// Immutably borrows from an owned value. See [`Borrow::borrow`]
+    ///
+    /// [`Borrow::borrow`]: std::borrow::Borrow::borrow
+    fn borrow(&self) -> &Borrowed;
+}
+impl<Borrowed> SampleBorrow<Borrowed> for Borrowed
+where Borrowed: SampleUniform
+{
+    #[inline(always)]
+    fn borrow(&self) -> &Borrowed {
+        self
+    }
+}
+impl<'a, Borrowed> SampleBorrow<Borrowed> for &'a Borrowed
+where Borrowed: SampleUniform
+{
+    #[inline(always)]
+    fn borrow(&self) -> &Borrowed {
+        *self
+    }
+}
+
+/// Range that supports generating a single sample efficiently.
+///
+/// Any type implementing this trait can be used to specify the sampled range
+/// for `Rng::gen_range`.
+pub trait SampleRange<T> {
+    /// Generate a sample from the given range.
+    fn sample_single<R: RngCore + ?Sized>(self, rng: &mut R) -> T;
+
+    /// Check whether the range is empty.
+    fn is_empty(&self) -> bool;
+}
+
+impl<T: SampleUniform + PartialOrd> SampleRange<T> for Range<T> {
+    #[inline]
+    fn sample_single<R: RngCore + ?Sized>(self, rng: &mut R) -> T {
+        T::Sampler::sample_single(self.start, self.end, rng)
+    }
+
+    #[inline]
+    fn is_empty(&self) -> bool {
+        !(self.start < self.end)
+    }
+}
+
+impl<T: SampleUniform + PartialOrd> SampleRange<T> for RangeInclusive<T> {
+    #[inline]
+    fn sample_single<R: RngCore + ?Sized>(self, rng: &mut R) -> T {
+        T::Sampler::sample_single_inclusive(self.start(), self.end(), rng)
+    }
+
+    #[inline]
+    fn is_empty(&self) -> bool {
+        !(self.start() <= self.end())
+    }
+}
+
+
+////////////////////////////////////////////////////////////////////////////////
+
+// What follows are all back-ends.
+
+
+/// The back-end implementing [`UniformSampler`] for integer types.
+///
+/// Unless you are implementing [`UniformSampler`] for your own type, this type
+/// should not be used directly, use [`Uniform`] instead.
+///
+/// # Implementation notes
+///
+/// For simplicity, we use the same generic struct `UniformInt<X>` for all
+/// integer types `X`. This gives us only one field type, `X`; to store unsigned
+/// values of this size, we take use the fact that these conversions are no-ops.
+///
+/// For a closed range, the number of possible numbers we should generate is
+/// `range = (high - low + 1)`. To avoid bias, we must ensure that the size of
+/// our sample space, `zone`, is a multiple of `range`; other values must be
+/// rejected (by replacing with a new random sample).
+///
+/// As a special case, we use `range = 0` to represent the full range of the
+/// result type (i.e. for `new_inclusive($ty::MIN, $ty::MAX)`).
+///
+/// The optimum `zone` is the largest product of `range` which fits in our
+/// (unsigned) target type. We calculate this by calculating how many numbers we
+/// must reject: `reject = (MAX + 1) % range = (MAX - range + 1) % range`. Any (large)
+/// product of `range` will suffice, thus in `sample_single` we multiply by a
+/// power of 2 via bit-shifting (faster but may cause more rejections).
+///
+/// The smallest integer PRNGs generate is `u32`. For 8- and 16-bit outputs we
+/// use `u32` for our `zone` and samples (because it's not slower and because
+/// it reduces the chance of having to reject a sample). In this case we cannot
+/// store `zone` in the target type since it is too large, however we know
+/// `ints_to_reject < range <= $unsigned::MAX`.
+///
+/// An alternative to using a modulus is widening multiply: After a widening
+/// multiply by `range`, the result is in the high word. Then comparing the low
+/// word against `zone` makes sure our distribution is uniform.
+#[derive(Clone, Copy, Debug, PartialEq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct UniformInt<X> {
+    low: X,
+    range: X,
+    z: X, // either ints_to_reject or zone depending on implementation
+}
+
+macro_rules! uniform_int_impl {
+    ($ty:ty, $unsigned:ident, $u_large:ident) => {
+        impl SampleUniform for $ty {
+            type Sampler = UniformInt<$ty>;
+        }
+
+        impl UniformSampler for UniformInt<$ty> {
+            // We play free and fast with unsigned vs signed here
+            // (when $ty is signed), but that's fine, since the
+            // contract of this macro is for $ty and $unsigned to be
+            // "bit-equal", so casting between them is a no-op.
+
+            type X = $ty;
+
+            #[inline] // if the range is constant, this helps LLVM to do the
+                      // calculations at compile-time.
+            fn new<B1, B2>(low_b: B1, high_b: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(low < high, "Uniform::new called with `low >= high`");
+                UniformSampler::new_inclusive(low, high - 1)
+            }
+
+            #[inline] // if the range is constant, this helps LLVM to do the
+                      // calculations at compile-time.
+            fn new_inclusive<B1, B2>(low_b: B1, high_b: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(
+                    low <= high,
+                    "Uniform::new_inclusive called with `low > high`"
+                );
+                let unsigned_max = ::core::$u_large::MAX;
+
+                let range = high.wrapping_sub(low).wrapping_add(1) as $unsigned;
+                let ints_to_reject = if range > 0 {
+                    let range = $u_large::from(range);
+                    (unsigned_max - range + 1) % range
+                } else {
+                    0
+                };
+
+                UniformInt {
+                    low,
+                    // These are really $unsigned values, but store as $ty:
+                    range: range as $ty,
+                    z: ints_to_reject as $unsigned as $ty,
+                }
+            }
+
+            #[inline]
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+                let range = self.range as $unsigned as $u_large;
+                if range > 0 {
+                    let unsigned_max = ::core::$u_large::MAX;
+                    let zone = unsigned_max - (self.z as $unsigned as $u_large);
+                    loop {
+                        let v: $u_large = rng.gen();
+                        let (hi, lo) = v.wmul(range);
+                        if lo <= zone {
+                            return self.low.wrapping_add(hi as $ty);
+                        }
+                    }
+                } else {
+                    // Sample from the entire integer range.
+                    rng.gen()
+                }
+            }
+
+            #[inline]
+            fn sample_single<R: Rng + ?Sized, B1, B2>(low_b: B1, high_b: B2, rng: &mut R) -> Self::X
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(low < high, "UniformSampler::sample_single: low >= high");
+                Self::sample_single_inclusive(low, high - 1, rng)
+            }
+
+            #[inline]
+            fn sample_single_inclusive<R: Rng + ?Sized, B1, B2>(low_b: B1, high_b: B2, rng: &mut R) -> Self::X
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(low <= high, "UniformSampler::sample_single_inclusive: low > high");
+                let range = high.wrapping_sub(low).wrapping_add(1) as $unsigned as $u_large;
+                // If the above resulted in wrap-around to 0, the range is $ty::MIN..=$ty::MAX,
+                // and any integer will do.
+                if range == 0 {
+                    return rng.gen();
+                }
+
+                let zone = if ::core::$unsigned::MAX <= ::core::u16::MAX as $unsigned {
+                    // Using a modulus is faster than the approximation for
+                    // i8 and i16. I suppose we trade the cost of one
+                    // modulus for near-perfect branch prediction.
+                    let unsigned_max: $u_large = ::core::$u_large::MAX;
+                    let ints_to_reject = (unsigned_max - range + 1) % range;
+                    unsigned_max - ints_to_reject
+                } else {
+                    // conservative but fast approximation. `- 1` is necessary to allow the
+                    // same comparison without bias.
+                    (range << range.leading_zeros()).wrapping_sub(1)
+                };
+
+                loop {
+                    let v: $u_large = rng.gen();
+                    let (hi, lo) = v.wmul(range);
+                    if lo <= zone {
+                        return low.wrapping_add(hi as $ty);
+                    }
+                }
+            }
+        }
+    };
+}
+
+uniform_int_impl! { i8, u8, u32 }
+uniform_int_impl! { i16, u16, u32 }
+uniform_int_impl! { i32, u32, u32 }
+uniform_int_impl! { i64, u64, u64 }
+uniform_int_impl! { i128, u128, u128 }
+uniform_int_impl! { isize, usize, usize }
+uniform_int_impl! { u8, u8, u32 }
+uniform_int_impl! { u16, u16, u32 }
+uniform_int_impl! { u32, u32, u32 }
+uniform_int_impl! { u64, u64, u64 }
+uniform_int_impl! { usize, usize, usize }
+uniform_int_impl! { u128, u128, u128 }
+
+#[cfg(feature = "simd_support")]
+macro_rules! uniform_simd_int_impl {
+    ($ty:ident, $unsigned:ident, $u_scalar:ident) => {
+        // The "pick the largest zone that can fit in an `u32`" optimization
+        // is less useful here. Multiple lanes complicate things, we don't
+        // know the PRNG's minimal output size, and casting to a larger vector
+        // is generally a bad idea for SIMD performance. The user can still
+        // implement it manually.
+
+        // TODO: look into `Uniform::<u32x4>::new(0u32, 100)` functionality
+        //       perhaps `impl SampleUniform for $u_scalar`?
+        impl SampleUniform for $ty {
+            type Sampler = UniformInt<$ty>;
+        }
+
+        impl UniformSampler for UniformInt<$ty> {
+            type X = $ty;
+
+            #[inline] // if the range is constant, this helps LLVM to do the
+                      // calculations at compile-time.
+            fn new<B1, B2>(low_b: B1, high_b: B2) -> Self
+                where B1: SampleBorrow<Self::X> + Sized,
+                      B2: SampleBorrow<Self::X> + Sized
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(low.lt(high).all(), "Uniform::new called with `low >= high`");
+                UniformSampler::new_inclusive(low, high - 1)
+            }
+
+            #[inline] // if the range is constant, this helps LLVM to do the
+                      // calculations at compile-time.
+            fn new_inclusive<B1, B2>(low_b: B1, high_b: B2) -> Self
+                where B1: SampleBorrow<Self::X> + Sized,
+                      B2: SampleBorrow<Self::X> + Sized
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                assert!(low.le(high).all(),
+                        "Uniform::new_inclusive called with `low > high`");
+                let unsigned_max = ::core::$u_scalar::MAX;
+
+                // NOTE: these may need to be replaced with explicitly
+                // wrapping operations if `packed_simd` changes
+                let range: $unsigned = ((high - low) + 1).cast();
+                // `% 0` will panic at runtime.
+                let not_full_range = range.gt($unsigned::splat(0));
+                // replacing 0 with `unsigned_max` allows a faster `select`
+                // with bitwise OR
+                let modulo = not_full_range.select(range, $unsigned::splat(unsigned_max));
+                // wrapping addition
+                let ints_to_reject = (unsigned_max - range + 1) % modulo;
+                // When `range` is 0, `lo` of `v.wmul(range)` will always be
+                // zero which means only one sample is needed.
+                let zone = unsigned_max - ints_to_reject;
+
+                UniformInt {
+                    low,
+                    // These are really $unsigned values, but store as $ty:
+                    range: range.cast(),
+                    z: zone.cast(),
+                }
+            }
+
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+                let range: $unsigned = self.range.cast();
+                let zone: $unsigned = self.z.cast();
+
+                // This might seem very slow, generating a whole new
+                // SIMD vector for every sample rejection. For most uses
+                // though, the chance of rejection is small and provides good
+                // general performance. With multiple lanes, that chance is
+                // multiplied. To mitigate this, we replace only the lanes of
+                // the vector which fail, iteratively reducing the chance of
+                // rejection. The replacement method does however add a little
+                // overhead. Benchmarking or calculating probabilities might
+                // reveal contexts where this replacement method is slower.
+                let mut v: $unsigned = rng.gen();
+                loop {
+                    let (hi, lo) = v.wmul(range);
+                    let mask = lo.le(zone);
+                    if mask.all() {
+                        let hi: $ty = hi.cast();
+                        // wrapping addition
+                        let result = self.low + hi;
+                        // `select` here compiles to a blend operation
+                        // When `range.eq(0).none()` the compare and blend
+                        // operations are avoided.
+                        let v: $ty = v.cast();
+                        return range.gt($unsigned::splat(0)).select(result, v);
+                    }
+                    // Replace only the failing lanes
+                    v = mask.select(v, rng.gen());
+                }
+            }
+        }
+    };
+
+    // bulk implementation
+    ($(($unsigned:ident, $signed:ident),)+ $u_scalar:ident) => {
+        $(
+            uniform_simd_int_impl!($unsigned, $unsigned, $u_scalar);
+            uniform_simd_int_impl!($signed, $unsigned, $u_scalar);
+        )+
+    };
+}
+
+#[cfg(feature = "simd_support")]
+uniform_simd_int_impl! {
+    (u64x2, i64x2),
+    (u64x4, i64x4),
+    (u64x8, i64x8),
+    u64
+}
+
+#[cfg(feature = "simd_support")]
+uniform_simd_int_impl! {
+    (u32x2, i32x2),
+    (u32x4, i32x4),
+    (u32x8, i32x8),
+    (u32x16, i32x16),
+    u32
+}
+
+#[cfg(feature = "simd_support")]
+uniform_simd_int_impl! {
+    (u16x2, i16x2),
+    (u16x4, i16x4),
+    (u16x8, i16x8),
+    (u16x16, i16x16),
+    (u16x32, i16x32),
+    u16
+}
+
+#[cfg(feature = "simd_support")]
+uniform_simd_int_impl! {
+    (u8x2, i8x2),
+    (u8x4, i8x4),
+    (u8x8, i8x8),
+    (u8x16, i8x16),
+    (u8x32, i8x32),
+    (u8x64, i8x64),
+    u8
+}
+
+impl SampleUniform for char {
+    type Sampler = UniformChar;
+}
+
+/// The back-end implementing [`UniformSampler`] for `char`.
+///
+/// Unless you are implementing [`UniformSampler`] for your own type, this type
+/// should not be used directly, use [`Uniform`] instead.
+///
+/// This differs from integer range sampling since the range `0xD800..=0xDFFF`
+/// are used for surrogate pairs in UCS and UTF-16, and consequently are not
+/// valid Unicode code points. We must therefore avoid sampling values in this
+/// range.
+#[derive(Clone, Copy, Debug)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct UniformChar {
+    sampler: UniformInt<u32>,
+}
+
+/// UTF-16 surrogate range start
+const CHAR_SURROGATE_START: u32 = 0xD800;
+/// UTF-16 surrogate range size
+const CHAR_SURROGATE_LEN: u32 = 0xE000 - CHAR_SURROGATE_START;
+
+/// Convert `char` to compressed `u32`
+fn char_to_comp_u32(c: char) -> u32 {
+    match c as u32 {
+        c if c >= CHAR_SURROGATE_START => c - CHAR_SURROGATE_LEN,
+        c => c,
+    }
+}
+
+impl UniformSampler for UniformChar {
+    type X = char;
+
+    #[inline] // if the range is constant, this helps LLVM to do the
+              // calculations at compile-time.
+    fn new<B1, B2>(low_b: B1, high_b: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized,
+    {
+        let low = char_to_comp_u32(*low_b.borrow());
+        let high = char_to_comp_u32(*high_b.borrow());
+        let sampler = UniformInt::<u32>::new(low, high);
+        UniformChar { sampler }
+    }
+
+    #[inline] // if the range is constant, this helps LLVM to do the
+              // calculations at compile-time.
+    fn new_inclusive<B1, B2>(low_b: B1, high_b: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized,
+    {
+        let low = char_to_comp_u32(*low_b.borrow());
+        let high = char_to_comp_u32(*high_b.borrow());
+        let sampler = UniformInt::<u32>::new_inclusive(low, high);
+        UniformChar { sampler }
+    }
+
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+        let mut x = self.sampler.sample(rng);
+        if x >= CHAR_SURROGATE_START {
+            x += CHAR_SURROGATE_LEN;
+        }
+        // SAFETY: x must not be in surrogate range or greater than char::MAX.
+        // This relies on range constructors which accept char arguments.
+        // Validity of input char values is assumed.
+        unsafe { core::char::from_u32_unchecked(x) }
+    }
+}
+
+/// The back-end implementing [`UniformSampler`] for floating-point types.
+///
+/// Unless you are implementing [`UniformSampler`] for your own type, this type
+/// should not be used directly, use [`Uniform`] instead.
+///
+/// # Implementation notes
+///
+/// Instead of generating a float in the `[0, 1)` range using [`Standard`], the
+/// `UniformFloat` implementation converts the output of an PRNG itself. This
+/// way one or two steps can be optimized out.
+///
+/// The floats are first converted to a value in the `[1, 2)` interval using a
+/// transmute-based method, and then mapped to the expected range with a
+/// multiply and addition. Values produced this way have what equals 23 bits of
+/// random digits for an `f32`, and 52 for an `f64`.
+///
+/// [`new`]: UniformSampler::new
+/// [`new_inclusive`]: UniformSampler::new_inclusive
+/// [`Standard`]: crate::distributions::Standard
+#[derive(Clone, Copy, Debug, PartialEq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct UniformFloat<X> {
+    low: X,
+    scale: X,
+}
+
+macro_rules! uniform_float_impl {
+    ($ty:ty, $uty:ident, $f_scalar:ident, $u_scalar:ident, $bits_to_discard:expr) => {
+        impl SampleUniform for $ty {
+            type Sampler = UniformFloat<$ty>;
+        }
+
+        impl UniformSampler for UniformFloat<$ty> {
+            type X = $ty;
+
+            fn new<B1, B2>(low_b: B1, high_b: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                debug_assert!(
+                    low.all_finite(),
+                    "Uniform::new called with `low` non-finite."
+                );
+                debug_assert!(
+                    high.all_finite(),
+                    "Uniform::new called with `high` non-finite."
+                );
+                assert!(low.all_lt(high), "Uniform::new called with `low >= high`");
+                let max_rand = <$ty>::splat(
+                    (::core::$u_scalar::MAX >> $bits_to_discard).into_float_with_exponent(0) - 1.0,
+                );
+
+                let mut scale = high - low;
+                assert!(scale.all_finite(), "Uniform::new: range overflow");
+
+                loop {
+                    let mask = (scale * max_rand + low).ge_mask(high);
+                    if mask.none() {
+                        break;
+                    }
+                    scale = scale.decrease_masked(mask);
+                }
+
+                debug_assert!(<$ty>::splat(0.0).all_le(scale));
+
+                UniformFloat { low, scale }
+            }
+
+            fn new_inclusive<B1, B2>(low_b: B1, high_b: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                debug_assert!(
+                    low.all_finite(),
+                    "Uniform::new_inclusive called with `low` non-finite."
+                );
+                debug_assert!(
+                    high.all_finite(),
+                    "Uniform::new_inclusive called with `high` non-finite."
+                );
+                assert!(
+                    low.all_le(high),
+                    "Uniform::new_inclusive called with `low > high`"
+                );
+                let max_rand = <$ty>::splat(
+                    (::core::$u_scalar::MAX >> $bits_to_discard).into_float_with_exponent(0) - 1.0,
+                );
+
+                let mut scale = (high - low) / max_rand;
+                assert!(scale.all_finite(), "Uniform::new_inclusive: range overflow");
+
+                loop {
+                    let mask = (scale * max_rand + low).gt_mask(high);
+                    if mask.none() {
+                        break;
+                    }
+                    scale = scale.decrease_masked(mask);
+                }
+
+                debug_assert!(<$ty>::splat(0.0).all_le(scale));
+
+                UniformFloat { low, scale }
+            }
+
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+                // Generate a value in the range [1, 2)
+                let value1_2 = (rng.gen::<$uty>() >> $bits_to_discard).into_float_with_exponent(0);
+
+                // Get a value in the range [0, 1) in order to avoid
+                // overflowing into infinity when multiplying with scale
+                let value0_1 = value1_2 - 1.0;
+
+                // We don't use `f64::mul_add`, because it is not available with
+                // `no_std`. Furthermore, it is slower for some targets (but
+                // faster for others). However, the order of multiplication and
+                // addition is important, because on some platforms (e.g. ARM)
+                // it will be optimized to a single (non-FMA) instruction.
+                value0_1 * self.scale + self.low
+            }
+
+            #[inline]
+            fn sample_single<R: Rng + ?Sized, B1, B2>(low_b: B1, high_b: B2, rng: &mut R) -> Self::X
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                let low = *low_b.borrow();
+                let high = *high_b.borrow();
+                debug_assert!(
+                    low.all_finite(),
+                    "UniformSampler::sample_single called with `low` non-finite."
+                );
+                debug_assert!(
+                    high.all_finite(),
+                    "UniformSampler::sample_single called with `high` non-finite."
+                );
+                assert!(
+                    low.all_lt(high),
+                    "UniformSampler::sample_single: low >= high"
+                );
+                let mut scale = high - low;
+                assert!(scale.all_finite(), "UniformSampler::sample_single: range overflow");
+
+                loop {
+                    // Generate a value in the range [1, 2)
+                    let value1_2 =
+                        (rng.gen::<$uty>() >> $bits_to_discard).into_float_with_exponent(0);
+
+                    // Get a value in the range [0, 1) in order to avoid
+                    // overflowing into infinity when multiplying with scale
+                    let value0_1 = value1_2 - 1.0;
+
+                    // Doing multiply before addition allows some architectures
+                    // to use a single instruction.
+                    let res = value0_1 * scale + low;
+
+                    debug_assert!(low.all_le(res) || !scale.all_finite());
+                    if res.all_lt(high) {
+                        return res;
+                    }
+
+                    // This handles a number of edge cases.
+                    // * `low` or `high` is NaN. In this case `scale` and
+                    //   `res` are going to end up as NaN.
+                    // * `low` is negative infinity and `high` is finite.
+                    //   `scale` is going to be infinite and `res` will be
+                    //   NaN.
+                    // * `high` is positive infinity and `low` is finite.
+                    //   `scale` is going to be infinite and `res` will
+                    //   be infinite or NaN (if value0_1 is 0).
+                    // * `low` is negative infinity and `high` is positive
+                    //   infinity. `scale` will be infinite and `res` will
+                    //   be NaN.
+                    // * `low` and `high` are finite, but `high - low`
+                    //   overflows to infinite. `scale` will be infinite
+                    //   and `res` will be infinite or NaN (if value0_1 is 0).
+                    // So if `high` or `low` are non-finite, we are guaranteed
+                    // to fail the `res < high` check above and end up here.
+                    //
+                    // While we technically should check for non-finite `low`
+                    // and `high` before entering the loop, by doing the checks
+                    // here instead, we allow the common case to avoid these
+                    // checks. But we are still guaranteed that if `low` or
+                    // `high` are non-finite we'll end up here and can do the
+                    // appropriate checks.
+                    //
+                    // Likewise `high - low` overflowing to infinity is also
+                    // rare, so handle it here after the common case.
+                    let mask = !scale.finite_mask();
+                    if mask.any() {
+                        assert!(
+                            low.all_finite() && high.all_finite(),
+                            "Uniform::sample_single: low and high must be finite"
+                        );
+                        scale = scale.decrease_masked(mask);
+                    }
+                }
+            }
+        }
+    };
+}
+
+uniform_float_impl! { f32, u32, f32, u32, 32 - 23 }
+uniform_float_impl! { f64, u64, f64, u64, 64 - 52 }
+
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f32x2, u32x2, f32, u32, 32 - 23 }
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f32x4, u32x4, f32, u32, 32 - 23 }
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f32x8, u32x8, f32, u32, 32 - 23 }
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f32x16, u32x16, f32, u32, 32 - 23 }
+
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f64x2, u64x2, f64, u64, 64 - 52 }
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f64x4, u64x4, f64, u64, 64 - 52 }
+#[cfg(feature = "simd_support")]
+uniform_float_impl! { f64x8, u64x8, f64, u64, 64 - 52 }
+
+
+/// The back-end implementing [`UniformSampler`] for `Duration`.
+///
+/// Unless you are implementing [`UniformSampler`] for your own types, this type
+/// should not be used directly, use [`Uniform`] instead.
+#[derive(Clone, Copy, Debug)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct UniformDuration {
+    mode: UniformDurationMode,
+    offset: u32,
+}
+
+#[derive(Debug, Copy, Clone)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+enum UniformDurationMode {
+    Small {
+        secs: u64,
+        nanos: Uniform<u32>,
+    },
+    Medium {
+        nanos: Uniform<u64>,
+    },
+    Large {
+        max_secs: u64,
+        max_nanos: u32,
+        secs: Uniform<u64>,
+    },
+}
+
+impl SampleUniform for Duration {
+    type Sampler = UniformDuration;
+}
+
+impl UniformSampler for UniformDuration {
+    type X = Duration;
+
+    #[inline]
+    fn new<B1, B2>(low_b: B1, high_b: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized,
+    {
+        let low = *low_b.borrow();
+        let high = *high_b.borrow();
+        assert!(low < high, "Uniform::new called with `low >= high`");
+        UniformDuration::new_inclusive(low, high - Duration::new(0, 1))
+    }
+
+    #[inline]
+    fn new_inclusive<B1, B2>(low_b: B1, high_b: B2) -> Self
+    where
+        B1: SampleBorrow<Self::X> + Sized,
+        B2: SampleBorrow<Self::X> + Sized,
+    {
+        let low = *low_b.borrow();
+        let high = *high_b.borrow();
+        assert!(
+            low <= high,
+            "Uniform::new_inclusive called with `low > high`"
+        );
+
+        let low_s = low.as_secs();
+        let low_n = low.subsec_nanos();
+        let mut high_s = high.as_secs();
+        let mut high_n = high.subsec_nanos();
+
+        if high_n < low_n {
+            high_s -= 1;
+            high_n += 1_000_000_000;
+        }
+
+        let mode = if low_s == high_s {
+            UniformDurationMode::Small {
+                secs: low_s,
+                nanos: Uniform::new_inclusive(low_n, high_n),
+            }
+        } else {
+            let max = high_s
+                .checked_mul(1_000_000_000)
+                .and_then(|n| n.checked_add(u64::from(high_n)));
+
+            if let Some(higher_bound) = max {
+                let lower_bound = low_s * 1_000_000_000 + u64::from(low_n);
+                UniformDurationMode::Medium {
+                    nanos: Uniform::new_inclusive(lower_bound, higher_bound),
+                }
+            } else {
+                // An offset is applied to simplify generation of nanoseconds
+                let max_nanos = high_n - low_n;
+                UniformDurationMode::Large {
+                    max_secs: high_s,
+                    max_nanos,
+                    secs: Uniform::new_inclusive(low_s, high_s),
+                }
+            }
+        };
+        UniformDuration {
+            mode,
+            offset: low_n,
+        }
+    }
+
+    #[inline]
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Duration {
+        match self.mode {
+            UniformDurationMode::Small { secs, nanos } => {
+                let n = nanos.sample(rng);
+                Duration::new(secs, n)
+            }
+            UniformDurationMode::Medium { nanos } => {
+                let nanos = nanos.sample(rng);
+                Duration::new(nanos / 1_000_000_000, (nanos % 1_000_000_000) as u32)
+            }
+            UniformDurationMode::Large {
+                max_secs,
+                max_nanos,
+                secs,
+            } => {
+                // constant folding means this is at least as fast as `Rng::sample(Range)`
+                let nano_range = Uniform::new(0, 1_000_000_000);
+                loop {
+                    let s = secs.sample(rng);
+                    let n = nano_range.sample(rng);
+                    if !(s == max_secs && n > max_nanos) {
+                        let sum = n + self.offset;
+                        break Duration::new(s, sum);
+                    }
+                }
+            }
+        }
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    use super::*;
+    use crate::rngs::mock::StepRng;
+
+    #[test]
+    #[cfg(feature = "serde1")]
+    fn test_serialization_uniform_duration() {
+        let distr = UniformDuration::new(Duration::from_secs(10), Duration::from_secs(60));
+        let de_distr: UniformDuration = bincode::deserialize(&bincode::serialize(&distr).unwrap()).unwrap();
+        assert_eq!(
+            distr.offset, de_distr.offset
+        );
+        match (distr.mode, de_distr.mode) {
+            (UniformDurationMode::Small {secs: a_secs, nanos: a_nanos}, UniformDurationMode::Small {secs, nanos}) => {
+                assert_eq!(a_secs, secs);
+
+                assert_eq!(a_nanos.0.low, nanos.0.low);
+                assert_eq!(a_nanos.0.range, nanos.0.range);
+                assert_eq!(a_nanos.0.z, nanos.0.z);
+            }
+            (UniformDurationMode::Medium {nanos: a_nanos} , UniformDurationMode::Medium {nanos}) => {
+                assert_eq!(a_nanos.0.low, nanos.0.low);
+                assert_eq!(a_nanos.0.range, nanos.0.range);
+                assert_eq!(a_nanos.0.z, nanos.0.z);
+            }
+            (UniformDurationMode::Large {max_secs:a_max_secs, max_nanos:a_max_nanos, secs:a_secs}, UniformDurationMode::Large {max_secs, max_nanos, secs} ) => {
+                assert_eq!(a_max_secs, max_secs);
+                assert_eq!(a_max_nanos, max_nanos);
+
+                assert_eq!(a_secs.0.low, secs.0.low);
+                assert_eq!(a_secs.0.range, secs.0.range);
+                assert_eq!(a_secs.0.z, secs.0.z);
+            }
+            _ => panic!("`UniformDurationMode` was not serialized/deserialized correctly")
+        }
+    }
+    
+    #[test]
+    #[cfg(feature = "serde1")]
+    fn test_uniform_serialization() {
+        let unit_box: Uniform<i32>  = Uniform::new(-1, 1);
+        let de_unit_box: Uniform<i32> = bincode::deserialize(&bincode::serialize(&unit_box).unwrap()).unwrap();
+
+        assert_eq!(unit_box.0.low, de_unit_box.0.low);
+        assert_eq!(unit_box.0.range, de_unit_box.0.range);
+        assert_eq!(unit_box.0.z, de_unit_box.0.z);
+
+        let unit_box: Uniform<f32> = Uniform::new(-1., 1.);
+        let de_unit_box: Uniform<f32> = bincode::deserialize(&bincode::serialize(&unit_box).unwrap()).unwrap();
+
+        assert_eq!(unit_box.0.low, de_unit_box.0.low);
+        assert_eq!(unit_box.0.scale, de_unit_box.0.scale);
+    }
+
+    #[should_panic]
+    #[test]
+    fn test_uniform_bad_limits_equal_int() {
+        Uniform::new(10, 10);
+    }
+
+    #[test]
+    fn test_uniform_good_limits_equal_int() {
+        let mut rng = crate::test::rng(804);
+        let dist = Uniform::new_inclusive(10, 10);
+        for _ in 0..20 {
+            assert_eq!(rng.sample(dist), 10);
+        }
+    }
+
+    #[should_panic]
+    #[test]
+    fn test_uniform_bad_limits_flipped_int() {
+        Uniform::new(10, 5);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_integers() {
+        use core::{i128, u128};
+        use core::{i16, i32, i64, i8, isize};
+        use core::{u16, u32, u64, u8, usize};
+
+        let mut rng = crate::test::rng(251);
+        macro_rules! t {
+            ($ty:ident, $v:expr, $le:expr, $lt:expr) => {{
+                for &(low, high) in $v.iter() {
+                    let my_uniform = Uniform::new(low, high);
+                    for _ in 0..1000 {
+                        let v: $ty = rng.sample(my_uniform);
+                        assert!($le(low, v) && $lt(v, high));
+                    }
+
+                    let my_uniform = Uniform::new_inclusive(low, high);
+                    for _ in 0..1000 {
+                        let v: $ty = rng.sample(my_uniform);
+                        assert!($le(low, v) && $le(v, high));
+                    }
+
+                    let my_uniform = Uniform::new(&low, high);
+                    for _ in 0..1000 {
+                        let v: $ty = rng.sample(my_uniform);
+                        assert!($le(low, v) && $lt(v, high));
+                    }
+
+                    let my_uniform = Uniform::new_inclusive(&low, &high);
+                    for _ in 0..1000 {
+                        let v: $ty = rng.sample(my_uniform);
+                        assert!($le(low, v) && $le(v, high));
+                    }
+
+                    for _ in 0..1000 {
+                        let v = <$ty as SampleUniform>::Sampler::sample_single(low, high, &mut rng);
+                        assert!($le(low, v) && $lt(v, high));
+                    }
+
+                    for _ in 0..1000 {
+                        let v = <$ty as SampleUniform>::Sampler::sample_single_inclusive(low, high, &mut rng);
+                        assert!($le(low, v) && $le(v, high));
+                    }
+                }
+            }};
+
+            // scalar bulk
+            ($($ty:ident),*) => {{
+                $(t!(
+                    $ty,
+                    [(0, 10), (10, 127), ($ty::MIN, $ty::MAX)],
+                    |x, y| x <= y,
+                    |x, y| x < y
+                );)*
+            }};
+
+            // simd bulk
+            ($($ty:ident),* => $scalar:ident) => {{
+                $(t!(
+                    $ty,
+                    [
+                        ($ty::splat(0), $ty::splat(10)),
+                        ($ty::splat(10), $ty::splat(127)),
+                        ($ty::splat($scalar::MIN), $ty::splat($scalar::MAX)),
+                    ],
+                    |x: $ty, y| x.le(y).all(),
+                    |x: $ty, y| x.lt(y).all()
+                );)*
+            }};
+        }
+        t!(i8, i16, i32, i64, isize, u8, u16, u32, u64, usize, i128, u128);
+
+        #[cfg(feature = "simd_support")]
+        {
+            t!(u8x2, u8x4, u8x8, u8x16, u8x32, u8x64 => u8);
+            t!(i8x2, i8x4, i8x8, i8x16, i8x32, i8x64 => i8);
+            t!(u16x2, u16x4, u16x8, u16x16, u16x32 => u16);
+            t!(i16x2, i16x4, i16x8, i16x16, i16x32 => i16);
+            t!(u32x2, u32x4, u32x8, u32x16 => u32);
+            t!(i32x2, i32x4, i32x8, i32x16 => i32);
+            t!(u64x2, u64x4, u64x8 => u64);
+            t!(i64x2, i64x4, i64x8 => i64);
+        }
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_char() {
+        let mut rng = crate::test::rng(891);
+        let mut max = core::char::from_u32(0).unwrap();
+        for _ in 0..100 {
+            let c = rng.gen_range('A'..='Z');
+            assert!(('A'..='Z').contains(&c));
+            max = max.max(c);
+        }
+        assert_eq!(max, 'Z');
+        let d = Uniform::new(
+            core::char::from_u32(0xD7F0).unwrap(),
+            core::char::from_u32(0xE010).unwrap(),
+        );
+        for _ in 0..100 {
+            let c = d.sample(&mut rng);
+            assert!((c as u32) < 0xD800 || (c as u32) > 0xDFFF);
+        }
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_floats() {
+        let mut rng = crate::test::rng(252);
+        let mut zero_rng = StepRng::new(0, 0);
+        let mut max_rng = StepRng::new(0xffff_ffff_ffff_ffff, 0);
+        macro_rules! t {
+            ($ty:ty, $f_scalar:ident, $bits_shifted:expr) => {{
+                let v: &[($f_scalar, $f_scalar)] = &[
+                    (0.0, 100.0),
+                    (-1e35, -1e25),
+                    (1e-35, 1e-25),
+                    (-1e35, 1e35),
+                    (<$f_scalar>::from_bits(0), <$f_scalar>::from_bits(3)),
+                    (-<$f_scalar>::from_bits(10), -<$f_scalar>::from_bits(1)),
+                    (-<$f_scalar>::from_bits(5), 0.0),
+                    (-<$f_scalar>::from_bits(7), -0.0),
+                    (0.1 * ::core::$f_scalar::MAX, ::core::$f_scalar::MAX),
+                    (-::core::$f_scalar::MAX * 0.2, ::core::$f_scalar::MAX * 0.7),
+                ];
+                for &(low_scalar, high_scalar) in v.iter() {
+                    for lane in 0..<$ty>::lanes() {
+                        let low = <$ty>::splat(0.0 as $f_scalar).replace(lane, low_scalar);
+                        let high = <$ty>::splat(1.0 as $f_scalar).replace(lane, high_scalar);
+                        let my_uniform = Uniform::new(low, high);
+                        let my_incl_uniform = Uniform::new_inclusive(low, high);
+                        for _ in 0..100 {
+                            let v = rng.sample(my_uniform).extract(lane);
+                            assert!(low_scalar <= v && v < high_scalar);
+                            let v = rng.sample(my_incl_uniform).extract(lane);
+                            assert!(low_scalar <= v && v <= high_scalar);
+                            let v = <$ty as SampleUniform>::Sampler
+                                ::sample_single(low, high, &mut rng).extract(lane);
+                            assert!(low_scalar <= v && v < high_scalar);
+                        }
+
+                        assert_eq!(
+                            rng.sample(Uniform::new_inclusive(low, low)).extract(lane),
+                            low_scalar
+                        );
+
+                        assert_eq!(zero_rng.sample(my_uniform).extract(lane), low_scalar);
+                        assert_eq!(zero_rng.sample(my_incl_uniform).extract(lane), low_scalar);
+                        assert_eq!(<$ty as SampleUniform>::Sampler
+                            ::sample_single(low, high, &mut zero_rng)
+                            .extract(lane), low_scalar);
+                        assert!(max_rng.sample(my_uniform).extract(lane) < high_scalar);
+                        assert!(max_rng.sample(my_incl_uniform).extract(lane) <= high_scalar);
+
+                        // Don't run this test for really tiny differences between high and low
+                        // since for those rounding might result in selecting high for a very
+                        // long time.
+                        if (high_scalar - low_scalar) > 0.0001 {
+                            let mut lowering_max_rng = StepRng::new(
+                                0xffff_ffff_ffff_ffff,
+                                (-1i64 << $bits_shifted) as u64,
+                            );
+                            assert!(
+                                <$ty as SampleUniform>::Sampler
+                                    ::sample_single(low, high, &mut lowering_max_rng)
+                                    .extract(lane) < high_scalar
+                            );
+                        }
+                    }
+                }
+
+                assert_eq!(
+                    rng.sample(Uniform::new_inclusive(
+                        ::core::$f_scalar::MAX,
+                        ::core::$f_scalar::MAX
+                    )),
+                    ::core::$f_scalar::MAX
+                );
+                assert_eq!(
+                    rng.sample(Uniform::new_inclusive(
+                        -::core::$f_scalar::MAX,
+                        -::core::$f_scalar::MAX
+                    )),
+                    -::core::$f_scalar::MAX
+                );
+            }};
+        }
+
+        t!(f32, f32, 32 - 23);
+        t!(f64, f64, 64 - 52);
+        #[cfg(feature = "simd_support")]
+        {
+            t!(f32x2, f32, 32 - 23);
+            t!(f32x4, f32, 32 - 23);
+            t!(f32x8, f32, 32 - 23);
+            t!(f32x16, f32, 32 - 23);
+            t!(f64x2, f64, 64 - 52);
+            t!(f64x4, f64, 64 - 52);
+            t!(f64x8, f64, 64 - 52);
+        }
+    }
+
+    #[test]
+    #[should_panic]
+    fn test_float_overflow() {
+        let _ = Uniform::from(::core::f64::MIN..::core::f64::MAX);
+    }
+
+    #[test]
+    #[should_panic]
+    fn test_float_overflow_single() {
+        let mut rng = crate::test::rng(252);
+        rng.gen_range(::core::f64::MIN..::core::f64::MAX);
+    }
+
+    #[test]
+    #[cfg(all(
+        feature = "std",
+        not(target_arch = "wasm32"),
+        not(target_arch = "asmjs")
+    ))]
+    fn test_float_assertions() {
+        use super::SampleUniform;
+        use std::panic::catch_unwind;
+        fn range<T: SampleUniform>(low: T, high: T) {
+            let mut rng = crate::test::rng(253);
+            T::Sampler::sample_single(low, high, &mut rng);
+        }
+
+        macro_rules! t {
+            ($ty:ident, $f_scalar:ident) => {{
+                let v: &[($f_scalar, $f_scalar)] = &[
+                    (::std::$f_scalar::NAN, 0.0),
+                    (1.0, ::std::$f_scalar::NAN),
+                    (::std::$f_scalar::NAN, ::std::$f_scalar::NAN),
+                    (1.0, 0.5),
+                    (::std::$f_scalar::MAX, -::std::$f_scalar::MAX),
+                    (::std::$f_scalar::INFINITY, ::std::$f_scalar::INFINITY),
+                    (
+                        ::std::$f_scalar::NEG_INFINITY,
+                        ::std::$f_scalar::NEG_INFINITY,
+                    ),
+                    (::std::$f_scalar::NEG_INFINITY, 5.0),
+                    (5.0, ::std::$f_scalar::INFINITY),
+                    (::std::$f_scalar::NAN, ::std::$f_scalar::INFINITY),
+                    (::std::$f_scalar::NEG_INFINITY, ::std::$f_scalar::NAN),
+                    (::std::$f_scalar::NEG_INFINITY, ::std::$f_scalar::INFINITY),
+                ];
+                for &(low_scalar, high_scalar) in v.iter() {
+                    for lane in 0..<$ty>::lanes() {
+                        let low = <$ty>::splat(0.0 as $f_scalar).replace(lane, low_scalar);
+                        let high = <$ty>::splat(1.0 as $f_scalar).replace(lane, high_scalar);
+                        assert!(catch_unwind(|| range(low, high)).is_err());
+                        assert!(catch_unwind(|| Uniform::new(low, high)).is_err());
+                        assert!(catch_unwind(|| Uniform::new_inclusive(low, high)).is_err());
+                        assert!(catch_unwind(|| range(low, low)).is_err());
+                        assert!(catch_unwind(|| Uniform::new(low, low)).is_err());
+                    }
+                }
+            }};
+        }
+
+        t!(f32, f32);
+        t!(f64, f64);
+        #[cfg(feature = "simd_support")]
+        {
+            t!(f32x2, f32);
+            t!(f32x4, f32);
+            t!(f32x8, f32);
+            t!(f32x16, f32);
+            t!(f64x2, f64);
+            t!(f64x4, f64);
+            t!(f64x8, f64);
+        }
+    }
+
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_durations() {
+        let mut rng = crate::test::rng(253);
+
+        let v = &[
+            (Duration::new(10, 50000), Duration::new(100, 1234)),
+            (Duration::new(0, 100), Duration::new(1, 50)),
+            (
+                Duration::new(0, 0),
+                Duration::new(u64::max_value(), 999_999_999),
+            ),
+        ];
+        for &(low, high) in v.iter() {
+            let my_uniform = Uniform::new(low, high);
+            for _ in 0..1000 {
+                let v = rng.sample(my_uniform);
+                assert!(low <= v && v < high);
+            }
+        }
+    }
+
+    #[test]
+    fn test_custom_uniform() {
+        use crate::distributions::uniform::{
+            SampleBorrow, SampleUniform, UniformFloat, UniformSampler,
+        };
+        #[derive(Clone, Copy, PartialEq, PartialOrd)]
+        struct MyF32 {
+            x: f32,
+        }
+        #[derive(Clone, Copy, Debug)]
+        struct UniformMyF32(UniformFloat<f32>);
+        impl UniformSampler for UniformMyF32 {
+            type X = MyF32;
+
+            fn new<B1, B2>(low: B1, high: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                UniformMyF32(UniformFloat::<f32>::new(low.borrow().x, high.borrow().x))
+            }
+
+            fn new_inclusive<B1, B2>(low: B1, high: B2) -> Self
+            where
+                B1: SampleBorrow<Self::X> + Sized,
+                B2: SampleBorrow<Self::X> + Sized,
+            {
+                UniformSampler::new(low, high)
+            }
+
+            fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> Self::X {
+                MyF32 {
+                    x: self.0.sample(rng),
+                }
+            }
+        }
+        impl SampleUniform for MyF32 {
+            type Sampler = UniformMyF32;
+        }
+
+        let (low, high) = (MyF32 { x: 17.0f32 }, MyF32 { x: 22.0f32 });
+        let uniform = Uniform::new(low, high);
+        let mut rng = crate::test::rng(804);
+        for _ in 0..100 {
+            let x: MyF32 = rng.sample(uniform);
+            assert!(low <= x && x < high);
+        }
+    }
+
+    #[test]
+    fn test_uniform_from_std_range() {
+        let r = Uniform::from(2u32..7);
+        assert_eq!(r.0.low, 2);
+        assert_eq!(r.0.range, 5);
+        let r = Uniform::from(2.0f64..7.0);
+        assert_eq!(r.0.low, 2.0);
+        assert_eq!(r.0.scale, 5.0);
+    }
+
+    #[test]
+    fn test_uniform_from_std_range_inclusive() {
+        let r = Uniform::from(2u32..=6);
+        assert_eq!(r.0.low, 2);
+        assert_eq!(r.0.range, 5);
+        let r = Uniform::from(2.0f64..=7.0);
+        assert_eq!(r.0.low, 2.0);
+        assert!(r.0.scale > 5.0);
+        assert!(r.0.scale < 5.0 + 1e-14);
+    }
+
+    #[test]
+    fn value_stability() {
+        fn test_samples<T: SampleUniform + Copy + core::fmt::Debug + PartialEq>(
+            lb: T, ub: T, expected_single: &[T], expected_multiple: &[T],
+        ) where Uniform<T>: Distribution<T> {
+            let mut rng = crate::test::rng(897);
+            let mut buf = [lb; 3];
+
+            for x in &mut buf {
+                *x = T::Sampler::sample_single(lb, ub, &mut rng);
+            }
+            assert_eq!(&buf, expected_single);
+
+            let distr = Uniform::new(lb, ub);
+            for x in &mut buf {
+                *x = rng.sample(&distr);
+            }
+            assert_eq!(&buf, expected_multiple);
+        }
+
+        // We test on a sub-set of types; possibly we should do more.
+        // TODO: SIMD types
+
+        test_samples(11u8, 219, &[17, 66, 214], &[181, 93, 165]);
+        test_samples(11u32, 219, &[17, 66, 214], &[181, 93, 165]);
+
+        test_samples(0f32, 1e-2f32, &[0.0003070104, 0.0026630748, 0.00979833], &[
+            0.008194133,
+            0.00398172,
+            0.007428536,
+        ]);
+        test_samples(
+            -1e10f64,
+            1e10f64,
+            &[-4673848682.871551, 6388267422.932352, 4857075081.198343],
+            &[1173375212.1808167, 1917642852.109581, 2365076174.3153973],
+        );
+
+        test_samples(
+            Duration::new(2, 0),
+            Duration::new(4, 0),
+            &[
+                Duration::new(2, 532615131),
+                Duration::new(3, 638826742),
+                Duration::new(3, 485707508),
+            ],
+            &[
+                Duration::new(3, 117337521),
+                Duration::new(3, 191764285),
+                Duration::new(3, 236507617),
+            ],
+        );
+    }
+
+    #[test]
+    fn uniform_distributions_can_be_compared() {
+        assert_eq!(Uniform::new(1.0, 2.0), Uniform::new(1.0, 2.0));
+
+        // To cover UniformInt
+        assert_eq!(Uniform::new(1 as u32, 2 as u32), Uniform::new(1 as u32, 2 as u32));
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/utils.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/utils.rs.html new file mode 100644 index 0000000..118f6fa --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/utils.rs.html @@ -0,0 +1,861 @@ +utils.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Math helper functions
+
+#[cfg(feature = "simd_support")] use packed_simd::*;
+
+
+pub(crate) trait WideningMultiply<RHS = Self> {
+    type Output;
+
+    fn wmul(self, x: RHS) -> Self::Output;
+}
+
+macro_rules! wmul_impl {
+    ($ty:ty, $wide:ty, $shift:expr) => {
+        impl WideningMultiply for $ty {
+            type Output = ($ty, $ty);
+
+            #[inline(always)]
+            fn wmul(self, x: $ty) -> Self::Output {
+                let tmp = (self as $wide) * (x as $wide);
+                ((tmp >> $shift) as $ty, tmp as $ty)
+            }
+        }
+    };
+
+    // simd bulk implementation
+    ($(($ty:ident, $wide:ident),)+, $shift:expr) => {
+        $(
+            impl WideningMultiply for $ty {
+                type Output = ($ty, $ty);
+
+                #[inline(always)]
+                fn wmul(self, x: $ty) -> Self::Output {
+                    // For supported vectors, this should compile to a couple
+                    // supported multiply & swizzle instructions (no actual
+                    // casting).
+                    // TODO: optimize
+                    let y: $wide = self.cast();
+                    let x: $wide = x.cast();
+                    let tmp = y * x;
+                    let hi: $ty = (tmp >> $shift).cast();
+                    let lo: $ty = tmp.cast();
+                    (hi, lo)
+                }
+            }
+        )+
+    };
+}
+wmul_impl! { u8, u16, 8 }
+wmul_impl! { u16, u32, 16 }
+wmul_impl! { u32, u64, 32 }
+wmul_impl! { u64, u128, 64 }
+
+// This code is a translation of the __mulddi3 function in LLVM's
+// compiler-rt. It is an optimised variant of the common method
+// `(a + b) * (c + d) = ac + ad + bc + bd`.
+//
+// For some reason LLVM can optimise the C version very well, but
+// keeps shuffling registers in this Rust translation.
+macro_rules! wmul_impl_large {
+    ($ty:ty, $half:expr) => {
+        impl WideningMultiply for $ty {
+            type Output = ($ty, $ty);
+
+            #[inline(always)]
+            fn wmul(self, b: $ty) -> Self::Output {
+                const LOWER_MASK: $ty = !0 >> $half;
+                let mut low = (self & LOWER_MASK).wrapping_mul(b & LOWER_MASK);
+                let mut t = low >> $half;
+                low &= LOWER_MASK;
+                t += (self >> $half).wrapping_mul(b & LOWER_MASK);
+                low += (t & LOWER_MASK) << $half;
+                let mut high = t >> $half;
+                t = low >> $half;
+                low &= LOWER_MASK;
+                t += (b >> $half).wrapping_mul(self & LOWER_MASK);
+                low += (t & LOWER_MASK) << $half;
+                high += t >> $half;
+                high += (self >> $half).wrapping_mul(b >> $half);
+
+                (high, low)
+            }
+        }
+    };
+
+    // simd bulk implementation
+    (($($ty:ty,)+) $scalar:ty, $half:expr) => {
+        $(
+            impl WideningMultiply for $ty {
+                type Output = ($ty, $ty);
+
+                #[inline(always)]
+                fn wmul(self, b: $ty) -> Self::Output {
+                    // needs wrapping multiplication
+                    const LOWER_MASK: $scalar = !0 >> $half;
+                    let mut low = (self & LOWER_MASK) * (b & LOWER_MASK);
+                    let mut t = low >> $half;
+                    low &= LOWER_MASK;
+                    t += (self >> $half) * (b & LOWER_MASK);
+                    low += (t & LOWER_MASK) << $half;
+                    let mut high = t >> $half;
+                    t = low >> $half;
+                    low &= LOWER_MASK;
+                    t += (b >> $half) * (self & LOWER_MASK);
+                    low += (t & LOWER_MASK) << $half;
+                    high += t >> $half;
+                    high += (self >> $half) * (b >> $half);
+
+                    (high, low)
+                }
+            }
+        )+
+    };
+}
+wmul_impl_large! { u128, 64 }
+
+macro_rules! wmul_impl_usize {
+    ($ty:ty) => {
+        impl WideningMultiply for usize {
+            type Output = (usize, usize);
+
+            #[inline(always)]
+            fn wmul(self, x: usize) -> Self::Output {
+                let (high, low) = (self as $ty).wmul(x as $ty);
+                (high as usize, low as usize)
+            }
+        }
+    };
+}
+#[cfg(target_pointer_width = "16")]
+wmul_impl_usize! { u16 }
+#[cfg(target_pointer_width = "32")]
+wmul_impl_usize! { u32 }
+#[cfg(target_pointer_width = "64")]
+wmul_impl_usize! { u64 }
+
+#[cfg(feature = "simd_support")]
+mod simd_wmul {
+    use super::*;
+    #[cfg(target_arch = "x86")] use core::arch::x86::*;
+    #[cfg(target_arch = "x86_64")] use core::arch::x86_64::*;
+
+    wmul_impl! {
+        (u8x2, u16x2),
+        (u8x4, u16x4),
+        (u8x8, u16x8),
+        (u8x16, u16x16),
+        (u8x32, u16x32),,
+        8
+    }
+
+    wmul_impl! { (u16x2, u32x2),, 16 }
+    wmul_impl! { (u16x4, u32x4),, 16 }
+    #[cfg(not(target_feature = "sse2"))]
+    wmul_impl! { (u16x8, u32x8),, 16 }
+    #[cfg(not(target_feature = "avx2"))]
+    wmul_impl! { (u16x16, u32x16),, 16 }
+
+    // 16-bit lane widths allow use of the x86 `mulhi` instructions, which
+    // means `wmul` can be implemented with only two instructions.
+    #[allow(unused_macros)]
+    macro_rules! wmul_impl_16 {
+        ($ty:ident, $intrinsic:ident, $mulhi:ident, $mullo:ident) => {
+            impl WideningMultiply for $ty {
+                type Output = ($ty, $ty);
+
+                #[inline(always)]
+                fn wmul(self, x: $ty) -> Self::Output {
+                    let b = $intrinsic::from_bits(x);
+                    let a = $intrinsic::from_bits(self);
+                    let hi = $ty::from_bits(unsafe { $mulhi(a, b) });
+                    let lo = $ty::from_bits(unsafe { $mullo(a, b) });
+                    (hi, lo)
+                }
+            }
+        };
+    }
+
+    #[cfg(target_feature = "sse2")]
+    wmul_impl_16! { u16x8, __m128i, _mm_mulhi_epu16, _mm_mullo_epi16 }
+    #[cfg(target_feature = "avx2")]
+    wmul_impl_16! { u16x16, __m256i, _mm256_mulhi_epu16, _mm256_mullo_epi16 }
+    // FIXME: there are no `__m512i` types in stdsimd yet, so `wmul::<u16x32>`
+    // cannot use the same implementation.
+
+    wmul_impl! {
+        (u32x2, u64x2),
+        (u32x4, u64x4),
+        (u32x8, u64x8),,
+        32
+    }
+
+    // TODO: optimize, this seems to seriously slow things down
+    wmul_impl_large! { (u8x64,) u8, 4 }
+    wmul_impl_large! { (u16x32,) u16, 8 }
+    wmul_impl_large! { (u32x16,) u32, 16 }
+    wmul_impl_large! { (u64x2, u64x4, u64x8,) u64, 32 }
+}
+
+/// Helper trait when dealing with scalar and SIMD floating point types.
+pub(crate) trait FloatSIMDUtils {
+    // `PartialOrd` for vectors compares lexicographically. We want to compare all
+    // the individual SIMD lanes instead, and get the combined result over all
+    // lanes. This is possible using something like `a.lt(b).all()`, but we
+    // implement it as a trait so we can write the same code for `f32` and `f64`.
+    // Only the comparison functions we need are implemented.
+    fn all_lt(self, other: Self) -> bool;
+    fn all_le(self, other: Self) -> bool;
+    fn all_finite(self) -> bool;
+
+    type Mask;
+    fn finite_mask(self) -> Self::Mask;
+    fn gt_mask(self, other: Self) -> Self::Mask;
+    fn ge_mask(self, other: Self) -> Self::Mask;
+
+    // Decrease all lanes where the mask is `true` to the next lower value
+    // representable by the floating-point type. At least one of the lanes
+    // must be set.
+    fn decrease_masked(self, mask: Self::Mask) -> Self;
+
+    // Convert from int value. Conversion is done while retaining the numerical
+    // value, not by retaining the binary representation.
+    type UInt;
+    fn cast_from_int(i: Self::UInt) -> Self;
+}
+
+/// Implement functions available in std builds but missing from core primitives
+#[cfg(not(std))]
+// False positive: We are following `std` here.
+#[allow(clippy::wrong_self_convention)]
+pub(crate) trait Float: Sized {
+    fn is_nan(self) -> bool;
+    fn is_infinite(self) -> bool;
+    fn is_finite(self) -> bool;
+}
+
+/// Implement functions on f32/f64 to give them APIs similar to SIMD types
+pub(crate) trait FloatAsSIMD: Sized {
+    #[inline(always)]
+    fn lanes() -> usize {
+        1
+    }
+    #[inline(always)]
+    fn splat(scalar: Self) -> Self {
+        scalar
+    }
+    #[inline(always)]
+    fn extract(self, index: usize) -> Self {
+        debug_assert_eq!(index, 0);
+        self
+    }
+    #[inline(always)]
+    fn replace(self, index: usize, new_value: Self) -> Self {
+        debug_assert_eq!(index, 0);
+        new_value
+    }
+}
+
+pub(crate) trait BoolAsSIMD: Sized {
+    fn any(self) -> bool;
+    fn all(self) -> bool;
+    fn none(self) -> bool;
+}
+
+impl BoolAsSIMD for bool {
+    #[inline(always)]
+    fn any(self) -> bool {
+        self
+    }
+
+    #[inline(always)]
+    fn all(self) -> bool {
+        self
+    }
+
+    #[inline(always)]
+    fn none(self) -> bool {
+        !self
+    }
+}
+
+macro_rules! scalar_float_impl {
+    ($ty:ident, $uty:ident) => {
+        #[cfg(not(std))]
+        impl Float for $ty {
+            #[inline]
+            fn is_nan(self) -> bool {
+                self != self
+            }
+
+            #[inline]
+            fn is_infinite(self) -> bool {
+                self == ::core::$ty::INFINITY || self == ::core::$ty::NEG_INFINITY
+            }
+
+            #[inline]
+            fn is_finite(self) -> bool {
+                !(self.is_nan() || self.is_infinite())
+            }
+        }
+
+        impl FloatSIMDUtils for $ty {
+            type Mask = bool;
+            type UInt = $uty;
+
+            #[inline(always)]
+            fn all_lt(self, other: Self) -> bool {
+                self < other
+            }
+
+            #[inline(always)]
+            fn all_le(self, other: Self) -> bool {
+                self <= other
+            }
+
+            #[inline(always)]
+            fn all_finite(self) -> bool {
+                self.is_finite()
+            }
+
+            #[inline(always)]
+            fn finite_mask(self) -> Self::Mask {
+                self.is_finite()
+            }
+
+            #[inline(always)]
+            fn gt_mask(self, other: Self) -> Self::Mask {
+                self > other
+            }
+
+            #[inline(always)]
+            fn ge_mask(self, other: Self) -> Self::Mask {
+                self >= other
+            }
+
+            #[inline(always)]
+            fn decrease_masked(self, mask: Self::Mask) -> Self {
+                debug_assert!(mask, "At least one lane must be set");
+                <$ty>::from_bits(self.to_bits() - 1)
+            }
+
+            #[inline]
+            fn cast_from_int(i: Self::UInt) -> Self {
+                i as $ty
+            }
+        }
+
+        impl FloatAsSIMD for $ty {}
+    };
+}
+
+scalar_float_impl!(f32, u32);
+scalar_float_impl!(f64, u64);
+
+
+#[cfg(feature = "simd_support")]
+macro_rules! simd_impl {
+    ($ty:ident, $f_scalar:ident, $mty:ident, $uty:ident) => {
+        impl FloatSIMDUtils for $ty {
+            type Mask = $mty;
+            type UInt = $uty;
+
+            #[inline(always)]
+            fn all_lt(self, other: Self) -> bool {
+                self.lt(other).all()
+            }
+
+            #[inline(always)]
+            fn all_le(self, other: Self) -> bool {
+                self.le(other).all()
+            }
+
+            #[inline(always)]
+            fn all_finite(self) -> bool {
+                self.finite_mask().all()
+            }
+
+            #[inline(always)]
+            fn finite_mask(self) -> Self::Mask {
+                // This can possibly be done faster by checking bit patterns
+                let neg_inf = $ty::splat(::core::$f_scalar::NEG_INFINITY);
+                let pos_inf = $ty::splat(::core::$f_scalar::INFINITY);
+                self.gt(neg_inf) & self.lt(pos_inf)
+            }
+
+            #[inline(always)]
+            fn gt_mask(self, other: Self) -> Self::Mask {
+                self.gt(other)
+            }
+
+            #[inline(always)]
+            fn ge_mask(self, other: Self) -> Self::Mask {
+                self.ge(other)
+            }
+
+            #[inline(always)]
+            fn decrease_masked(self, mask: Self::Mask) -> Self {
+                // Casting a mask into ints will produce all bits set for
+                // true, and 0 for false. Adding that to the binary
+                // representation of a float means subtracting one from
+                // the binary representation, resulting in the next lower
+                // value representable by $ty. This works even when the
+                // current value is infinity.
+                debug_assert!(mask.any(), "At least one lane must be set");
+                <$ty>::from_bits(<$uty>::from_bits(self) + <$uty>::from_bits(mask))
+            }
+
+            #[inline]
+            fn cast_from_int(i: Self::UInt) -> Self {
+                i.cast()
+            }
+        }
+    };
+}
+
+#[cfg(feature="simd_support")] simd_impl! { f32x2, f32, m32x2, u32x2 }
+#[cfg(feature="simd_support")] simd_impl! { f32x4, f32, m32x4, u32x4 }
+#[cfg(feature="simd_support")] simd_impl! { f32x8, f32, m32x8, u32x8 }
+#[cfg(feature="simd_support")] simd_impl! { f32x16, f32, m32x16, u32x16 }
+#[cfg(feature="simd_support")] simd_impl! { f64x2, f64, m64x2, u64x2 }
+#[cfg(feature="simd_support")] simd_impl! { f64x4, f64, m64x4, u64x4 }
+#[cfg(feature="simd_support")] simd_impl! { f64x8, f64, m64x8, u64x8 }
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted.rs.html new file mode 100644 index 0000000..7ae8d0d --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted.rs.html @@ -0,0 +1,97 @@ +weighted.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Weighted index sampling
+//!
+//! This module is deprecated. Use [`crate::distributions::WeightedIndex`] and
+//! [`crate::distributions::WeightedError`] instead.
+
+pub use super::{WeightedIndex, WeightedError};
+
+#[allow(missing_docs)]
+#[deprecated(since = "0.8.0", note = "moved to rand_distr crate")]
+pub mod alias_method {
+    // This module exists to provide a deprecation warning which minimises
+    // compile errors, but still fails to compile if ever used.
+    use core::marker::PhantomData;
+    use alloc::vec::Vec;
+    use super::WeightedError;
+
+    #[derive(Debug)]
+    pub struct WeightedIndex<W: Weight> {
+        _phantom: PhantomData<W>,
+    }
+    impl<W: Weight> WeightedIndex<W> {
+        pub fn new(_weights: Vec<W>) -> Result<Self, WeightedError> {
+            Err(WeightedError::NoItem)
+        }
+    }
+
+    pub trait Weight {}
+    macro_rules! impl_weight {
+        () => {};
+        ($T:ident, $($more:ident,)*) => {
+            impl Weight for $T {}
+            impl_weight!($($more,)*);
+        };
+    }
+    impl_weight!(f64, f32,);
+    impl_weight!(u8, u16, u32, u64, usize,);
+    impl_weight!(i8, i16, i32, i64, isize,);
+    impl_weight!(u128, i128,);
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted_index.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted_index.rs.html new file mode 100644 index 0000000..7439a5b --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/distributions/weighted_index.rs.html @@ -0,0 +1,919 @@ +weighted_index.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Weighted index sampling
+
+use crate::distributions::uniform::{SampleBorrow, SampleUniform, UniformSampler};
+use crate::distributions::Distribution;
+use crate::Rng;
+use core::cmp::PartialOrd;
+use core::fmt;
+
+// Note that this whole module is only imported if feature="alloc" is enabled.
+use alloc::vec::Vec;
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+
+/// A distribution using weighted sampling of discrete items
+///
+/// Sampling a `WeightedIndex` distribution returns the index of a randomly
+/// selected element from the iterator used when the `WeightedIndex` was
+/// created. The chance of a given element being picked is proportional to the
+/// value of the element. The weights can use any type `X` for which an
+/// implementation of [`Uniform<X>`] exists.
+///
+/// # Performance
+///
+/// Time complexity of sampling from `WeightedIndex` is `O(log N)` where
+/// `N` is the number of weights. As an alternative,
+/// [`rand_distr::weighted_alias`](https://docs.rs/rand_distr/*/rand_distr/weighted_alias/index.html)
+/// supports `O(1)` sampling, but with much higher initialisation cost.
+///
+/// A `WeightedIndex<X>` contains a `Vec<X>` and a [`Uniform<X>`] and so its
+/// size is the sum of the size of those objects, possibly plus some alignment.
+///
+/// Creating a `WeightedIndex<X>` will allocate enough space to hold `N - 1`
+/// weights of type `X`, where `N` is the number of weights. However, since
+/// `Vec` doesn't guarantee a particular growth strategy, additional memory
+/// might be allocated but not used. Since the `WeightedIndex` object also
+/// contains, this might cause additional allocations, though for primitive
+/// types, [`Uniform<X>`] doesn't allocate any memory.
+///
+/// Sampling from `WeightedIndex` will result in a single call to
+/// `Uniform<X>::sample` (method of the [`Distribution`] trait), which typically
+/// will request a single value from the underlying [`RngCore`], though the
+/// exact number depends on the implementation of `Uniform<X>::sample`.
+///
+/// # Example
+///
+/// ```
+/// use rand::prelude::*;
+/// use rand::distributions::WeightedIndex;
+///
+/// let choices = ['a', 'b', 'c'];
+/// let weights = [2,   1,   1];
+/// let dist = WeightedIndex::new(&weights).unwrap();
+/// let mut rng = thread_rng();
+/// for _ in 0..100 {
+///     // 50% chance to print 'a', 25% chance to print 'b', 25% chance to print 'c'
+///     println!("{}", choices[dist.sample(&mut rng)]);
+/// }
+///
+/// let items = [('a', 0), ('b', 3), ('c', 7)];
+/// let dist2 = WeightedIndex::new(items.iter().map(|item| item.1)).unwrap();
+/// for _ in 0..100 {
+///     // 0% chance to print 'a', 30% chance to print 'b', 70% chance to print 'c'
+///     println!("{}", items[dist2.sample(&mut rng)].0);
+/// }
+/// ```
+///
+/// [`Uniform<X>`]: crate::distributions::Uniform
+/// [`RngCore`]: crate::RngCore
+#[derive(Debug, Clone, PartialEq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+pub struct WeightedIndex<X: SampleUniform + PartialOrd> {
+    cumulative_weights: Vec<X>,
+    total_weight: X,
+    weight_distribution: X::Sampler,
+}
+
+impl<X: SampleUniform + PartialOrd> WeightedIndex<X> {
+    /// Creates a new a `WeightedIndex` [`Distribution`] using the values
+    /// in `weights`. The weights can use any type `X` for which an
+    /// implementation of [`Uniform<X>`] exists.
+    ///
+    /// Returns an error if the iterator is empty, if any weight is `< 0`, or
+    /// if its total value is 0.
+    ///
+    /// [`Uniform<X>`]: crate::distributions::uniform::Uniform
+    pub fn new<I>(weights: I) -> Result<WeightedIndex<X>, WeightedError>
+    where
+        I: IntoIterator,
+        I::Item: SampleBorrow<X>,
+        X: for<'a> ::core::ops::AddAssign<&'a X> + Clone + Default,
+    {
+        let mut iter = weights.into_iter();
+        let mut total_weight: X = iter.next().ok_or(WeightedError::NoItem)?.borrow().clone();
+
+        let zero = <X as Default>::default();
+        if !(total_weight >= zero) {
+            return Err(WeightedError::InvalidWeight);
+        }
+
+        let mut weights = Vec::<X>::with_capacity(iter.size_hint().0);
+        for w in iter {
+            // Note that `!(w >= x)` is not equivalent to `w < x` for partially
+            // ordered types due to NaNs which are equal to nothing.
+            if !(w.borrow() >= &zero) {
+                return Err(WeightedError::InvalidWeight);
+            }
+            weights.push(total_weight.clone());
+            total_weight += w.borrow();
+        }
+
+        if total_weight == zero {
+            return Err(WeightedError::AllWeightsZero);
+        }
+        let distr = X::Sampler::new(zero, total_weight.clone());
+
+        Ok(WeightedIndex {
+            cumulative_weights: weights,
+            total_weight,
+            weight_distribution: distr,
+        })
+    }
+
+    /// Update a subset of weights, without changing the number of weights.
+    ///
+    /// `new_weights` must be sorted by the index.
+    ///
+    /// Using this method instead of `new` might be more efficient if only a small number of
+    /// weights is modified. No allocations are performed, unless the weight type `X` uses
+    /// allocation internally.
+    ///
+    /// In case of error, `self` is not modified.
+    pub fn update_weights(&mut self, new_weights: &[(usize, &X)]) -> Result<(), WeightedError>
+    where X: for<'a> ::core::ops::AddAssign<&'a X>
+            + for<'a> ::core::ops::SubAssign<&'a X>
+            + Clone
+            + Default {
+        if new_weights.is_empty() {
+            return Ok(());
+        }
+
+        let zero = <X as Default>::default();
+
+        let mut total_weight = self.total_weight.clone();
+
+        // Check for errors first, so we don't modify `self` in case something
+        // goes wrong.
+        let mut prev_i = None;
+        for &(i, w) in new_weights {
+            if let Some(old_i) = prev_i {
+                if old_i >= i {
+                    return Err(WeightedError::InvalidWeight);
+                }
+            }
+            if !(*w >= zero) {
+                return Err(WeightedError::InvalidWeight);
+            }
+            if i > self.cumulative_weights.len() {
+                return Err(WeightedError::TooMany);
+            }
+
+            let mut old_w = if i < self.cumulative_weights.len() {
+                self.cumulative_weights[i].clone()
+            } else {
+                self.total_weight.clone()
+            };
+            if i > 0 {
+                old_w -= &self.cumulative_weights[i - 1];
+            }
+
+            total_weight -= &old_w;
+            total_weight += w;
+            prev_i = Some(i);
+        }
+        if total_weight <= zero {
+            return Err(WeightedError::AllWeightsZero);
+        }
+
+        // Update the weights. Because we checked all the preconditions in the
+        // previous loop, this should never panic.
+        let mut iter = new_weights.iter();
+
+        let mut prev_weight = zero.clone();
+        let mut next_new_weight = iter.next();
+        let &(first_new_index, _) = next_new_weight.unwrap();
+        let mut cumulative_weight = if first_new_index > 0 {
+            self.cumulative_weights[first_new_index - 1].clone()
+        } else {
+            zero.clone()
+        };
+        for i in first_new_index..self.cumulative_weights.len() {
+            match next_new_weight {
+                Some(&(j, w)) if i == j => {
+                    cumulative_weight += w;
+                    next_new_weight = iter.next();
+                }
+                _ => {
+                    let mut tmp = self.cumulative_weights[i].clone();
+                    tmp -= &prev_weight; // We know this is positive.
+                    cumulative_weight += &tmp;
+                }
+            }
+            prev_weight = cumulative_weight.clone();
+            core::mem::swap(&mut prev_weight, &mut self.cumulative_weights[i]);
+        }
+
+        self.total_weight = total_weight;
+        self.weight_distribution = X::Sampler::new(zero, self.total_weight.clone());
+
+        Ok(())
+    }
+}
+
+impl<X> Distribution<usize> for WeightedIndex<X>
+where X: SampleUniform + PartialOrd
+{
+    fn sample<R: Rng + ?Sized>(&self, rng: &mut R) -> usize {
+        use ::core::cmp::Ordering;
+        let chosen_weight = self.weight_distribution.sample(rng);
+        // Find the first item which has a weight *higher* than the chosen weight.
+        self.cumulative_weights
+            .binary_search_by(|w| {
+                if *w <= chosen_weight {
+                    Ordering::Less
+                } else {
+                    Ordering::Greater
+                }
+            })
+            .unwrap_err()
+    }
+}
+
+#[cfg(test)]
+mod test {
+    use super::*;
+
+    #[cfg(feature = "serde1")]
+    #[test]
+    fn test_weightedindex_serde1() {
+        let weighted_index = WeightedIndex::new(&[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]).unwrap();
+
+        let ser_weighted_index = bincode::serialize(&weighted_index).unwrap();
+        let de_weighted_index: WeightedIndex<i32> =
+            bincode::deserialize(&ser_weighted_index).unwrap();
+
+        assert_eq!(
+            de_weighted_index.cumulative_weights,
+            weighted_index.cumulative_weights
+        );
+        assert_eq!(de_weighted_index.total_weight, weighted_index.total_weight);
+    }
+
+    #[test]
+    fn test_accepting_nan(){
+        assert_eq!(
+            WeightedIndex::new(&[core::f32::NAN, 0.5]).unwrap_err(),
+            WeightedError::InvalidWeight,
+        );
+        assert_eq!(
+            WeightedIndex::new(&[core::f32::NAN]).unwrap_err(),
+            WeightedError::InvalidWeight,
+        );
+        assert_eq!(
+            WeightedIndex::new(&[0.5, core::f32::NAN]).unwrap_err(),
+            WeightedError::InvalidWeight,
+        );
+
+        assert_eq!(
+            WeightedIndex::new(&[0.5, 7.0])
+                .unwrap()
+                .update_weights(&[(0, &core::f32::NAN)])
+                .unwrap_err(),
+            WeightedError::InvalidWeight,
+        )
+    }
+
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_weightedindex() {
+        let mut r = crate::test::rng(700);
+        const N_REPS: u32 = 5000;
+        let weights = [1u32, 2, 3, 0, 5, 6, 7, 1, 2, 3, 4, 5, 6, 7];
+        let total_weight = weights.iter().sum::<u32>() as f32;
+
+        let verify = |result: [i32; 14]| {
+            for (i, count) in result.iter().enumerate() {
+                let exp = (weights[i] * N_REPS) as f32 / total_weight;
+                let mut err = (*count as f32 - exp).abs();
+                if err != 0.0 {
+                    err /= exp;
+                }
+                assert!(err <= 0.25);
+            }
+        };
+
+        // WeightedIndex from vec
+        let mut chosen = [0i32; 14];
+        let distr = WeightedIndex::new(weights.to_vec()).unwrap();
+        for _ in 0..N_REPS {
+            chosen[distr.sample(&mut r)] += 1;
+        }
+        verify(chosen);
+
+        // WeightedIndex from slice
+        chosen = [0i32; 14];
+        let distr = WeightedIndex::new(&weights[..]).unwrap();
+        for _ in 0..N_REPS {
+            chosen[distr.sample(&mut r)] += 1;
+        }
+        verify(chosen);
+
+        // WeightedIndex from iterator
+        chosen = [0i32; 14];
+        let distr = WeightedIndex::new(weights.iter()).unwrap();
+        for _ in 0..N_REPS {
+            chosen[distr.sample(&mut r)] += 1;
+        }
+        verify(chosen);
+
+        for _ in 0..5 {
+            assert_eq!(WeightedIndex::new(&[0, 1]).unwrap().sample(&mut r), 1);
+            assert_eq!(WeightedIndex::new(&[1, 0]).unwrap().sample(&mut r), 0);
+            assert_eq!(
+                WeightedIndex::new(&[0, 0, 0, 0, 10, 0])
+                    .unwrap()
+                    .sample(&mut r),
+                4
+            );
+        }
+
+        assert_eq!(
+            WeightedIndex::new(&[10][0..0]).unwrap_err(),
+            WeightedError::NoItem
+        );
+        assert_eq!(
+            WeightedIndex::new(&[0]).unwrap_err(),
+            WeightedError::AllWeightsZero
+        );
+        assert_eq!(
+            WeightedIndex::new(&[10, 20, -1, 30]).unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+        assert_eq!(
+            WeightedIndex::new(&[-10, 20, 1, 30]).unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+        assert_eq!(
+            WeightedIndex::new(&[-10]).unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+    }
+
+    #[test]
+    fn test_update_weights() {
+        let data = [
+            (
+                &[10u32, 2, 3, 4][..],
+                &[(1, &100), (2, &4)][..], // positive change
+                &[10, 100, 4, 4][..],
+            ),
+            (
+                &[1u32, 2, 3, 0, 5, 6, 7, 1, 2, 3, 4, 5, 6, 7][..],
+                &[(2, &1), (5, &1), (13, &100)][..], // negative change and last element
+                &[1u32, 2, 1, 0, 5, 1, 7, 1, 2, 3, 4, 5, 6, 100][..],
+            ),
+        ];
+
+        for (weights, update, expected_weights) in data.iter() {
+            let total_weight = weights.iter().sum::<u32>();
+            let mut distr = WeightedIndex::new(weights.to_vec()).unwrap();
+            assert_eq!(distr.total_weight, total_weight);
+
+            distr.update_weights(update).unwrap();
+            let expected_total_weight = expected_weights.iter().sum::<u32>();
+            let expected_distr = WeightedIndex::new(expected_weights.to_vec()).unwrap();
+            assert_eq!(distr.total_weight, expected_total_weight);
+            assert_eq!(distr.total_weight, expected_distr.total_weight);
+            assert_eq!(distr.cumulative_weights, expected_distr.cumulative_weights);
+        }
+    }
+
+    #[test]
+    fn value_stability() {
+        fn test_samples<X: SampleUniform + PartialOrd, I>(
+            weights: I, buf: &mut [usize], expected: &[usize],
+        ) where
+            I: IntoIterator,
+            I::Item: SampleBorrow<X>,
+            X: for<'a> ::core::ops::AddAssign<&'a X> + Clone + Default,
+        {
+            assert_eq!(buf.len(), expected.len());
+            let distr = WeightedIndex::new(weights).unwrap();
+            let mut rng = crate::test::rng(701);
+            for r in buf.iter_mut() {
+                *r = rng.sample(&distr);
+            }
+            assert_eq!(buf, expected);
+        }
+
+        let mut buf = [0; 10];
+        test_samples(&[1i32, 1, 1, 1, 1, 1, 1, 1, 1], &mut buf, &[
+            0, 6, 2, 6, 3, 4, 7, 8, 2, 5,
+        ]);
+        test_samples(&[0.7f32, 0.1, 0.1, 0.1], &mut buf, &[
+            0, 0, 0, 1, 0, 0, 2, 3, 0, 0,
+        ]);
+        test_samples(&[1.0f64, 0.999, 0.998, 0.997], &mut buf, &[
+            2, 2, 1, 3, 2, 1, 3, 3, 2, 1,
+        ]);
+    }
+
+    #[test]
+    fn weighted_index_distributions_can_be_compared() {
+        assert_eq!(WeightedIndex::new(&[1, 2]), WeightedIndex::new(&[1, 2]));
+    }
+}
+
+/// Error type returned from `WeightedIndex::new`.
+#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+#[derive(Debug, Clone, Copy, PartialEq, Eq)]
+pub enum WeightedError {
+    /// The provided weight collection contains no items.
+    NoItem,
+
+    /// A weight is either less than zero, greater than the supported maximum,
+    /// NaN, or otherwise invalid.
+    InvalidWeight,
+
+    /// All items in the provided weight collection are zero.
+    AllWeightsZero,
+
+    /// Too many weights are provided (length greater than `u32::MAX`)
+    TooMany,
+}
+
+#[cfg(feature = "std")]
+impl std::error::Error for WeightedError {}
+
+impl fmt::Display for WeightedError {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        f.write_str(match *self {
+            WeightedError::NoItem => "No weights provided in distribution",
+            WeightedError::InvalidWeight => "A weight is invalid in distribution",
+            WeightedError::AllWeightsZero => "All weights are zero in distribution",
+            WeightedError::TooMany => "Too many weights (hit u32::MAX) in distribution",
+        })
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/lib.rs.html new file mode 100644 index 0000000..d4db1df --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/lib.rs.html @@ -0,0 +1,431 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013-2017 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Utilities for random number generation
+//!
+//! Rand provides utilities to generate random numbers, to convert them to
+//! useful types and distributions, and some randomness-related algorithms.
+//!
+//! # Quick Start
+//!
+//! To get you started quickly, the easiest and highest-level way to get
+//! a random value is to use [`random()`]; alternatively you can use
+//! [`thread_rng()`]. The [`Rng`] trait provides a useful API on all RNGs, while
+//! the [`distributions`] and [`seq`] modules provide further
+//! functionality on top of RNGs.
+//!
+//! ```
+//! use rand::prelude::*;
+//!
+//! if rand::random() { // generates a boolean
+//!     // Try printing a random unicode code point (probably a bad idea)!
+//!     println!("char: {}", rand::random::<char>());
+//! }
+//!
+//! let mut rng = rand::thread_rng();
+//! let y: f64 = rng.gen(); // generates a float between 0 and 1
+//!
+//! let mut nums: Vec<i32> = (1..100).collect();
+//! nums.shuffle(&mut rng);
+//! ```
+//!
+//! # The Book
+//!
+//! For the user guide and further documentation, please read
+//! [The Rust Rand Book](https://rust-random.github.io/book).
+
+#![doc(
+    html_logo_url = "https://www.rust-lang.org/logos/rust-logo-128x128-blk.png",
+    html_favicon_url = "https://www.rust-lang.org/favicon.ico",
+    html_root_url = "https://rust-random.github.io/rand/"
+)]
+#![deny(missing_docs)]
+#![deny(missing_debug_implementations)]
+#![doc(test(attr(allow(unused_variables), deny(warnings))))]
+#![no_std]
+#![cfg_attr(feature = "simd_support", feature(stdsimd))]
+#![cfg_attr(doc_cfg, feature(doc_cfg))]
+#![allow(
+    clippy::float_cmp,
+    clippy::neg_cmp_op_on_partial_ord,
+)]
+
+#[cfg(feature = "std")] extern crate std;
+#[cfg(feature = "alloc")] extern crate alloc;
+
+#[allow(unused)]
+macro_rules! trace { ($($x:tt)*) => (
+    #[cfg(feature = "log")] {
+        log::trace!($($x)*)
+    }
+) }
+#[allow(unused)]
+macro_rules! debug { ($($x:tt)*) => (
+    #[cfg(feature = "log")] {
+        log::debug!($($x)*)
+    }
+) }
+#[allow(unused)]
+macro_rules! info { ($($x:tt)*) => (
+    #[cfg(feature = "log")] {
+        log::info!($($x)*)
+    }
+) }
+#[allow(unused)]
+macro_rules! warn { ($($x:tt)*) => (
+    #[cfg(feature = "log")] {
+        log::warn!($($x)*)
+    }
+) }
+#[allow(unused)]
+macro_rules! error { ($($x:tt)*) => (
+    #[cfg(feature = "log")] {
+        log::error!($($x)*)
+    }
+) }
+
+// Re-exports from rand_core
+pub use rand_core::{CryptoRng, Error, RngCore, SeedableRng};
+
+// Public modules
+pub mod distributions;
+pub mod prelude;
+mod rng;
+pub mod rngs;
+pub mod seq;
+
+// Public exports
+#[cfg(all(feature = "std", feature = "std_rng"))]
+pub use crate::rngs::thread::thread_rng;
+pub use rng::{Fill, Rng};
+
+#[cfg(all(feature = "std", feature = "std_rng"))]
+use crate::distributions::{Distribution, Standard};
+
+/// Generates a random value using the thread-local random number generator.
+///
+/// This is simply a shortcut for `thread_rng().gen()`. See [`thread_rng`] for
+/// documentation of the entropy source and [`Standard`] for documentation of
+/// distributions and type-specific generation.
+///
+/// # Provided implementations
+///
+/// The following types have provided implementations that
+/// generate values with the following ranges and distributions:
+///
+/// * Integers (`i32`, `u32`, `isize`, `usize`, etc.): Uniformly distributed
+///   over all values of the type.
+/// * `char`: Uniformly distributed over all Unicode scalar values, i.e. all
+///   code points in the range `0...0x10_FFFF`, except for the range
+///   `0xD800...0xDFFF` (the surrogate code points). This includes
+///   unassigned/reserved code points.
+/// * `bool`: Generates `false` or `true`, each with probability 0.5.
+/// * Floating point types (`f32` and `f64`): Uniformly distributed in the
+///   half-open range `[0, 1)`. See notes below.
+/// * Wrapping integers (`Wrapping<T>`), besides the type identical to their
+///   normal integer variants.
+///
+/// Also supported is the generation of the following
+/// compound types where all component types are supported:
+///
+/// *   Tuples (up to 12 elements): each element is generated sequentially.
+/// *   Arrays (up to 32 elements): each element is generated sequentially;
+///     see also [`Rng::fill`] which supports arbitrary array length for integer
+///     types and tends to be faster for `u32` and smaller types.
+/// *   `Option<T>` first generates a `bool`, and if true generates and returns
+///     `Some(value)` where `value: T`, otherwise returning `None`.
+///
+/// # Examples
+///
+/// ```
+/// let x = rand::random::<u8>();
+/// println!("{}", x);
+///
+/// let y = rand::random::<f64>();
+/// println!("{}", y);
+///
+/// if rand::random() { // generates a boolean
+///     println!("Better lucky than good!");
+/// }
+/// ```
+///
+/// If you're calling `random()` in a loop, caching the generator as in the
+/// following example can increase performance.
+///
+/// ```
+/// use rand::Rng;
+///
+/// let mut v = vec![1, 2, 3];
+///
+/// for x in v.iter_mut() {
+///     *x = rand::random()
+/// }
+///
+/// // can be made faster by caching thread_rng
+///
+/// let mut rng = rand::thread_rng();
+///
+/// for x in v.iter_mut() {
+///     *x = rng.gen();
+/// }
+/// ```
+///
+/// [`Standard`]: distributions::Standard
+#[cfg(all(feature = "std", feature = "std_rng"))]
+#[cfg_attr(doc_cfg, doc(cfg(all(feature = "std", feature = "std_rng"))))]
+#[inline]
+pub fn random<T>() -> T
+where Standard: Distribution<T> {
+    thread_rng().gen()
+}
+
+#[cfg(test)]
+mod test {
+    use super::*;
+
+    /// Construct a deterministic RNG with the given seed
+    pub fn rng(seed: u64) -> impl RngCore {
+        // For tests, we want a statistically good, fast, reproducible RNG.
+        // PCG32 will do fine, and will be easy to embed if we ever need to.
+        const INC: u64 = 11634580027462260723;
+        rand_pcg::Pcg32::new(seed, INC)
+    }
+
+    #[test]
+    #[cfg(all(feature = "std", feature = "std_rng"))]
+    fn test_random() {
+        let _n: usize = random();
+        let _f: f32 = random();
+        let _o: Option<Option<i8>> = random();
+        #[allow(clippy::type_complexity)]
+        let _many: (
+            (),
+            (usize, isize, Option<(u32, (bool,))>),
+            (u8, i8, u16, i16, u32, i32, u64, i64),
+            (f32, (f64, (f64,))),
+        ) = random();
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/prelude.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/prelude.rs.html new file mode 100644 index 0000000..777b203 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/prelude.rs.html @@ -0,0 +1,71 @@ +prelude.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Convenience re-export of common members
+//!
+//! Like the standard library's prelude, this module simplifies importing of
+//! common items. Unlike the standard prelude, the contents of this module must
+//! be imported manually:
+//!
+//! ```
+//! use rand::prelude::*;
+//! # let mut r = StdRng::from_rng(thread_rng()).unwrap();
+//! # let _: f32 = r.gen();
+//! ```
+
+#[doc(no_inline)] pub use crate::distributions::Distribution;
+#[cfg(feature = "small_rng")]
+#[doc(no_inline)]
+pub use crate::rngs::SmallRng;
+#[cfg(feature = "std_rng")]
+#[doc(no_inline)] pub use crate::rngs::StdRng;
+#[doc(no_inline)]
+#[cfg(all(feature = "std", feature = "std_rng"))]
+pub use crate::rngs::ThreadRng;
+#[doc(no_inline)] pub use crate::seq::{IteratorRandom, SliceRandom};
+#[doc(no_inline)]
+#[cfg(all(feature = "std", feature = "std_rng"))]
+pub use crate::{random, thread_rng};
+#[doc(no_inline)] pub use crate::{CryptoRng, Rng, RngCore, SeedableRng};
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rng.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rng.rs.html new file mode 100644 index 0000000..1e28705 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rng.rs.html @@ -0,0 +1,1203 @@ +rng.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013-2017 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! [`Rng`] trait
+
+use rand_core::{Error, RngCore};
+use crate::distributions::uniform::{SampleRange, SampleUniform};
+use crate::distributions::{self, Distribution, Standard};
+use core::num::Wrapping;
+use core::{mem, slice};
+
+/// An automatically-implemented extension trait on [`RngCore`] providing high-level
+/// generic methods for sampling values and other convenience methods.
+///
+/// This is the primary trait to use when generating random values.
+///
+/// # Generic usage
+///
+/// The basic pattern is `fn foo<R: Rng + ?Sized>(rng: &mut R)`. Some
+/// things are worth noting here:
+///
+/// - Since `Rng: RngCore` and every `RngCore` implements `Rng`, it makes no
+///   difference whether we use `R: Rng` or `R: RngCore`.
+/// - The `+ ?Sized` un-bounding allows functions to be called directly on
+///   type-erased references; i.e. `foo(r)` where `r: &mut dyn RngCore`. Without
+///   this it would be necessary to write `foo(&mut r)`.
+///
+/// An alternative pattern is possible: `fn foo<R: Rng>(rng: R)`. This has some
+/// trade-offs. It allows the argument to be consumed directly without a `&mut`
+/// (which is how `from_rng(thread_rng())` works); also it still works directly
+/// on references (including type-erased references). Unfortunately within the
+/// function `foo` it is not known whether `rng` is a reference type or not,
+/// hence many uses of `rng` require an extra reference, either explicitly
+/// (`distr.sample(&mut rng)`) or implicitly (`rng.gen()`); one may hope the
+/// optimiser can remove redundant references later.
+///
+/// Example:
+///
+/// ```
+/// # use rand::thread_rng;
+/// use rand::Rng;
+///
+/// fn foo<R: Rng + ?Sized>(rng: &mut R) -> f32 {
+///     rng.gen()
+/// }
+///
+/// # let v = foo(&mut thread_rng());
+/// ```
+pub trait Rng: RngCore {
+    /// Return a random value supporting the [`Standard`] distribution.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut rng = thread_rng();
+    /// let x: u32 = rng.gen();
+    /// println!("{}", x);
+    /// println!("{:?}", rng.gen::<(f64, bool)>());
+    /// ```
+    ///
+    /// # Arrays and tuples
+    ///
+    /// The `rng.gen()` method is able to generate arrays (up to 32 elements)
+    /// and tuples (up to 12 elements), so long as all element types can be
+    /// generated.
+    /// When using `rustc` ≥ 1.51, enable the `min_const_gen` feature to support
+    /// arrays larger than 32 elements.
+    ///
+    /// For arrays of integers, especially for those with small element types
+    /// (< 64 bit), it will likely be faster to instead use [`Rng::fill`].
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut rng = thread_rng();
+    /// let tuple: (u8, i32, char) = rng.gen(); // arbitrary tuple support
+    ///
+    /// let arr1: [f32; 32] = rng.gen();        // array construction
+    /// let mut arr2 = [0u8; 128];
+    /// rng.fill(&mut arr2);                    // array fill
+    /// ```
+    ///
+    /// [`Standard`]: distributions::Standard
+    #[inline]
+    fn gen<T>(&mut self) -> T
+    where Standard: Distribution<T> {
+        Standard.sample(self)
+    }
+
+    /// Generate a random value in the given range.
+    ///
+    /// This function is optimised for the case that only a single sample is
+    /// made from the given range. See also the [`Uniform`] distribution
+    /// type which may be faster if sampling from the same range repeatedly.
+    ///
+    /// Only `gen_range(low..high)` and `gen_range(low..=high)` are supported.
+    ///
+    /// # Panics
+    ///
+    /// Panics if the range is empty.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut rng = thread_rng();
+    ///
+    /// // Exclusive range
+    /// let n: u32 = rng.gen_range(0..10);
+    /// println!("{}", n);
+    /// let m: f64 = rng.gen_range(-40.0..1.3e5);
+    /// println!("{}", m);
+    ///
+    /// // Inclusive range
+    /// let n: u32 = rng.gen_range(0..=10);
+    /// println!("{}", n);
+    /// ```
+    ///
+    /// [`Uniform`]: distributions::uniform::Uniform
+    fn gen_range<T, R>(&mut self, range: R) -> T
+    where
+        T: SampleUniform,
+        R: SampleRange<T>
+    {
+        assert!(!range.is_empty(), "cannot sample empty range");
+        range.sample_single(self)
+    }
+
+    /// Sample a new value, using the given distribution.
+    ///
+    /// ### Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    /// use rand::distributions::Uniform;
+    ///
+    /// let mut rng = thread_rng();
+    /// let x = rng.sample(Uniform::new(10u32, 15));
+    /// // Type annotation requires two types, the type and distribution; the
+    /// // distribution can be inferred.
+    /// let y = rng.sample::<u16, _>(Uniform::new(10, 15));
+    /// ```
+    fn sample<T, D: Distribution<T>>(&mut self, distr: D) -> T {
+        distr.sample(self)
+    }
+
+    /// Create an iterator that generates values using the given distribution.
+    ///
+    /// Note that this function takes its arguments by value. This works since
+    /// `(&mut R): Rng where R: Rng` and
+    /// `(&D): Distribution where D: Distribution`,
+    /// however borrowing is not automatic hence `rng.sample_iter(...)` may
+    /// need to be replaced with `(&mut rng).sample_iter(...)`.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    /// use rand::distributions::{Alphanumeric, Uniform, Standard};
+    ///
+    /// let mut rng = thread_rng();
+    ///
+    /// // Vec of 16 x f32:
+    /// let v: Vec<f32> = (&mut rng).sample_iter(Standard).take(16).collect();
+    ///
+    /// // String:
+    /// let s: String = (&mut rng).sample_iter(Alphanumeric)
+    ///     .take(7)
+    ///     .map(char::from)
+    ///     .collect();
+    ///
+    /// // Combined values
+    /// println!("{:?}", (&mut rng).sample_iter(Standard).take(5)
+    ///                              .collect::<Vec<(f64, bool)>>());
+    ///
+    /// // Dice-rolling:
+    /// let die_range = Uniform::new_inclusive(1, 6);
+    /// let mut roll_die = (&mut rng).sample_iter(die_range);
+    /// while roll_die.next().unwrap() != 6 {
+    ///     println!("Not a 6; rolling again!");
+    /// }
+    /// ```
+    fn sample_iter<T, D>(self, distr: D) -> distributions::DistIter<D, Self, T>
+    where
+        D: Distribution<T>,
+        Self: Sized,
+    {
+        distr.sample_iter(self)
+    }
+
+    /// Fill any type implementing [`Fill`] with random data
+    ///
+    /// The distribution is expected to be uniform with portable results, but
+    /// this cannot be guaranteed for third-party implementations.
+    ///
+    /// This is identical to [`try_fill`] except that it panics on error.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut arr = [0i8; 20];
+    /// thread_rng().fill(&mut arr[..]);
+    /// ```
+    ///
+    /// [`fill_bytes`]: RngCore::fill_bytes
+    /// [`try_fill`]: Rng::try_fill
+    fn fill<T: Fill + ?Sized>(&mut self, dest: &mut T) {
+        dest.try_fill(self).unwrap_or_else(|_| panic!("Rng::fill failed"))
+    }
+
+    /// Fill any type implementing [`Fill`] with random data
+    ///
+    /// The distribution is expected to be uniform with portable results, but
+    /// this cannot be guaranteed for third-party implementations.
+    ///
+    /// This is identical to [`fill`] except that it forwards errors.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// # use rand::Error;
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// # fn try_inner() -> Result<(), Error> {
+    /// let mut arr = [0u64; 4];
+    /// thread_rng().try_fill(&mut arr[..])?;
+    /// # Ok(())
+    /// # }
+    ///
+    /// # try_inner().unwrap()
+    /// ```
+    ///
+    /// [`try_fill_bytes`]: RngCore::try_fill_bytes
+    /// [`fill`]: Rng::fill
+    fn try_fill<T: Fill + ?Sized>(&mut self, dest: &mut T) -> Result<(), Error> {
+        dest.try_fill(self)
+    }
+
+    /// Return a bool with a probability `p` of being true.
+    ///
+    /// See also the [`Bernoulli`] distribution, which may be faster if
+    /// sampling from the same probability repeatedly.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut rng = thread_rng();
+    /// println!("{}", rng.gen_bool(1.0 / 3.0));
+    /// ```
+    ///
+    /// # Panics
+    ///
+    /// If `p < 0` or `p > 1`.
+    ///
+    /// [`Bernoulli`]: distributions::Bernoulli
+    #[inline]
+    fn gen_bool(&mut self, p: f64) -> bool {
+        let d = distributions::Bernoulli::new(p).unwrap();
+        self.sample(d)
+    }
+
+    /// Return a bool with a probability of `numerator/denominator` of being
+    /// true. I.e. `gen_ratio(2, 3)` has chance of 2 in 3, or about 67%, of
+    /// returning true. If `numerator == denominator`, then the returned value
+    /// is guaranteed to be `true`. If `numerator == 0`, then the returned
+    /// value is guaranteed to be `false`.
+    ///
+    /// See also the [`Bernoulli`] distribution, which may be faster if
+    /// sampling from the same `numerator` and `denominator` repeatedly.
+    ///
+    /// # Panics
+    ///
+    /// If `denominator == 0` or `numerator > denominator`.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::{thread_rng, Rng};
+    ///
+    /// let mut rng = thread_rng();
+    /// println!("{}", rng.gen_ratio(2, 3));
+    /// ```
+    ///
+    /// [`Bernoulli`]: distributions::Bernoulli
+    #[inline]
+    fn gen_ratio(&mut self, numerator: u32, denominator: u32) -> bool {
+        let d = distributions::Bernoulli::from_ratio(numerator, denominator).unwrap();
+        self.sample(d)
+    }
+}
+
+impl<R: RngCore + ?Sized> Rng for R {}
+
+/// Types which may be filled with random data
+///
+/// This trait allows arrays to be efficiently filled with random data.
+///
+/// Implementations are expected to be portable across machines unless
+/// clearly documented otherwise (see the
+/// [Chapter on Portability](https://rust-random.github.io/book/portability.html)).
+pub trait Fill {
+    /// Fill self with random data
+    fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error>;
+}
+
+macro_rules! impl_fill_each {
+    () => {};
+    ($t:ty) => {
+        impl Fill for [$t] {
+            fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+                for elt in self.iter_mut() {
+                    *elt = rng.gen();
+                }
+                Ok(())
+            }
+        }
+    };
+    ($t:ty, $($tt:ty,)*) => {
+        impl_fill_each!($t);
+        impl_fill_each!($($tt,)*);
+    };
+}
+
+impl_fill_each!(bool, char, f32, f64,);
+
+impl Fill for [u8] {
+    fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+        rng.try_fill_bytes(self)
+    }
+}
+
+macro_rules! impl_fill {
+    () => {};
+    ($t:ty) => {
+        impl Fill for [$t] {
+            #[inline(never)] // in micro benchmarks, this improves performance
+            fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+                if self.len() > 0 {
+                    rng.try_fill_bytes(unsafe {
+                        slice::from_raw_parts_mut(self.as_mut_ptr()
+                            as *mut u8,
+                            self.len() * mem::size_of::<$t>()
+                        )
+                    })?;
+                    for x in self {
+                        *x = x.to_le();
+                    }
+                }
+                Ok(())
+            }
+        }
+
+        impl Fill for [Wrapping<$t>] {
+            #[inline(never)]
+            fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+                if self.len() > 0 {
+                    rng.try_fill_bytes(unsafe {
+                        slice::from_raw_parts_mut(self.as_mut_ptr()
+                            as *mut u8,
+                            self.len() * mem::size_of::<$t>()
+                        )
+                    })?;
+                    for x in self {
+                    *x = Wrapping(x.0.to_le());
+                    }
+                }
+                Ok(())
+            }
+        }
+    };
+    ($t:ty, $($tt:ty,)*) => {
+        impl_fill!($t);
+        // TODO: this could replace above impl once Rust #32463 is fixed
+        // impl_fill!(Wrapping<$t>);
+        impl_fill!($($tt,)*);
+    }
+}
+
+impl_fill!(u16, u32, u64, usize, u128,);
+impl_fill!(i8, i16, i32, i64, isize, i128,);
+
+#[cfg_attr(doc_cfg, doc(cfg(feature = "min_const_gen")))]
+#[cfg(feature = "min_const_gen")]
+impl<T, const N: usize> Fill for [T; N]
+where [T]: Fill
+{
+    fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+        self[..].try_fill(rng)
+    }
+}
+
+#[cfg(not(feature = "min_const_gen"))]
+macro_rules! impl_fill_arrays {
+    ($n:expr,) => {};
+    ($n:expr, $N:ident) => {
+        impl<T> Fill for [T; $n] where [T]: Fill {
+            fn try_fill<R: Rng + ?Sized>(&mut self, rng: &mut R) -> Result<(), Error> {
+                self[..].try_fill(rng)
+            }
+        }
+    };
+    ($n:expr, $N:ident, $($NN:ident,)*) => {
+        impl_fill_arrays!($n, $N);
+        impl_fill_arrays!($n - 1, $($NN,)*);
+    };
+    (!div $n:expr,) => {};
+    (!div $n:expr, $N:ident, $($NN:ident,)*) => {
+        impl_fill_arrays!($n, $N);
+        impl_fill_arrays!(!div $n / 2, $($NN,)*);
+    };
+}
+#[cfg(not(feature = "min_const_gen"))]
+#[rustfmt::skip]
+impl_fill_arrays!(32, N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,N,);
+#[cfg(not(feature = "min_const_gen"))]
+impl_fill_arrays!(!div 4096, N,N,N,N,N,N,N,);
+
+#[cfg(test)]
+mod test {
+    use super::*;
+    use crate::test::rng;
+    use crate::rngs::mock::StepRng;
+    #[cfg(feature = "alloc")] use alloc::boxed::Box;
+
+    #[test]
+    fn test_fill_bytes_default() {
+        let mut r = StepRng::new(0x11_22_33_44_55_66_77_88, 0);
+
+        // check every remainder mod 8, both in small and big vectors.
+        let lengths = [0, 1, 2, 3, 4, 5, 6, 7, 80, 81, 82, 83, 84, 85, 86, 87];
+        for &n in lengths.iter() {
+            let mut buffer = [0u8; 87];
+            let v = &mut buffer[0..n];
+            r.fill_bytes(v);
+
+            // use this to get nicer error messages.
+            for (i, &byte) in v.iter().enumerate() {
+                if byte == 0 {
+                    panic!("byte {} of {} is zero", i, n)
+                }
+            }
+        }
+    }
+
+    #[test]
+    fn test_fill() {
+        let x = 9041086907909331047; // a random u64
+        let mut rng = StepRng::new(x, 0);
+
+        // Convert to byte sequence and back to u64; byte-swap twice if BE.
+        let mut array = [0u64; 2];
+        rng.fill(&mut array[..]);
+        assert_eq!(array, [x, x]);
+        assert_eq!(rng.next_u64(), x);
+
+        // Convert to bytes then u32 in LE order
+        let mut array = [0u32; 2];
+        rng.fill(&mut array[..]);
+        assert_eq!(array, [x as u32, (x >> 32) as u32]);
+        assert_eq!(rng.next_u32(), x as u32);
+
+        // Check equivalence using wrapped arrays
+        let mut warray = [Wrapping(0u32); 2];
+        rng.fill(&mut warray[..]);
+        assert_eq!(array[0], warray[0].0);
+        assert_eq!(array[1], warray[1].0);
+
+        // Check equivalence for generated floats
+        let mut array = [0f32; 2];
+        rng.fill(&mut array);
+        let gen: [f32; 2] = rng.gen();
+        assert_eq!(array, gen);
+    }
+
+    #[test]
+    fn test_fill_empty() {
+        let mut array = [0u32; 0];
+        let mut rng = StepRng::new(0, 1);
+        rng.fill(&mut array);
+        rng.fill(&mut array[..]);
+    }
+
+    #[test]
+    fn test_gen_range_int() {
+        let mut r = rng(101);
+        for _ in 0..1000 {
+            let a = r.gen_range(-4711..17);
+            assert!((-4711..17).contains(&a));
+            let a: i8 = r.gen_range(-3..42);
+            assert!((-3..42).contains(&a));
+            let a: u16 = r.gen_range(10..99);
+            assert!((10..99).contains(&a));
+            let a: i32 = r.gen_range(-100..2000);
+            assert!((-100..2000).contains(&a));
+            let a: u32 = r.gen_range(12..=24);
+            assert!((12..=24).contains(&a));
+
+            assert_eq!(r.gen_range(0u32..1), 0u32);
+            assert_eq!(r.gen_range(-12i64..-11), -12i64);
+            assert_eq!(r.gen_range(3_000_000..3_000_001), 3_000_000);
+        }
+    }
+
+    #[test]
+    fn test_gen_range_float() {
+        let mut r = rng(101);
+        for _ in 0..1000 {
+            let a = r.gen_range(-4.5..1.7);
+            assert!((-4.5..1.7).contains(&a));
+            let a = r.gen_range(-1.1..=-0.3);
+            assert!((-1.1..=-0.3).contains(&a));
+
+            assert_eq!(r.gen_range(0.0f32..=0.0), 0.);
+            assert_eq!(r.gen_range(-11.0..=-11.0), -11.);
+            assert_eq!(r.gen_range(3_000_000.0..=3_000_000.0), 3_000_000.);
+        }
+    }
+
+    #[test]
+    #[should_panic]
+    fn test_gen_range_panic_int() {
+        #![allow(clippy::reversed_empty_ranges)]
+        let mut r = rng(102);
+        r.gen_range(5..-2);
+    }
+
+    #[test]
+    #[should_panic]
+    fn test_gen_range_panic_usize() {
+        #![allow(clippy::reversed_empty_ranges)]
+        let mut r = rng(103);
+        r.gen_range(5..2);
+    }
+
+    #[test]
+    fn test_gen_bool() {
+        #![allow(clippy::bool_assert_comparison)]
+
+        let mut r = rng(105);
+        for _ in 0..5 {
+            assert_eq!(r.gen_bool(0.0), false);
+            assert_eq!(r.gen_bool(1.0), true);
+        }
+    }
+
+    #[test]
+    fn test_rng_trait_object() {
+        use crate::distributions::{Distribution, Standard};
+        let mut rng = rng(109);
+        let mut r = &mut rng as &mut dyn RngCore;
+        r.next_u32();
+        r.gen::<i32>();
+        assert_eq!(r.gen_range(0..1), 0);
+        let _c: u8 = Standard.sample(&mut r);
+    }
+
+    #[test]
+    #[cfg(feature = "alloc")]
+    fn test_rng_boxed_trait() {
+        use crate::distributions::{Distribution, Standard};
+        let rng = rng(110);
+        let mut r = Box::new(rng) as Box<dyn RngCore>;
+        r.next_u32();
+        r.gen::<i32>();
+        assert_eq!(r.gen_range(0..1), 0);
+        let _c: u8 = Standard.sample(&mut r);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_gen_ratio_average() {
+        const NUM: u32 = 3;
+        const DENOM: u32 = 10;
+        const N: u32 = 100_000;
+
+        let mut sum: u32 = 0;
+        let mut rng = rng(111);
+        for _ in 0..N {
+            if rng.gen_ratio(NUM, DENOM) {
+                sum += 1;
+            }
+        }
+        // Have Binomial(N, NUM/DENOM) distribution
+        let expected = (NUM * N) / DENOM; // exact integer
+        assert!(((sum - expected) as i32).abs() < 500);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/mod.rs.html new file mode 100644 index 0000000..a272f93 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/mod.rs.html @@ -0,0 +1,35 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Wrappers / adapters forming RNGs
+
+mod read;
+mod reseeding;
+
+#[allow(deprecated)]
+pub use self::read::{ReadError, ReadRng};
+pub use self::reseeding::ReseedingRng;
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/read.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/read.rs.html new file mode 100644 index 0000000..d16c0fb --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/read.rs.html @@ -0,0 +1,303 @@ +read.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! A wrapper around any Read to treat it as an RNG.
+
+#![allow(deprecated)]
+
+use std::fmt;
+use std::io::Read;
+
+use rand_core::{impls, Error, RngCore};
+
+
+/// An RNG that reads random bytes straight from any type supporting
+/// [`std::io::Read`], for example files.
+///
+/// This will work best with an infinite reader, but that is not required.
+///
+/// This can be used with `/dev/urandom` on Unix but it is recommended to use
+/// [`OsRng`] instead.
+///
+/// # Panics
+///
+/// `ReadRng` uses [`std::io::Read::read_exact`], which retries on interrupts.
+/// All other errors from the underlying reader, including when it does not
+/// have enough data, will only be reported through [`try_fill_bytes`].
+/// The other [`RngCore`] methods will panic in case of an error.
+///
+/// [`OsRng`]: crate::rngs::OsRng
+/// [`try_fill_bytes`]: RngCore::try_fill_bytes
+#[derive(Debug)]
+#[deprecated(since="0.8.4", note="removal due to lack of usage")]
+pub struct ReadRng<R> {
+    reader: R,
+}
+
+impl<R: Read> ReadRng<R> {
+    /// Create a new `ReadRng` from a `Read`.
+    pub fn new(r: R) -> ReadRng<R> {
+        ReadRng { reader: r }
+    }
+}
+
+impl<R: Read> RngCore for ReadRng<R> {
+    fn next_u32(&mut self) -> u32 {
+        impls::next_u32_via_fill(self)
+    }
+
+    fn next_u64(&mut self) -> u64 {
+        impls::next_u64_via_fill(self)
+    }
+
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        self.try_fill_bytes(dest).unwrap_or_else(|err| {
+            panic!(
+                "reading random bytes from Read implementation failed; error: {}",
+                err
+            )
+        });
+    }
+
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        if dest.is_empty() {
+            return Ok(());
+        }
+        // Use `std::io::read_exact`, which retries on `ErrorKind::Interrupted`.
+        self.reader
+            .read_exact(dest)
+            .map_err(|e| Error::new(ReadError(e)))
+    }
+}
+
+/// `ReadRng` error type
+#[derive(Debug)]
+#[deprecated(since="0.8.4")]
+pub struct ReadError(std::io::Error);
+
+impl fmt::Display for ReadError {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        write!(f, "ReadError: {}", self.0)
+    }
+}
+
+impl std::error::Error for ReadError {
+    fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
+        Some(&self.0)
+    }
+}
+
+
+#[cfg(test)]
+mod test {
+    use std::println;
+
+    use super::ReadRng;
+    use crate::RngCore;
+
+    #[test]
+    fn test_reader_rng_u64() {
+        // transmute from the target to avoid endianness concerns.
+        #[rustfmt::skip]
+        let v = [0u8, 0, 0, 0, 0, 0, 0, 1,
+                 0,   4, 0, 0, 3, 0, 0, 2,
+                 5,   0, 0, 0, 0, 0, 0, 0];
+        let mut rng = ReadRng::new(&v[..]);
+
+        assert_eq!(rng.next_u64(), 1 << 56);
+        assert_eq!(rng.next_u64(), (2 << 56) + (3 << 32) + (4 << 8));
+        assert_eq!(rng.next_u64(), 5);
+    }
+
+    #[test]
+    fn test_reader_rng_u32() {
+        let v = [0u8, 0, 0, 1, 0, 0, 2, 0, 3, 0, 0, 0];
+        let mut rng = ReadRng::new(&v[..]);
+
+        assert_eq!(rng.next_u32(), 1 << 24);
+        assert_eq!(rng.next_u32(), 2 << 16);
+        assert_eq!(rng.next_u32(), 3);
+    }
+
+    #[test]
+    fn test_reader_rng_fill_bytes() {
+        let v = [1u8, 2, 3, 4, 5, 6, 7, 8];
+        let mut w = [0u8; 8];
+
+        let mut rng = ReadRng::new(&v[..]);
+        rng.fill_bytes(&mut w);
+
+        assert!(v == w);
+    }
+
+    #[test]
+    fn test_reader_rng_insufficient_bytes() {
+        let v = [1u8, 2, 3, 4, 5, 6, 7, 8];
+        let mut w = [0u8; 9];
+
+        let mut rng = ReadRng::new(&v[..]);
+
+        let result = rng.try_fill_bytes(&mut w);
+        assert!(result.is_err());
+        println!("Error: {}", result.unwrap_err());
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/reseeding.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/reseeding.rs.html new file mode 100644 index 0000000..93f4eaf --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/adapter/reseeding.rs.html @@ -0,0 +1,775 @@ +reseeding.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2013 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! A wrapper around another PRNG that reseeds it after it
+//! generates a certain number of random bytes.
+
+use core::mem::size_of;
+
+use rand_core::block::{BlockRng, BlockRngCore};
+use rand_core::{CryptoRng, Error, RngCore, SeedableRng};
+
+/// A wrapper around any PRNG that implements [`BlockRngCore`], that adds the
+/// ability to reseed it.
+///
+/// `ReseedingRng` reseeds the underlying PRNG in the following cases:
+///
+/// - On a manual call to [`reseed()`].
+/// - After `clone()`, the clone will be reseeded on first use.
+/// - When a process is forked on UNIX, the RNGs in both the parent and child
+///   processes will be reseeded just before the next call to
+///   [`BlockRngCore::generate`], i.e. "soon". For ChaCha and Hc128 this is a
+///   maximum of fifteen `u32` values before reseeding.
+/// - After the PRNG has generated a configurable number of random bytes.
+///
+/// # When should reseeding after a fixed number of generated bytes be used?
+///
+/// Reseeding after a fixed number of generated bytes is never strictly
+/// *necessary*. Cryptographic PRNGs don't have a limited number of bytes they
+/// can output, or at least not a limit reachable in any practical way. There is
+/// no such thing as 'running out of entropy'.
+///
+/// Occasionally reseeding can be seen as some form of 'security in depth'. Even
+/// if in the future a cryptographic weakness is found in the CSPRNG being used,
+/// or a flaw in the implementation, occasionally reseeding should make
+/// exploiting it much more difficult or even impossible.
+///
+/// Use [`ReseedingRng::new`] with a `threshold` of `0` to disable reseeding
+/// after a fixed number of generated bytes.
+///
+/// # Limitations
+///
+/// It is recommended that a `ReseedingRng` (including `ThreadRng`) not be used
+/// from a fork handler.
+/// Use `OsRng` or `getrandom`, or defer your use of the RNG until later.
+///
+/// # Error handling
+///
+/// Although unlikely, reseeding the wrapped PRNG can fail. `ReseedingRng` will
+/// never panic but try to handle the error intelligently through some
+/// combination of retrying and delaying reseeding until later.
+/// If handling the source error fails `ReseedingRng` will continue generating
+/// data from the wrapped PRNG without reseeding.
+///
+/// Manually calling [`reseed()`] will not have this retry or delay logic, but
+/// reports the error.
+///
+/// # Example
+///
+/// ```
+/// use rand::prelude::*;
+/// use rand_chacha::ChaCha20Core; // Internal part of ChaChaRng that
+///                              // implements BlockRngCore
+/// use rand::rngs::OsRng;
+/// use rand::rngs::adapter::ReseedingRng;
+///
+/// let prng = ChaCha20Core::from_entropy();
+/// let mut reseeding_rng = ReseedingRng::new(prng, 0, OsRng);
+///
+/// println!("{}", reseeding_rng.gen::<u64>());
+///
+/// let mut cloned_rng = reseeding_rng.clone();
+/// assert!(reseeding_rng.gen::<u64>() != cloned_rng.gen::<u64>());
+/// ```
+///
+/// [`BlockRngCore`]: rand_core::block::BlockRngCore
+/// [`ReseedingRng::new`]: ReseedingRng::new
+/// [`reseed()`]: ReseedingRng::reseed
+#[derive(Debug)]
+pub struct ReseedingRng<R, Rsdr>(BlockRng<ReseedingCore<R, Rsdr>>)
+where
+    R: BlockRngCore + SeedableRng,
+    Rsdr: RngCore;
+
+impl<R, Rsdr> ReseedingRng<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng,
+    Rsdr: RngCore,
+{
+    /// Create a new `ReseedingRng` from an existing PRNG, combined with a RNG
+    /// to use as reseeder.
+    ///
+    /// `threshold` sets the number of generated bytes after which to reseed the
+    /// PRNG. Set it to zero to never reseed based on the number of generated
+    /// values.
+    pub fn new(rng: R, threshold: u64, reseeder: Rsdr) -> Self {
+        ReseedingRng(BlockRng::new(ReseedingCore::new(rng, threshold, reseeder)))
+    }
+
+    /// Reseed the internal PRNG.
+    pub fn reseed(&mut self) -> Result<(), Error> {
+        self.0.core.reseed()
+    }
+}
+
+// TODO: this should be implemented for any type where the inner type
+// implements RngCore, but we can't specify that because ReseedingCore is private
+impl<R, Rsdr: RngCore> RngCore for ReseedingRng<R, Rsdr>
+where
+    R: BlockRngCore<Item = u32> + SeedableRng,
+    <R as BlockRngCore>::Results: AsRef<[u32]> + AsMut<[u32]>,
+{
+    #[inline(always)]
+    fn next_u32(&mut self) -> u32 {
+        self.0.next_u32()
+    }
+
+    #[inline(always)]
+    fn next_u64(&mut self) -> u64 {
+        self.0.next_u64()
+    }
+
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        self.0.fill_bytes(dest)
+    }
+
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        self.0.try_fill_bytes(dest)
+    }
+}
+
+impl<R, Rsdr> Clone for ReseedingRng<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng + Clone,
+    Rsdr: RngCore + Clone,
+{
+    fn clone(&self) -> ReseedingRng<R, Rsdr> {
+        // Recreating `BlockRng` seems easier than cloning it and resetting
+        // the index.
+        ReseedingRng(BlockRng::new(self.0.core.clone()))
+    }
+}
+
+impl<R, Rsdr> CryptoRng for ReseedingRng<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng + CryptoRng,
+    Rsdr: RngCore + CryptoRng,
+{
+}
+
+#[derive(Debug)]
+struct ReseedingCore<R, Rsdr> {
+    inner: R,
+    reseeder: Rsdr,
+    threshold: i64,
+    bytes_until_reseed: i64,
+    fork_counter: usize,
+}
+
+impl<R, Rsdr> BlockRngCore for ReseedingCore<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng,
+    Rsdr: RngCore,
+{
+    type Item = <R as BlockRngCore>::Item;
+    type Results = <R as BlockRngCore>::Results;
+
+    fn generate(&mut self, results: &mut Self::Results) {
+        let global_fork_counter = fork::get_fork_counter();
+        if self.bytes_until_reseed <= 0 || self.is_forked(global_fork_counter) {
+            // We get better performance by not calling only `reseed` here
+            // and continuing with the rest of the function, but by directly
+            // returning from a non-inlined function.
+            return self.reseed_and_generate(results, global_fork_counter);
+        }
+        let num_bytes = results.as_ref().len() * size_of::<Self::Item>();
+        self.bytes_until_reseed -= num_bytes as i64;
+        self.inner.generate(results);
+    }
+}
+
+impl<R, Rsdr> ReseedingCore<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng,
+    Rsdr: RngCore,
+{
+    /// Create a new `ReseedingCore`.
+    fn new(rng: R, threshold: u64, reseeder: Rsdr) -> Self {
+        use ::core::i64::MAX;
+        fork::register_fork_handler();
+
+        // Because generating more values than `i64::MAX` takes centuries on
+        // current hardware, we just clamp to that value.
+        // Also we set a threshold of 0, which indicates no limit, to that
+        // value.
+        let threshold = if threshold == 0 {
+            MAX
+        } else if threshold <= MAX as u64 {
+            threshold as i64
+        } else {
+            MAX
+        };
+
+        ReseedingCore {
+            inner: rng,
+            reseeder,
+            threshold: threshold as i64,
+            bytes_until_reseed: threshold as i64,
+            fork_counter: 0,
+        }
+    }
+
+    /// Reseed the internal PRNG.
+    fn reseed(&mut self) -> Result<(), Error> {
+        R::from_rng(&mut self.reseeder).map(|result| {
+            self.bytes_until_reseed = self.threshold;
+            self.inner = result
+        })
+    }
+
+    fn is_forked(&self, global_fork_counter: usize) -> bool {
+        // In theory, on 32-bit platforms, it is possible for
+        // `global_fork_counter` to wrap around after ~4e9 forks.
+        //
+        // This check will detect a fork in the normal case where
+        // `fork_counter < global_fork_counter`, and also when the difference
+        // between both is greater than `isize::MAX` (wrapped around).
+        //
+        // It will still fail to detect a fork if there have been more than
+        // `isize::MAX` forks, without any reseed in between. Seems unlikely
+        // enough.
+        (self.fork_counter.wrapping_sub(global_fork_counter) as isize) < 0
+    }
+
+    #[inline(never)]
+    fn reseed_and_generate(
+        &mut self, results: &mut <Self as BlockRngCore>::Results, global_fork_counter: usize,
+    ) {
+        #![allow(clippy::if_same_then_else)] // false positive
+        if self.is_forked(global_fork_counter) {
+            info!("Fork detected, reseeding RNG");
+        } else {
+            trace!("Reseeding RNG (periodic reseed)");
+        }
+
+        let num_bytes = results.as_ref().len() * size_of::<<R as BlockRngCore>::Item>();
+
+        if let Err(e) = self.reseed() {
+            warn!("Reseeding RNG failed: {}", e);
+            let _ = e;
+        }
+        self.fork_counter = global_fork_counter;
+
+        self.bytes_until_reseed = self.threshold - num_bytes as i64;
+        self.inner.generate(results);
+    }
+}
+
+impl<R, Rsdr> Clone for ReseedingCore<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng + Clone,
+    Rsdr: RngCore + Clone,
+{
+    fn clone(&self) -> ReseedingCore<R, Rsdr> {
+        ReseedingCore {
+            inner: self.inner.clone(),
+            reseeder: self.reseeder.clone(),
+            threshold: self.threshold,
+            bytes_until_reseed: 0, // reseed clone on first use
+            fork_counter: self.fork_counter,
+        }
+    }
+}
+
+impl<R, Rsdr> CryptoRng for ReseedingCore<R, Rsdr>
+where
+    R: BlockRngCore + SeedableRng + CryptoRng,
+    Rsdr: RngCore + CryptoRng,
+{
+}
+
+
+#[cfg(all(unix, not(target_os = "emscripten")))]
+mod fork {
+    use core::sync::atomic::{AtomicUsize, Ordering};
+    use std::sync::Once;
+
+    // Fork protection
+    //
+    // We implement fork protection on Unix using `pthread_atfork`.
+    // When the process is forked, we increment `RESEEDING_RNG_FORK_COUNTER`.
+    // Every `ReseedingRng` stores the last known value of the static in
+    // `fork_counter`. If the cached `fork_counter` is less than
+    // `RESEEDING_RNG_FORK_COUNTER`, it is time to reseed this RNG.
+    //
+    // If reseeding fails, we don't deal with this by setting a delay, but just
+    // don't update `fork_counter`, so a reseed is attempted as soon as
+    // possible.
+
+    static RESEEDING_RNG_FORK_COUNTER: AtomicUsize = AtomicUsize::new(0);
+
+    pub fn get_fork_counter() -> usize {
+        RESEEDING_RNG_FORK_COUNTER.load(Ordering::Relaxed)
+    }
+
+    extern "C" fn fork_handler() {
+        // Note: fetch_add is defined to wrap on overflow
+        // (which is what we want).
+        RESEEDING_RNG_FORK_COUNTER.fetch_add(1, Ordering::Relaxed);
+    }
+
+    pub fn register_fork_handler() {
+        static REGISTER: Once = Once::new();
+        REGISTER.call_once(|| {
+            // Bump the counter before and after forking (see #1169):
+            let ret = unsafe { libc::pthread_atfork(
+                Some(fork_handler),
+                Some(fork_handler),
+                Some(fork_handler),
+            ) };
+            if ret != 0 {
+                panic!("libc::pthread_atfork failed with code {}", ret);
+            }
+        });
+    }
+}
+
+#[cfg(not(all(unix, not(target_os = "emscripten"))))]
+mod fork {
+    pub fn get_fork_counter() -> usize {
+        0
+    }
+    pub fn register_fork_handler() {}
+}
+
+
+#[cfg(feature = "std_rng")]
+#[cfg(test)]
+mod test {
+    use super::ReseedingRng;
+    use crate::rngs::mock::StepRng;
+    use crate::rngs::std::Core;
+    use crate::{Rng, SeedableRng};
+
+    #[test]
+    fn test_reseeding() {
+        let mut zero = StepRng::new(0, 0);
+        let rng = Core::from_rng(&mut zero).unwrap();
+        let thresh = 1; // reseed every time the buffer is exhausted
+        let mut reseeding = ReseedingRng::new(rng, thresh, zero);
+
+        // RNG buffer size is [u32; 64]
+        // Debug is only implemented up to length 32 so use two arrays
+        let mut buf = ([0u32; 32], [0u32; 32]);
+        reseeding.fill(&mut buf.0);
+        reseeding.fill(&mut buf.1);
+        let seq = buf;
+        for _ in 0..10 {
+            reseeding.fill(&mut buf.0);
+            reseeding.fill(&mut buf.1);
+            assert_eq!(buf, seq);
+        }
+    }
+
+    #[test]
+    fn test_clone_reseeding() {
+        #![allow(clippy::redundant_clone)]
+
+        let mut zero = StepRng::new(0, 0);
+        let rng = Core::from_rng(&mut zero).unwrap();
+        let mut rng1 = ReseedingRng::new(rng, 32 * 4, zero);
+
+        let first: u32 = rng1.gen();
+        for _ in 0..10 {
+            let _ = rng1.gen::<u32>();
+        }
+
+        let mut rng2 = rng1.clone();
+        assert_eq!(first, rng2.gen::<u32>());
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mock.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mock.rs.html new file mode 100644 index 0000000..819baf1 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mock.rs.html @@ -0,0 +1,177 @@ +mock.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Mock random number generator
+
+use rand_core::{impls, Error, RngCore};
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+
+/// A simple implementation of `RngCore` for testing purposes.
+///
+/// This generates an arithmetic sequence (i.e. adds a constant each step)
+/// over a `u64` number, using wrapping arithmetic. If the increment is 0
+/// the generator yields a constant.
+///
+/// ```
+/// use rand::Rng;
+/// use rand::rngs::mock::StepRng;
+///
+/// let mut my_rng = StepRng::new(2, 1);
+/// let sample: [u64; 3] = my_rng.gen();
+/// assert_eq!(sample, [2, 3, 4]);
+/// ```
+#[derive(Debug, Clone, PartialEq, Eq)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct StepRng {
+    v: u64,
+    a: u64,
+}
+
+impl StepRng {
+    /// Create a `StepRng`, yielding an arithmetic sequence starting with
+    /// `initial` and incremented by `increment` each time.
+    pub fn new(initial: u64, increment: u64) -> Self {
+        StepRng {
+            v: initial,
+            a: increment,
+        }
+    }
+}
+
+impl RngCore for StepRng {
+    #[inline]
+    fn next_u32(&mut self) -> u32 {
+        self.next_u64() as u32
+    }
+
+    #[inline]
+    fn next_u64(&mut self) -> u64 {
+        let result = self.v;
+        self.v = self.v.wrapping_add(self.a);
+        result
+    }
+
+    #[inline]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        impls::fill_bytes_via_next(self, dest);
+    }
+
+    #[inline]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        self.fill_bytes(dest);
+        Ok(())
+    }
+}
+
+#[cfg(test)]
+mod tests {
+    #[test]
+    #[cfg(feature = "serde1")]
+    fn test_serialization_step_rng() {
+        use super::StepRng;
+
+        let some_rng = StepRng::new(42, 7);
+        let de_some_rng: StepRng =
+            bincode::deserialize(&bincode::serialize(&some_rng).unwrap()).unwrap();
+        assert_eq!(some_rng.v, de_some_rng.v);
+        assert_eq!(some_rng.a, de_some_rng.a);
+
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mod.rs.html new file mode 100644 index 0000000..48767fa --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/mod.rs.html @@ -0,0 +1,241 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Random number generators and adapters
+//!
+//! ## Background: Random number generators (RNGs)
+//!
+//! Computers cannot produce random numbers from nowhere. We classify
+//! random number generators as follows:
+//!
+//! -   "True" random number generators (TRNGs) use hard-to-predict data sources
+//!     (e.g. the high-resolution parts of event timings and sensor jitter) to
+//!     harvest random bit-sequences, apply algorithms to remove bias and
+//!     estimate available entropy, then combine these bits into a byte-sequence
+//!     or an entropy pool. This job is usually done by the operating system or
+//!     a hardware generator (HRNG).
+//! -   "Pseudo"-random number generators (PRNGs) use algorithms to transform a
+//!     seed into a sequence of pseudo-random numbers. These generators can be
+//!     fast and produce well-distributed unpredictable random numbers (or not).
+//!     They are usually deterministic: given algorithm and seed, the output
+//!     sequence can be reproduced. They have finite period and eventually loop;
+//!     with many algorithms this period is fixed and can be proven sufficiently
+//!     long, while others are chaotic and the period depends on the seed.
+//! -   "Cryptographically secure" pseudo-random number generators (CSPRNGs)
+//!     are the sub-set of PRNGs which are secure. Security of the generator
+//!     relies both on hiding the internal state and using a strong algorithm.
+//!
+//! ## Traits and functionality
+//!
+//! All RNGs implement the [`RngCore`] trait, as a consequence of which the
+//! [`Rng`] extension trait is automatically implemented. Secure RNGs may
+//! additionally implement the [`CryptoRng`] trait.
+//!
+//! All PRNGs require a seed to produce their random number sequence. The
+//! [`SeedableRng`] trait provides three ways of constructing PRNGs:
+//!
+//! -   `from_seed` accepts a type specific to the PRNG
+//! -   `from_rng` allows a PRNG to be seeded from any other RNG
+//! -   `seed_from_u64` allows any PRNG to be seeded from a `u64` insecurely
+//! -   `from_entropy` securely seeds a PRNG from fresh entropy
+//!
+//! Use the [`rand_core`] crate when implementing your own RNGs.
+//!
+//! ## Our generators
+//!
+//! This crate provides several random number generators:
+//!
+//! -   [`OsRng`] is an interface to the operating system's random number
+//!     source. Typically the operating system uses a CSPRNG with entropy
+//!     provided by a TRNG and some type of on-going re-seeding.
+//! -   [`ThreadRng`], provided by the [`thread_rng`] function, is a handle to a
+//!     thread-local CSPRNG with periodic seeding from [`OsRng`]. Because this
+//!     is local, it is typically much faster than [`OsRng`]. It should be
+//!     secure, though the paranoid may prefer [`OsRng`].
+//! -   [`StdRng`] is a CSPRNG chosen for good performance and trust of security
+//!     (based on reviews, maturity and usage). The current algorithm is ChaCha12,
+//!     which is well established and rigorously analysed.
+//!     [`StdRng`] provides the algorithm used by [`ThreadRng`] but without
+//!     periodic reseeding.
+//! -   [`SmallRng`] is an **insecure** PRNG designed to be fast, simple, require
+//!     little memory, and have good output quality.
+//!
+//! The algorithms selected for [`StdRng`] and [`SmallRng`] may change in any
+//! release and may be platform-dependent, therefore they should be considered
+//! **not reproducible**.
+//!
+//! ## Additional generators
+//!
+//! **TRNGs**: The [`rdrand`] crate provides an interface to the RDRAND and
+//! RDSEED instructions available in modern Intel and AMD CPUs.
+//! The [`rand_jitter`] crate provides a user-space implementation of
+//! entropy harvesting from CPU timer jitter, but is very slow and has
+//! [security issues](https://github.com/rust-random/rand/issues/699).
+//!
+//! **PRNGs**: Several companion crates are available, providing individual or
+//! families of PRNG algorithms. These provide the implementations behind
+//! [`StdRng`] and [`SmallRng`] but can also be used directly, indeed *should*
+//! be used directly when **reproducibility** matters.
+//! Some suggestions are: [`rand_chacha`], [`rand_pcg`], [`rand_xoshiro`].
+//! A full list can be found by searching for crates with the [`rng` tag].
+//!
+//! [`Rng`]: crate::Rng
+//! [`RngCore`]: crate::RngCore
+//! [`CryptoRng`]: crate::CryptoRng
+//! [`SeedableRng`]: crate::SeedableRng
+//! [`thread_rng`]: crate::thread_rng
+//! [`rdrand`]: https://crates.io/crates/rdrand
+//! [`rand_jitter`]: https://crates.io/crates/rand_jitter
+//! [`rand_chacha`]: https://crates.io/crates/rand_chacha
+//! [`rand_pcg`]: https://crates.io/crates/rand_pcg
+//! [`rand_xoshiro`]: https://crates.io/crates/rand_xoshiro
+//! [`rng` tag]: https://crates.io/keywords/rng
+
+#[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+#[cfg(feature = "std")] pub mod adapter;
+
+pub mod mock; // Public so we don't export `StepRng` directly, making it a bit
+              // more clear it is intended for testing.
+
+#[cfg(all(feature = "small_rng", target_pointer_width = "64"))]
+mod xoshiro256plusplus;
+#[cfg(all(feature = "small_rng", not(target_pointer_width = "64")))]
+mod xoshiro128plusplus;
+#[cfg(feature = "small_rng")] mod small;
+
+#[cfg(feature = "std_rng")] mod std;
+#[cfg(all(feature = "std", feature = "std_rng"))] pub(crate) mod thread;
+
+#[cfg(feature = "small_rng")] pub use self::small::SmallRng;
+#[cfg(feature = "std_rng")] pub use self::std::StdRng;
+#[cfg(all(feature = "std", feature = "std_rng"))] pub use self::thread::ThreadRng;
+
+#[cfg_attr(doc_cfg, doc(cfg(feature = "getrandom")))]
+#[cfg(feature = "getrandom")] pub use rand_core::OsRng;
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/std.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/std.rs.html new file mode 100644 index 0000000..a7d324f --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/std.rs.html @@ -0,0 +1,199 @@ +std.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The standard RNG
+
+use crate::{CryptoRng, Error, RngCore, SeedableRng};
+
+pub(crate) use rand_chacha::ChaCha12Core as Core;
+
+use rand_chacha::ChaCha12Rng as Rng;
+
+/// The standard RNG. The PRNG algorithm in `StdRng` is chosen to be efficient
+/// on the current platform, to be statistically strong and unpredictable
+/// (meaning a cryptographically secure PRNG).
+///
+/// The current algorithm used is the ChaCha block cipher with 12 rounds. Please
+/// see this relevant [rand issue] for the discussion. This may change as new 
+/// evidence of cipher security and performance becomes available.
+///
+/// The algorithm is deterministic but should not be considered reproducible
+/// due to dependence on configuration and possible replacement in future
+/// library versions. For a secure reproducible generator, we recommend use of
+/// the [rand_chacha] crate directly.
+///
+/// [rand_chacha]: https://crates.io/crates/rand_chacha
+/// [rand issue]: https://github.com/rust-random/rand/issues/932
+#[cfg_attr(doc_cfg, doc(cfg(feature = "std_rng")))]
+#[derive(Clone, Debug, PartialEq, Eq)]
+pub struct StdRng(Rng);
+
+impl RngCore for StdRng {
+    #[inline(always)]
+    fn next_u32(&mut self) -> u32 {
+        self.0.next_u32()
+    }
+
+    #[inline(always)]
+    fn next_u64(&mut self) -> u64 {
+        self.0.next_u64()
+    }
+
+    #[inline(always)]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        self.0.fill_bytes(dest);
+    }
+
+    #[inline(always)]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        self.0.try_fill_bytes(dest)
+    }
+}
+
+impl SeedableRng for StdRng {
+    type Seed = <Rng as SeedableRng>::Seed;
+
+    #[inline(always)]
+    fn from_seed(seed: Self::Seed) -> Self {
+        StdRng(Rng::from_seed(seed))
+    }
+
+    #[inline(always)]
+    fn from_rng<R: RngCore>(rng: R) -> Result<Self, Error> {
+        Rng::from_rng(rng).map(StdRng)
+    }
+}
+
+impl CryptoRng for StdRng {}
+
+
+#[cfg(test)]
+mod test {
+    use crate::rngs::StdRng;
+    use crate::{RngCore, SeedableRng};
+
+    #[test]
+    fn test_stdrng_construction() {
+        // Test value-stability of StdRng. This is expected to break any time
+        // the algorithm is changed.
+        #[rustfmt::skip]
+        let seed = [1,0,0,0, 23,0,0,0, 200,1,0,0, 210,30,0,0,
+                    0,0,0,0, 0,0,0,0, 0,0,0,0, 0,0,0,0];
+
+        let target = [10719222850664546238, 14064965282130556830];
+
+        let mut rng0 = StdRng::from_seed(seed);
+        let x0 = rng0.next_u64();
+
+        let mut rng1 = StdRng::from_rng(rng0).unwrap();
+        let x1 = rng1.next_u64();
+
+        assert_eq!([x0, x1], target);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/thread.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/thread.rs.html new file mode 100644 index 0000000..5243758 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/rngs/thread.rs.html @@ -0,0 +1,289 @@ +thread.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Thread-local random number generator
+
+use core::cell::UnsafeCell;
+use std::rc::Rc;
+use std::thread_local;
+
+use super::std::Core;
+use crate::rngs::adapter::ReseedingRng;
+use crate::rngs::OsRng;
+use crate::{CryptoRng, Error, RngCore, SeedableRng};
+
+// Rationale for using `UnsafeCell` in `ThreadRng`:
+//
+// Previously we used a `RefCell`, with an overhead of ~15%. There will only
+// ever be one mutable reference to the interior of the `UnsafeCell`, because
+// we only have such a reference inside `next_u32`, `next_u64`, etc. Within a
+// single thread (which is the definition of `ThreadRng`), there will only ever
+// be one of these methods active at a time.
+//
+// A possible scenario where there could be multiple mutable references is if
+// `ThreadRng` is used inside `next_u32` and co. But the implementation is
+// completely under our control. We just have to ensure none of them use
+// `ThreadRng` internally, which is nonsensical anyway. We should also never run
+// `ThreadRng` in destructors of its implementation, which is also nonsensical.
+
+
+// Number of generated bytes after which to reseed `ThreadRng`.
+// According to benchmarks, reseeding has a noticeable impact with thresholds
+// of 32 kB and less. We choose 64 kB to avoid significant overhead.
+const THREAD_RNG_RESEED_THRESHOLD: u64 = 1024 * 64;
+
+/// A reference to the thread-local generator
+///
+/// An instance can be obtained via [`thread_rng`] or via `ThreadRng::default()`.
+/// This handle is safe to use everywhere (including thread-local destructors),
+/// though it is recommended not to use inside a fork handler.
+/// The handle cannot be passed between threads (is not `Send` or `Sync`).
+///
+/// `ThreadRng` uses the same PRNG as [`StdRng`] for security and performance
+/// and is automatically seeded from [`OsRng`].
+///
+/// Unlike `StdRng`, `ThreadRng` uses the  [`ReseedingRng`] wrapper to reseed
+/// the PRNG from fresh entropy every 64 kiB of random data as well as after a
+/// fork on Unix (though not quite immediately; see documentation of
+/// [`ReseedingRng`]).
+/// Note that the reseeding is done as an extra precaution against side-channel
+/// attacks and mis-use (e.g. if somehow weak entropy were supplied initially).
+/// The PRNG algorithms used are assumed to be secure.
+///
+/// [`ReseedingRng`]: crate::rngs::adapter::ReseedingRng
+/// [`StdRng`]: crate::rngs::StdRng
+#[cfg_attr(doc_cfg, doc(cfg(all(feature = "std", feature = "std_rng"))))]
+#[derive(Clone, Debug)]
+pub struct ThreadRng {
+    // Rc is explicitly !Send and !Sync
+    rng: Rc<UnsafeCell<ReseedingRng<Core, OsRng>>>,
+}
+
+thread_local!(
+    // We require Rc<..> to avoid premature freeing when thread_rng is used
+    // within thread-local destructors. See #968.
+    static THREAD_RNG_KEY: Rc<UnsafeCell<ReseedingRng<Core, OsRng>>> = {
+        let r = Core::from_rng(OsRng).unwrap_or_else(|err|
+                panic!("could not initialize thread_rng: {}", err));
+        let rng = ReseedingRng::new(r,
+                                    THREAD_RNG_RESEED_THRESHOLD,
+                                    OsRng);
+        Rc::new(UnsafeCell::new(rng))
+    }
+);
+
+/// Retrieve the lazily-initialized thread-local random number generator,
+/// seeded by the system. Intended to be used in method chaining style,
+/// e.g. `thread_rng().gen::<i32>()`, or cached locally, e.g.
+/// `let mut rng = thread_rng();`.  Invoked by the `Default` trait, making
+/// `ThreadRng::default()` equivalent.
+///
+/// For more information see [`ThreadRng`].
+#[cfg_attr(doc_cfg, doc(cfg(all(feature = "std", feature = "std_rng"))))]
+pub fn thread_rng() -> ThreadRng {
+    let rng = THREAD_RNG_KEY.with(|t| t.clone());
+    ThreadRng { rng }
+}
+
+impl Default for ThreadRng {
+    fn default() -> ThreadRng {
+        crate::prelude::thread_rng()
+    }
+}
+
+impl RngCore for ThreadRng {
+    #[inline(always)]
+    fn next_u32(&mut self) -> u32 {
+        // SAFETY: We must make sure to stop using `rng` before anyone else
+        // creates another mutable reference
+        let rng = unsafe { &mut *self.rng.get() };
+        rng.next_u32()
+    }
+
+    #[inline(always)]
+    fn next_u64(&mut self) -> u64 {
+        // SAFETY: We must make sure to stop using `rng` before anyone else
+        // creates another mutable reference
+        let rng = unsafe { &mut *self.rng.get() };
+        rng.next_u64()
+    }
+
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        // SAFETY: We must make sure to stop using `rng` before anyone else
+        // creates another mutable reference
+        let rng = unsafe { &mut *self.rng.get() };
+        rng.fill_bytes(dest)
+    }
+
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        // SAFETY: We must make sure to stop using `rng` before anyone else
+        // creates another mutable reference
+        let rng = unsafe { &mut *self.rng.get() };
+        rng.try_fill_bytes(dest)
+    }
+}
+
+impl CryptoRng for ThreadRng {}
+
+
+#[cfg(test)]
+mod test {
+    #[test]
+    fn test_thread_rng() {
+        use crate::Rng;
+        let mut r = crate::thread_rng();
+        r.gen::<i32>();
+        assert_eq!(r.gen_range(0..1), 0);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/index.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/index.rs.html new file mode 100644 index 0000000..9f59f7f --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/index.rs.html @@ -0,0 +1,1359 @@ +index.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Low-level API for sampling indices
+
+#[cfg(feature = "alloc")] use core::slice;
+
+#[cfg(feature = "alloc")] use alloc::vec::{self, Vec};
+// BTreeMap is not as fast in tests, but better than nothing.
+#[cfg(all(feature = "alloc", not(feature = "std")))]
+use alloc::collections::BTreeSet;
+#[cfg(feature = "std")] use std::collections::HashSet;
+
+#[cfg(feature = "std")]
+use crate::distributions::WeightedError;
+
+#[cfg(feature = "alloc")]
+use crate::{Rng, distributions::{uniform::SampleUniform, Distribution, Uniform}};
+
+#[cfg(feature = "serde1")]
+use serde::{Serialize, Deserialize};
+
+/// A vector of indices.
+///
+/// Multiple internal representations are possible.
+#[derive(Clone, Debug)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub enum IndexVec {
+    #[doc(hidden)]
+    U32(Vec<u32>),
+    #[doc(hidden)]
+    USize(Vec<usize>),
+}
+
+impl IndexVec {
+    /// Returns the number of indices
+    #[inline]
+    pub fn len(&self) -> usize {
+        match *self {
+            IndexVec::U32(ref v) => v.len(),
+            IndexVec::USize(ref v) => v.len(),
+        }
+    }
+
+    /// Returns `true` if the length is 0.
+    #[inline]
+    pub fn is_empty(&self) -> bool {
+        match *self {
+            IndexVec::U32(ref v) => v.is_empty(),
+            IndexVec::USize(ref v) => v.is_empty(),
+        }
+    }
+
+    /// Return the value at the given `index`.
+    ///
+    /// (Note: we cannot implement [`std::ops::Index`] because of lifetime
+    /// restrictions.)
+    #[inline]
+    pub fn index(&self, index: usize) -> usize {
+        match *self {
+            IndexVec::U32(ref v) => v[index] as usize,
+            IndexVec::USize(ref v) => v[index],
+        }
+    }
+
+    /// Return result as a `Vec<usize>`. Conversion may or may not be trivial.
+    #[inline]
+    pub fn into_vec(self) -> Vec<usize> {
+        match self {
+            IndexVec::U32(v) => v.into_iter().map(|i| i as usize).collect(),
+            IndexVec::USize(v) => v,
+        }
+    }
+
+    /// Iterate over the indices as a sequence of `usize` values
+    #[inline]
+    pub fn iter(&self) -> IndexVecIter<'_> {
+        match *self {
+            IndexVec::U32(ref v) => IndexVecIter::U32(v.iter()),
+            IndexVec::USize(ref v) => IndexVecIter::USize(v.iter()),
+        }
+    }
+}
+
+impl IntoIterator for IndexVec {
+    type Item = usize;
+    type IntoIter = IndexVecIntoIter;
+
+    /// Convert into an iterator over the indices as a sequence of `usize` values
+    #[inline]
+    fn into_iter(self) -> IndexVecIntoIter {
+        match self {
+            IndexVec::U32(v) => IndexVecIntoIter::U32(v.into_iter()),
+            IndexVec::USize(v) => IndexVecIntoIter::USize(v.into_iter()),
+        }
+    }
+}
+
+impl PartialEq for IndexVec {
+    fn eq(&self, other: &IndexVec) -> bool {
+        use self::IndexVec::*;
+        match (self, other) {
+            (&U32(ref v1), &U32(ref v2)) => v1 == v2,
+            (&USize(ref v1), &USize(ref v2)) => v1 == v2,
+            (&U32(ref v1), &USize(ref v2)) => {
+                (v1.len() == v2.len()) && (v1.iter().zip(v2.iter()).all(|(x, y)| *x as usize == *y))
+            }
+            (&USize(ref v1), &U32(ref v2)) => {
+                (v1.len() == v2.len()) && (v1.iter().zip(v2.iter()).all(|(x, y)| *x == *y as usize))
+            }
+        }
+    }
+}
+
+impl From<Vec<u32>> for IndexVec {
+    #[inline]
+    fn from(v: Vec<u32>) -> Self {
+        IndexVec::U32(v)
+    }
+}
+
+impl From<Vec<usize>> for IndexVec {
+    #[inline]
+    fn from(v: Vec<usize>) -> Self {
+        IndexVec::USize(v)
+    }
+}
+
+/// Return type of `IndexVec::iter`.
+#[derive(Debug)]
+pub enum IndexVecIter<'a> {
+    #[doc(hidden)]
+    U32(slice::Iter<'a, u32>),
+    #[doc(hidden)]
+    USize(slice::Iter<'a, usize>),
+}
+
+impl<'a> Iterator for IndexVecIter<'a> {
+    type Item = usize;
+
+    #[inline]
+    fn next(&mut self) -> Option<usize> {
+        use self::IndexVecIter::*;
+        match *self {
+            U32(ref mut iter) => iter.next().map(|i| *i as usize),
+            USize(ref mut iter) => iter.next().cloned(),
+        }
+    }
+
+    #[inline]
+    fn size_hint(&self) -> (usize, Option<usize>) {
+        match *self {
+            IndexVecIter::U32(ref v) => v.size_hint(),
+            IndexVecIter::USize(ref v) => v.size_hint(),
+        }
+    }
+}
+
+impl<'a> ExactSizeIterator for IndexVecIter<'a> {}
+
+/// Return type of `IndexVec::into_iter`.
+#[derive(Clone, Debug)]
+pub enum IndexVecIntoIter {
+    #[doc(hidden)]
+    U32(vec::IntoIter<u32>),
+    #[doc(hidden)]
+    USize(vec::IntoIter<usize>),
+}
+
+impl Iterator for IndexVecIntoIter {
+    type Item = usize;
+
+    #[inline]
+    fn next(&mut self) -> Option<Self::Item> {
+        use self::IndexVecIntoIter::*;
+        match *self {
+            U32(ref mut v) => v.next().map(|i| i as usize),
+            USize(ref mut v) => v.next(),
+        }
+    }
+
+    #[inline]
+    fn size_hint(&self) -> (usize, Option<usize>) {
+        use self::IndexVecIntoIter::*;
+        match *self {
+            U32(ref v) => v.size_hint(),
+            USize(ref v) => v.size_hint(),
+        }
+    }
+}
+
+impl ExactSizeIterator for IndexVecIntoIter {}
+
+
+/// Randomly sample exactly `amount` distinct indices from `0..length`, and
+/// return them in random order (fully shuffled).
+///
+/// This method is used internally by the slice sampling methods, but it can
+/// sometimes be useful to have the indices themselves so this is provided as
+/// an alternative.
+///
+/// The implementation used is not specified; we automatically select the
+/// fastest available algorithm for the `length` and `amount` parameters
+/// (based on detailed profiling on an Intel Haswell CPU). Roughly speaking,
+/// complexity is `O(amount)`, except that when `amount` is small, performance
+/// is closer to `O(amount^2)`, and when `length` is close to `amount` then
+/// `O(length)`.
+///
+/// Note that performance is significantly better over `u32` indices than over
+/// `u64` indices. Because of this we hide the underlying type behind an
+/// abstraction, `IndexVec`.
+///
+/// If an allocation-free `no_std` function is required, it is suggested
+/// to adapt the internal `sample_floyd` implementation.
+///
+/// Panics if `amount > length`.
+pub fn sample<R>(rng: &mut R, length: usize, amount: usize) -> IndexVec
+where R: Rng + ?Sized {
+    if amount > length {
+        panic!("`amount` of samples must be less than or equal to `length`");
+    }
+    if length > (::core::u32::MAX as usize) {
+        // We never want to use inplace here, but could use floyd's alg
+        // Lazy version: always use the cache alg.
+        return sample_rejection(rng, length, amount);
+    }
+    let amount = amount as u32;
+    let length = length as u32;
+
+    // Choice of algorithm here depends on both length and amount. See:
+    // https://github.com/rust-random/rand/pull/479
+    // We do some calculations with f32. Accuracy is not very important.
+
+    if amount < 163 {
+        const C: [[f32; 2]; 2] = [[1.6, 8.0 / 45.0], [10.0, 70.0 / 9.0]];
+        let j = if length < 500_000 { 0 } else { 1 };
+        let amount_fp = amount as f32;
+        let m4 = C[0][j] * amount_fp;
+        // Short-cut: when amount < 12, floyd's is always faster
+        if amount > 11 && (length as f32) < (C[1][j] + m4) * amount_fp {
+            sample_inplace(rng, length, amount)
+        } else {
+            sample_floyd(rng, length, amount)
+        }
+    } else {
+        const C: [f32; 2] = [270.0, 330.0 / 9.0];
+        let j = if length < 500_000 { 0 } else { 1 };
+        if (length as f32) < C[j] * (amount as f32) {
+            sample_inplace(rng, length, amount)
+        } else {
+            sample_rejection(rng, length, amount)
+        }
+    }
+}
+
+/// Randomly sample exactly `amount` distinct indices from `0..length`, and
+/// return them in an arbitrary order (there is no guarantee of shuffling or
+/// ordering). The weights are to be provided by the input function `weights`,
+/// which will be called once for each index.
+///
+/// This method is used internally by the slice sampling methods, but it can
+/// sometimes be useful to have the indices themselves so this is provided as
+/// an alternative.
+///
+/// This implementation uses `O(length + amount)` space and `O(length)` time
+/// if the "nightly" feature is enabled, or `O(length)` space and
+/// `O(length + amount * log length)` time otherwise.
+///
+/// Panics if `amount > length`.
+#[cfg(feature = "std")]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+pub fn sample_weighted<R, F, X>(
+    rng: &mut R, length: usize, weight: F, amount: usize,
+) -> Result<IndexVec, WeightedError>
+where
+    R: Rng + ?Sized,
+    F: Fn(usize) -> X,
+    X: Into<f64>,
+{
+    if length > (core::u32::MAX as usize) {
+        sample_efraimidis_spirakis(rng, length, weight, amount)
+    } else {
+        assert!(amount <= core::u32::MAX as usize);
+        let amount = amount as u32;
+        let length = length as u32;
+        sample_efraimidis_spirakis(rng, length, weight, amount)
+    }
+}
+
+
+/// Randomly sample exactly `amount` distinct indices from `0..length`, and
+/// return them in an arbitrary order (there is no guarantee of shuffling or
+/// ordering). The weights are to be provided by the input function `weights`,
+/// which will be called once for each index.
+///
+/// This implementation uses the algorithm described by Efraimidis and Spirakis
+/// in this paper: https://doi.org/10.1016/j.ipl.2005.11.003
+/// It uses `O(length + amount)` space and `O(length)` time if the
+/// "nightly" feature is enabled, or `O(length)` space and `O(length
+/// + amount * log length)` time otherwise.
+///
+/// Panics if `amount > length`.
+#[cfg(feature = "std")]
+fn sample_efraimidis_spirakis<R, F, X, N>(
+    rng: &mut R, length: N, weight: F, amount: N,
+) -> Result<IndexVec, WeightedError>
+where
+    R: Rng + ?Sized,
+    F: Fn(usize) -> X,
+    X: Into<f64>,
+    N: UInt,
+    IndexVec: From<Vec<N>>,
+{
+    if amount == N::zero() {
+        return Ok(IndexVec::U32(Vec::new()));
+    }
+
+    if amount > length {
+        panic!("`amount` of samples must be less than or equal to `length`");
+    }
+
+    struct Element<N> {
+        index: N,
+        key: f64,
+    }
+    impl<N> PartialOrd for Element<N> {
+        fn partial_cmp(&self, other: &Self) -> Option<core::cmp::Ordering> {
+            self.key.partial_cmp(&other.key)
+        }
+    }
+    impl<N> Ord for Element<N> {
+        fn cmp(&self, other: &Self) -> core::cmp::Ordering {
+             // partial_cmp will always produce a value,
+             // because we check that the weights are not nan
+            self.partial_cmp(other).unwrap()
+        }
+    }
+    impl<N> PartialEq for Element<N> {
+        fn eq(&self, other: &Self) -> bool {
+            self.key == other.key
+        }
+    }
+    impl<N> Eq for Element<N> {}
+
+    #[cfg(feature = "nightly")]
+    {
+        let mut candidates = Vec::with_capacity(length.as_usize());
+        let mut index = N::zero();
+        while index < length {
+            let weight = weight(index.as_usize()).into();
+            if !(weight >= 0.) {
+                return Err(WeightedError::InvalidWeight);
+            }
+
+            let key = rng.gen::<f64>().powf(1.0 / weight);
+            candidates.push(Element { index, key });
+
+            index += N::one();
+        }
+
+        // Partially sort the array to find the `amount` elements with the greatest
+        // keys. Do this by using `select_nth_unstable` to put the elements with
+        // the *smallest* keys at the beginning of the list in `O(n)` time, which
+        // provides equivalent information about the elements with the *greatest* keys.
+        let (_, mid, greater)
+            = candidates.select_nth_unstable(length.as_usize() - amount.as_usize());
+
+        let mut result: Vec<N> = Vec::with_capacity(amount.as_usize());
+        result.push(mid.index);
+        for element in greater {
+            result.push(element.index);
+        }
+        Ok(IndexVec::from(result))
+    }
+
+    #[cfg(not(feature = "nightly"))]
+    {
+        use alloc::collections::BinaryHeap;
+
+        // Partially sort the array such that the `amount` elements with the largest
+        // keys are first using a binary max heap.
+        let mut candidates = BinaryHeap::with_capacity(length.as_usize());
+        let mut index = N::zero();
+        while index < length {
+            let weight = weight(index.as_usize()).into();
+            if !(weight >= 0.) {
+                return Err(WeightedError::InvalidWeight);
+            }
+
+            let key = rng.gen::<f64>().powf(1.0 / weight);
+            candidates.push(Element { index, key });
+
+            index += N::one();
+        }
+
+        let mut result: Vec<N> = Vec::with_capacity(amount.as_usize());
+        while result.len() < amount.as_usize() {
+            result.push(candidates.pop().unwrap().index);
+        }
+        Ok(IndexVec::from(result))
+    }
+}
+
+/// Randomly sample exactly `amount` indices from `0..length`, using Floyd's
+/// combination algorithm.
+///
+/// The output values are fully shuffled. (Overhead is under 50%.)
+///
+/// This implementation uses `O(amount)` memory and `O(amount^2)` time.
+fn sample_floyd<R>(rng: &mut R, length: u32, amount: u32) -> IndexVec
+where R: Rng + ?Sized {
+    // For small amount we use Floyd's fully-shuffled variant. For larger
+    // amounts this is slow due to Vec::insert performance, so we shuffle
+    // afterwards. Benchmarks show little overhead from extra logic.
+    let floyd_shuffle = amount < 50;
+
+    debug_assert!(amount <= length);
+    let mut indices = Vec::with_capacity(amount as usize);
+    for j in length - amount..length {
+        let t = rng.gen_range(0..=j);
+        if floyd_shuffle {
+            if let Some(pos) = indices.iter().position(|&x| x == t) {
+                indices.insert(pos, j);
+                continue;
+            }
+        } else if indices.contains(&t) {
+            indices.push(j);
+            continue;
+        }
+        indices.push(t);
+    }
+    if !floyd_shuffle {
+        // Reimplement SliceRandom::shuffle with smaller indices
+        for i in (1..amount).rev() {
+            // invariant: elements with index > i have been locked in place.
+            indices.swap(i as usize, rng.gen_range(0..=i) as usize);
+        }
+    }
+    IndexVec::from(indices)
+}
+
+/// Randomly sample exactly `amount` indices from `0..length`, using an inplace
+/// partial Fisher-Yates method.
+/// Sample an amount of indices using an inplace partial fisher yates method.
+///
+/// This allocates the entire `length` of indices and randomizes only the first `amount`.
+/// It then truncates to `amount` and returns.
+///
+/// This method is not appropriate for large `length` and potentially uses a lot
+/// of memory; because of this we only implement for `u32` index (which improves
+/// performance in all cases).
+///
+/// Set-up is `O(length)` time and memory and shuffling is `O(amount)` time.
+fn sample_inplace<R>(rng: &mut R, length: u32, amount: u32) -> IndexVec
+where R: Rng + ?Sized {
+    debug_assert!(amount <= length);
+    let mut indices: Vec<u32> = Vec::with_capacity(length as usize);
+    indices.extend(0..length);
+    for i in 0..amount {
+        let j: u32 = rng.gen_range(i..length);
+        indices.swap(i as usize, j as usize);
+    }
+    indices.truncate(amount as usize);
+    debug_assert_eq!(indices.len(), amount as usize);
+    IndexVec::from(indices)
+}
+
+trait UInt: Copy + PartialOrd + Ord + PartialEq + Eq + SampleUniform
+    + core::hash::Hash + core::ops::AddAssign {
+    fn zero() -> Self;
+    fn one() -> Self;
+    fn as_usize(self) -> usize;
+}
+impl UInt for u32 {
+    #[inline]
+    fn zero() -> Self {
+        0
+    }
+
+    #[inline]
+    fn one() -> Self {
+        1
+    }
+
+    #[inline]
+    fn as_usize(self) -> usize {
+        self as usize
+    }
+}
+impl UInt for usize {
+    #[inline]
+    fn zero() -> Self {
+        0
+    }
+
+    #[inline]
+    fn one() -> Self {
+        1
+    }
+
+    #[inline]
+    fn as_usize(self) -> usize {
+        self
+    }
+}
+
+/// Randomly sample exactly `amount` indices from `0..length`, using rejection
+/// sampling.
+///
+/// Since `amount <<< length` there is a low chance of a random sample in
+/// `0..length` being a duplicate. We test for duplicates and resample where
+/// necessary. The algorithm is `O(amount)` time and memory.
+///
+/// This function  is generic over X primarily so that results are value-stable
+/// over 32-bit and 64-bit platforms.
+fn sample_rejection<X: UInt, R>(rng: &mut R, length: X, amount: X) -> IndexVec
+where
+    R: Rng + ?Sized,
+    IndexVec: From<Vec<X>>,
+{
+    debug_assert!(amount < length);
+    #[cfg(feature = "std")]
+    let mut cache = HashSet::with_capacity(amount.as_usize());
+    #[cfg(not(feature = "std"))]
+    let mut cache = BTreeSet::new();
+    let distr = Uniform::new(X::zero(), length);
+    let mut indices = Vec::with_capacity(amount.as_usize());
+    for _ in 0..amount.as_usize() {
+        let mut pos = distr.sample(rng);
+        while !cache.insert(pos) {
+            pos = distr.sample(rng);
+        }
+        indices.push(pos);
+    }
+
+    debug_assert_eq!(indices.len(), amount.as_usize());
+    IndexVec::from(indices)
+}
+
+#[cfg(test)]
+mod test {
+    use super::*;
+
+    #[test]
+    #[cfg(feature = "serde1")]
+    fn test_serialization_index_vec() {
+        let some_index_vec = IndexVec::from(vec![254_usize, 234, 2, 1]);
+        let de_some_index_vec: IndexVec = bincode::deserialize(&bincode::serialize(&some_index_vec).unwrap()).unwrap();
+        match (some_index_vec, de_some_index_vec) {
+            (IndexVec::U32(a), IndexVec::U32(b)) => {
+                assert_eq!(a, b);
+            },
+            (IndexVec::USize(a), IndexVec::USize(b)) => {
+                assert_eq!(a, b);
+            },
+            _ => {panic!("failed to seralize/deserialize `IndexVec`")}
+        }
+    }
+
+    #[cfg(feature = "alloc")] use alloc::vec;
+
+    #[test]
+    fn test_sample_boundaries() {
+        let mut r = crate::test::rng(404);
+
+        assert_eq!(sample_inplace(&mut r, 0, 0).len(), 0);
+        assert_eq!(sample_inplace(&mut r, 1, 0).len(), 0);
+        assert_eq!(sample_inplace(&mut r, 1, 1).into_vec(), vec![0]);
+
+        assert_eq!(sample_rejection(&mut r, 1u32, 0).len(), 0);
+
+        assert_eq!(sample_floyd(&mut r, 0, 0).len(), 0);
+        assert_eq!(sample_floyd(&mut r, 1, 0).len(), 0);
+        assert_eq!(sample_floyd(&mut r, 1, 1).into_vec(), vec![0]);
+
+        // These algorithms should be fast with big numbers. Test average.
+        let sum: usize = sample_rejection(&mut r, 1 << 25, 10u32).into_iter().sum();
+        assert!(1 << 25 < sum && sum < (1 << 25) * 25);
+
+        let sum: usize = sample_floyd(&mut r, 1 << 25, 10).into_iter().sum();
+        assert!(1 << 25 < sum && sum < (1 << 25) * 25);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_sample_alg() {
+        let seed_rng = crate::test::rng;
+
+        // We can't test which algorithm is used directly, but Floyd's alg
+        // should produce different results from the others. (Also, `inplace`
+        // and `cached` currently use different sizes thus produce different results.)
+
+        // A small length and relatively large amount should use inplace
+        let (length, amount): (usize, usize) = (100, 50);
+        let v1 = sample(&mut seed_rng(420), length, amount);
+        let v2 = sample_inplace(&mut seed_rng(420), length as u32, amount as u32);
+        assert!(v1.iter().all(|e| e < length));
+        assert_eq!(v1, v2);
+
+        // Test Floyd's alg does produce different results
+        let v3 = sample_floyd(&mut seed_rng(420), length as u32, amount as u32);
+        assert!(v1 != v3);
+
+        // A large length and small amount should use Floyd
+        let (length, amount): (usize, usize) = (1 << 20, 50);
+        let v1 = sample(&mut seed_rng(421), length, amount);
+        let v2 = sample_floyd(&mut seed_rng(421), length as u32, amount as u32);
+        assert!(v1.iter().all(|e| e < length));
+        assert_eq!(v1, v2);
+
+        // A large length and larger amount should use cache
+        let (length, amount): (usize, usize) = (1 << 20, 600);
+        let v1 = sample(&mut seed_rng(422), length, amount);
+        let v2 = sample_rejection(&mut seed_rng(422), length as u32, amount as u32);
+        assert!(v1.iter().all(|e| e < length));
+        assert_eq!(v1, v2);
+    }
+
+    #[cfg(feature = "std")]
+    #[test]
+    fn test_sample_weighted() {
+        let seed_rng = crate::test::rng;
+        for &(amount, len) in &[(0, 10), (5, 10), (10, 10)] {
+            let v = sample_weighted(&mut seed_rng(423), len, |i| i as f64, amount).unwrap();
+            match v {
+                IndexVec::U32(mut indices) => {
+                    assert_eq!(indices.len(), amount);
+                    indices.sort_unstable();
+                    indices.dedup();
+                    assert_eq!(indices.len(), amount);
+                    for &i in &indices {
+                        assert!((i as usize) < len);
+                    }
+                },
+                IndexVec::USize(_) => panic!("expected `IndexVec::U32`"),
+            }
+        }
+    }
+
+    #[test]
+    fn value_stability_sample() {
+        let do_test = |length, amount, values: &[u32]| {
+            let mut buf = [0u32; 8];
+            let mut rng = crate::test::rng(410);
+
+            let res = sample(&mut rng, length, amount);
+            let len = res.len().min(buf.len());
+            for (x, y) in res.into_iter().zip(buf.iter_mut()) {
+                *y = x as u32;
+            }
+            assert_eq!(
+                &buf[0..len],
+                values,
+                "failed sampling {}, {}",
+                length,
+                amount
+            );
+        };
+
+        do_test(10, 6, &[8, 0, 3, 5, 9, 6]); // floyd
+        do_test(25, 10, &[18, 15, 14, 9, 0, 13, 5, 24]); // floyd
+        do_test(300, 8, &[30, 283, 150, 1, 73, 13, 285, 35]); // floyd
+        do_test(300, 80, &[31, 289, 248, 154, 5, 78, 19, 286]); // inplace
+        do_test(300, 180, &[31, 289, 248, 154, 5, 78, 19, 286]); // inplace
+
+        do_test(1_000_000, 8, &[
+            103717, 963485, 826422, 509101, 736394, 807035, 5327, 632573,
+        ]); // floyd
+        do_test(1_000_000, 180, &[
+            103718, 963490, 826426, 509103, 736396, 807036, 5327, 632573,
+        ]); // rejection
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/mod.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/mod.rs.html new file mode 100644 index 0000000..99cd32d --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand/seq/mod.rs.html @@ -0,0 +1,2715 @@ +mod.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+633
+634
+635
+636
+637
+638
+639
+640
+641
+642
+643
+644
+645
+646
+647
+648
+649
+650
+651
+652
+653
+654
+655
+656
+657
+658
+659
+660
+661
+662
+663
+664
+665
+666
+667
+668
+669
+670
+671
+672
+673
+674
+675
+676
+677
+678
+679
+680
+681
+682
+683
+684
+685
+686
+687
+688
+689
+690
+691
+692
+693
+694
+695
+696
+697
+698
+699
+700
+701
+702
+703
+704
+705
+706
+707
+708
+709
+710
+711
+712
+713
+714
+715
+716
+717
+718
+719
+720
+721
+722
+723
+724
+725
+726
+727
+728
+729
+730
+731
+732
+733
+734
+735
+736
+737
+738
+739
+740
+741
+742
+743
+744
+745
+746
+747
+748
+749
+750
+751
+752
+753
+754
+755
+756
+757
+758
+759
+760
+761
+762
+763
+764
+765
+766
+767
+768
+769
+770
+771
+772
+773
+774
+775
+776
+777
+778
+779
+780
+781
+782
+783
+784
+785
+786
+787
+788
+789
+790
+791
+792
+793
+794
+795
+796
+797
+798
+799
+800
+801
+802
+803
+804
+805
+806
+807
+808
+809
+810
+811
+812
+813
+814
+815
+816
+817
+818
+819
+820
+821
+822
+823
+824
+825
+826
+827
+828
+829
+830
+831
+832
+833
+834
+835
+836
+837
+838
+839
+840
+841
+842
+843
+844
+845
+846
+847
+848
+849
+850
+851
+852
+853
+854
+855
+856
+857
+858
+859
+860
+861
+862
+863
+864
+865
+866
+867
+868
+869
+870
+871
+872
+873
+874
+875
+876
+877
+878
+879
+880
+881
+882
+883
+884
+885
+886
+887
+888
+889
+890
+891
+892
+893
+894
+895
+896
+897
+898
+899
+900
+901
+902
+903
+904
+905
+906
+907
+908
+909
+910
+911
+912
+913
+914
+915
+916
+917
+918
+919
+920
+921
+922
+923
+924
+925
+926
+927
+928
+929
+930
+931
+932
+933
+934
+935
+936
+937
+938
+939
+940
+941
+942
+943
+944
+945
+946
+947
+948
+949
+950
+951
+952
+953
+954
+955
+956
+957
+958
+959
+960
+961
+962
+963
+964
+965
+966
+967
+968
+969
+970
+971
+972
+973
+974
+975
+976
+977
+978
+979
+980
+981
+982
+983
+984
+985
+986
+987
+988
+989
+990
+991
+992
+993
+994
+995
+996
+997
+998
+999
+1000
+1001
+1002
+1003
+1004
+1005
+1006
+1007
+1008
+1009
+1010
+1011
+1012
+1013
+1014
+1015
+1016
+1017
+1018
+1019
+1020
+1021
+1022
+1023
+1024
+1025
+1026
+1027
+1028
+1029
+1030
+1031
+1032
+1033
+1034
+1035
+1036
+1037
+1038
+1039
+1040
+1041
+1042
+1043
+1044
+1045
+1046
+1047
+1048
+1049
+1050
+1051
+1052
+1053
+1054
+1055
+1056
+1057
+1058
+1059
+1060
+1061
+1062
+1063
+1064
+1065
+1066
+1067
+1068
+1069
+1070
+1071
+1072
+1073
+1074
+1075
+1076
+1077
+1078
+1079
+1080
+1081
+1082
+1083
+1084
+1085
+1086
+1087
+1088
+1089
+1090
+1091
+1092
+1093
+1094
+1095
+1096
+1097
+1098
+1099
+1100
+1101
+1102
+1103
+1104
+1105
+1106
+1107
+1108
+1109
+1110
+1111
+1112
+1113
+1114
+1115
+1116
+1117
+1118
+1119
+1120
+1121
+1122
+1123
+1124
+1125
+1126
+1127
+1128
+1129
+1130
+1131
+1132
+1133
+1134
+1135
+1136
+1137
+1138
+1139
+1140
+1141
+1142
+1143
+1144
+1145
+1146
+1147
+1148
+1149
+1150
+1151
+1152
+1153
+1154
+1155
+1156
+1157
+1158
+1159
+1160
+1161
+1162
+1163
+1164
+1165
+1166
+1167
+1168
+1169
+1170
+1171
+1172
+1173
+1174
+1175
+1176
+1177
+1178
+1179
+1180
+1181
+1182
+1183
+1184
+1185
+1186
+1187
+1188
+1189
+1190
+1191
+1192
+1193
+1194
+1195
+1196
+1197
+1198
+1199
+1200
+1201
+1202
+1203
+1204
+1205
+1206
+1207
+1208
+1209
+1210
+1211
+1212
+1213
+1214
+1215
+1216
+1217
+1218
+1219
+1220
+1221
+1222
+1223
+1224
+1225
+1226
+1227
+1228
+1229
+1230
+1231
+1232
+1233
+1234
+1235
+1236
+1237
+1238
+1239
+1240
+1241
+1242
+1243
+1244
+1245
+1246
+1247
+1248
+1249
+1250
+1251
+1252
+1253
+1254
+1255
+1256
+1257
+1258
+1259
+1260
+1261
+1262
+1263
+1264
+1265
+1266
+1267
+1268
+1269
+1270
+1271
+1272
+1273
+1274
+1275
+1276
+1277
+1278
+1279
+1280
+1281
+1282
+1283
+1284
+1285
+1286
+1287
+1288
+1289
+1290
+1291
+1292
+1293
+1294
+1295
+1296
+1297
+1298
+1299
+1300
+1301
+1302
+1303
+1304
+1305
+1306
+1307
+1308
+1309
+1310
+1311
+1312
+1313
+1314
+1315
+1316
+1317
+1318
+1319
+1320
+1321
+1322
+1323
+1324
+1325
+1326
+1327
+1328
+1329
+1330
+1331
+1332
+1333
+1334
+1335
+1336
+1337
+1338
+1339
+1340
+1341
+1342
+1343
+1344
+1345
+1346
+1347
+1348
+1349
+1350
+1351
+1352
+1353
+1354
+1355
+1356
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Sequence-related functionality
+//!
+//! This module provides:
+//!
+//! *   [`SliceRandom`] slice sampling and mutation
+//! *   [`IteratorRandom`] iterator sampling
+//! *   [`index::sample`] low-level API to choose multiple indices from
+//!     `0..length`
+//!
+//! Also see:
+//!
+//! *   [`crate::distributions::WeightedIndex`] distribution which provides
+//!     weighted index sampling.
+//!
+//! In order to make results reproducible across 32-64 bit architectures, all
+//! `usize` indices are sampled as a `u32` where possible (also providing a
+//! small performance boost in some cases).
+
+
+#[cfg(feature = "alloc")]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+pub mod index;
+
+#[cfg(feature = "alloc")] use core::ops::Index;
+
+#[cfg(feature = "alloc")] use alloc::vec::Vec;
+
+#[cfg(feature = "alloc")]
+use crate::distributions::uniform::{SampleBorrow, SampleUniform};
+#[cfg(feature = "alloc")] use crate::distributions::WeightedError;
+use crate::Rng;
+
+/// Extension trait on slices, providing random mutation and sampling methods.
+///
+/// This trait is implemented on all `[T]` slice types, providing several
+/// methods for choosing and shuffling elements. You must `use` this trait:
+///
+/// ```
+/// use rand::seq::SliceRandom;
+///
+/// let mut rng = rand::thread_rng();
+/// let mut bytes = "Hello, random!".to_string().into_bytes();
+/// bytes.shuffle(&mut rng);
+/// let str = String::from_utf8(bytes).unwrap();
+/// println!("{}", str);
+/// ```
+/// Example output (non-deterministic):
+/// ```none
+/// l,nmroHado !le
+/// ```
+pub trait SliceRandom {
+    /// The element type.
+    type Item;
+
+    /// Returns a reference to one random element of the slice, or `None` if the
+    /// slice is empty.
+    ///
+    /// For slices, complexity is `O(1)`.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::thread_rng;
+    /// use rand::seq::SliceRandom;
+    ///
+    /// let choices = [1, 2, 4, 8, 16, 32];
+    /// let mut rng = thread_rng();
+    /// println!("{:?}", choices.choose(&mut rng));
+    /// assert_eq!(choices[..0].choose(&mut rng), None);
+    /// ```
+    fn choose<R>(&self, rng: &mut R) -> Option<&Self::Item>
+    where R: Rng + ?Sized;
+
+    /// Returns a mutable reference to one random element of the slice, or
+    /// `None` if the slice is empty.
+    ///
+    /// For slices, complexity is `O(1)`.
+    fn choose_mut<R>(&mut self, rng: &mut R) -> Option<&mut Self::Item>
+    where R: Rng + ?Sized;
+
+    /// Chooses `amount` elements from the slice at random, without repetition,
+    /// and in random order. The returned iterator is appropriate both for
+    /// collection into a `Vec` and filling an existing buffer (see example).
+    ///
+    /// In case this API is not sufficiently flexible, use [`index::sample`].
+    ///
+    /// For slices, complexity is the same as [`index::sample`].
+    ///
+    /// # Example
+    /// ```
+    /// use rand::seq::SliceRandom;
+    ///
+    /// let mut rng = &mut rand::thread_rng();
+    /// let sample = "Hello, audience!".as_bytes();
+    ///
+    /// // collect the results into a vector:
+    /// let v: Vec<u8> = sample.choose_multiple(&mut rng, 3).cloned().collect();
+    ///
+    /// // store in a buffer:
+    /// let mut buf = [0u8; 5];
+    /// for (b, slot) in sample.choose_multiple(&mut rng, buf.len()).zip(buf.iter_mut()) {
+    ///     *slot = *b;
+    /// }
+    /// ```
+    #[cfg(feature = "alloc")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+    fn choose_multiple<R>(&self, rng: &mut R, amount: usize) -> SliceChooseIter<Self, Self::Item>
+    where R: Rng + ?Sized;
+
+    /// Similar to [`choose`], but where the likelihood of each outcome may be
+    /// specified.
+    ///
+    /// The specified function `weight` maps each item `x` to a relative
+    /// likelihood `weight(x)`. The probability of each item being selected is
+    /// therefore `weight(x) / s`, where `s` is the sum of all `weight(x)`.
+    ///
+    /// For slices of length `n`, complexity is `O(n)`.
+    /// See also [`choose_weighted_mut`], [`distributions::weighted`].
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::prelude::*;
+    ///
+    /// let choices = [('a', 2), ('b', 1), ('c', 1)];
+    /// let mut rng = thread_rng();
+    /// // 50% chance to print 'a', 25% chance to print 'b', 25% chance to print 'c'
+    /// println!("{:?}", choices.choose_weighted(&mut rng, |item| item.1).unwrap().0);
+    /// ```
+    /// [`choose`]: SliceRandom::choose
+    /// [`choose_weighted_mut`]: SliceRandom::choose_weighted_mut
+    /// [`distributions::weighted`]: crate::distributions::weighted
+    #[cfg(feature = "alloc")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+    fn choose_weighted<R, F, B, X>(
+        &self, rng: &mut R, weight: F,
+    ) -> Result<&Self::Item, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> B,
+        B: SampleBorrow<X>,
+        X: SampleUniform
+            + for<'a> ::core::ops::AddAssign<&'a X>
+            + ::core::cmp::PartialOrd<X>
+            + Clone
+            + Default;
+
+    /// Similar to [`choose_mut`], but where the likelihood of each outcome may
+    /// be specified.
+    ///
+    /// The specified function `weight` maps each item `x` to a relative
+    /// likelihood `weight(x)`. The probability of each item being selected is
+    /// therefore `weight(x) / s`, where `s` is the sum of all `weight(x)`.
+    ///
+    /// For slices of length `n`, complexity is `O(n)`.
+    /// See also [`choose_weighted`], [`distributions::weighted`].
+    ///
+    /// [`choose_mut`]: SliceRandom::choose_mut
+    /// [`choose_weighted`]: SliceRandom::choose_weighted
+    /// [`distributions::weighted`]: crate::distributions::weighted
+    #[cfg(feature = "alloc")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+    fn choose_weighted_mut<R, F, B, X>(
+        &mut self, rng: &mut R, weight: F,
+    ) -> Result<&mut Self::Item, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> B,
+        B: SampleBorrow<X>,
+        X: SampleUniform
+            + for<'a> ::core::ops::AddAssign<&'a X>
+            + ::core::cmp::PartialOrd<X>
+            + Clone
+            + Default;
+
+    /// Similar to [`choose_multiple`], but where the likelihood of each element's
+    /// inclusion in the output may be specified. The elements are returned in an
+    /// arbitrary, unspecified order.
+    ///
+    /// The specified function `weight` maps each item `x` to a relative
+    /// likelihood `weight(x)`. The probability of each item being selected is
+    /// therefore `weight(x) / s`, where `s` is the sum of all `weight(x)`.
+    ///
+    /// If all of the weights are equal, even if they are all zero, each element has
+    /// an equal likelihood of being selected.
+    ///
+    /// The complexity of this method depends on the feature `partition_at_index`.
+    /// If the feature is enabled, then for slices of length `n`, the complexity
+    /// is `O(n)` space and `O(n)` time. Otherwise, the complexity is `O(n)` space and
+    /// `O(n * log amount)` time.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::prelude::*;
+    ///
+    /// let choices = [('a', 2), ('b', 1), ('c', 1)];
+    /// let mut rng = thread_rng();
+    /// // First Draw * Second Draw = total odds
+    /// // -----------------------
+    /// // (50% * 50%) + (25% * 67%) = 41.7% chance that the output is `['a', 'b']` in some order.
+    /// // (50% * 50%) + (25% * 67%) = 41.7% chance that the output is `['a', 'c']` in some order.
+    /// // (25% * 33%) + (25% * 33%) = 16.6% chance that the output is `['b', 'c']` in some order.
+    /// println!("{:?}", choices.choose_multiple_weighted(&mut rng, 2, |item| item.1).unwrap().collect::<Vec<_>>());
+    /// ```
+    /// [`choose_multiple`]: SliceRandom::choose_multiple
+    //
+    // Note: this is feature-gated on std due to usage of f64::powf.
+    // If necessary, we may use alloc+libm as an alternative (see PR #1089).
+    #[cfg(feature = "std")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+    fn choose_multiple_weighted<R, F, X>(
+        &self, rng: &mut R, amount: usize, weight: F,
+    ) -> Result<SliceChooseIter<Self, Self::Item>, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> X,
+        X: Into<f64>;
+
+    /// Shuffle a mutable slice in place.
+    ///
+    /// For slices of length `n`, complexity is `O(n)`.
+    ///
+    /// # Example
+    ///
+    /// ```
+    /// use rand::seq::SliceRandom;
+    /// use rand::thread_rng;
+    ///
+    /// let mut rng = thread_rng();
+    /// let mut y = [1, 2, 3, 4, 5];
+    /// println!("Unshuffled: {:?}", y);
+    /// y.shuffle(&mut rng);
+    /// println!("Shuffled:   {:?}", y);
+    /// ```
+    fn shuffle<R>(&mut self, rng: &mut R)
+    where R: Rng + ?Sized;
+
+    /// Shuffle a slice in place, but exit early.
+    ///
+    /// Returns two mutable slices from the source slice. The first contains
+    /// `amount` elements randomly permuted. The second has the remaining
+    /// elements that are not fully shuffled.
+    ///
+    /// This is an efficient method to select `amount` elements at random from
+    /// the slice, provided the slice may be mutated.
+    ///
+    /// If you only need to choose elements randomly and `amount > self.len()/2`
+    /// then you may improve performance by taking
+    /// `amount = values.len() - amount` and using only the second slice.
+    ///
+    /// If `amount` is greater than the number of elements in the slice, this
+    /// will perform a full shuffle.
+    ///
+    /// For slices, complexity is `O(m)` where `m = amount`.
+    fn partial_shuffle<R>(
+        &mut self, rng: &mut R, amount: usize,
+    ) -> (&mut [Self::Item], &mut [Self::Item])
+    where R: Rng + ?Sized;
+}
+
+/// Extension trait on iterators, providing random sampling methods.
+///
+/// This trait is implemented on all iterators `I` where `I: Iterator + Sized`
+/// and provides methods for
+/// choosing one or more elements. You must `use` this trait:
+///
+/// ```
+/// use rand::seq::IteratorRandom;
+///
+/// let mut rng = rand::thread_rng();
+///
+/// let faces = "😀😎😐😕😠😢";
+/// println!("I am {}!", faces.chars().choose(&mut rng).unwrap());
+/// ```
+/// Example output (non-deterministic):
+/// ```none
+/// I am 😀!
+/// ```
+pub trait IteratorRandom: Iterator + Sized {
+    /// Choose one element at random from the iterator.
+    ///
+    /// Returns `None` if and only if the iterator is empty.
+    ///
+    /// This method uses [`Iterator::size_hint`] for optimisation. With an
+    /// accurate hint and where [`Iterator::nth`] is a constant-time operation
+    /// this method can offer `O(1)` performance. Where no size hint is
+    /// available, complexity is `O(n)` where `n` is the iterator length.
+    /// Partial hints (where `lower > 0`) also improve performance.
+    ///
+    /// Note that the output values and the number of RNG samples used
+    /// depends on size hints. In particular, `Iterator` combinators that don't
+    /// change the values yielded but change the size hints may result in
+    /// `choose` returning different elements. If you want consistent results
+    /// and RNG usage consider using [`IteratorRandom::choose_stable`].
+    fn choose<R>(mut self, rng: &mut R) -> Option<Self::Item>
+    where R: Rng + ?Sized {
+        let (mut lower, mut upper) = self.size_hint();
+        let mut consumed = 0;
+        let mut result = None;
+
+        // Handling for this condition outside the loop allows the optimizer to eliminate the loop
+        // when the Iterator is an ExactSizeIterator. This has a large performance impact on e.g.
+        // seq_iter_choose_from_1000.
+        if upper == Some(lower) {
+            return if lower == 0 {
+                None
+            } else {
+                self.nth(gen_index(rng, lower))
+            };
+        }
+
+        // Continue until the iterator is exhausted
+        loop {
+            if lower > 1 {
+                let ix = gen_index(rng, lower + consumed);
+                let skip = if ix < lower {
+                    result = self.nth(ix);
+                    lower - (ix + 1)
+                } else {
+                    lower
+                };
+                if upper == Some(lower) {
+                    return result;
+                }
+                consumed += lower;
+                if skip > 0 {
+                    self.nth(skip - 1);
+                }
+            } else {
+                let elem = self.next();
+                if elem.is_none() {
+                    return result;
+                }
+                consumed += 1;
+                if gen_index(rng, consumed) == 0 {
+                    result = elem;
+                }
+            }
+
+            let hint = self.size_hint();
+            lower = hint.0;
+            upper = hint.1;
+        }
+    }
+
+    /// Choose one element at random from the iterator.
+    ///
+    /// Returns `None` if and only if the iterator is empty.
+    ///
+    /// This method is very similar to [`choose`] except that the result
+    /// only depends on the length of the iterator and the values produced by
+    /// `rng`. Notably for any iterator of a given length this will make the
+    /// same requests to `rng` and if the same sequence of values are produced
+    /// the same index will be selected from `self`. This may be useful if you
+    /// need consistent results no matter what type of iterator you are working
+    /// with. If you do not need this stability prefer [`choose`].
+    ///
+    /// Note that this method still uses [`Iterator::size_hint`] to skip
+    /// constructing elements where possible, however the selection and `rng`
+    /// calls are the same in the face of this optimization. If you want to
+    /// force every element to be created regardless call `.inspect(|e| ())`.
+    ///
+    /// [`choose`]: IteratorRandom::choose
+    fn choose_stable<R>(mut self, rng: &mut R) -> Option<Self::Item>
+    where R: Rng + ?Sized {
+        let mut consumed = 0;
+        let mut result = None;
+
+        loop {
+            // Currently the only way to skip elements is `nth()`. So we need to
+            // store what index to access next here.
+            // This should be replaced by `advance_by()` once it is stable:
+            // https://github.com/rust-lang/rust/issues/77404
+            let mut next = 0;
+
+            let (lower, _) = self.size_hint();
+            if lower >= 2 {
+                let highest_selected = (0..lower)
+                    .filter(|ix| gen_index(rng, consumed+ix+1) == 0)
+                    .last();
+
+                consumed += lower;
+                next = lower;
+
+                if let Some(ix) = highest_selected {
+                    result = self.nth(ix);
+                    next -= ix + 1;
+                    debug_assert!(result.is_some(), "iterator shorter than size_hint().0");
+                }
+            }
+
+            let elem = self.nth(next);
+            if elem.is_none() {
+                return result
+            }
+
+            if gen_index(rng, consumed+1) == 0 {
+                result = elem;
+            }
+            consumed += 1;
+        }
+    }
+
+    /// Collects values at random from the iterator into a supplied buffer
+    /// until that buffer is filled.
+    ///
+    /// Although the elements are selected randomly, the order of elements in
+    /// the buffer is neither stable nor fully random. If random ordering is
+    /// desired, shuffle the result.
+    ///
+    /// Returns the number of elements added to the buffer. This equals the length
+    /// of the buffer unless the iterator contains insufficient elements, in which
+    /// case this equals the number of elements available.
+    ///
+    /// Complexity is `O(n)` where `n` is the length of the iterator.
+    /// For slices, prefer [`SliceRandom::choose_multiple`].
+    fn choose_multiple_fill<R>(mut self, rng: &mut R, buf: &mut [Self::Item]) -> usize
+    where R: Rng + ?Sized {
+        let amount = buf.len();
+        let mut len = 0;
+        while len < amount {
+            if let Some(elem) = self.next() {
+                buf[len] = elem;
+                len += 1;
+            } else {
+                // Iterator exhausted; stop early
+                return len;
+            }
+        }
+
+        // Continue, since the iterator was not exhausted
+        for (i, elem) in self.enumerate() {
+            let k = gen_index(rng, i + 1 + amount);
+            if let Some(slot) = buf.get_mut(k) {
+                *slot = elem;
+            }
+        }
+        len
+    }
+
+    /// Collects `amount` values at random from the iterator into a vector.
+    ///
+    /// This is equivalent to `choose_multiple_fill` except for the result type.
+    ///
+    /// Although the elements are selected randomly, the order of elements in
+    /// the buffer is neither stable nor fully random. If random ordering is
+    /// desired, shuffle the result.
+    ///
+    /// The length of the returned vector equals `amount` unless the iterator
+    /// contains insufficient elements, in which case it equals the number of
+    /// elements available.
+    ///
+    /// Complexity is `O(n)` where `n` is the length of the iterator.
+    /// For slices, prefer [`SliceRandom::choose_multiple`].
+    #[cfg(feature = "alloc")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+    fn choose_multiple<R>(mut self, rng: &mut R, amount: usize) -> Vec<Self::Item>
+    where R: Rng + ?Sized {
+        let mut reservoir = Vec::with_capacity(amount);
+        reservoir.extend(self.by_ref().take(amount));
+
+        // Continue unless the iterator was exhausted
+        //
+        // note: this prevents iterators that "restart" from causing problems.
+        // If the iterator stops once, then so do we.
+        if reservoir.len() == amount {
+            for (i, elem) in self.enumerate() {
+                let k = gen_index(rng, i + 1 + amount);
+                if let Some(slot) = reservoir.get_mut(k) {
+                    *slot = elem;
+                }
+            }
+        } else {
+            // Don't hang onto extra memory. There is a corner case where
+            // `amount` was much less than `self.len()`.
+            reservoir.shrink_to_fit();
+        }
+        reservoir
+    }
+}
+
+
+impl<T> SliceRandom for [T] {
+    type Item = T;
+
+    fn choose<R>(&self, rng: &mut R) -> Option<&Self::Item>
+    where R: Rng + ?Sized {
+        if self.is_empty() {
+            None
+        } else {
+            Some(&self[gen_index(rng, self.len())])
+        }
+    }
+
+    fn choose_mut<R>(&mut self, rng: &mut R) -> Option<&mut Self::Item>
+    where R: Rng + ?Sized {
+        if self.is_empty() {
+            None
+        } else {
+            let len = self.len();
+            Some(&mut self[gen_index(rng, len)])
+        }
+    }
+
+    #[cfg(feature = "alloc")]
+    fn choose_multiple<R>(&self, rng: &mut R, amount: usize) -> SliceChooseIter<Self, Self::Item>
+    where R: Rng + ?Sized {
+        let amount = ::core::cmp::min(amount, self.len());
+        SliceChooseIter {
+            slice: self,
+            _phantom: Default::default(),
+            indices: index::sample(rng, self.len(), amount).into_iter(),
+        }
+    }
+
+    #[cfg(feature = "alloc")]
+    fn choose_weighted<R, F, B, X>(
+        &self, rng: &mut R, weight: F,
+    ) -> Result<&Self::Item, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> B,
+        B: SampleBorrow<X>,
+        X: SampleUniform
+            + for<'a> ::core::ops::AddAssign<&'a X>
+            + ::core::cmp::PartialOrd<X>
+            + Clone
+            + Default,
+    {
+        use crate::distributions::{Distribution, WeightedIndex};
+        let distr = WeightedIndex::new(self.iter().map(weight))?;
+        Ok(&self[distr.sample(rng)])
+    }
+
+    #[cfg(feature = "alloc")]
+    fn choose_weighted_mut<R, F, B, X>(
+        &mut self, rng: &mut R, weight: F,
+    ) -> Result<&mut Self::Item, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> B,
+        B: SampleBorrow<X>,
+        X: SampleUniform
+            + for<'a> ::core::ops::AddAssign<&'a X>
+            + ::core::cmp::PartialOrd<X>
+            + Clone
+            + Default,
+    {
+        use crate::distributions::{Distribution, WeightedIndex};
+        let distr = WeightedIndex::new(self.iter().map(weight))?;
+        Ok(&mut self[distr.sample(rng)])
+    }
+
+    #[cfg(feature = "std")]
+    fn choose_multiple_weighted<R, F, X>(
+        &self, rng: &mut R, amount: usize, weight: F,
+    ) -> Result<SliceChooseIter<Self, Self::Item>, WeightedError>
+    where
+        R: Rng + ?Sized,
+        F: Fn(&Self::Item) -> X,
+        X: Into<f64>,
+    {
+        let amount = ::core::cmp::min(amount, self.len());
+        Ok(SliceChooseIter {
+            slice: self,
+            _phantom: Default::default(),
+            indices: index::sample_weighted(
+                rng,
+                self.len(),
+                |idx| weight(&self[idx]).into(),
+                amount,
+            )?
+            .into_iter(),
+        })
+    }
+
+    fn shuffle<R>(&mut self, rng: &mut R)
+    where R: Rng + ?Sized {
+        for i in (1..self.len()).rev() {
+            // invariant: elements with index > i have been locked in place.
+            self.swap(i, gen_index(rng, i + 1));
+        }
+    }
+
+    fn partial_shuffle<R>(
+        &mut self, rng: &mut R, amount: usize,
+    ) -> (&mut [Self::Item], &mut [Self::Item])
+    where R: Rng + ?Sized {
+        // This applies Durstenfeld's algorithm for the
+        // [Fisher–Yates shuffle](https://en.wikipedia.org/wiki/Fisher%E2%80%93Yates_shuffle#The_modern_algorithm)
+        // for an unbiased permutation, but exits early after choosing `amount`
+        // elements.
+
+        let len = self.len();
+        let end = if amount >= len { 0 } else { len - amount };
+
+        for i in (end..len).rev() {
+            // invariant: elements with index > i have been locked in place.
+            self.swap(i, gen_index(rng, i + 1));
+        }
+        let r = self.split_at_mut(end);
+        (r.1, r.0)
+    }
+}
+
+impl<I> IteratorRandom for I where I: Iterator + Sized {}
+
+
+/// An iterator over multiple slice elements.
+///
+/// This struct is created by
+/// [`SliceRandom::choose_multiple`](trait.SliceRandom.html#tymethod.choose_multiple).
+#[cfg(feature = "alloc")]
+#[cfg_attr(doc_cfg, doc(cfg(feature = "alloc")))]
+#[derive(Debug)]
+pub struct SliceChooseIter<'a, S: ?Sized + 'a, T: 'a> {
+    slice: &'a S,
+    _phantom: ::core::marker::PhantomData<T>,
+    indices: index::IndexVecIntoIter,
+}
+
+#[cfg(feature = "alloc")]
+impl<'a, S: Index<usize, Output = T> + ?Sized + 'a, T: 'a> Iterator for SliceChooseIter<'a, S, T> {
+    type Item = &'a T;
+
+    fn next(&mut self) -> Option<Self::Item> {
+        // TODO: investigate using SliceIndex::get_unchecked when stable
+        self.indices.next().map(|i| &self.slice[i as usize])
+    }
+
+    fn size_hint(&self) -> (usize, Option<usize>) {
+        (self.indices.len(), Some(self.indices.len()))
+    }
+}
+
+#[cfg(feature = "alloc")]
+impl<'a, S: Index<usize, Output = T> + ?Sized + 'a, T: 'a> ExactSizeIterator
+    for SliceChooseIter<'a, S, T>
+{
+    fn len(&self) -> usize {
+        self.indices.len()
+    }
+}
+
+
+// Sample a number uniformly between 0 and `ubound`. Uses 32-bit sampling where
+// possible, primarily in order to produce the same output on 32-bit and 64-bit
+// platforms.
+#[inline]
+fn gen_index<R: Rng + ?Sized>(rng: &mut R, ubound: usize) -> usize {
+    if ubound <= (core::u32::MAX as usize) {
+        rng.gen_range(0..ubound as u32) as usize
+    } else {
+        rng.gen_range(0..ubound)
+    }
+}
+
+
+#[cfg(test)]
+mod test {
+    use super::*;
+    #[cfg(feature = "alloc")] use crate::Rng;
+    #[cfg(all(feature = "alloc", not(feature = "std")))] use alloc::vec::Vec;
+
+    #[test]
+    fn test_slice_choose() {
+        let mut r = crate::test::rng(107);
+        let chars = [
+            'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
+        ];
+        let mut chosen = [0i32; 14];
+        // The below all use a binomial distribution with n=1000, p=1/14.
+        // binocdf(40, 1000, 1/14) ~= 2e-5; 1-binocdf(106, ..) ~= 2e-5
+        for _ in 0..1000 {
+            let picked = *chars.choose(&mut r).unwrap();
+            chosen[(picked as usize) - ('a' as usize)] += 1;
+        }
+        for count in chosen.iter() {
+            assert!(40 < *count && *count < 106);
+        }
+
+        chosen.iter_mut().for_each(|x| *x = 0);
+        for _ in 0..1000 {
+            *chosen.choose_mut(&mut r).unwrap() += 1;
+        }
+        for count in chosen.iter() {
+            assert!(40 < *count && *count < 106);
+        }
+
+        let mut v: [isize; 0] = [];
+        assert_eq!(v.choose(&mut r), None);
+        assert_eq!(v.choose_mut(&mut r), None);
+    }
+
+    #[test]
+    fn value_stability_slice() {
+        let mut r = crate::test::rng(413);
+        let chars = [
+            'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h', 'i', 'j', 'k', 'l', 'm', 'n',
+        ];
+        let mut nums = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
+
+        assert_eq!(chars.choose(&mut r), Some(&'l'));
+        assert_eq!(nums.choose_mut(&mut r), Some(&mut 10));
+
+        #[cfg(feature = "alloc")]
+        assert_eq!(
+            &chars
+                .choose_multiple(&mut r, 8)
+                .cloned()
+                .collect::<Vec<char>>(),
+            &['d', 'm', 'b', 'n', 'c', 'k', 'h', 'e']
+        );
+
+        #[cfg(feature = "alloc")]
+        assert_eq!(chars.choose_weighted(&mut r, |_| 1), Ok(&'f'));
+        #[cfg(feature = "alloc")]
+        assert_eq!(nums.choose_weighted_mut(&mut r, |_| 1), Ok(&mut 5));
+
+        let mut r = crate::test::rng(414);
+        nums.shuffle(&mut r);
+        assert_eq!(nums, [9, 5, 3, 10, 7, 12, 8, 11, 6, 4, 0, 2, 1]);
+        nums = [0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12];
+        let res = nums.partial_shuffle(&mut r, 6);
+        assert_eq!(res.0, &mut [7, 4, 8, 6, 9, 3]);
+        assert_eq!(res.1, &mut [0, 1, 2, 12, 11, 5, 10]);
+    }
+
+    #[derive(Clone)]
+    struct UnhintedIterator<I: Iterator + Clone> {
+        iter: I,
+    }
+    impl<I: Iterator + Clone> Iterator for UnhintedIterator<I> {
+        type Item = I::Item;
+
+        fn next(&mut self) -> Option<Self::Item> {
+            self.iter.next()
+        }
+    }
+
+    #[derive(Clone)]
+    struct ChunkHintedIterator<I: ExactSizeIterator + Iterator + Clone> {
+        iter: I,
+        chunk_remaining: usize,
+        chunk_size: usize,
+        hint_total_size: bool,
+    }
+    impl<I: ExactSizeIterator + Iterator + Clone> Iterator for ChunkHintedIterator<I> {
+        type Item = I::Item;
+
+        fn next(&mut self) -> Option<Self::Item> {
+            if self.chunk_remaining == 0 {
+                self.chunk_remaining = ::core::cmp::min(self.chunk_size, self.iter.len());
+            }
+            self.chunk_remaining = self.chunk_remaining.saturating_sub(1);
+
+            self.iter.next()
+        }
+
+        fn size_hint(&self) -> (usize, Option<usize>) {
+            (
+                self.chunk_remaining,
+                if self.hint_total_size {
+                    Some(self.iter.len())
+                } else {
+                    None
+                },
+            )
+        }
+    }
+
+    #[derive(Clone)]
+    struct WindowHintedIterator<I: ExactSizeIterator + Iterator + Clone> {
+        iter: I,
+        window_size: usize,
+        hint_total_size: bool,
+    }
+    impl<I: ExactSizeIterator + Iterator + Clone> Iterator for WindowHintedIterator<I> {
+        type Item = I::Item;
+
+        fn next(&mut self) -> Option<Self::Item> {
+            self.iter.next()
+        }
+
+        fn size_hint(&self) -> (usize, Option<usize>) {
+            (
+                ::core::cmp::min(self.iter.len(), self.window_size),
+                if self.hint_total_size {
+                    Some(self.iter.len())
+                } else {
+                    None
+                },
+            )
+        }
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_iterator_choose() {
+        let r = &mut crate::test::rng(109);
+        fn test_iter<R: Rng + ?Sized, Iter: Iterator<Item = usize> + Clone>(r: &mut R, iter: Iter) {
+            let mut chosen = [0i32; 9];
+            for _ in 0..1000 {
+                let picked = iter.clone().choose(r).unwrap();
+                chosen[picked] += 1;
+            }
+            for count in chosen.iter() {
+                // Samples should follow Binomial(1000, 1/9)
+                // Octave: binopdf(x, 1000, 1/9) gives the prob of *count == x
+                // Note: have seen 153, which is unlikely but not impossible.
+                assert!(
+                    72 < *count && *count < 154,
+                    "count not close to 1000/9: {}",
+                    count
+                );
+            }
+        }
+
+        test_iter(r, 0..9);
+        test_iter(r, [0, 1, 2, 3, 4, 5, 6, 7, 8].iter().cloned());
+        #[cfg(feature = "alloc")]
+        test_iter(r, (0..9).collect::<Vec<_>>().into_iter());
+        test_iter(r, UnhintedIterator { iter: 0..9 });
+        test_iter(r, ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: false,
+        });
+        test_iter(r, ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: true,
+        });
+        test_iter(r, WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: false,
+        });
+        test_iter(r, WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: true,
+        });
+
+        assert_eq!((0..0).choose(r), None);
+        assert_eq!(UnhintedIterator { iter: 0..0 }.choose(r), None);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_iterator_choose_stable() {
+        let r = &mut crate::test::rng(109);
+        fn test_iter<R: Rng + ?Sized, Iter: Iterator<Item = usize> + Clone>(r: &mut R, iter: Iter) {
+            let mut chosen = [0i32; 9];
+            for _ in 0..1000 {
+                let picked = iter.clone().choose_stable(r).unwrap();
+                chosen[picked] += 1;
+            }
+            for count in chosen.iter() {
+                // Samples should follow Binomial(1000, 1/9)
+                // Octave: binopdf(x, 1000, 1/9) gives the prob of *count == x
+                // Note: have seen 153, which is unlikely but not impossible.
+                assert!(
+                    72 < *count && *count < 154,
+                    "count not close to 1000/9: {}",
+                    count
+                );
+            }
+        }
+
+        test_iter(r, 0..9);
+        test_iter(r, [0, 1, 2, 3, 4, 5, 6, 7, 8].iter().cloned());
+        #[cfg(feature = "alloc")]
+        test_iter(r, (0..9).collect::<Vec<_>>().into_iter());
+        test_iter(r, UnhintedIterator { iter: 0..9 });
+        test_iter(r, ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: false,
+        });
+        test_iter(r, ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: true,
+        });
+        test_iter(r, WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: false,
+        });
+        test_iter(r, WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: true,
+        });
+
+        assert_eq!((0..0).choose(r), None);
+        assert_eq!(UnhintedIterator { iter: 0..0 }.choose(r), None);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_iterator_choose_stable_stability() {
+        fn test_iter(iter: impl Iterator<Item = usize> + Clone) -> [i32; 9] {
+            let r = &mut crate::test::rng(109);
+            let mut chosen = [0i32; 9];
+            for _ in 0..1000 {
+                let picked = iter.clone().choose_stable(r).unwrap();
+                chosen[picked] += 1;
+            }
+            chosen
+        }
+
+        let reference = test_iter(0..9);
+        assert_eq!(test_iter([0, 1, 2, 3, 4, 5, 6, 7, 8].iter().cloned()), reference);
+
+        #[cfg(feature = "alloc")]
+        assert_eq!(test_iter((0..9).collect::<Vec<_>>().into_iter()), reference);
+        assert_eq!(test_iter(UnhintedIterator { iter: 0..9 }), reference);
+        assert_eq!(test_iter(ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: false,
+        }), reference);
+        assert_eq!(test_iter(ChunkHintedIterator {
+            iter: 0..9,
+            chunk_size: 4,
+            chunk_remaining: 4,
+            hint_total_size: true,
+        }), reference);
+        assert_eq!(test_iter(WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: false,
+        }), reference);
+        assert_eq!(test_iter(WindowHintedIterator {
+            iter: 0..9,
+            window_size: 2,
+            hint_total_size: true,
+        }), reference);
+    }
+
+    #[test]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_shuffle() {
+        let mut r = crate::test::rng(108);
+        let empty: &mut [isize] = &mut [];
+        empty.shuffle(&mut r);
+        let mut one = [1];
+        one.shuffle(&mut r);
+        let b: &[_] = &[1];
+        assert_eq!(one, b);
+
+        let mut two = [1, 2];
+        two.shuffle(&mut r);
+        assert!(two == [1, 2] || two == [2, 1]);
+
+        fn move_last(slice: &mut [usize], pos: usize) {
+            // use slice[pos..].rotate_left(1); once we can use that
+            let last_val = slice[pos];
+            for i in pos..slice.len() - 1 {
+                slice[i] = slice[i + 1];
+            }
+            *slice.last_mut().unwrap() = last_val;
+        }
+        let mut counts = [0i32; 24];
+        for _ in 0..10000 {
+            let mut arr: [usize; 4] = [0, 1, 2, 3];
+            arr.shuffle(&mut r);
+            let mut permutation = 0usize;
+            let mut pos_value = counts.len();
+            for i in 0..4 {
+                pos_value /= 4 - i;
+                let pos = arr.iter().position(|&x| x == i).unwrap();
+                assert!(pos < (4 - i));
+                permutation += pos * pos_value;
+                move_last(&mut arr, pos);
+                assert_eq!(arr[3], i);
+            }
+            for (i, &a) in arr.iter().enumerate() {
+                assert_eq!(a, i);
+            }
+            counts[permutation] += 1;
+        }
+        for count in counts.iter() {
+            // Binomial(10000, 1/24) with average 416.667
+            // Octave: binocdf(n, 10000, 1/24)
+            // 99.9% chance samples lie within this range:
+            assert!(352 <= *count && *count <= 483, "count: {}", count);
+        }
+    }
+
+    #[test]
+    fn test_partial_shuffle() {
+        let mut r = crate::test::rng(118);
+
+        let mut empty: [u32; 0] = [];
+        let res = empty.partial_shuffle(&mut r, 10);
+        assert_eq!((res.0.len(), res.1.len()), (0, 0));
+
+        let mut v = [1, 2, 3, 4, 5];
+        let res = v.partial_shuffle(&mut r, 2);
+        assert_eq!((res.0.len(), res.1.len()), (2, 3));
+        assert!(res.0[0] != res.0[1]);
+        // First elements are only modified if selected, so at least one isn't modified:
+        assert!(res.1[0] == 1 || res.1[1] == 2 || res.1[2] == 3);
+    }
+
+    #[test]
+    #[cfg(feature = "alloc")]
+    fn test_sample_iter() {
+        let min_val = 1;
+        let max_val = 100;
+
+        let mut r = crate::test::rng(401);
+        let vals = (min_val..max_val).collect::<Vec<i32>>();
+        let small_sample = vals.iter().choose_multiple(&mut r, 5);
+        let large_sample = vals.iter().choose_multiple(&mut r, vals.len() + 5);
+
+        assert_eq!(small_sample.len(), 5);
+        assert_eq!(large_sample.len(), vals.len());
+        // no randomization happens when amount >= len
+        assert_eq!(large_sample, vals.iter().collect::<Vec<_>>());
+
+        assert!(small_sample
+            .iter()
+            .all(|e| { **e >= min_val && **e <= max_val }));
+    }
+
+    #[test]
+    #[cfg(feature = "alloc")]
+    #[cfg_attr(miri, ignore)] // Miri is too slow
+    fn test_weighted() {
+        let mut r = crate::test::rng(406);
+        const N_REPS: u32 = 3000;
+        let weights = [1u32, 2, 3, 0, 5, 6, 7, 1, 2, 3, 4, 5, 6, 7];
+        let total_weight = weights.iter().sum::<u32>() as f32;
+
+        let verify = |result: [i32; 14]| {
+            for (i, count) in result.iter().enumerate() {
+                let exp = (weights[i] * N_REPS) as f32 / total_weight;
+                let mut err = (*count as f32 - exp).abs();
+                if err != 0.0 {
+                    err /= exp;
+                }
+                assert!(err <= 0.25);
+            }
+        };
+
+        // choose_weighted
+        fn get_weight<T>(item: &(u32, T)) -> u32 {
+            item.0
+        }
+        let mut chosen = [0i32; 14];
+        let mut items = [(0u32, 0usize); 14]; // (weight, index)
+        for (i, item) in items.iter_mut().enumerate() {
+            *item = (weights[i], i);
+        }
+        for _ in 0..N_REPS {
+            let item = items.choose_weighted(&mut r, get_weight).unwrap();
+            chosen[item.1] += 1;
+        }
+        verify(chosen);
+
+        // choose_weighted_mut
+        let mut items = [(0u32, 0i32); 14]; // (weight, count)
+        for (i, item) in items.iter_mut().enumerate() {
+            *item = (weights[i], 0);
+        }
+        for _ in 0..N_REPS {
+            items.choose_weighted_mut(&mut r, get_weight).unwrap().1 += 1;
+        }
+        for (ch, item) in chosen.iter_mut().zip(items.iter()) {
+            *ch = item.1;
+        }
+        verify(chosen);
+
+        // Check error cases
+        let empty_slice = &mut [10][0..0];
+        assert_eq!(
+            empty_slice.choose_weighted(&mut r, |_| 1),
+            Err(WeightedError::NoItem)
+        );
+        assert_eq!(
+            empty_slice.choose_weighted_mut(&mut r, |_| 1),
+            Err(WeightedError::NoItem)
+        );
+        assert_eq!(
+            ['x'].choose_weighted_mut(&mut r, |_| 0),
+            Err(WeightedError::AllWeightsZero)
+        );
+        assert_eq!(
+            [0, -1].choose_weighted_mut(&mut r, |x| *x),
+            Err(WeightedError::InvalidWeight)
+        );
+        assert_eq!(
+            [-1, 0].choose_weighted_mut(&mut r, |x| *x),
+            Err(WeightedError::InvalidWeight)
+        );
+    }
+
+    #[test]
+    fn value_stability_choose() {
+        fn choose<I: Iterator<Item = u32>>(iter: I) -> Option<u32> {
+            let mut rng = crate::test::rng(411);
+            iter.choose(&mut rng)
+        }
+
+        assert_eq!(choose([].iter().cloned()), None);
+        assert_eq!(choose(0..100), Some(33));
+        assert_eq!(choose(UnhintedIterator { iter: 0..100 }), Some(40));
+        assert_eq!(
+            choose(ChunkHintedIterator {
+                iter: 0..100,
+                chunk_size: 32,
+                chunk_remaining: 32,
+                hint_total_size: false,
+            }),
+            Some(39)
+        );
+        assert_eq!(
+            choose(ChunkHintedIterator {
+                iter: 0..100,
+                chunk_size: 32,
+                chunk_remaining: 32,
+                hint_total_size: true,
+            }),
+            Some(39)
+        );
+        assert_eq!(
+            choose(WindowHintedIterator {
+                iter: 0..100,
+                window_size: 32,
+                hint_total_size: false,
+            }),
+            Some(90)
+        );
+        assert_eq!(
+            choose(WindowHintedIterator {
+                iter: 0..100,
+                window_size: 32,
+                hint_total_size: true,
+            }),
+            Some(90)
+        );
+    }
+
+    #[test]
+    fn value_stability_choose_stable() {
+        fn choose<I: Iterator<Item = u32>>(iter: I) -> Option<u32> {
+            let mut rng = crate::test::rng(411);
+            iter.choose_stable(&mut rng)
+        }
+
+        assert_eq!(choose([].iter().cloned()), None);
+        assert_eq!(choose(0..100), Some(40));
+        assert_eq!(choose(UnhintedIterator { iter: 0..100 }), Some(40));
+        assert_eq!(
+            choose(ChunkHintedIterator {
+                iter: 0..100,
+                chunk_size: 32,
+                chunk_remaining: 32,
+                hint_total_size: false,
+            }),
+            Some(40)
+        );
+        assert_eq!(
+            choose(ChunkHintedIterator {
+                iter: 0..100,
+                chunk_size: 32,
+                chunk_remaining: 32,
+                hint_total_size: true,
+            }),
+            Some(40)
+        );
+        assert_eq!(
+            choose(WindowHintedIterator {
+                iter: 0..100,
+                window_size: 32,
+                hint_total_size: false,
+            }),
+            Some(40)
+        );
+        assert_eq!(
+            choose(WindowHintedIterator {
+                iter: 0..100,
+                window_size: 32,
+                hint_total_size: true,
+            }),
+            Some(40)
+        );
+    }
+
+    #[test]
+    fn value_stability_choose_multiple() {
+        fn do_test<I: Iterator<Item = u32>>(iter: I, v: &[u32]) {
+            let mut rng = crate::test::rng(412);
+            let mut buf = [0u32; 8];
+            assert_eq!(iter.choose_multiple_fill(&mut rng, &mut buf), v.len());
+            assert_eq!(&buf[0..v.len()], v);
+        }
+
+        do_test(0..4, &[0, 1, 2, 3]);
+        do_test(0..8, &[0, 1, 2, 3, 4, 5, 6, 7]);
+        do_test(0..100, &[58, 78, 80, 92, 43, 8, 96, 7]);
+
+        #[cfg(feature = "alloc")]
+        {
+            fn do_test<I: Iterator<Item = u32>>(iter: I, v: &[u32]) {
+                let mut rng = crate::test::rng(412);
+                assert_eq!(iter.choose_multiple(&mut rng, v.len()), v);
+            }
+
+            do_test(0..4, &[0, 1, 2, 3]);
+            do_test(0..8, &[0, 1, 2, 3, 4, 5, 6, 7]);
+            do_test(0..100, &[58, 78, 80, 92, 43, 8, 96, 7]);
+        }
+    }
+
+    #[test]
+    #[cfg(feature = "std")]
+    fn test_multiple_weighted_edge_cases() {
+        use super::*;
+
+        let mut rng = crate::test::rng(413);
+
+        // Case 1: One of the weights is 0
+        let choices = [('a', 2), ('b', 1), ('c', 0)];
+        for _ in 0..100 {
+            let result = choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap()
+                .collect::<Vec<_>>();
+
+            assert_eq!(result.len(), 2);
+            assert!(!result.iter().any(|val| val.0 == 'c'));
+        }
+
+        // Case 2: All of the weights are 0
+        let choices = [('a', 0), ('b', 0), ('c', 0)];
+
+        assert_eq!(choices
+            .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+            .unwrap().count(), 2);
+
+        // Case 3: Negative weights
+        let choices = [('a', -1), ('b', 1), ('c', 1)];
+        assert_eq!(
+            choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+
+        // Case 4: Empty list
+        let choices = [];
+        assert_eq!(choices
+            .choose_multiple_weighted(&mut rng, 0, |_: &()| 0)
+            .unwrap().count(), 0);
+
+        // Case 5: NaN weights
+        let choices = [('a', core::f64::NAN), ('b', 1.0), ('c', 1.0)];
+        assert_eq!(
+            choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+
+        // Case 6: +infinity weights
+        let choices = [('a', core::f64::INFINITY), ('b', 1.0), ('c', 1.0)];
+        for _ in 0..100 {
+            let result = choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap()
+                .collect::<Vec<_>>();
+            assert_eq!(result.len(), 2);
+            assert!(result.iter().any(|val| val.0 == 'a'));
+        }
+
+        // Case 7: -infinity weights
+        let choices = [('a', core::f64::NEG_INFINITY), ('b', 1.0), ('c', 1.0)];
+        assert_eq!(
+            choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap_err(),
+            WeightedError::InvalidWeight
+        );
+
+        // Case 8: -0 weights
+        let choices = [('a', -0.0), ('b', 1.0), ('c', 1.0)];
+        assert!(choices
+            .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+            .is_ok());
+    }
+
+    #[test]
+    #[cfg(feature = "std")]
+    fn test_multiple_weighted_distributions() {
+        use super::*;
+
+        // The theoretical probabilities of the different outcomes are:
+        // AB: 0.5  * 0.5  = 0.250
+        // AC: 0.5  * 0.5  = 0.250
+        // BA: 0.25 * 0.67 = 0.167
+        // BC: 0.25 * 0.33 = 0.082
+        // CA: 0.25 * 0.67 = 0.167
+        // CB: 0.25 * 0.33 = 0.082
+        let choices = [('a', 2), ('b', 1), ('c', 1)];
+        let mut rng = crate::test::rng(414);
+
+        let mut results = [0i32; 3];
+        let expected_results = [4167, 4167, 1666];
+        for _ in 0..10000 {
+            let result = choices
+                .choose_multiple_weighted(&mut rng, 2, |item| item.1)
+                .unwrap()
+                .collect::<Vec<_>>();
+
+            assert_eq!(result.len(), 2);
+
+            match (result[0].0, result[1].0) {
+                ('a', 'b') | ('b', 'a') => {
+                    results[0] += 1;
+                }
+                ('a', 'c') | ('c', 'a') => {
+                    results[1] += 1;
+                }
+                ('b', 'c') | ('c', 'b') => {
+                    results[2] += 1;
+                }
+                (_, _) => panic!("unexpected result"),
+            }
+        }
+
+        let mut diffs = results
+            .iter()
+            .zip(&expected_results)
+            .map(|(a, b)| (a - b).abs());
+        assert!(!diffs.any(|deviation| deviation > 100));
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/chacha.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/chacha.rs.html new file mode 100644 index 0000000..8547efa --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/chacha.rs.html @@ -0,0 +1,1267 @@ +chacha.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+540
+541
+542
+543
+544
+545
+546
+547
+548
+549
+550
+551
+552
+553
+554
+555
+556
+557
+558
+559
+560
+561
+562
+563
+564
+565
+566
+567
+568
+569
+570
+571
+572
+573
+574
+575
+576
+577
+578
+579
+580
+581
+582
+583
+584
+585
+586
+587
+588
+589
+590
+591
+592
+593
+594
+595
+596
+597
+598
+599
+600
+601
+602
+603
+604
+605
+606
+607
+608
+609
+610
+611
+612
+613
+614
+615
+616
+617
+618
+619
+620
+621
+622
+623
+624
+625
+626
+627
+628
+629
+630
+631
+632
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The ChaCha random number generator.
+
+#[cfg(not(feature = "std"))] use core;
+#[cfg(feature = "std")] use std as core;
+
+use self::core::fmt;
+use crate::guts::ChaCha;
+use rand_core::block::{BlockRng, BlockRngCore};
+use rand_core::{CryptoRng, Error, RngCore, SeedableRng};
+
+#[cfg(feature = "serde1")] use serde::{Serialize, Deserialize, Serializer, Deserializer};
+
+// NB. this must remain consistent with some currently hard-coded numbers in this module
+const BUF_BLOCKS: u8 = 4;
+// number of 32-bit words per ChaCha block (fixed by algorithm definition)
+const BLOCK_WORDS: u8 = 16;
+
+#[repr(transparent)]
+pub struct Array64<T>([T; 64]);
+impl<T> Default for Array64<T>
+where T: Default
+{
+    #[rustfmt::skip]
+    fn default() -> Self {
+        Self([
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+            T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(), T::default(),
+        ])
+    }
+}
+impl<T> AsRef<[T]> for Array64<T> {
+    fn as_ref(&self) -> &[T] {
+        &self.0
+    }
+}
+impl<T> AsMut<[T]> for Array64<T> {
+    fn as_mut(&mut self) -> &mut [T] {
+        &mut self.0
+    }
+}
+impl<T> Clone for Array64<T>
+where T: Copy + Default
+{
+    fn clone(&self) -> Self {
+        let mut new = Self::default();
+        new.0.copy_from_slice(&self.0);
+        new
+    }
+}
+impl<T> fmt::Debug for Array64<T> {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        write!(f, "Array64 {{}}")
+    }
+}
+
+macro_rules! chacha_impl {
+    ($ChaChaXCore:ident, $ChaChaXRng:ident, $rounds:expr, $doc:expr, $abst:ident) => {
+        #[doc=$doc]
+        #[derive(Clone, PartialEq, Eq)]
+        pub struct $ChaChaXCore {
+            state: ChaCha,
+        }
+
+        // Custom Debug implementation that does not expose the internal state
+        impl fmt::Debug for $ChaChaXCore {
+            fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+                write!(f, "ChaChaXCore {{}}")
+            }
+        }
+
+        impl BlockRngCore for $ChaChaXCore {
+            type Item = u32;
+            type Results = Array64<u32>;
+            #[inline]
+            fn generate(&mut self, r: &mut Self::Results) {
+                // Fill slice of words by writing to equivalent slice of bytes, then fixing endianness.
+                self.state.refill4($rounds, unsafe {
+                    &mut *(&mut *r as *mut Array64<u32> as *mut [u8; 256])
+                });
+                for x in r.as_mut() {
+                    *x = x.to_le();
+                }
+            }
+        }
+
+        impl SeedableRng for $ChaChaXCore {
+            type Seed = [u8; 32];
+            #[inline]
+            fn from_seed(seed: Self::Seed) -> Self {
+                $ChaChaXCore { state: ChaCha::new(&seed, &[0u8; 8]) }
+            }
+        }
+
+        impl CryptoRng for $ChaChaXCore {}
+
+        /// A cryptographically secure random number generator that uses the ChaCha algorithm.
+        ///
+        /// ChaCha is a stream cipher designed by Daniel J. Bernstein[^1], that we use as an RNG. It is
+        /// an improved variant of the Salsa20 cipher family, which was selected as one of the "stream
+        /// ciphers suitable for widespread adoption" by eSTREAM[^2].
+        ///
+        /// ChaCha uses add-rotate-xor (ARX) operations as its basis. These are safe against timing
+        /// attacks, although that is mostly a concern for ciphers and not for RNGs. We provide a SIMD
+        /// implementation to support high throughput on a variety of common hardware platforms.
+        ///
+        /// With the ChaCha algorithm it is possible to choose the number of rounds the core algorithm
+        /// should run. The number of rounds is a tradeoff between performance and security, where 8
+        /// rounds is the minimum potentially secure configuration, and 20 rounds is widely used as a
+        /// conservative choice.
+        ///
+        /// We use a 64-bit counter and 64-bit stream identifier as in Bernstein's implementation[^1]
+        /// except that we use a stream identifier in place of a nonce. A 64-bit counter over 64-byte
+        /// (16 word) blocks allows 1 ZiB of output before cycling, and the stream identifier allows
+        /// 2<sup>64</sup> unique streams of output per seed. Both counter and stream are initialized
+        /// to zero but may be set via the `set_word_pos` and `set_stream` methods.
+        ///
+        /// The word layout is:
+        ///
+        /// ```text
+        /// constant  constant  constant  constant
+        /// seed      seed      seed      seed
+        /// seed      seed      seed      seed
+        /// counter   counter   stream_id stream_id
+        /// ```
+        ///
+        /// This implementation uses an output buffer of sixteen `u32` words, and uses
+        /// [`BlockRng`] to implement the [`RngCore`] methods.
+        ///
+        /// [^1]: D. J. Bernstein, [*ChaCha, a variant of Salsa20*](
+        ///       https://cr.yp.to/chacha.html)
+        ///
+        /// [^2]: [eSTREAM: the ECRYPT Stream Cipher Project](
+        ///       http://www.ecrypt.eu.org/stream/)
+        #[derive(Clone, Debug)]
+        pub struct $ChaChaXRng {
+            rng: BlockRng<$ChaChaXCore>,
+        }
+
+        impl SeedableRng for $ChaChaXRng {
+            type Seed = [u8; 32];
+            #[inline]
+            fn from_seed(seed: Self::Seed) -> Self {
+                let core = $ChaChaXCore::from_seed(seed);
+                Self {
+                    rng: BlockRng::new(core),
+                }
+            }
+        }
+
+        impl RngCore for $ChaChaXRng {
+            #[inline]
+            fn next_u32(&mut self) -> u32 {
+                self.rng.next_u32()
+            }
+            #[inline]
+            fn next_u64(&mut self) -> u64 {
+                self.rng.next_u64()
+            }
+            #[inline]
+            fn fill_bytes(&mut self, bytes: &mut [u8]) {
+                self.rng.fill_bytes(bytes)
+            }
+            #[inline]
+            fn try_fill_bytes(&mut self, bytes: &mut [u8]) -> Result<(), Error> {
+                self.rng.try_fill_bytes(bytes)
+            }
+        }
+
+        impl $ChaChaXRng {
+            // The buffer is a 4-block window, i.e. it is always at a block-aligned position in the
+            // stream but if the stream has been seeked it may not be self-aligned.
+
+            /// Get the offset from the start of the stream, in 32-bit words.
+            ///
+            /// Since the generated blocks are 16 words (2<sup>4</sup>) long and the
+            /// counter is 64-bits, the offset is a 68-bit number. Sub-word offsets are
+            /// not supported, hence the result can simply be multiplied by 4 to get a
+            /// byte-offset.
+            #[inline]
+            pub fn get_word_pos(&self) -> u128 {
+                let buf_start_block = {
+                    let buf_end_block = self.rng.core.state.get_block_pos();
+                    u64::wrapping_sub(buf_end_block, BUF_BLOCKS.into())
+                };
+                let (buf_offset_blocks, block_offset_words) = {
+                    let buf_offset_words = self.rng.index() as u64;
+                    let blocks_part = buf_offset_words / u64::from(BLOCK_WORDS);
+                    let words_part = buf_offset_words % u64::from(BLOCK_WORDS);
+                    (blocks_part, words_part)
+                };
+                let pos_block = u64::wrapping_add(buf_start_block, buf_offset_blocks);
+                let pos_block_words = u128::from(pos_block) * u128::from(BLOCK_WORDS);
+                pos_block_words + u128::from(block_offset_words)
+            }
+
+            /// Set the offset from the start of the stream, in 32-bit words.
+            ///
+            /// As with `get_word_pos`, we use a 68-bit number. Since the generator
+            /// simply cycles at the end of its period (1 ZiB), we ignore the upper
+            /// 60 bits.
+            #[inline]
+            pub fn set_word_pos(&mut self, word_offset: u128) {
+                let block = (word_offset / u128::from(BLOCK_WORDS)) as u64;
+                self.rng
+                    .core
+                    .state
+                    .set_block_pos(block);
+                self.rng.generate_and_set((word_offset % u128::from(BLOCK_WORDS)) as usize);
+            }
+
+            /// Set the stream number.
+            ///
+            /// This is initialized to zero; 2<sup>64</sup> unique streams of output
+            /// are available per seed/key.
+            ///
+            /// Note that in order to reproduce ChaCha output with a specific 64-bit
+            /// nonce, one can convert that nonce to a `u64` in little-endian fashion
+            /// and pass to this function. In theory a 96-bit nonce can be used by
+            /// passing the last 64-bits to this function and using the first 32-bits as
+            /// the most significant half of the 64-bit counter (which may be set
+            /// indirectly via `set_word_pos`), but this is not directly supported.
+            #[inline]
+            pub fn set_stream(&mut self, stream: u64) {
+                self.rng
+                    .core
+                    .state
+                    .set_nonce(stream);
+                if self.rng.index() != 64 {
+                    let wp = self.get_word_pos();
+                    self.set_word_pos(wp);
+                }
+            }
+
+            /// Get the stream number.
+            #[inline]
+            pub fn get_stream(&self) -> u64 {
+                self.rng
+                    .core
+                    .state
+                    .get_nonce()
+            }
+
+            /// Get the seed.
+            #[inline]
+            pub fn get_seed(&self) -> [u8; 32] {
+                self.rng
+                    .core
+                    .state
+                    .get_seed()
+            }
+        }
+
+        impl CryptoRng for $ChaChaXRng {}
+
+        impl From<$ChaChaXCore> for $ChaChaXRng {
+            fn from(core: $ChaChaXCore) -> Self {
+                $ChaChaXRng {
+                    rng: BlockRng::new(core),
+                }
+            }
+        }
+
+        impl PartialEq<$ChaChaXRng> for $ChaChaXRng {
+            fn eq(&self, rhs: &$ChaChaXRng) -> bool {
+                let a: $abst::$ChaChaXRng = self.into();
+                let b: $abst::$ChaChaXRng = rhs.into();
+                a == b
+            }
+        }
+        impl Eq for $ChaChaXRng {}
+
+        #[cfg(feature = "serde1")]
+        impl Serialize for $ChaChaXRng {
+            fn serialize<S>(&self, s: S) -> Result<S::Ok, S::Error>
+            where S: Serializer {
+                $abst::$ChaChaXRng::from(self).serialize(s)
+            }
+        }
+        #[cfg(feature = "serde1")]
+        impl<'de> Deserialize<'de> for $ChaChaXRng {
+            fn deserialize<D>(d: D) -> Result<Self, D::Error> where D: Deserializer<'de> {
+                $abst::$ChaChaXRng::deserialize(d).map(|x| Self::from(&x))
+            }
+        }
+
+        mod $abst {
+            #[cfg(feature = "serde1")] use serde::{Serialize, Deserialize};
+
+            // The abstract state of a ChaCha stream, independent of implementation choices. The
+            // comparison and serialization of this object is considered a semver-covered part of
+            // the API.
+            #[derive(Debug, PartialEq, Eq)]
+            #[cfg_attr(
+                feature = "serde1",
+                derive(Serialize, Deserialize),
+            )]
+            pub(crate) struct $ChaChaXRng {
+                seed: [u8; 32],
+                stream: u64,
+                word_pos: u128,
+            }
+
+            impl From<&super::$ChaChaXRng> for $ChaChaXRng {
+                // Forget all information about the input except what is necessary to determine the
+                // outputs of any sequence of pub API calls.
+                fn from(r: &super::$ChaChaXRng) -> Self {
+                    Self {
+                        seed: r.get_seed(),
+                        stream: r.get_stream(),
+                        word_pos: r.get_word_pos(),
+                    }
+                }
+            }
+
+            impl From<&$ChaChaXRng> for super::$ChaChaXRng {
+                // Construct one of the possible concrete RNGs realizing an abstract state.
+                fn from(a: &$ChaChaXRng) -> Self {
+                    use rand_core::SeedableRng;
+                    let mut r = Self::from_seed(a.seed);
+                    r.set_stream(a.stream);
+                    r.set_word_pos(a.word_pos);
+                    r
+                }
+            }
+        }
+    }
+}
+
+chacha_impl!(ChaCha20Core, ChaCha20Rng, 10, "ChaCha with 20 rounds", abstract20);
+chacha_impl!(ChaCha12Core, ChaCha12Rng, 6, "ChaCha with 12 rounds", abstract12);
+chacha_impl!(ChaCha8Core, ChaCha8Rng, 4, "ChaCha with 8 rounds", abstract8);
+
+#[cfg(test)]
+mod test {
+    use rand_core::{RngCore, SeedableRng};
+
+    #[cfg(feature = "serde1")] use super::{ChaCha20Rng, ChaCha12Rng, ChaCha8Rng};
+
+    type ChaChaRng = super::ChaCha20Rng;
+
+    #[cfg(feature = "serde1")]
+    #[test]
+    fn test_chacha_serde_roundtrip() {
+        let seed = [
+            1, 0, 52, 0, 0, 0, 0, 0, 1, 0, 10, 0, 22, 32, 0, 0, 2, 0, 55, 49, 0, 11, 0, 0, 3, 0, 0, 0, 0,
+            0, 2, 92,
+        ];
+        let mut rng1 = ChaCha20Rng::from_seed(seed);
+        let mut rng2 = ChaCha12Rng::from_seed(seed);
+        let mut rng3 = ChaCha8Rng::from_seed(seed);
+
+        let encoded1 = serde_json::to_string(&rng1).unwrap();
+        let encoded2 = serde_json::to_string(&rng2).unwrap();
+        let encoded3 = serde_json::to_string(&rng3).unwrap();
+
+        let mut decoded1: ChaCha20Rng = serde_json::from_str(&encoded1).unwrap();
+        let mut decoded2: ChaCha12Rng = serde_json::from_str(&encoded2).unwrap();
+        let mut decoded3: ChaCha8Rng = serde_json::from_str(&encoded3).unwrap();
+
+        assert_eq!(rng1, decoded1);
+        assert_eq!(rng2, decoded2);
+        assert_eq!(rng3, decoded3);
+
+        assert_eq!(rng1.next_u32(), decoded1.next_u32());
+        assert_eq!(rng2.next_u32(), decoded2.next_u32());
+        assert_eq!(rng3.next_u32(), decoded3.next_u32());
+    }
+
+    // This test validates that:
+    // 1. a hard-coded serialization demonstrating the format at time of initial release can still
+    //    be deserialized to a ChaChaRng
+    // 2. re-serializing the resultant object produces exactly the original string
+    //
+    // Condition 2 is stronger than necessary: an equivalent serialization (e.g. with field order
+    // permuted, or whitespace differences) would also be admissible, but would fail this test.
+    // However testing for equivalence of serialized data is difficult, and there shouldn't be any
+    // reason we need to violate the stronger-than-needed condition, e.g. by changing the field
+    // definition order.
+    #[cfg(feature = "serde1")]
+    #[test]
+    fn test_chacha_serde_format_stability() {
+        let j = r#"{"seed":[4,8,15,16,23,42,4,8,15,16,23,42,4,8,15,16,23,42,4,8,15,16,23,42,4,8,15,16,23,42,4,8],"stream":27182818284,"word_pos":314159265359}"#;
+        let r: ChaChaRng = serde_json::from_str(&j).unwrap();
+        let j1 = serde_json::to_string(&r).unwrap();
+        assert_eq!(j, j1);
+    }
+
+    #[test]
+    fn test_chacha_construction() {
+        let seed = [
+            0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 3, 0, 0, 0, 0,
+            0, 0, 0,
+        ];
+        let mut rng1 = ChaChaRng::from_seed(seed);
+        assert_eq!(rng1.next_u32(), 137206642);
+
+        let mut rng2 = ChaChaRng::from_rng(rng1).unwrap();
+        assert_eq!(rng2.next_u32(), 1325750369);
+    }
+
+    #[test]
+    fn test_chacha_true_values_a() {
+        // Test vectors 1 and 2 from
+        // https://tools.ietf.org/html/draft-nir-cfrg-chacha20-poly1305-04
+        let seed = [0u8; 32];
+        let mut rng = ChaChaRng::from_seed(seed);
+
+        let mut results = [0u32; 16];
+        for i in results.iter_mut() {
+            *i = rng.next_u32();
+        }
+        let expected = [
+            0xade0b876, 0x903df1a0, 0xe56a5d40, 0x28bd8653, 0xb819d2bd, 0x1aed8da0, 0xccef36a8,
+            0xc70d778b, 0x7c5941da, 0x8d485751, 0x3fe02477, 0x374ad8b8, 0xf4b8436a, 0x1ca11815,
+            0x69b687c3, 0x8665eeb2,
+        ];
+        assert_eq!(results, expected);
+
+        for i in results.iter_mut() {
+            *i = rng.next_u32();
+        }
+        let expected = [
+            0xbee7079f, 0x7a385155, 0x7c97ba98, 0x0d082d73, 0xa0290fcb, 0x6965e348, 0x3e53c612,
+            0xed7aee32, 0x7621b729, 0x434ee69c, 0xb03371d5, 0xd539d874, 0x281fed31, 0x45fb0a51,
+            0x1f0ae1ac, 0x6f4d794b,
+        ];
+        assert_eq!(results, expected);
+    }
+
+    #[test]
+    fn test_chacha_true_values_b() {
+        // Test vector 3 from
+        // https://tools.ietf.org/html/draft-nir-cfrg-chacha20-poly1305-04
+        let seed = [
+            0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            0, 0, 1,
+        ];
+        let mut rng = ChaChaRng::from_seed(seed);
+
+        // Skip block 0
+        for _ in 0..16 {
+            rng.next_u32();
+        }
+
+        let mut results = [0u32; 16];
+        for i in results.iter_mut() {
+            *i = rng.next_u32();
+        }
+        let expected = [
+            0x2452eb3a, 0x9249f8ec, 0x8d829d9b, 0xddd4ceb1, 0xe8252083, 0x60818b01, 0xf38422b8,
+            0x5aaa49c9, 0xbb00ca8e, 0xda3ba7b4, 0xc4b592d1, 0xfdf2732f, 0x4436274e, 0x2561b3c8,
+            0xebdd4aa6, 0xa0136c00,
+        ];
+        assert_eq!(results, expected);
+    }
+
+    #[test]
+    fn test_chacha_true_values_c() {
+        // Test vector 4 from
+        // https://tools.ietf.org/html/draft-nir-cfrg-chacha20-poly1305-04
+        let seed = [
+            0, 0xff, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
+            0, 0, 0, 0,
+        ];
+        let expected = [
+            0xfb4dd572, 0x4bc42ef1, 0xdf922636, 0x327f1394, 0xa78dea8f, 0x5e269039, 0xa1bebbc1,
+            0xcaf09aae, 0xa25ab213, 0x48a6b46c, 0x1b9d9bcb, 0x092c5be6, 0x546ca624, 0x1bec45d5,
+            0x87f47473, 0x96f0992e,
+        ];
+        let expected_end = 3 * 16;
+        let mut results = [0u32; 16];
+
+        // Test block 2 by skipping block 0 and 1
+        let mut rng1 = ChaChaRng::from_seed(seed);
+        for _ in 0..32 {
+            rng1.next_u32();
+        }
+        for i in results.iter_mut() {
+            *i = rng1.next_u32();
+        }
+        assert_eq!(results, expected);
+        assert_eq!(rng1.get_word_pos(), expected_end);
+
+        // Test block 2 by using `set_word_pos`
+        let mut rng2 = ChaChaRng::from_seed(seed);
+        rng2.set_word_pos(2 * 16);
+        for i in results.iter_mut() {
+            *i = rng2.next_u32();
+        }
+        assert_eq!(results, expected);
+        assert_eq!(rng2.get_word_pos(), expected_end);
+
+        // Test skipping behaviour with other types
+        let mut buf = [0u8; 32];
+        rng2.fill_bytes(&mut buf[..]);
+        assert_eq!(rng2.get_word_pos(), expected_end + 8);
+        rng2.fill_bytes(&mut buf[0..25]);
+        assert_eq!(rng2.get_word_pos(), expected_end + 15);
+        rng2.next_u64();
+        assert_eq!(rng2.get_word_pos(), expected_end + 17);
+        rng2.next_u32();
+        rng2.next_u64();
+        assert_eq!(rng2.get_word_pos(), expected_end + 20);
+        rng2.fill_bytes(&mut buf[0..1]);
+        assert_eq!(rng2.get_word_pos(), expected_end + 21);
+    }
+
+    #[test]
+    fn test_chacha_multiple_blocks() {
+        let seed = [
+            0, 0, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 4, 0, 0, 0, 5, 0, 0, 0, 6, 0, 0, 0, 7,
+            0, 0, 0,
+        ];
+        let mut rng = ChaChaRng::from_seed(seed);
+
+        // Store the 17*i-th 32-bit word,
+        // i.e., the i-th word of the i-th 16-word block
+        let mut results = [0u32; 16];
+        for i in results.iter_mut() {
+            *i = rng.next_u32();
+            for _ in 0..16 {
+                rng.next_u32();
+            }
+        }
+        let expected = [
+            0xf225c81a, 0x6ab1be57, 0x04d42951, 0x70858036, 0x49884684, 0x64efec72, 0x4be2d186,
+            0x3615b384, 0x11cfa18e, 0xd3c50049, 0x75c775f6, 0x434c6530, 0x2c5bad8f, 0x898881dc,
+            0x5f1c86d9, 0xc1f8e7f4,
+        ];
+        assert_eq!(results, expected);
+    }
+
+    #[test]
+    fn test_chacha_true_bytes() {
+        let seed = [0u8; 32];
+        let mut rng = ChaChaRng::from_seed(seed);
+        let mut results = [0u8; 32];
+        rng.fill_bytes(&mut results);
+        let expected = [
+            118, 184, 224, 173, 160, 241, 61, 144, 64, 93, 106, 229, 83, 134, 189, 40, 189, 210,
+            25, 184, 160, 141, 237, 26, 168, 54, 239, 204, 139, 119, 13, 199,
+        ];
+        assert_eq!(results, expected);
+    }
+
+    #[test]
+    fn test_chacha_nonce() {
+        // Test vector 5 from
+        // https://tools.ietf.org/html/draft-nir-cfrg-chacha20-poly1305-04
+        // Although we do not support setting a nonce, we try it here anyway so
+        // we can use this test vector.
+        let seed = [0u8; 32];
+        let mut rng = ChaChaRng::from_seed(seed);
+        // 96-bit nonce in LE order is: 0,0,0,0, 0,0,0,0, 0,0,0,2
+        rng.set_stream(2u64 << (24 + 32));
+
+        let mut results = [0u32; 16];
+        for i in results.iter_mut() {
+            *i = rng.next_u32();
+        }
+        let expected = [
+            0x374dc6c2, 0x3736d58c, 0xb904e24a, 0xcd3f93ef, 0x88228b1a, 0x96a4dfb3, 0x5b76ab72,
+            0xc727ee54, 0x0e0e978a, 0xf3145c95, 0x1b748ea8, 0xf786c297, 0x99c28f5f, 0x628314e8,
+            0x398a19fa, 0x6ded1b53,
+        ];
+        assert_eq!(results, expected);
+    }
+
+    #[test]
+    fn test_chacha_clone_streams() {
+        let seed = [
+            0, 0, 0, 0, 1, 0, 0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 4, 0, 0, 0, 5, 0, 0, 0, 6, 0, 0, 0, 7,
+            0, 0, 0,
+        ];
+        let mut rng = ChaChaRng::from_seed(seed);
+        let mut clone = rng.clone();
+        for _ in 0..16 {
+            assert_eq!(rng.next_u64(), clone.next_u64());
+        }
+
+        rng.set_stream(51);
+        for _ in 0..7 {
+            assert!(rng.next_u32() != clone.next_u32());
+        }
+        clone.set_stream(51); // switch part way through block
+        for _ in 7..16 {
+            assert_eq!(rng.next_u32(), clone.next_u32());
+        }
+    }
+
+    #[test]
+    fn test_chacha_word_pos_wrap_exact() {
+        use super::{BUF_BLOCKS, BLOCK_WORDS};
+        let mut rng = ChaChaRng::from_seed(Default::default());
+        // refilling the buffer in set_word_pos will wrap the block counter to 0
+        let last_block = (1 << 68) - u128::from(BUF_BLOCKS * BLOCK_WORDS);
+        rng.set_word_pos(last_block);
+        assert_eq!(rng.get_word_pos(), last_block);
+    }
+
+    #[test]
+    fn test_chacha_word_pos_wrap_excess() {
+        use super::BLOCK_WORDS;
+        let mut rng = ChaChaRng::from_seed(Default::default());
+        // refilling the buffer in set_word_pos will wrap the block counter past 0
+        let last_block = (1 << 68) - u128::from(BLOCK_WORDS);
+        rng.set_word_pos(last_block);
+        assert_eq!(rng.get_word_pos(), last_block);
+    }
+
+    #[test]
+    fn test_chacha_word_pos_zero() {
+        let mut rng = ChaChaRng::from_seed(Default::default());
+        assert_eq!(rng.get_word_pos(), 0);
+        rng.set_word_pos(0);
+        assert_eq!(rng.get_word_pos(), 0);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/guts.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/guts.rs.html new file mode 100644 index 0000000..dd1feff --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/guts.rs.html @@ -0,0 +1,549 @@ +guts.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+
// Copyright 2019 The CryptoCorrosion Contributors
+// Copyright 2020 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The ChaCha random number generator.
+
+use ppv_lite86::{dispatch, dispatch_light128};
+
+pub use ppv_lite86::Machine;
+use ppv_lite86::{vec128_storage, ArithOps, BitOps32, LaneWords4, MultiLane, StoreBytes, Vec4};
+
+pub(crate) const BLOCK: usize = 64;
+pub(crate) const BLOCK64: u64 = BLOCK as u64;
+const LOG2_BUFBLOCKS: u64 = 2;
+const BUFBLOCKS: u64 = 1 << LOG2_BUFBLOCKS;
+pub(crate) const BUFSZ64: u64 = BLOCK64 * BUFBLOCKS;
+pub(crate) const BUFSZ: usize = BUFSZ64 as usize;
+
+const STREAM_PARAM_NONCE: u32 = 1;
+const STREAM_PARAM_BLOCK: u32 = 0;
+
+#[derive(Clone, PartialEq, Eq)]
+pub struct ChaCha {
+    pub(crate) b: vec128_storage,
+    pub(crate) c: vec128_storage,
+    pub(crate) d: vec128_storage,
+}
+
+#[derive(Clone)]
+pub struct State<V> {
+    pub(crate) a: V,
+    pub(crate) b: V,
+    pub(crate) c: V,
+    pub(crate) d: V,
+}
+
+#[inline(always)]
+pub(crate) fn round<V: ArithOps + BitOps32>(mut x: State<V>) -> State<V> {
+    x.a += x.b;
+    x.d = (x.d ^ x.a).rotate_each_word_right16();
+    x.c += x.d;
+    x.b = (x.b ^ x.c).rotate_each_word_right20();
+    x.a += x.b;
+    x.d = (x.d ^ x.a).rotate_each_word_right24();
+    x.c += x.d;
+    x.b = (x.b ^ x.c).rotate_each_word_right25();
+    x
+}
+
+#[inline(always)]
+pub(crate) fn diagonalize<V: LaneWords4>(mut x: State<V>) -> State<V> {
+    x.b = x.b.shuffle_lane_words3012();
+    x.c = x.c.shuffle_lane_words2301();
+    x.d = x.d.shuffle_lane_words1230();
+    x
+}
+#[inline(always)]
+pub(crate) fn undiagonalize<V: LaneWords4>(mut x: State<V>) -> State<V> {
+    x.b = x.b.shuffle_lane_words1230();
+    x.c = x.c.shuffle_lane_words2301();
+    x.d = x.d.shuffle_lane_words3012();
+    x
+}
+
+impl ChaCha {
+    #[inline(always)]
+    pub fn new(key: &[u8; 32], nonce: &[u8]) -> Self {
+        init_chacha(key, nonce)
+    }
+
+    #[inline(always)]
+    fn pos64<M: Machine>(&self, m: M) -> u64 {
+        let d: M::u32x4 = m.unpack(self.d);
+        ((d.extract(1) as u64) << 32) | d.extract(0) as u64
+    }
+
+    /// Produce 4 blocks of output, advancing the state
+    #[inline(always)]
+    pub fn refill4(&mut self, drounds: u32, out: &mut [u8; BUFSZ]) {
+        refill_wide(self, drounds, out)
+    }
+
+    #[inline(always)]
+    pub fn set_block_pos(&mut self, value: u64) {
+        set_stream_param(self, STREAM_PARAM_BLOCK, value)
+    }
+
+    #[inline(always)]
+    pub fn get_block_pos(&self) -> u64 {
+        get_stream_param(self, STREAM_PARAM_BLOCK)
+    }
+
+    #[inline(always)]
+    pub fn set_nonce(&mut self, value: u64) {
+        set_stream_param(self, STREAM_PARAM_NONCE, value)
+    }
+
+    #[inline(always)]
+    pub fn get_nonce(&self) -> u64 {
+        get_stream_param(self, STREAM_PARAM_NONCE)
+    }
+
+    #[inline(always)]
+    pub fn get_seed(&self) -> [u8; 32] {
+        get_seed(self)
+    }
+}
+
+#[allow(clippy::many_single_char_names)]
+#[inline(always)]
+fn refill_wide_impl<Mach: Machine>(
+    m: Mach, state: &mut ChaCha, drounds: u32, out: &mut [u8; BUFSZ],
+) {
+    let k = m.vec([0x6170_7865, 0x3320_646e, 0x7962_2d32, 0x6b20_6574]);
+    let mut pos = state.pos64(m);
+    let d0: Mach::u32x4 = m.unpack(state.d);
+    pos = pos.wrapping_add(1);
+    let d1 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+    pos = pos.wrapping_add(1);
+    let d2 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+    pos = pos.wrapping_add(1);
+    let d3 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+
+    let b = m.unpack(state.b);
+    let c = m.unpack(state.c);
+    let mut x = State {
+        a: Mach::u32x4x4::from_lanes([k, k, k, k]),
+        b: Mach::u32x4x4::from_lanes([b, b, b, b]),
+        c: Mach::u32x4x4::from_lanes([c, c, c, c]),
+        d: m.unpack(Mach::u32x4x4::from_lanes([d0, d1, d2, d3]).into()),
+    };
+    for _ in 0..drounds {
+        x = round(x);
+        x = undiagonalize(round(diagonalize(x)));
+    }
+    let mut pos = state.pos64(m);
+    let d0: Mach::u32x4 = m.unpack(state.d);
+    pos = pos.wrapping_add(1);
+    let d1 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+    pos = pos.wrapping_add(1);
+    let d2 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+    pos = pos.wrapping_add(1);
+    let d3 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+    pos = pos.wrapping_add(1);
+    let d4 = d0.insert((pos >> 32) as u32, 1).insert(pos as u32, 0);
+
+    let (a, b, c, d) = (
+        x.a.to_lanes(),
+        x.b.to_lanes(),
+        x.c.to_lanes(),
+        x.d.to_lanes(),
+    );
+    let sb = m.unpack(state.b);
+    let sc = m.unpack(state.c);
+    let sd = [m.unpack(state.d), d1, d2, d3];
+    state.d = d4.into();
+    let mut words = out.chunks_exact_mut(16);
+    for ((((&a, &b), &c), &d), &sd) in a.iter().zip(&b).zip(&c).zip(&d).zip(&sd) {
+        (a + k).write_le(words.next().unwrap());
+        (b + sb).write_le(words.next().unwrap());
+        (c + sc).write_le(words.next().unwrap());
+        (d + sd).write_le(words.next().unwrap());
+    }
+}
+
+dispatch!(m, Mach, {
+    fn refill_wide(state: &mut ChaCha, drounds: u32, out: &mut [u8; BUFSZ]) {
+        refill_wide_impl(m, state, drounds, out);
+    }
+});
+
+// Single-block, rounds-only; shared by try_apply_keystream for tails shorter than BUFSZ
+// and XChaCha's setup step.
+dispatch!(m, Mach, {
+    fn refill_narrow_rounds(state: &mut ChaCha, drounds: u32) -> State<vec128_storage> {
+        let k: Mach::u32x4 = m.vec([0x6170_7865, 0x3320_646e, 0x7962_2d32, 0x6b20_6574]);
+        let mut x = State {
+            a: k,
+            b: m.unpack(state.b),
+            c: m.unpack(state.c),
+            d: m.unpack(state.d),
+        };
+        for _ in 0..drounds {
+            x = round(x);
+            x = undiagonalize(round(diagonalize(x)));
+        }
+        State {
+            a: x.a.into(),
+            b: x.b.into(),
+            c: x.c.into(),
+            d: x.d.into(),
+        }
+    }
+});
+
+dispatch_light128!(m, Mach, {
+    fn set_stream_param(state: &mut ChaCha, param: u32, value: u64) {
+        let d: Mach::u32x4 = m.unpack(state.d);
+        state.d = d
+            .insert((value >> 32) as u32, (param << 1) | 1)
+            .insert(value as u32, param << 1)
+            .into();
+    }
+});
+
+dispatch_light128!(m, Mach, {
+    fn get_stream_param(state: &ChaCha, param: u32) -> u64 {
+        let d: Mach::u32x4 = m.unpack(state.d);
+        ((d.extract((param << 1) | 1) as u64) << 32) | d.extract(param << 1) as u64
+    }
+});
+
+dispatch_light128!(m, Mach, {
+    fn get_seed(state: &ChaCha) -> [u8; 32] {
+        let b: Mach::u32x4 = m.unpack(state.b);
+        let c: Mach::u32x4 = m.unpack(state.c);
+        let mut key = [0u8; 32];
+        b.write_le(&mut key[..16]);
+        c.write_le(&mut key[16..]);
+        key
+    }
+});
+
+fn read_u32le(xs: &[u8]) -> u32 {
+    assert_eq!(xs.len(), 4);
+    u32::from(xs[0]) | (u32::from(xs[1]) << 8) | (u32::from(xs[2]) << 16) | (u32::from(xs[3]) << 24)
+}
+
+dispatch_light128!(m, Mach, {
+    fn init_chacha(key: &[u8; 32], nonce: &[u8]) -> ChaCha {
+        let ctr_nonce = [
+            0,
+            if nonce.len() == 12 {
+                read_u32le(&nonce[0..4])
+            } else {
+                0
+            },
+            read_u32le(&nonce[nonce.len() - 8..nonce.len() - 4]),
+            read_u32le(&nonce[nonce.len() - 4..]),
+        ];
+        let key0: Mach::u32x4 = m.read_le(&key[..16]);
+        let key1: Mach::u32x4 = m.read_le(&key[16..]);
+        ChaCha {
+            b: key0.into(),
+            c: key1.into(),
+            d: ctr_nonce.into(),
+        }
+    }
+});
+
+dispatch_light128!(m, Mach, {
+    fn init_chacha_x(key: &[u8; 32], nonce: &[u8; 24], rounds: u32) -> ChaCha {
+        let key0: Mach::u32x4 = m.read_le(&key[..16]);
+        let key1: Mach::u32x4 = m.read_le(&key[16..]);
+        let nonce0: Mach::u32x4 = m.read_le(&nonce[..16]);
+        let mut state = ChaCha {
+            b: key0.into(),
+            c: key1.into(),
+            d: nonce0.into(),
+        };
+        let x = refill_narrow_rounds(&mut state, rounds);
+        let ctr_nonce1 = [0, 0, read_u32le(&nonce[16..20]), read_u32le(&nonce[20..24])];
+        state.b = x.a;
+        state.c = x.d;
+        state.d = ctr_nonce1.into();
+        state
+    }
+});
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/lib.rs.html new file mode 100644 index 0000000..12d8c8e --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_chacha/lib.rs.html @@ -0,0 +1,69 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The ChaCha random number generator.
+
+#![doc(
+    html_logo_url = "https://www.rust-lang.org/logos/rust-logo-128x128-blk.png",
+    html_favicon_url = "https://www.rust-lang.org/favicon.ico",
+    html_root_url = "https://rust-random.github.io/rand/"
+)]
+#![deny(missing_docs)]
+#![deny(missing_debug_implementations)]
+#![doc(test(attr(allow(unused_variables), deny(warnings))))]
+#![cfg_attr(not(feature = "std"), no_std)]
+
+pub use rand_core;
+
+mod chacha;
+mod guts;
+
+pub use crate::chacha::{
+    ChaCha12Core, ChaCha12Rng, ChaCha20Core, ChaCha20Rng, ChaCha8Core, ChaCha8Rng,
+};
+
+/// ChaCha with 20 rounds
+pub type ChaChaRng = ChaCha20Rng;
+/// ChaCha with 20 rounds, low-level interface
+pub type ChaChaCore = ChaCha20Core;
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/block.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/block.rs.html new file mode 100644 index 0000000..fdcdb70 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/block.rs.html @@ -0,0 +1,1081 @@ +block.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+532
+533
+534
+535
+536
+537
+538
+539
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! The `BlockRngCore` trait and implementation helpers
+//!
+//! The [`BlockRngCore`] trait exists to assist in the implementation of RNGs
+//! which generate a block of data in a cache instead of returning generated
+//! values directly.
+//!
+//! Usage of this trait is optional, but provides two advantages:
+//! implementations only need to concern themselves with generation of the
+//! block, not the various [`RngCore`] methods (especially [`fill_bytes`], where
+//! the optimal implementations are not trivial), and this allows
+//! `ReseedingRng` (see [`rand`](https://docs.rs/rand) crate) perform periodic
+//! reseeding with very low overhead.
+//!
+//! # Example
+//!
+//! ```no_run
+//! use rand_core::{RngCore, SeedableRng};
+//! use rand_core::block::{BlockRngCore, BlockRng};
+//!
+//! struct MyRngCore;
+//!
+//! impl BlockRngCore for MyRngCore {
+//!     type Item = u32;
+//!     type Results = [u32; 16];
+//!
+//!     fn generate(&mut self, results: &mut Self::Results) {
+//!         unimplemented!()
+//!     }
+//! }
+//!
+//! impl SeedableRng for MyRngCore {
+//!     type Seed = [u8; 32];
+//!     fn from_seed(seed: Self::Seed) -> Self {
+//!         unimplemented!()
+//!     }
+//! }
+//!
+//! // optionally, also implement CryptoRng for MyRngCore
+//!
+//! // Final RNG.
+//! let mut rng = BlockRng::<MyRngCore>::seed_from_u64(0);
+//! println!("First value: {}", rng.next_u32());
+//! ```
+//!
+//! [`BlockRngCore`]: crate::block::BlockRngCore
+//! [`fill_bytes`]: RngCore::fill_bytes
+
+use crate::impls::{fill_via_u32_chunks, fill_via_u64_chunks};
+use crate::{CryptoRng, Error, RngCore, SeedableRng};
+use core::convert::AsRef;
+use core::fmt;
+#[cfg(feature = "serde1")]
+use serde::{Deserialize, Serialize};
+
+/// A trait for RNGs which do not generate random numbers individually, but in
+/// blocks (typically `[u32; N]`). This technique is commonly used by
+/// cryptographic RNGs to improve performance.
+///
+/// See the [module][crate::block] documentation for details.
+pub trait BlockRngCore {
+    /// Results element type, e.g. `u32`.
+    type Item;
+
+    /// Results type. This is the 'block' an RNG implementing `BlockRngCore`
+    /// generates, which will usually be an array like `[u32; 16]`.
+    type Results: AsRef<[Self::Item]> + AsMut<[Self::Item]> + Default;
+
+    /// Generate a new block of results.
+    fn generate(&mut self, results: &mut Self::Results);
+}
+
+/// A wrapper type implementing [`RngCore`] for some type implementing
+/// [`BlockRngCore`] with `u32` array buffer; i.e. this can be used to implement
+/// a full RNG from just a `generate` function.
+///
+/// The `core` field may be accessed directly but the results buffer may not.
+/// PRNG implementations can simply use a type alias
+/// (`pub type MyRng = BlockRng<MyRngCore>;`) but might prefer to use a
+/// wrapper type (`pub struct MyRng(BlockRng<MyRngCore>);`); the latter must
+/// re-implement `RngCore` but hides the implementation details and allows
+/// extra functionality to be defined on the RNG
+/// (e.g. `impl MyRng { fn set_stream(...){...} }`).
+///
+/// `BlockRng` has heavily optimized implementations of the [`RngCore`] methods
+/// reading values from the results buffer, as well as
+/// calling [`BlockRngCore::generate`] directly on the output array when
+/// [`fill_bytes`] / [`try_fill_bytes`] is called on a large array. These methods
+/// also handle the bookkeeping of when to generate a new batch of values.
+///
+/// No whole generated `u32` values are thrown away and all values are consumed
+/// in-order. [`next_u32`] simply takes the next available `u32` value.
+/// [`next_u64`] is implemented by combining two `u32` values, least
+/// significant first. [`fill_bytes`] and [`try_fill_bytes`] consume a whole
+/// number of `u32` values, converting each `u32` to a byte slice in
+/// little-endian order. If the requested byte length is not a multiple of 4,
+/// some bytes will be discarded.
+///
+/// See also [`BlockRng64`] which uses `u64` array buffers. Currently there is
+/// no direct support for other buffer types.
+///
+/// For easy initialization `BlockRng` also implements [`SeedableRng`].
+///
+/// [`next_u32`]: RngCore::next_u32
+/// [`next_u64`]: RngCore::next_u64
+/// [`fill_bytes`]: RngCore::fill_bytes
+/// [`try_fill_bytes`]: RngCore::try_fill_bytes
+#[derive(Clone)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+#[cfg_attr(
+    feature = "serde1",
+    serde(
+        bound = "for<'x> R: Serialize + Deserialize<'x> + Sized, for<'x> R::Results: Serialize + Deserialize<'x>"
+    )
+)]
+pub struct BlockRng<R: BlockRngCore + ?Sized> {
+    results: R::Results,
+    index: usize,
+    /// The *core* part of the RNG, implementing the `generate` function.
+    pub core: R,
+}
+
+// Custom Debug implementation that does not expose the contents of `results`.
+impl<R: BlockRngCore + fmt::Debug> fmt::Debug for BlockRng<R> {
+    fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
+        fmt.debug_struct("BlockRng")
+            .field("core", &self.core)
+            .field("result_len", &self.results.as_ref().len())
+            .field("index", &self.index)
+            .finish()
+    }
+}
+
+impl<R: BlockRngCore> BlockRng<R> {
+    /// Create a new `BlockRng` from an existing RNG implementing
+    /// `BlockRngCore`. Results will be generated on first use.
+    #[inline]
+    pub fn new(core: R) -> BlockRng<R> {
+        let results_empty = R::Results::default();
+        BlockRng {
+            core,
+            index: results_empty.as_ref().len(),
+            results: results_empty,
+        }
+    }
+
+    /// Get the index into the result buffer.
+    ///
+    /// If this is equal to or larger than the size of the result buffer then
+    /// the buffer is "empty" and `generate()` must be called to produce new
+    /// results.
+    #[inline(always)]
+    pub fn index(&self) -> usize {
+        self.index
+    }
+
+    /// Reset the number of available results.
+    /// This will force a new set of results to be generated on next use.
+    #[inline]
+    pub fn reset(&mut self) {
+        self.index = self.results.as_ref().len();
+    }
+
+    /// Generate a new set of results immediately, setting the index to the
+    /// given value.
+    #[inline]
+    pub fn generate_and_set(&mut self, index: usize) {
+        assert!(index < self.results.as_ref().len());
+        self.core.generate(&mut self.results);
+        self.index = index;
+    }
+}
+
+impl<R: BlockRngCore<Item = u32>> RngCore for BlockRng<R>
+where
+    <R as BlockRngCore>::Results: AsRef<[u32]> + AsMut<[u32]>,
+{
+    #[inline]
+    fn next_u32(&mut self) -> u32 {
+        if self.index >= self.results.as_ref().len() {
+            self.generate_and_set(0);
+        }
+
+        let value = self.results.as_ref()[self.index];
+        self.index += 1;
+        value
+    }
+
+    #[inline]
+    fn next_u64(&mut self) -> u64 {
+        let read_u64 = |results: &[u32], index| {
+            let data = &results[index..=index + 1];
+            u64::from(data[1]) << 32 | u64::from(data[0])
+        };
+
+        let len = self.results.as_ref().len();
+
+        let index = self.index;
+        if index < len - 1 {
+            self.index += 2;
+            // Read an u64 from the current index
+            read_u64(self.results.as_ref(), index)
+        } else if index >= len {
+            self.generate_and_set(2);
+            read_u64(self.results.as_ref(), 0)
+        } else {
+            let x = u64::from(self.results.as_ref()[len - 1]);
+            self.generate_and_set(1);
+            let y = u64::from(self.results.as_ref()[0]);
+            (y << 32) | x
+        }
+    }
+
+    #[inline]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        let mut read_len = 0;
+        while read_len < dest.len() {
+            if self.index >= self.results.as_ref().len() {
+                self.generate_and_set(0);
+            }
+            let (consumed_u32, filled_u8) =
+                fill_via_u32_chunks(&self.results.as_ref()[self.index..], &mut dest[read_len..]);
+
+            self.index += consumed_u32;
+            read_len += filled_u8;
+        }
+    }
+
+    #[inline(always)]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        self.fill_bytes(dest);
+        Ok(())
+    }
+}
+
+impl<R: BlockRngCore + SeedableRng> SeedableRng for BlockRng<R> {
+    type Seed = R::Seed;
+
+    #[inline(always)]
+    fn from_seed(seed: Self::Seed) -> Self {
+        Self::new(R::from_seed(seed))
+    }
+
+    #[inline(always)]
+    fn seed_from_u64(seed: u64) -> Self {
+        Self::new(R::seed_from_u64(seed))
+    }
+
+    #[inline(always)]
+    fn from_rng<S: RngCore>(rng: S) -> Result<Self, Error> {
+        Ok(Self::new(R::from_rng(rng)?))
+    }
+}
+
+/// A wrapper type implementing [`RngCore`] for some type implementing
+/// [`BlockRngCore`] with `u64` array buffer; i.e. this can be used to implement
+/// a full RNG from just a `generate` function.
+///
+/// This is similar to [`BlockRng`], but specialized for algorithms that operate
+/// on `u64` values.
+///
+/// No whole generated `u64` values are thrown away and all values are consumed
+/// in-order. [`next_u64`] simply takes the next available `u64` value.
+/// [`next_u32`] is however a bit special: half of a `u64` is consumed, leaving
+/// the other half in the buffer. If the next function called is [`next_u32`]
+/// then the other half is then consumed, however both [`next_u64`] and
+/// [`fill_bytes`] discard the rest of any half-consumed `u64`s when called.
+///
+/// [`fill_bytes`] and [`try_fill_bytes`] consume a whole number of `u64`
+/// values. If the requested length is not a multiple of 8, some bytes will be
+/// discarded.
+///
+/// [`next_u32`]: RngCore::next_u32
+/// [`next_u64`]: RngCore::next_u64
+/// [`fill_bytes`]: RngCore::fill_bytes
+/// [`try_fill_bytes`]: RngCore::try_fill_bytes
+#[derive(Clone)]
+#[cfg_attr(feature = "serde1", derive(Serialize, Deserialize))]
+pub struct BlockRng64<R: BlockRngCore + ?Sized> {
+    results: R::Results,
+    index: usize,
+    half_used: bool, // true if only half of the previous result is used
+    /// The *core* part of the RNG, implementing the `generate` function.
+    pub core: R,
+}
+
+// Custom Debug implementation that does not expose the contents of `results`.
+impl<R: BlockRngCore + fmt::Debug> fmt::Debug for BlockRng64<R> {
+    fn fmt(&self, fmt: &mut fmt::Formatter) -> fmt::Result {
+        fmt.debug_struct("BlockRng64")
+            .field("core", &self.core)
+            .field("result_len", &self.results.as_ref().len())
+            .field("index", &self.index)
+            .field("half_used", &self.half_used)
+            .finish()
+    }
+}
+
+impl<R: BlockRngCore> BlockRng64<R> {
+    /// Create a new `BlockRng` from an existing RNG implementing
+    /// `BlockRngCore`. Results will be generated on first use.
+    #[inline]
+    pub fn new(core: R) -> BlockRng64<R> {
+        let results_empty = R::Results::default();
+        BlockRng64 {
+            core,
+            index: results_empty.as_ref().len(),
+            half_used: false,
+            results: results_empty,
+        }
+    }
+
+    /// Get the index into the result buffer.
+    ///
+    /// If this is equal to or larger than the size of the result buffer then
+    /// the buffer is "empty" and `generate()` must be called to produce new
+    /// results.
+    #[inline(always)]
+    pub fn index(&self) -> usize {
+        self.index
+    }
+
+    /// Reset the number of available results.
+    /// This will force a new set of results to be generated on next use.
+    #[inline]
+    pub fn reset(&mut self) {
+        self.index = self.results.as_ref().len();
+        self.half_used = false;
+    }
+
+    /// Generate a new set of results immediately, setting the index to the
+    /// given value.
+    #[inline]
+    pub fn generate_and_set(&mut self, index: usize) {
+        assert!(index < self.results.as_ref().len());
+        self.core.generate(&mut self.results);
+        self.index = index;
+        self.half_used = false;
+    }
+}
+
+impl<R: BlockRngCore<Item = u64>> RngCore for BlockRng64<R>
+where
+    <R as BlockRngCore>::Results: AsRef<[u64]> + AsMut<[u64]>,
+{
+    #[inline]
+    fn next_u32(&mut self) -> u32 {
+        let mut index = self.index - self.half_used as usize;
+        if index >= self.results.as_ref().len() {
+            self.core.generate(&mut self.results);
+            self.index = 0;
+            index = 0;
+            // `self.half_used` is by definition `false`
+            self.half_used = false;
+        }
+
+        let shift = 32 * (self.half_used as usize);
+
+        self.half_used = !self.half_used;
+        self.index += self.half_used as usize;
+
+        (self.results.as_ref()[index] >> shift) as u32
+    }
+
+    #[inline]
+    fn next_u64(&mut self) -> u64 {
+        if self.index >= self.results.as_ref().len() {
+            self.core.generate(&mut self.results);
+            self.index = 0;
+        }
+
+        let value = self.results.as_ref()[self.index];
+        self.index += 1;
+        self.half_used = false;
+        value
+    }
+
+    #[inline]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        let mut read_len = 0;
+        self.half_used = false;
+        while read_len < dest.len() {
+            if self.index as usize >= self.results.as_ref().len() {
+                self.core.generate(&mut self.results);
+                self.index = 0;
+            }
+
+            let (consumed_u64, filled_u8) = fill_via_u64_chunks(
+                &self.results.as_ref()[self.index as usize..],
+                &mut dest[read_len..],
+            );
+
+            self.index += consumed_u64;
+            read_len += filled_u8;
+        }
+    }
+
+    #[inline(always)]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        self.fill_bytes(dest);
+        Ok(())
+    }
+}
+
+impl<R: BlockRngCore + SeedableRng> SeedableRng for BlockRng64<R> {
+    type Seed = R::Seed;
+
+    #[inline(always)]
+    fn from_seed(seed: Self::Seed) -> Self {
+        Self::new(R::from_seed(seed))
+    }
+
+    #[inline(always)]
+    fn seed_from_u64(seed: u64) -> Self {
+        Self::new(R::seed_from_u64(seed))
+    }
+
+    #[inline(always)]
+    fn from_rng<S: RngCore>(rng: S) -> Result<Self, Error> {
+        Ok(Self::new(R::from_rng(rng)?))
+    }
+}
+
+impl<R: BlockRngCore + CryptoRng> CryptoRng for BlockRng<R> {}
+
+#[cfg(test)]
+mod test {
+    use crate::{SeedableRng, RngCore};
+    use crate::block::{BlockRng, BlockRng64, BlockRngCore};
+
+    #[derive(Debug, Clone)]
+    struct DummyRng {
+        counter: u32,
+    }
+
+    impl BlockRngCore for DummyRng {
+        type Item = u32;
+
+        type Results = [u32; 16];
+
+        fn generate(&mut self, results: &mut Self::Results) {
+            for r in results {
+                *r = self.counter;
+                self.counter = self.counter.wrapping_add(3511615421);
+            }
+        }
+    }
+
+    impl SeedableRng for DummyRng {
+        type Seed = [u8; 4];
+
+        fn from_seed(seed: Self::Seed) -> Self {
+            DummyRng { counter: u32::from_le_bytes(seed) }
+        }
+    }
+
+    #[test]
+    fn blockrng_next_u32_vs_next_u64() {
+        let mut rng1 = BlockRng::<DummyRng>::from_seed([1, 2, 3, 4]);
+        let mut rng2 = rng1.clone();
+        let mut rng3 = rng1.clone();
+
+        let mut a = [0; 16];
+        (&mut a[..4]).copy_from_slice(&rng1.next_u32().to_le_bytes());
+        (&mut a[4..12]).copy_from_slice(&rng1.next_u64().to_le_bytes());
+        (&mut a[12..]).copy_from_slice(&rng1.next_u32().to_le_bytes());
+
+        let mut b = [0; 16];
+        (&mut b[..4]).copy_from_slice(&rng2.next_u32().to_le_bytes());
+        (&mut b[4..8]).copy_from_slice(&rng2.next_u32().to_le_bytes());
+        (&mut b[8..]).copy_from_slice(&rng2.next_u64().to_le_bytes());
+        assert_eq!(a, b);
+
+        let mut c = [0; 16];
+        (&mut c[..8]).copy_from_slice(&rng3.next_u64().to_le_bytes());
+        (&mut c[8..12]).copy_from_slice(&rng3.next_u32().to_le_bytes());
+        (&mut c[12..]).copy_from_slice(&rng3.next_u32().to_le_bytes());
+        assert_eq!(a, c);
+    }
+
+    #[derive(Debug, Clone)]
+    struct DummyRng64 {
+        counter: u64,
+    }
+
+    impl BlockRngCore for DummyRng64 {
+        type Item = u64;
+
+        type Results = [u64; 8];
+
+        fn generate(&mut self, results: &mut Self::Results) {
+            for r in results {
+                *r = self.counter;
+                self.counter = self.counter.wrapping_add(2781463553396133981);
+            }
+        }
+    }
+
+    impl SeedableRng for DummyRng64 {
+        type Seed = [u8; 8];
+
+        fn from_seed(seed: Self::Seed) -> Self {
+            DummyRng64 { counter: u64::from_le_bytes(seed) }
+        }
+    }
+
+    #[test]
+    fn blockrng64_next_u32_vs_next_u64() {
+        let mut rng1 = BlockRng64::<DummyRng64>::from_seed([1, 2, 3, 4, 5, 6, 7, 8]);
+        let mut rng2 = rng1.clone();
+        let mut rng3 = rng1.clone();
+
+        let mut a = [0; 16];
+        (&mut a[..4]).copy_from_slice(&rng1.next_u32().to_le_bytes());
+        (&mut a[4..12]).copy_from_slice(&rng1.next_u64().to_le_bytes());
+        (&mut a[12..]).copy_from_slice(&rng1.next_u32().to_le_bytes());
+
+        let mut b = [0; 16];
+        (&mut b[..4]).copy_from_slice(&rng2.next_u32().to_le_bytes());
+        (&mut b[4..8]).copy_from_slice(&rng2.next_u32().to_le_bytes());
+        (&mut b[8..]).copy_from_slice(&rng2.next_u64().to_le_bytes());
+        assert_ne!(a, b);
+        assert_eq!(&a[..4], &b[..4]);
+        assert_eq!(&a[4..12], &b[8..]);
+
+        let mut c = [0; 16];
+        (&mut c[..8]).copy_from_slice(&rng3.next_u64().to_le_bytes());
+        (&mut c[8..12]).copy_from_slice(&rng3.next_u32().to_le_bytes());
+        (&mut c[12..]).copy_from_slice(&rng3.next_u32().to_le_bytes());
+        assert_eq!(b, c);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/error.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/error.rs.html new file mode 100644 index 0000000..5d08008 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/error.rs.html @@ -0,0 +1,459 @@ +error.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Error types
+
+use core::fmt;
+use core::num::NonZeroU32;
+
+#[cfg(feature = "std")] use std::boxed::Box;
+
+/// Error type of random number generators
+///
+/// In order to be compatible with `std` and `no_std`, this type has two
+/// possible implementations: with `std` a boxed `Error` trait object is stored,
+/// while with `no_std` we merely store an error code.
+pub struct Error {
+    #[cfg(feature = "std")]
+    inner: Box<dyn std::error::Error + Send + Sync + 'static>,
+    #[cfg(not(feature = "std"))]
+    code: NonZeroU32,
+}
+
+impl Error {
+    /// Codes at or above this point can be used by users to define their own
+    /// custom errors.
+    ///
+    /// This has a fixed value of `(1 << 31) + (1 << 30) = 0xC000_0000`,
+    /// therefore the number of values available for custom codes is `1 << 30`.
+    ///
+    /// This is identical to [`getrandom::Error::CUSTOM_START`](https://docs.rs/getrandom/latest/getrandom/struct.Error.html#associatedconstant.CUSTOM_START).
+    pub const CUSTOM_START: u32 = (1 << 31) + (1 << 30);
+    /// Codes below this point represent OS Errors (i.e. positive i32 values).
+    /// Codes at or above this point, but below [`Error::CUSTOM_START`] are
+    /// reserved for use by the `rand` and `getrandom` crates.
+    ///
+    /// This is identical to [`getrandom::Error::INTERNAL_START`](https://docs.rs/getrandom/latest/getrandom/struct.Error.html#associatedconstant.INTERNAL_START).
+    pub const INTERNAL_START: u32 = 1 << 31;
+
+    /// Construct from any type supporting `std::error::Error`
+    ///
+    /// Available only when configured with `std`.
+    ///
+    /// See also `From<NonZeroU32>`, which is available with and without `std`.
+    #[cfg(feature = "std")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+    #[inline]
+    pub fn new<E>(err: E) -> Self
+    where
+        E: Into<Box<dyn std::error::Error + Send + Sync + 'static>>,
+    {
+        Error { inner: err.into() }
+    }
+
+    /// Reference the inner error (`std` only)
+    ///
+    /// When configured with `std`, this is a trivial operation and never
+    /// panics. Without `std`, this method is simply unavailable.
+    #[cfg(feature = "std")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+    #[inline]
+    pub fn inner(&self) -> &(dyn std::error::Error + Send + Sync + 'static) {
+        &*self.inner
+    }
+
+    /// Unwrap the inner error (`std` only)
+    ///
+    /// When configured with `std`, this is a trivial operation and never
+    /// panics. Without `std`, this method is simply unavailable.
+    #[cfg(feature = "std")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "std")))]
+    #[inline]
+    pub fn take_inner(self) -> Box<dyn std::error::Error + Send + Sync + 'static> {
+        self.inner
+    }
+
+    /// Extract the raw OS error code (if this error came from the OS)
+    ///
+    /// This method is identical to `std::io::Error::raw_os_error()`, except
+    /// that it works in `no_std` contexts. If this method returns `None`, the
+    /// error value can still be formatted via the `Display` implementation.
+    #[inline]
+    pub fn raw_os_error(&self) -> Option<i32> {
+        #[cfg(feature = "std")]
+        {
+            if let Some(e) = self.inner.downcast_ref::<std::io::Error>() {
+                return e.raw_os_error();
+            }
+        }
+        match self.code() {
+            Some(code) if u32::from(code) < Self::INTERNAL_START => Some(u32::from(code) as i32),
+            _ => None,
+        }
+    }
+
+    /// Retrieve the error code, if any.
+    ///
+    /// If this `Error` was constructed via `From<NonZeroU32>`, then this method
+    /// will return this `NonZeroU32` code (for `no_std` this is always the
+    /// case). Otherwise, this method will return `None`.
+    #[inline]
+    pub fn code(&self) -> Option<NonZeroU32> {
+        #[cfg(feature = "std")]
+        {
+            self.inner.downcast_ref::<ErrorCode>().map(|c| c.0)
+        }
+        #[cfg(not(feature = "std"))]
+        {
+            Some(self.code)
+        }
+    }
+}
+
+impl fmt::Debug for Error {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        #[cfg(feature = "std")]
+        {
+            write!(f, "Error {{ inner: {:?} }}", self.inner)
+        }
+        #[cfg(all(feature = "getrandom", not(feature = "std")))]
+        {
+            getrandom::Error::from(self.code).fmt(f)
+        }
+        #[cfg(not(feature = "getrandom"))]
+        {
+            write!(f, "Error {{ code: {} }}", self.code)
+        }
+    }
+}
+
+impl fmt::Display for Error {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        #[cfg(feature = "std")]
+        {
+            write!(f, "{}", self.inner)
+        }
+        #[cfg(all(feature = "getrandom", not(feature = "std")))]
+        {
+            getrandom::Error::from(self.code).fmt(f)
+        }
+        #[cfg(not(feature = "getrandom"))]
+        {
+            write!(f, "error code {}", self.code)
+        }
+    }
+}
+
+impl From<NonZeroU32> for Error {
+    #[inline]
+    fn from(code: NonZeroU32) -> Self {
+        #[cfg(feature = "std")]
+        {
+            Error {
+                inner: Box::new(ErrorCode(code)),
+            }
+        }
+        #[cfg(not(feature = "std"))]
+        {
+            Error { code }
+        }
+    }
+}
+
+#[cfg(feature = "getrandom")]
+impl From<getrandom::Error> for Error {
+    #[inline]
+    fn from(error: getrandom::Error) -> Self {
+        #[cfg(feature = "std")]
+        {
+            Error {
+                inner: Box::new(error),
+            }
+        }
+        #[cfg(not(feature = "std"))]
+        {
+            Error { code: error.code() }
+        }
+    }
+}
+
+#[cfg(feature = "std")]
+impl std::error::Error for Error {
+    #[inline]
+    fn source(&self) -> Option<&(dyn std::error::Error + 'static)> {
+        self.inner.source()
+    }
+}
+
+#[cfg(feature = "std")]
+impl From<Error> for std::io::Error {
+    #[inline]
+    fn from(error: Error) -> Self {
+        if let Some(code) = error.raw_os_error() {
+            std::io::Error::from_raw_os_error(code)
+        } else {
+            std::io::Error::new(std::io::ErrorKind::Other, error)
+        }
+    }
+}
+
+#[cfg(feature = "std")]
+#[derive(Debug, Copy, Clone)]
+struct ErrorCode(NonZeroU32);
+
+#[cfg(feature = "std")]
+impl fmt::Display for ErrorCode {
+    fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
+        write!(f, "error code {}", self.0)
+    }
+}
+
+#[cfg(feature = "std")]
+impl std::error::Error for ErrorCode {}
+
+#[cfg(test)]
+mod test {
+    #[cfg(feature = "getrandom")]
+    #[test]
+    fn test_error_codes() {
+        // Make sure the values are the same as in `getrandom`.
+        assert_eq!(super::Error::CUSTOM_START, getrandom::Error::CUSTOM_START);
+        assert_eq!(super::Error::INTERNAL_START, getrandom::Error::INTERNAL_START);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/impls.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/impls.rs.html new file mode 100644 index 0000000..e42bd6d --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/impls.rs.html @@ -0,0 +1,417 @@ +impls.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Helper functions for implementing `RngCore` functions.
+//!
+//! For cross-platform reproducibility, these functions all use Little Endian:
+//! least-significant part first. For example, `next_u64_via_u32` takes `u32`
+//! values `x, y`, then outputs `(y << 32) | x`. To implement `next_u32`
+//! from `next_u64` in little-endian order, one should use `next_u64() as u32`.
+//!
+//! Byte-swapping (like the std `to_le` functions) is only needed to convert
+//! to/from byte sequences, and since its purpose is reproducibility,
+//! non-reproducible sources (e.g. `OsRng`) need not bother with it.
+
+use crate::RngCore;
+use core::cmp::min;
+
+/// Implement `next_u64` via `next_u32`, little-endian order.
+pub fn next_u64_via_u32<R: RngCore + ?Sized>(rng: &mut R) -> u64 {
+    // Use LE; we explicitly generate one value before the next.
+    let x = u64::from(rng.next_u32());
+    let y = u64::from(rng.next_u32());
+    (y << 32) | x
+}
+
+/// Implement `fill_bytes` via `next_u64` and `next_u32`, little-endian order.
+///
+/// The fastest way to fill a slice is usually to work as long as possible with
+/// integers. That is why this method mostly uses `next_u64`, and only when
+/// there are 4 or less bytes remaining at the end of the slice it uses
+/// `next_u32` once.
+pub fn fill_bytes_via_next<R: RngCore + ?Sized>(rng: &mut R, dest: &mut [u8]) {
+    let mut left = dest;
+    while left.len() >= 8 {
+        let (l, r) = { left }.split_at_mut(8);
+        left = r;
+        let chunk: [u8; 8] = rng.next_u64().to_le_bytes();
+        l.copy_from_slice(&chunk);
+    }
+    let n = left.len();
+    if n > 4 {
+        let chunk: [u8; 8] = rng.next_u64().to_le_bytes();
+        left.copy_from_slice(&chunk[..n]);
+    } else if n > 0 {
+        let chunk: [u8; 4] = rng.next_u32().to_le_bytes();
+        left.copy_from_slice(&chunk[..n]);
+    }
+}
+
+trait Observable: Copy {
+    type Bytes: AsRef<[u8]>;
+    fn to_le_bytes(self) -> Self::Bytes;
+
+    // Contract: observing self is memory-safe (implies no uninitialised padding)
+    fn as_byte_slice(x: &[Self]) -> &[u8];
+}
+impl Observable for u32 {
+    type Bytes = [u8; 4];
+    fn to_le_bytes(self) -> Self::Bytes {
+        self.to_le_bytes()
+    }
+    fn as_byte_slice(x: &[Self]) -> &[u8] {
+        let ptr = x.as_ptr() as *const u8;
+        let len = x.len() * core::mem::size_of::<Self>();
+        unsafe { core::slice::from_raw_parts(ptr, len) }
+    }
+}
+impl Observable for u64 {
+    type Bytes = [u8; 8];
+    fn to_le_bytes(self) -> Self::Bytes {
+        self.to_le_bytes()
+    }
+    fn as_byte_slice(x: &[Self]) -> &[u8] {
+        let ptr = x.as_ptr() as *const u8;
+        let len = x.len() * core::mem::size_of::<Self>();
+        unsafe { core::slice::from_raw_parts(ptr, len) }
+    }
+}
+
+fn fill_via_chunks<T: Observable>(src: &[T], dest: &mut [u8]) -> (usize, usize) {
+    let size = core::mem::size_of::<T>();
+    let byte_len = min(src.len() * size, dest.len());
+    let num_chunks = (byte_len + size - 1) / size;
+
+    if cfg!(target_endian = "little") {
+        // On LE we can do a simple copy, which is 25-50% faster:
+        dest[..byte_len].copy_from_slice(&T::as_byte_slice(&src[..num_chunks])[..byte_len]);
+    } else {
+        // This code is valid on all arches, but slower than the above:
+        let mut i = 0;
+        let mut iter = dest[..byte_len].chunks_exact_mut(size);
+        for chunk in &mut iter {
+            chunk.copy_from_slice(src[i].to_le_bytes().as_ref());
+            i += 1;
+        }
+        let chunk = iter.into_remainder();
+        if !chunk.is_empty() {
+            chunk.copy_from_slice(&src[i].to_le_bytes().as_ref()[..chunk.len()]);
+        }
+    }
+
+    (num_chunks, byte_len)
+}
+
+/// Implement `fill_bytes` by reading chunks from the output buffer of a block
+/// based RNG.
+///
+/// The return values are `(consumed_u32, filled_u8)`.
+///
+/// `filled_u8` is the number of filled bytes in `dest`, which may be less than
+/// the length of `dest`.
+/// `consumed_u32` is the number of words consumed from `src`, which is the same
+/// as `filled_u8 / 4` rounded up.
+///
+/// # Example
+/// (from `IsaacRng`)
+///
+/// ```ignore
+/// fn fill_bytes(&mut self, dest: &mut [u8]) {
+///     let mut read_len = 0;
+///     while read_len < dest.len() {
+///         if self.index >= self.rsl.len() {
+///             self.isaac();
+///         }
+///
+///         let (consumed_u32, filled_u8) =
+///             impls::fill_via_u32_chunks(&mut self.rsl[self.index..],
+///                                        &mut dest[read_len..]);
+///
+///         self.index += consumed_u32;
+///         read_len += filled_u8;
+///     }
+/// }
+/// ```
+pub fn fill_via_u32_chunks(src: &[u32], dest: &mut [u8]) -> (usize, usize) {
+    fill_via_chunks(src, dest)
+}
+
+/// Implement `fill_bytes` by reading chunks from the output buffer of a block
+/// based RNG.
+///
+/// The return values are `(consumed_u64, filled_u8)`.
+/// `filled_u8` is the number of filled bytes in `dest`, which may be less than
+/// the length of `dest`.
+/// `consumed_u64` is the number of words consumed from `src`, which is the same
+/// as `filled_u8 / 8` rounded up.
+///
+/// See `fill_via_u32_chunks` for an example.
+pub fn fill_via_u64_chunks(src: &[u64], dest: &mut [u8]) -> (usize, usize) {
+    fill_via_chunks(src, dest)
+}
+
+/// Implement `next_u32` via `fill_bytes`, little-endian order.
+pub fn next_u32_via_fill<R: RngCore + ?Sized>(rng: &mut R) -> u32 {
+    let mut buf = [0; 4];
+    rng.fill_bytes(&mut buf);
+    u32::from_le_bytes(buf)
+}
+
+/// Implement `next_u64` via `fill_bytes`, little-endian order.
+pub fn next_u64_via_fill<R: RngCore + ?Sized>(rng: &mut R) -> u64 {
+    let mut buf = [0; 8];
+    rng.fill_bytes(&mut buf);
+    u64::from_le_bytes(buf)
+}
+
+#[cfg(test)]
+mod test {
+    use super::*;
+
+    #[test]
+    fn test_fill_via_u32_chunks() {
+        let src = [1, 2, 3];
+        let mut dst = [0u8; 11];
+        assert_eq!(fill_via_u32_chunks(&src, &mut dst), (3, 11));
+        assert_eq!(dst, [1, 0, 0, 0, 2, 0, 0, 0, 3, 0, 0]);
+
+        let mut dst = [0u8; 13];
+        assert_eq!(fill_via_u32_chunks(&src, &mut dst), (3, 12));
+        assert_eq!(dst, [1, 0, 0, 0, 2, 0, 0, 0, 3, 0, 0, 0, 0]);
+
+        let mut dst = [0u8; 5];
+        assert_eq!(fill_via_u32_chunks(&src, &mut dst), (2, 5));
+        assert_eq!(dst, [1, 0, 0, 0, 2]);
+    }
+
+    #[test]
+    fn test_fill_via_u64_chunks() {
+        let src = [1, 2];
+        let mut dst = [0u8; 11];
+        assert_eq!(fill_via_u64_chunks(&src, &mut dst), (2, 11));
+        assert_eq!(dst, [1, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0]);
+
+        let mut dst = [0u8; 17];
+        assert_eq!(fill_via_u64_chunks(&src, &mut dst), (2, 16));
+        assert_eq!(dst, [1, 0, 0, 0, 0, 0, 0, 0, 2, 0, 0, 0, 0, 0, 0, 0, 0]);
+
+        let mut dst = [0u8; 5];
+        assert_eq!(fill_via_u64_chunks(&src, &mut dst), (1, 5));
+        assert_eq!(dst, [1, 0, 0, 0, 0]);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/le.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/le.rs.html new file mode 100644 index 0000000..119a894 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/le.rs.html @@ -0,0 +1,115 @@ +le.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+
// Copyright 2018 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Little-Endian utilities
+//!
+//! Little-Endian order has been chosen for internal usage; this makes some
+//! useful functions available.
+
+use core::convert::TryInto;
+
+/// Reads unsigned 32 bit integers from `src` into `dst`.
+#[inline]
+pub fn read_u32_into(src: &[u8], dst: &mut [u32]) {
+    assert!(src.len() >= 4 * dst.len());
+    for (out, chunk) in dst.iter_mut().zip(src.chunks_exact(4)) {
+        *out = u32::from_le_bytes(chunk.try_into().unwrap());
+    }
+}
+
+/// Reads unsigned 64 bit integers from `src` into `dst`.
+#[inline]
+pub fn read_u64_into(src: &[u8], dst: &mut [u64]) {
+    assert!(src.len() >= 8 * dst.len());
+    for (out, chunk) in dst.iter_mut().zip(src.chunks_exact(8)) {
+        *out = u64::from_le_bytes(chunk.try_into().unwrap());
+    }
+}
+
+#[test]
+fn test_read() {
+    let bytes = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16];
+
+    let mut buf = [0u32; 4];
+    read_u32_into(&bytes, &mut buf);
+    assert_eq!(buf[0], 0x04030201);
+    assert_eq!(buf[3], 0x100F0E0D);
+
+    let mut buf = [0u32; 3];
+    read_u32_into(&bytes[1..13], &mut buf); // unaligned
+    assert_eq!(buf[0], 0x05040302);
+    assert_eq!(buf[2], 0x0D0C0B0A);
+
+    let mut buf = [0u64; 2];
+    read_u64_into(&bytes, &mut buf);
+    assert_eq!(buf[0], 0x0807060504030201);
+    assert_eq!(buf[1], 0x100F0E0D0C0B0A09);
+
+    let mut buf = [0u64; 1];
+    read_u64_into(&bytes[7..15], &mut buf); // unaligned
+    assert_eq!(buf[0], 0x0F0E0D0C0B0A0908);
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/lib.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/lib.rs.html new file mode 100644 index 0000000..b043d23 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/lib.rs.html @@ -0,0 +1,1065 @@ +lib.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+86
+87
+88
+89
+90
+91
+92
+93
+94
+95
+96
+97
+98
+99
+100
+101
+102
+103
+104
+105
+106
+107
+108
+109
+110
+111
+112
+113
+114
+115
+116
+117
+118
+119
+120
+121
+122
+123
+124
+125
+126
+127
+128
+129
+130
+131
+132
+133
+134
+135
+136
+137
+138
+139
+140
+141
+142
+143
+144
+145
+146
+147
+148
+149
+150
+151
+152
+153
+154
+155
+156
+157
+158
+159
+160
+161
+162
+163
+164
+165
+166
+167
+168
+169
+170
+171
+172
+173
+174
+175
+176
+177
+178
+179
+180
+181
+182
+183
+184
+185
+186
+187
+188
+189
+190
+191
+192
+193
+194
+195
+196
+197
+198
+199
+200
+201
+202
+203
+204
+205
+206
+207
+208
+209
+210
+211
+212
+213
+214
+215
+216
+217
+218
+219
+220
+221
+222
+223
+224
+225
+226
+227
+228
+229
+230
+231
+232
+233
+234
+235
+236
+237
+238
+239
+240
+241
+242
+243
+244
+245
+246
+247
+248
+249
+250
+251
+252
+253
+254
+255
+256
+257
+258
+259
+260
+261
+262
+263
+264
+265
+266
+267
+268
+269
+270
+271
+272
+273
+274
+275
+276
+277
+278
+279
+280
+281
+282
+283
+284
+285
+286
+287
+288
+289
+290
+291
+292
+293
+294
+295
+296
+297
+298
+299
+300
+301
+302
+303
+304
+305
+306
+307
+308
+309
+310
+311
+312
+313
+314
+315
+316
+317
+318
+319
+320
+321
+322
+323
+324
+325
+326
+327
+328
+329
+330
+331
+332
+333
+334
+335
+336
+337
+338
+339
+340
+341
+342
+343
+344
+345
+346
+347
+348
+349
+350
+351
+352
+353
+354
+355
+356
+357
+358
+359
+360
+361
+362
+363
+364
+365
+366
+367
+368
+369
+370
+371
+372
+373
+374
+375
+376
+377
+378
+379
+380
+381
+382
+383
+384
+385
+386
+387
+388
+389
+390
+391
+392
+393
+394
+395
+396
+397
+398
+399
+400
+401
+402
+403
+404
+405
+406
+407
+408
+409
+410
+411
+412
+413
+414
+415
+416
+417
+418
+419
+420
+421
+422
+423
+424
+425
+426
+427
+428
+429
+430
+431
+432
+433
+434
+435
+436
+437
+438
+439
+440
+441
+442
+443
+444
+445
+446
+447
+448
+449
+450
+451
+452
+453
+454
+455
+456
+457
+458
+459
+460
+461
+462
+463
+464
+465
+466
+467
+468
+469
+470
+471
+472
+473
+474
+475
+476
+477
+478
+479
+480
+481
+482
+483
+484
+485
+486
+487
+488
+489
+490
+491
+492
+493
+494
+495
+496
+497
+498
+499
+500
+501
+502
+503
+504
+505
+506
+507
+508
+509
+510
+511
+512
+513
+514
+515
+516
+517
+518
+519
+520
+521
+522
+523
+524
+525
+526
+527
+528
+529
+530
+531
+
// Copyright 2018 Developers of the Rand project.
+// Copyright 2017-2018 The Rust Project Developers.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Random number generation traits
+//!
+//! This crate is mainly of interest to crates publishing implementations of
+//! [`RngCore`]. Other users are encouraged to use the [`rand`] crate instead
+//! which re-exports the main traits and error types.
+//!
+//! [`RngCore`] is the core trait implemented by algorithmic pseudo-random number
+//! generators and external random-number sources.
+//!
+//! [`SeedableRng`] is an extension trait for construction from fixed seeds and
+//! other random number generators.
+//!
+//! [`Error`] is provided for error-handling. It is safe to use in `no_std`
+//! environments.
+//!
+//! The [`impls`] and [`le`] sub-modules include a few small functions to assist
+//! implementation of [`RngCore`].
+//!
+//! [`rand`]: https://docs.rs/rand
+
+#![doc(
+    html_logo_url = "https://www.rust-lang.org/logos/rust-logo-128x128-blk.png",
+    html_favicon_url = "https://www.rust-lang.org/favicon.ico",
+    html_root_url = "https://rust-random.github.io/rand/"
+)]
+#![deny(missing_docs)]
+#![deny(missing_debug_implementations)]
+#![doc(test(attr(allow(unused_variables), deny(warnings))))]
+#![cfg_attr(doc_cfg, feature(doc_cfg))]
+#![no_std]
+
+use core::convert::AsMut;
+use core::default::Default;
+
+#[cfg(feature = "std")] extern crate std;
+#[cfg(feature = "alloc")] extern crate alloc;
+#[cfg(feature = "alloc")] use alloc::boxed::Box;
+
+pub use error::Error;
+#[cfg(feature = "getrandom")] pub use os::OsRng;
+
+
+pub mod block;
+mod error;
+pub mod impls;
+pub mod le;
+#[cfg(feature = "getrandom")] mod os;
+
+
+/// The core of a random number generator.
+///
+/// This trait encapsulates the low-level functionality common to all
+/// generators, and is the "back end", to be implemented by generators.
+/// End users should normally use the `Rng` trait from the [`rand`] crate,
+/// which is automatically implemented for every type implementing `RngCore`.
+///
+/// Three different methods for generating random data are provided since the
+/// optimal implementation of each is dependent on the type of generator. There
+/// is no required relationship between the output of each; e.g. many
+/// implementations of [`fill_bytes`] consume a whole number of `u32` or `u64`
+/// values and drop any remaining unused bytes. The same can happen with the
+/// [`next_u32`] and [`next_u64`] methods, implementations may discard some
+/// random bits for efficiency.
+///
+/// The [`try_fill_bytes`] method is a variant of [`fill_bytes`] allowing error
+/// handling; it is not deemed sufficiently useful to add equivalents for
+/// [`next_u32`] or [`next_u64`] since the latter methods are almost always used
+/// with algorithmic generators (PRNGs), which are normally infallible.
+///
+/// Implementers should produce bits uniformly. Pathological RNGs (e.g. always
+/// returning the same value, or never setting certain bits) can break rejection
+/// sampling used by random distributions, and also break other RNGs when
+/// seeding them via [`SeedableRng::from_rng`].
+///
+/// Algorithmic generators implementing [`SeedableRng`] should normally have
+/// *portable, reproducible* output, i.e. fix Endianness when converting values
+/// to avoid platform differences, and avoid making any changes which affect
+/// output (except by communicating that the release has breaking changes).
+///
+/// Typically an RNG will implement only one of the methods available
+/// in this trait directly, then use the helper functions from the
+/// [`impls`] module to implement the other methods.
+///
+/// It is recommended that implementations also implement:
+///
+/// - `Debug` with a custom implementation which *does not* print any internal
+///   state (at least, [`CryptoRng`]s should not risk leaking state through
+///   `Debug`).
+/// - `Serialize` and `Deserialize` (from Serde), preferably making Serde
+///   support optional at the crate level in PRNG libs.
+/// - `Clone`, if possible.
+/// - *never* implement `Copy` (accidental copies may cause repeated values).
+/// - *do not* implement `Default` for pseudorandom generators, but instead
+///   implement [`SeedableRng`], to guide users towards proper seeding.
+///   External / hardware RNGs can choose to implement `Default`.
+/// - `Eq` and `PartialEq` could be implemented, but are probably not useful.
+///
+/// # Example
+///
+/// A simple example, obviously not generating very *random* output:
+///
+/// ```
+/// #![allow(dead_code)]
+/// use rand_core::{RngCore, Error, impls};
+///
+/// struct CountingRng(u64);
+///
+/// impl RngCore for CountingRng {
+///     fn next_u32(&mut self) -> u32 {
+///         self.next_u64() as u32
+///     }
+///
+///     fn next_u64(&mut self) -> u64 {
+///         self.0 += 1;
+///         self.0
+///     }
+///
+///     fn fill_bytes(&mut self, dest: &mut [u8]) {
+///         impls::fill_bytes_via_next(self, dest)
+///     }
+///
+///     fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+///         Ok(self.fill_bytes(dest))
+///     }
+/// }
+/// ```
+///
+/// [`rand`]: https://docs.rs/rand
+/// [`try_fill_bytes`]: RngCore::try_fill_bytes
+/// [`fill_bytes`]: RngCore::fill_bytes
+/// [`next_u32`]: RngCore::next_u32
+/// [`next_u64`]: RngCore::next_u64
+pub trait RngCore {
+    /// Return the next random `u32`.
+    ///
+    /// RNGs must implement at least one method from this trait directly. In
+    /// the case this method is not implemented directly, it can be implemented
+    /// using `self.next_u64() as u32` or via [`impls::next_u32_via_fill`].
+    fn next_u32(&mut self) -> u32;
+
+    /// Return the next random `u64`.
+    ///
+    /// RNGs must implement at least one method from this trait directly. In
+    /// the case this method is not implemented directly, it can be implemented
+    /// via [`impls::next_u64_via_u32`] or via [`impls::next_u64_via_fill`].
+    fn next_u64(&mut self) -> u64;
+
+    /// Fill `dest` with random data.
+    ///
+    /// RNGs must implement at least one method from this trait directly. In
+    /// the case this method is not implemented directly, it can be implemented
+    /// via [`impls::fill_bytes_via_next`] or
+    /// via [`RngCore::try_fill_bytes`]; if this generator can
+    /// fail the implementation must choose how best to handle errors here
+    /// (e.g. panic with a descriptive message or log a warning and retry a few
+    /// times).
+    ///
+    /// This method should guarantee that `dest` is entirely filled
+    /// with new data, and may panic if this is impossible
+    /// (e.g. reading past the end of a file that is being used as the
+    /// source of randomness).
+    fn fill_bytes(&mut self, dest: &mut [u8]);
+
+    /// Fill `dest` entirely with random data.
+    ///
+    /// This is the only method which allows an RNG to report errors while
+    /// generating random data thus making this the primary method implemented
+    /// by external (true) RNGs (e.g. `OsRng`) which can fail. It may be used
+    /// directly to generate keys and to seed (infallible) PRNGs.
+    ///
+    /// Other than error handling, this method is identical to [`RngCore::fill_bytes`];
+    /// thus this may be implemented using `Ok(self.fill_bytes(dest))` or
+    /// `fill_bytes` may be implemented with
+    /// `self.try_fill_bytes(dest).unwrap()` or more specific error handling.
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error>;
+}
+
+/// A marker trait used to indicate that an [`RngCore`] or [`BlockRngCore`]
+/// implementation is supposed to be cryptographically secure.
+///
+/// *Cryptographically secure generators*, also known as *CSPRNGs*, should
+/// satisfy an additional properties over other generators: given the first
+/// *k* bits of an algorithm's output
+/// sequence, it should not be possible using polynomial-time algorithms to
+/// predict the next bit with probability significantly greater than 50%.
+///
+/// Some generators may satisfy an additional property, however this is not
+/// required by this trait: if the CSPRNG's state is revealed, it should not be
+/// computationally-feasible to reconstruct output prior to this. Some other
+/// generators allow backwards-computation and are considered *reversible*.
+///
+/// Note that this trait is provided for guidance only and cannot guarantee
+/// suitability for cryptographic applications. In general it should only be
+/// implemented for well-reviewed code implementing well-regarded algorithms.
+///
+/// Note also that use of a `CryptoRng` does not protect against other
+/// weaknesses such as seeding from a weak entropy source or leaking state.
+///
+/// [`BlockRngCore`]: block::BlockRngCore
+pub trait CryptoRng {}
+
+/// An extension trait that is automatically implemented for any type
+/// implementing [`RngCore`] and [`CryptoRng`].
+///
+/// It may be used as a trait object, and supports upcasting to [`RngCore`] via
+/// the [`CryptoRngCore::as_rngcore`] method.
+///
+/// # Example
+///
+/// ```
+/// use rand_core::CryptoRngCore;
+///
+/// #[allow(unused)]
+/// fn make_token(rng: &mut dyn CryptoRngCore) -> [u8; 32] {
+///     let mut buf = [0u8; 32];
+///     rng.fill_bytes(&mut buf);
+///     buf
+/// }
+/// ```
+pub trait CryptoRngCore: CryptoRng + RngCore {
+    /// Upcast to an [`RngCore`] trait object.
+    fn as_rngcore(&mut self) -> &mut dyn RngCore;
+}
+
+impl<T: CryptoRng + RngCore> CryptoRngCore for T {
+    fn as_rngcore(&mut self) -> &mut dyn RngCore {
+        self
+    }
+}
+
+/// A random number generator that can be explicitly seeded.
+///
+/// This trait encapsulates the low-level functionality common to all
+/// pseudo-random number generators (PRNGs, or algorithmic generators).
+///
+/// [`rand`]: https://docs.rs/rand
+pub trait SeedableRng: Sized {
+    /// Seed type, which is restricted to types mutably-dereferenceable as `u8`
+    /// arrays (we recommend `[u8; N]` for some `N`).
+    ///
+    /// It is recommended to seed PRNGs with a seed of at least circa 100 bits,
+    /// which means an array of `[u8; 12]` or greater to avoid picking RNGs with
+    /// partially overlapping periods.
+    ///
+    /// For cryptographic RNG's a seed of 256 bits is recommended, `[u8; 32]`.
+    ///
+    ///
+    /// # Implementing `SeedableRng` for RNGs with large seeds
+    ///
+    /// Note that the required traits `core::default::Default` and
+    /// `core::convert::AsMut<u8>` are not implemented for large arrays
+    /// `[u8; N]` with `N` > 32. To be able to implement the traits required by
+    /// `SeedableRng` for RNGs with such large seeds, the newtype pattern can be
+    /// used:
+    ///
+    /// ```
+    /// use rand_core::SeedableRng;
+    ///
+    /// const N: usize = 64;
+    /// pub struct MyRngSeed(pub [u8; N]);
+    /// pub struct MyRng(MyRngSeed);
+    ///
+    /// impl Default for MyRngSeed {
+    ///     fn default() -> MyRngSeed {
+    ///         MyRngSeed([0; N])
+    ///     }
+    /// }
+    ///
+    /// impl AsMut<[u8]> for MyRngSeed {
+    ///     fn as_mut(&mut self) -> &mut [u8] {
+    ///         &mut self.0
+    ///     }
+    /// }
+    ///
+    /// impl SeedableRng for MyRng {
+    ///     type Seed = MyRngSeed;
+    ///
+    ///     fn from_seed(seed: MyRngSeed) -> MyRng {
+    ///         MyRng(seed)
+    ///     }
+    /// }
+    /// ```
+    type Seed: Sized + Default + AsMut<[u8]>;
+
+    /// Create a new PRNG using the given seed.
+    ///
+    /// PRNG implementations are allowed to assume that bits in the seed are
+    /// well distributed. That means usually that the number of one and zero
+    /// bits are roughly equal, and values like 0, 1 and (size - 1) are unlikely.
+    /// Note that many non-cryptographic PRNGs will show poor quality output
+    /// if this is not adhered to. If you wish to seed from simple numbers, use
+    /// `seed_from_u64` instead.
+    ///
+    /// All PRNG implementations should be reproducible unless otherwise noted:
+    /// given a fixed `seed`, the same sequence of output should be produced
+    /// on all runs, library versions and architectures (e.g. check endianness).
+    /// Any "value-breaking" changes to the generator should require bumping at
+    /// least the minor version and documentation of the change.
+    ///
+    /// It is not required that this function yield the same state as a
+    /// reference implementation of the PRNG given equivalent seed; if necessary
+    /// another constructor replicating behaviour from a reference
+    /// implementation can be added.
+    ///
+    /// PRNG implementations should make sure `from_seed` never panics. In the
+    /// case that some special values (like an all zero seed) are not viable
+    /// seeds it is preferable to map these to alternative constant value(s),
+    /// for example `0xBAD5EEDu32` or `0x0DDB1A5E5BAD5EEDu64` ("odd biases? bad
+    /// seed"). This is assuming only a small number of values must be rejected.
+    fn from_seed(seed: Self::Seed) -> Self;
+
+    /// Create a new PRNG using a `u64` seed.
+    ///
+    /// This is a convenience-wrapper around `from_seed` to allow construction
+    /// of any `SeedableRng` from a simple `u64` value. It is designed such that
+    /// low Hamming Weight numbers like 0 and 1 can be used and should still
+    /// result in good, independent seeds to the PRNG which is returned.
+    ///
+    /// This **is not suitable for cryptography**, as should be clear given that
+    /// the input size is only 64 bits.
+    ///
+    /// Implementations for PRNGs *may* provide their own implementations of
+    /// this function, but the default implementation should be good enough for
+    /// all purposes. *Changing* the implementation of this function should be
+    /// considered a value-breaking change.
+    fn seed_from_u64(mut state: u64) -> Self {
+        // We use PCG32 to generate a u32 sequence, and copy to the seed
+        fn pcg32(state: &mut u64) -> [u8; 4] {
+            const MUL: u64 = 6364136223846793005;
+            const INC: u64 = 11634580027462260723;
+
+            // We advance the state first (to get away from the input value,
+            // in case it has low Hamming Weight).
+            *state = state.wrapping_mul(MUL).wrapping_add(INC);
+            let state = *state;
+
+            // Use PCG output function with to_le to generate x:
+            let xorshifted = (((state >> 18) ^ state) >> 27) as u32;
+            let rot = (state >> 59) as u32;
+            let x = xorshifted.rotate_right(rot);
+            x.to_le_bytes()
+        }
+
+        let mut seed = Self::Seed::default();
+        let mut iter = seed.as_mut().chunks_exact_mut(4);
+        for chunk in &mut iter {
+            chunk.copy_from_slice(&pcg32(&mut state));
+        }
+        let rem = iter.into_remainder();
+        if !rem.is_empty() {
+            rem.copy_from_slice(&pcg32(&mut state)[..rem.len()]);
+        }
+
+        Self::from_seed(seed)
+    }
+
+    /// Create a new PRNG seeded from another `Rng`.
+    ///
+    /// This may be useful when needing to rapidly seed many PRNGs from a master
+    /// PRNG, and to allow forking of PRNGs. It may be considered deterministic.
+    ///
+    /// The master PRNG should be at least as high quality as the child PRNGs.
+    /// When seeding non-cryptographic child PRNGs, we recommend using a
+    /// different algorithm for the master PRNG (ideally a CSPRNG) to avoid
+    /// correlations between the child PRNGs. If this is not possible (e.g.
+    /// forking using small non-crypto PRNGs) ensure that your PRNG has a good
+    /// mixing function on the output or consider use of a hash function with
+    /// `from_seed`.
+    ///
+    /// Note that seeding `XorShiftRng` from another `XorShiftRng` provides an
+    /// extreme example of what can go wrong: the new PRNG will be a clone
+    /// of the parent.
+    ///
+    /// PRNG implementations are allowed to assume that a good RNG is provided
+    /// for seeding, and that it is cryptographically secure when appropriate.
+    /// As of `rand` 0.7 / `rand_core` 0.5, implementations overriding this
+    /// method should ensure the implementation satisfies reproducibility
+    /// (in prior versions this was not required).
+    ///
+    /// [`rand`]: https://docs.rs/rand
+    fn from_rng<R: RngCore>(mut rng: R) -> Result<Self, Error> {
+        let mut seed = Self::Seed::default();
+        rng.try_fill_bytes(seed.as_mut())?;
+        Ok(Self::from_seed(seed))
+    }
+
+    /// Creates a new instance of the RNG seeded via [`getrandom`].
+    ///
+    /// This method is the recommended way to construct non-deterministic PRNGs
+    /// since it is convenient and secure.
+    ///
+    /// In case the overhead of using [`getrandom`] to seed *many* PRNGs is an
+    /// issue, one may prefer to seed from a local PRNG, e.g.
+    /// `from_rng(thread_rng()).unwrap()`.
+    ///
+    /// # Panics
+    ///
+    /// If [`getrandom`] is unable to provide secure entropy this method will panic.
+    ///
+    /// [`getrandom`]: https://docs.rs/getrandom
+    #[cfg(feature = "getrandom")]
+    #[cfg_attr(doc_cfg, doc(cfg(feature = "getrandom")))]
+    fn from_entropy() -> Self {
+        let mut seed = Self::Seed::default();
+        if let Err(err) = getrandom::getrandom(seed.as_mut()) {
+            panic!("from_entropy failed: {}", err);
+        }
+        Self::from_seed(seed)
+    }
+}
+
+// Implement `RngCore` for references to an `RngCore`.
+// Force inlining all functions, so that it is up to the `RngCore`
+// implementation and the optimizer to decide on inlining.
+impl<'a, R: RngCore + ?Sized> RngCore for &'a mut R {
+    #[inline(always)]
+    fn next_u32(&mut self) -> u32 {
+        (**self).next_u32()
+    }
+
+    #[inline(always)]
+    fn next_u64(&mut self) -> u64 {
+        (**self).next_u64()
+    }
+
+    #[inline(always)]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        (**self).fill_bytes(dest)
+    }
+
+    #[inline(always)]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        (**self).try_fill_bytes(dest)
+    }
+}
+
+// Implement `RngCore` for boxed references to an `RngCore`.
+// Force inlining all functions, so that it is up to the `RngCore`
+// implementation and the optimizer to decide on inlining.
+#[cfg(feature = "alloc")]
+impl<R: RngCore + ?Sized> RngCore for Box<R> {
+    #[inline(always)]
+    fn next_u32(&mut self) -> u32 {
+        (**self).next_u32()
+    }
+
+    #[inline(always)]
+    fn next_u64(&mut self) -> u64 {
+        (**self).next_u64()
+    }
+
+    #[inline(always)]
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        (**self).fill_bytes(dest)
+    }
+
+    #[inline(always)]
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        (**self).try_fill_bytes(dest)
+    }
+}
+
+#[cfg(feature = "std")]
+impl std::io::Read for dyn RngCore {
+    fn read(&mut self, buf: &mut [u8]) -> Result<usize, std::io::Error> {
+        self.try_fill_bytes(buf)?;
+        Ok(buf.len())
+    }
+}
+
+// Implement `CryptoRng` for references to a `CryptoRng`.
+impl<'a, R: CryptoRng + ?Sized> CryptoRng for &'a mut R {}
+
+// Implement `CryptoRng` for boxed references to a `CryptoRng`.
+#[cfg(feature = "alloc")]
+impl<R: CryptoRng + ?Sized> CryptoRng for Box<R> {}
+
+#[cfg(test)]
+mod test {
+    use super::*;
+
+    #[test]
+    fn test_seed_from_u64() {
+        struct SeedableNum(u64);
+        impl SeedableRng for SeedableNum {
+            type Seed = [u8; 8];
+
+            fn from_seed(seed: Self::Seed) -> Self {
+                let mut x = [0u64; 1];
+                le::read_u64_into(&seed, &mut x);
+                SeedableNum(x[0])
+            }
+        }
+
+        const N: usize = 8;
+        const SEEDS: [u64; N] = [0u64, 1, 2, 3, 4, 8, 16, -1i64 as u64];
+        let mut results = [0u64; N];
+        for (i, seed) in SEEDS.iter().enumerate() {
+            let SeedableNum(x) = SeedableNum::seed_from_u64(*seed);
+            results[i] = x;
+        }
+
+        for (i1, r1) in results.iter().enumerate() {
+            let weight = r1.count_ones();
+            // This is the binomial distribution B(64, 0.5), so chance of
+            // weight < 20 is binocdf(19, 64, 0.5) = 7.8e-4, and same for
+            // weight > 44.
+            assert!((20..=44).contains(&weight));
+
+            for (i2, r2) in results.iter().enumerate() {
+                if i1 == i2 {
+                    continue;
+                }
+                let diff_weight = (r1 ^ r2).count_ones();
+                assert!(diff_weight >= 20);
+            }
+        }
+
+        // value-breakage test:
+        assert_eq!(results[0], 5029875928683246316);
+    }
+}
+
+
\ No newline at end of file diff --git a/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/os.rs.html b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/os.rs.html new file mode 100644 index 0000000..9a5d873 --- /dev/null +++ b/rust/theBook/chapter-2-guessing-game/guessing_game/target/doc/src/rand_core/os.rs.html @@ -0,0 +1,173 @@ +os.rs - source
1
+2
+3
+4
+5
+6
+7
+8
+9
+10
+11
+12
+13
+14
+15
+16
+17
+18
+19
+20
+21
+22
+23
+24
+25
+26
+27
+28
+29
+30
+31
+32
+33
+34
+35
+36
+37
+38
+39
+40
+41
+42
+43
+44
+45
+46
+47
+48
+49
+50
+51
+52
+53
+54
+55
+56
+57
+58
+59
+60
+61
+62
+63
+64
+65
+66
+67
+68
+69
+70
+71
+72
+73
+74
+75
+76
+77
+78
+79
+80
+81
+82
+83
+84
+85
+
// Copyright 2019 Developers of the Rand project.
+//
+// Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
+// https://www.apache.org/licenses/LICENSE-2.0> or the MIT license
+// <LICENSE-MIT or https://opensource.org/licenses/MIT>, at your
+// option. This file may not be copied, modified, or distributed
+// except according to those terms.
+
+//! Interface to the random number generator of the operating system.
+
+use crate::{impls, CryptoRng, Error, RngCore};
+use getrandom::getrandom;
+
+/// A random number generator that retrieves randomness from the
+/// operating system.
+///
+/// This is a zero-sized struct. It can be freely constructed with `OsRng`.
+///
+/// The implementation is provided by the [getrandom] crate. Refer to
+/// [getrandom] documentation for details.
+///
+/// This struct is only available when specifying the crate feature `getrandom`
+/// or `std`. When using the `rand` lib, it is also available as `rand::rngs::OsRng`.
+///
+/// # Blocking and error handling
+///
+/// It is possible that when used during early boot the first call to `OsRng`
+/// will block until the system's RNG is initialised. It is also possible
+/// (though highly unlikely) for `OsRng` to fail on some platforms, most
+/// likely due to system mis-configuration.
+///
+/// After the first successful call, it is highly unlikely that failures or
+/// significant delays will occur (although performance should be expected to
+/// be much slower than a user-space PRNG).
+///
+/// # Usage example
+/// ```
+/// use rand_core::{RngCore, OsRng};
+///
+/// let mut key = [0u8; 16];
+/// OsRng.fill_bytes(&mut key);
+/// let random_u64 = OsRng.next_u64();
+/// ```
+///
+/// [getrandom]: https://crates.io/crates/getrandom
+#[cfg_attr(doc_cfg, doc(cfg(feature = "getrandom")))]
+#[derive(Clone, Copy, Debug, Default)]
+pub struct OsRng;
+
+impl CryptoRng for OsRng {}
+
+impl RngCore for OsRng {
+    fn next_u32(&mut self) -> u32 {
+        impls::next_u32_via_fill(self)
+    }
+
+    fn next_u64(&mut self) -> u64 {
+        impls::next_u64_via_fill(self)
+    }
+
+    fn fill_bytes(&mut self, dest: &mut [u8]) {
+        if let Err(e) = self.try_fill_bytes(dest) {
+            panic!("Error: {}", e);
+        }
+    }
+
+    fn try_fill_bytes(&mut self, dest: &mut [u8]) -> Result<(), Error> {
+        getrandom(dest)?;
+        Ok(())
+    }
+}
+
+#[test]
+fn test_os_rng() {
+    let x = OsRng.next_u64();
+    let y = OsRng.next_u64();
+    assert!(x != 0);
+    assert!(x != y);
+}
+
+#[test]
+fn test_construction() {
+    let mut rng = OsRng::default();
+    assert!(rng.next_u64() != 0);
+}
+
+
\ No newline at end of file -- cgit v1.2.3-70-g09d2