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
//! Non-owning unsafe I/O
//!
//! A brief explanation of the naming convention:
//!
//! `Raw` is for platform-specific types and traits, such as `std`'s [`RawFd`],
//! [`AsRawFd`], [`RawHandle`], [`AsRawHandle`], and similar, as well as
//! `unsafe-io`'s [`RawHandleOrSocket`], [`AsRawHandleOrSocket`], and similar.
//! "Handle" in this context means a Windows [`HANDLE`].
//!
//! `Unsafe` is for minimal platform-independent abstractions on top of the
//! platform-specific types, such as [`UnsafeHandle`] (abstracts over `RawFd`
//! and `RawHandleOrSocket`), [`UnsafeFile`] (abstracts over `RawFd` and
//! `RawHandle`), and [`UnsafeSocket`] (abstracts over `RawFd` and `RawSocket`).
//! "Handle" in this context means any kind of I/O handle.
//!
//! In table form, the main types are:
//!
//! | Resource | Posix-ish type | Windows type          || Platform-independent types           |
//! | -------- | -------------- | --------------------- || ------------------------------------ |
//! | File     | [`RawFd`]      | [`RawHandle`]         || [`UnsafeHandle`] or [`UnsafeFile`]   |
//! | Pipe     | [`RawFd`]      | [`RawHandle`]         || [`UnsafeHandle`] or [`UnsafeFile`]   |
//! | Socket   | [`RawFd`]      | [`RawSocket`]         || [`UnsafeHandle`] or [`UnsafeSocket`] |
//! | Any      | [`RawFd`]      | [`RawHandleOrSocket`] || [`UnsafeHandle`]                     |
//!
//! and the main traits are:
//!
//! | Type             | `As` trait         | `Into` trait         | `From` trait         |
//! | ---------------- | ------------------ | -------------------- | -------------------- |
//! | [`RawFd`]        | [`AsRawFd`]        | [`IntoRawFd`]        | [`FromRawFd`]        |
//! | [`RawHandle`]    | [`AsRawHandle`]    | [`IntoRawHandle`]    | [`FromRawHandle`]    |
//! | [`RawSocket`]    | [`AsRawSocket`]    | [`IntoRawSocket`]    | [`FromRawSocket`]    |
//! | [`RawHandleOrSocket`] | [`AsRawHandleOrSocket`] | [`IntoRawHandleOrSocket`] | *     |
//! |                  |                    |                      |                      |
//! | [`UnsafeFile`]   | [`AsUnsafeFile`]   | [`IntoUnsafeFile`]   | [`FromUnsafeFile`]   |
//! | [`UnsafeSocket`] | [`AsUnsafeSocket`] | [`IntoUnsafeSocket`] | [`FromUnsafeSocket`] |
//! | [`UnsafeHandle`] | [`AsUnsafeHandle`] | [`IntoUnsafeHandle`] | *                    |
//!
//! \* These types do not have `From` traits.
//!
//! The `AsUnsafe*` and `IntoUnsafe*` traits require types to guarantee that
//! they own the handles that they return. This differs from their `AsRaw*` and
//! `IntoRaw*` counterparts, which require no such guarantee. This crate defines
//! an [`OwnsRaw`] trait which is unsafe to implement and which allows types to
//! declare that they own the handles they hold, allowing them to opt into the
//! blanket `AsUnsafe*` and `IntoUnsafe*` implementations. See
//! [rust-lang/rust#76969] for further background.
//!
//! This crates also defines several additional utilities:
//!
//! [`UnsafeHandle`] has methods [`as_readable`] and [`as_writeable`] which
//! return similar non-owning types [`UnsafeReadable`] and [`UnsafeWriteable`],
//! respectively, which implement [`Read`] and [`Write`].
//!
//! [`AsUnsafeReadWriteHandle`], [`AsRawReadWriteFd`], and
//! [`AsRawReadWriteHandleOrSocket`], are traits for working with types that
//! implement both [`Read`] and [`Write`] and may contain either one handle
//! (such as a socket) or two (such as stdin and stdout, or a pair of pipes).
//!
//! [`RawFd`]: https://doc.rust-lang.org/std/os/unix/io/type.RawFd.html
//! [`AsRawFd`]: https://doc.rust-lang.org/std/os/unix/io/trait.AsRawFd.html
//! [`IntoRawFd`]: https://doc.rust-lang.org/std/os/unix/io/trait.IntoRawFd.html
//! [`FromRawFd`]: https://doc.rust-lang.org/std/os/unix/io/trait.FromRawFd.html
//! [`RawHandle`]: https://doc.rust-lang.org/std/os/windows/io/type.RawHandle.html
//! [`AsRawHandle`]: https://doc.rust-lang.org/std/os/windows/io/trait.AsRawHandle.html
//! [`IntoRawHandle`]: https://doc.rust-lang.org/std/os/windows/io/trait.IntoRawHandle.html
//! [`FromRawHandle`]: https://doc.rust-lang.org/std/os/windows/io/trait.FromRawHandle.html
//! [`RawSocket`]: https://doc.rust-lang.org/std/os/windows/io/type.RawSocket.html
//! [`AsRawSocket`]: https://doc.rust-lang.org/std/os/windows/io/trait.AsRawHandle.html
//! [`IntoRawSocket`]: https://doc.rust-lang.org/std/os/windows/io/trait.IntoRawHandle.html
//! [`FromRawSocket`]: https://doc.rust-lang.org/std/os/windows/io/trait.FromRawHandle.html
//! [`RawHandleOrSocket`]: https://docs.rs/unsafe-io/latest/x86_64-pc-windows-msvc/unsafe_io/struct.RawHandleOrSocket.html
//! [`AsRawHandleOrSocket`]: https://docs.rs/unsafe-io/latest/x86_64-pc-windows-msvc/unsafe_io/trait.AsRawHandleOrSocket.html
//! [`IntoRawHandleOrSocket`]: https://docs.rs/unsafe-io/latest/x86_64-pc-windows-msvc/unsafe_io/trait.IntoRawHandleOrSocket.html
//! [`AsRawReadWriteHandleOrSocket`]: https://docs.rs/unsafe-io/latest/x86_64-pc-windows-msvc/unsafe_io/trait.AsRawReadWriteHandleOrSocket.html
//! [`AsRawReadWriteFd`]: https://docs.rs/unsafe-io/latest/unsafe_io/trait.AsRawReadWriteFd.html
//! [`HANDLE`]: https://doc.rust-lang.org/std/os/windows/raw/type.HANDLE.html
//! [`Read`]: std::io::Read
//! [`Write`]: std::io::Write
//! [`as_readable`]: UnsafeHandle::as_readable
//! [`as_writeable`]: UnsafeHandle::as_writeable
//! [rust-lang/rust#76969]: https://github.com/rust-lang/rust/issues/76969

#![deny(missing_docs)]
#![cfg_attr(can_vector, feature(can_vector))]
#![cfg_attr(write_all_vectored, feature(write_all_vectored))]
#![cfg_attr(target_os = "wasi", feature(wasi_ext))]

mod owns_raw;
#[cfg(windows)]
mod raw_handle_or_socket;
mod read_write;
mod unsafe_handle;

pub use owns_raw::OwnsRaw;
#[cfg(windows)]
pub use raw_handle_or_socket::{AsRawHandleOrSocket, IntoRawHandleOrSocket, RawHandleOrSocket};
#[cfg(not(windows))]
pub use read_write::AsRawReadWriteFd;
#[cfg(windows)]
pub use read_write::AsRawReadWriteHandleOrSocket;
pub use read_write::AsUnsafeReadWriteHandle;
pub use unsafe_handle::{
    AsUnsafeFile, AsUnsafeHandle, AsUnsafeSocket, FromUnsafeFile, FromUnsafeSocket, IntoUnsafeFile,
    IntoUnsafeHandle, IntoUnsafeSocket, UnsafeFile, UnsafeHandle, UnsafeReadable, UnsafeSocket,
    UnsafeWriteable, View,
};