summaryrefslogtreecommitdiffstats
path: root/vendor/winapi-util/src
diff options
context:
space:
mode:
authorDaniel Baumann <daniel.baumann@progress-linux.org>2024-05-04 12:41:35 +0000
committerDaniel Baumann <daniel.baumann@progress-linux.org>2024-05-04 12:41:35 +0000
commit7e5d7eea9c580ef4b41a765bde624af431942b96 (patch)
tree2c0d9ca12878fc4525650aa4e54d77a81a07cc09 /vendor/winapi-util/src
parentAdding debian version 1.70.0+dfsg1-9. (diff)
downloadrustc-7e5d7eea9c580ef4b41a765bde624af431942b96.tar.xz
rustc-7e5d7eea9c580ef4b41a765bde624af431942b96.zip
Merging upstream version 1.70.0+dfsg2.
Signed-off-by: Daniel Baumann <daniel.baumann@progress-linux.org>
Diffstat (limited to 'vendor/winapi-util/src')
-rw-r--r--vendor/winapi-util/src/console.rs402
-rw-r--r--vendor/winapi-util/src/file.rs168
-rw-r--r--vendor/winapi-util/src/lib.rs32
-rw-r--r--vendor/winapi-util/src/win.rs246
4 files changed, 0 insertions, 848 deletions
diff --git a/vendor/winapi-util/src/console.rs b/vendor/winapi-util/src/console.rs
deleted file mode 100644
index 233d5c969..000000000
--- a/vendor/winapi-util/src/console.rs
+++ /dev/null
@@ -1,402 +0,0 @@
-use std::io;
-use std::mem;
-
-use winapi::shared::minwindef::WORD;
-use winapi::um::consoleapi::{GetConsoleMode, SetConsoleMode};
-use winapi::um::wincon::{
- self, GetConsoleScreenBufferInfo, SetConsoleTextAttribute,
- CONSOLE_SCREEN_BUFFER_INFO, FOREGROUND_BLUE as FG_BLUE,
- FOREGROUND_GREEN as FG_GREEN, FOREGROUND_INTENSITY as FG_INTENSITY,
- FOREGROUND_RED as FG_RED,
-};
-
-use crate::{AsHandleRef, HandleRef};
-
-const FG_CYAN: WORD = FG_BLUE | FG_GREEN;
-const FG_MAGENTA: WORD = FG_BLUE | FG_RED;
-const FG_YELLOW: WORD = FG_GREEN | FG_RED;
-const FG_WHITE: WORD = FG_BLUE | FG_GREEN | FG_RED;
-
-/// Query the given handle for information about the console's screen buffer.
-///
-/// The given handle should represent a console. Otherwise, an error is
-/// returned.
-///
-/// This corresponds to calling [`GetConsoleScreenBufferInfo`].
-///
-/// [`GetConsoleScreenBufferInfo`]: https://docs.microsoft.com/en-us/windows/console/getconsolescreenbufferinfo
-pub fn screen_buffer_info<H: AsHandleRef>(
- h: H,
-) -> io::Result<ScreenBufferInfo> {
- unsafe {
- let mut info: CONSOLE_SCREEN_BUFFER_INFO = mem::zeroed();
- let rc = GetConsoleScreenBufferInfo(h.as_raw(), &mut info);
- if rc == 0 {
- return Err(io::Error::last_os_error());
- }
- Ok(ScreenBufferInfo(info))
- }
-}
-
-/// Set the text attributes of the console represented by the given handle.
-///
-/// This corresponds to calling [`SetConsoleTextAttribute`].
-///
-/// [`SetConsoleTextAttribute`]: https://docs.microsoft.com/en-us/windows/console/setconsoletextattribute
-pub fn set_text_attributes<H: AsHandleRef>(
- h: H,
- attributes: u16,
-) -> io::Result<()> {
- if unsafe { SetConsoleTextAttribute(h.as_raw(), attributes) } == 0 {
- Err(io::Error::last_os_error())
- } else {
- Ok(())
- }
-}
-
-/// Query the mode of the console represented by the given handle.
-///
-/// This corresponds to calling [`GetConsoleMode`], which describes the return
-/// value.
-///
-/// [`GetConsoleMode`]: https://docs.microsoft.com/en-us/windows/console/getconsolemode
-pub fn mode<H: AsHandleRef>(h: H) -> io::Result<u32> {
- let mut mode = 0;
- if unsafe { GetConsoleMode(h.as_raw(), &mut mode) } == 0 {
- Err(io::Error::last_os_error())
- } else {
- Ok(mode)
- }
-}
-
-/// Set the mode of the console represented by the given handle.
-///
-/// This corresponds to calling [`SetConsoleMode`], which describes the format
-/// of the mode parameter.
-///
-/// [`SetConsoleMode`]: https://docs.microsoft.com/en-us/windows/console/setconsolemode
-pub fn set_mode<H: AsHandleRef>(h: H, mode: u32) -> io::Result<()> {
- if unsafe { SetConsoleMode(h.as_raw(), mode) } == 0 {
- Err(io::Error::last_os_error())
- } else {
- Ok(())
- }
-}
-
-/// Represents console screen buffer information such as size, cursor position
-/// and styling attributes.
-///
-/// This wraps a [`CONSOLE_SCREEN_BUFFER_INFO`].
-///
-/// [`CONSOLE_SCREEN_BUFFER_INFO`]: https://docs.microsoft.com/en-us/windows/console/console-screen-buffer-info-str
-#[derive(Clone)]
-pub struct ScreenBufferInfo(CONSOLE_SCREEN_BUFFER_INFO);
-
-impl ScreenBufferInfo {
- /// Returns the size of the console screen buffer, in character columns and
- /// rows.
- ///
- /// This corresponds to `dwSize`.
- pub fn size(&self) -> (i16, i16) {
- (self.0.dwSize.X, self.0.dwSize.Y)
- }
-
- /// Returns the position of the cursor in terms of column and row
- /// coordinates of the console screen buffer.
- ///
- /// This corresponds to `dwCursorPosition`.
- pub fn cursor_position(&self) -> (i16, i16) {
- (self.0.dwCursorPosition.X, self.0.dwCursorPosition.Y)
- }
-
- /// Returns the character attributes associated with this console.
- ///
- /// This corresponds to `wAttributes`.
- ///
- /// See [`char info`] for more details.
- ///
- /// [`char info`]: https://docs.microsoft.com/en-us/windows/console/char-info-str
- pub fn attributes(&self) -> u16 {
- self.0.wAttributes
- }
-
- /// Returns the maximum size of the console window, in character columns
- /// and rows, given the current screen buffer size and font and the screen
- /// size.
- pub fn max_window_size(&self) -> (i16, i16) {
- (self.0.dwMaximumWindowSize.X, self.0.dwMaximumWindowSize.Y)
- }
-
- /// Returns the console screen buffer coordinates of the upper-left and
- /// lower-right corners of the display window.
- ///
- /// This corresponds to `srWindow`.
- pub fn window_rect(&self) -> SmallRect {
- SmallRect {
- left: self.0.srWindow.Left,
- top: self.0.srWindow.Top,
- right: self.0.srWindow.Right,
- bottom: self.0.srWindow.Bottom,
- }
- }
-}
-
-/// Defines the coordinates of the upper left and lower right corners of a rectangle.
-///
-/// This corresponds to [`SMALL_RECT`].
-///
-/// [`SMALL_RECT`]: https://docs.microsoft.com/en-us/windows/console/small-rect-str
-pub struct SmallRect {
- pub left: i16,
- pub top: i16,
- pub right: i16,
- pub bottom: i16,
-}
-
-/// A Windows console.
-///
-/// This represents a very limited set of functionality available to a Windows
-/// console. In particular, it can only change text attributes such as color
-/// and intensity. This may grow over time. If you need more routines, please
-/// file an issue and/or PR.
-///
-/// There is no way to "write" to this console. Simply write to
-/// stdout or stderr instead, while interleaving instructions to the console
-/// to change text attributes.
-///
-/// A common pitfall when using a console is to forget to flush writes to
-/// stdout before setting new text attributes.
-///
-/// # Example
-/// ```no_run
-/// # #[cfg(windows)]
-/// # {
-/// use winapi_util::console::{Console, Color, Intense};
-///
-/// let mut con = Console::stdout().unwrap();
-/// con.fg(Intense::Yes, Color::Cyan).unwrap();
-/// println!("This text will be intense cyan.");
-/// con.reset().unwrap();
-/// println!("This text will be normal.");
-/// # }
-/// ```
-#[derive(Debug)]
-pub struct Console {
- kind: HandleKind,
- start_attr: TextAttributes,
- cur_attr: TextAttributes,
-}
-
-#[derive(Clone, Copy, Debug)]
-enum HandleKind {
- Stdout,
- Stderr,
-}
-
-impl HandleKind {
- fn handle(&self) -> HandleRef {
- match *self {
- HandleKind::Stdout => HandleRef::stdout(),
- HandleKind::Stderr => HandleRef::stderr(),
- }
- }
-}
-
-impl Console {
- /// Get a console for a standard I/O stream.
- fn create_for_stream(kind: HandleKind) -> io::Result<Console> {
- let h = kind.handle();
- let info = screen_buffer_info(&h)?;
- let attr = TextAttributes::from_word(info.attributes());
- Ok(Console { kind: kind, start_attr: attr, cur_attr: attr })
- }
-
- /// Create a new Console to stdout.
- ///
- /// If there was a problem creating the console, then an error is returned.
- pub fn stdout() -> io::Result<Console> {
- Self::create_for_stream(HandleKind::Stdout)
- }
-
- /// Create a new Console to stderr.
- ///
- /// If there was a problem creating the console, then an error is returned.
- pub fn stderr() -> io::Result<Console> {
- Self::create_for_stream(HandleKind::Stderr)
- }
-
- /// Applies the current text attributes.
- fn set(&mut self) -> io::Result<()> {
- set_text_attributes(self.kind.handle(), self.cur_attr.to_word())
- }
-
- /// Apply the given intensity and color attributes to the console
- /// foreground.
- ///
- /// If there was a problem setting attributes on the console, then an error
- /// is returned.
- pub fn fg(&mut self, intense: Intense, color: Color) -> io::Result<()> {
- self.cur_attr.fg_color = color;
- self.cur_attr.fg_intense = intense;
- self.set()
- }
-
- /// Apply the given intensity and color attributes to the console
- /// background.
- ///
- /// If there was a problem setting attributes on the console, then an error
- /// is returned.
- pub fn bg(&mut self, intense: Intense, color: Color) -> io::Result<()> {
- self.cur_attr.bg_color = color;
- self.cur_attr.bg_intense = intense;
- self.set()
- }
-
- /// Reset the console text attributes to their original settings.
- ///
- /// The original settings correspond to the text attributes on the console
- /// when this `Console` value was created.
- ///
- /// If there was a problem setting attributes on the console, then an error
- /// is returned.
- pub fn reset(&mut self) -> io::Result<()> {
- self.cur_attr = self.start_attr;
- self.set()
- }
-
- /// Toggle virtual terminal processing.
- ///
- /// This method attempts to toggle virtual terminal processing for this
- /// console. If there was a problem toggling it, then an error returned.
- /// On success, the caller may assume that toggling it was successful.
- ///
- /// When virtual terminal processing is enabled, characters emitted to the
- /// console are parsed for VT100 and similar control character sequences
- /// that control color and other similar operations.
- pub fn set_virtual_terminal_processing(
- &mut self,
- yes: bool,
- ) -> io::Result<()> {
- let vt = wincon::ENABLE_VIRTUAL_TERMINAL_PROCESSING;
-
- let handle = self.kind.handle();
- let old_mode = mode(&handle)?;
- let new_mode = if yes { old_mode | vt } else { old_mode & !vt };
- if old_mode == new_mode {
- return Ok(());
- }
- set_mode(&handle, new_mode)
- }
-}
-
-/// A representation of text attributes for the Windows console.
-#[derive(Copy, Clone, Debug, Eq, PartialEq)]
-struct TextAttributes {
- fg_color: Color,
- fg_intense: Intense,
- bg_color: Color,
- bg_intense: Intense,
-}
-
-impl TextAttributes {
- fn to_word(&self) -> WORD {
- let mut w = 0;
- w |= self.fg_color.to_fg();
- w |= self.fg_intense.to_fg();
- w |= self.bg_color.to_bg();
- w |= self.bg_intense.to_bg();
- w
- }
-
- fn from_word(word: WORD) -> TextAttributes {
- TextAttributes {
- fg_color: Color::from_fg(word),
- fg_intense: Intense::from_fg(word),
- bg_color: Color::from_bg(word),
- bg_intense: Intense::from_bg(word),
- }
- }
-}
-
-/// Whether to use intense colors or not.
-#[allow(missing_docs)]
-#[derive(Clone, Copy, Debug, Eq, PartialEq)]
-pub enum Intense {
- Yes,
- No,
-}
-
-impl Intense {
- fn to_bg(&self) -> WORD {
- self.to_fg() << 4
- }
-
- fn from_bg(word: WORD) -> Intense {
- Intense::from_fg(word >> 4)
- }
-
- fn to_fg(&self) -> WORD {
- match *self {
- Intense::No => 0,
- Intense::Yes => FG_INTENSITY,
- }
- }
-
- fn from_fg(word: WORD) -> Intense {
- if word & FG_INTENSITY > 0 {
- Intense::Yes
- } else {
- Intense::No
- }
- }
-}
-
-/// The set of available colors for use with a Windows console.
-#[allow(missing_docs)]
-#[derive(Clone, Copy, Debug, Eq, PartialEq)]
-pub enum Color {
- Black,
- Blue,
- Green,
- Red,
- Cyan,
- Magenta,
- Yellow,
- White,
-}
-
-impl Color {
- fn to_bg(&self) -> WORD {
- self.to_fg() << 4
- }
-
- fn from_bg(word: WORD) -> Color {
- Color::from_fg(word >> 4)
- }
-
- fn to_fg(&self) -> WORD {
- match *self {
- Color::Black => 0,
- Color::Blue => FG_BLUE,
- Color::Green => FG_GREEN,
- Color::Red => FG_RED,
- Color::Cyan => FG_CYAN,
- Color::Magenta => FG_MAGENTA,
- Color::Yellow => FG_YELLOW,
- Color::White => FG_WHITE,
- }
- }
-
- fn from_fg(word: WORD) -> Color {
- match word & 0b111 {
- FG_BLUE => Color::Blue,
- FG_GREEN => Color::Green,
- FG_RED => Color::Red,
- FG_CYAN => Color::Cyan,
- FG_MAGENTA => Color::Magenta,
- FG_YELLOW => Color::Yellow,
- FG_WHITE => Color::White,
- _ => Color::Black,
- }
- }
-}
diff --git a/vendor/winapi-util/src/file.rs b/vendor/winapi-util/src/file.rs
deleted file mode 100644
index 56a1e4105..000000000
--- a/vendor/winapi-util/src/file.rs
+++ /dev/null
@@ -1,168 +0,0 @@
-use std::io;
-use std::mem;
-
-use winapi::shared::minwindef::FILETIME;
-use winapi::shared::winerror::NO_ERROR;
-use winapi::um::errhandlingapi::GetLastError;
-use winapi::um::fileapi::{
- GetFileInformationByHandle, GetFileType, BY_HANDLE_FILE_INFORMATION,
-};
-use winapi::um::winnt;
-
-use crate::AsHandleRef;
-
-/// Return various pieces of information about a file.
-///
-/// This includes information such as a file's size, unique identifier and
-/// time related fields.
-///
-/// This corresponds to calling [`GetFileInformationByHandle`].
-///
-/// [`GetFileInformationByHandle`]: https://docs.microsoft.com/en-us/windows/desktop/api/fileapi/nf-fileapi-getfileinformationbyhandle
-pub fn information<H: AsHandleRef>(h: H) -> io::Result<Information> {
- unsafe {
- let mut info: BY_HANDLE_FILE_INFORMATION = mem::zeroed();
- let rc = GetFileInformationByHandle(h.as_raw(), &mut info);
- if rc == 0 {
- return Err(io::Error::last_os_error());
- };
- Ok(Information(info))
- }
-}
-
-/// Returns the file type of the given handle.
-///
-/// If there was a problem querying the file type, then an error is returned.
-///
-/// This corresponds to calling [`GetFileType`].
-///
-/// [`GetFileType`]: https://docs.microsoft.com/en-us/windows/desktop/api/fileapi/nf-fileapi-getfiletype
-pub fn typ<H: AsHandleRef>(h: H) -> io::Result<Type> {
- unsafe {
- let rc = GetFileType(h.as_raw());
- if rc == 0 && GetLastError() != NO_ERROR {
- return Err(io::Error::last_os_error());
- }
- Ok(Type(rc))
- }
-}
-
-/// Returns true if and only if the given file attributes contain the
-/// `FILE_ATTRIBUTE_HIDDEN` attribute.
-pub fn is_hidden(file_attributes: u64) -> bool {
- file_attributes & (winnt::FILE_ATTRIBUTE_HIDDEN as u64) > 0
-}
-
-/// Represents file information such as creation time, file size, etc.
-///
-/// This wraps a [`BY_HANDLE_FILE_INFORMATION`].
-///
-/// [`BY_HANDLE_FILE_INFORMATION`]: https://docs.microsoft.com/en-us/windows/desktop/api/fileapi/ns-fileapi-_by_handle_file_information
-#[derive(Clone)]
-pub struct Information(BY_HANDLE_FILE_INFORMATION);
-
-impl Information {
- /// Returns file attributes.
- ///
- /// This corresponds to `dwFileAttributes`.
- pub fn file_attributes(&self) -> u64 {
- self.0.dwFileAttributes as u64
- }
-
- /// Returns true if and only if this file information has the
- /// `FILE_ATTRIBUTE_HIDDEN` attribute.
- pub fn is_hidden(&self) -> bool {
- is_hidden(self.file_attributes())
- }
-
- /// Return the creation time, if one exists.
- ///
- /// This corresponds to `ftCreationTime`.
- pub fn creation_time(&self) -> Option<u64> {
- filetime_to_u64(self.0.ftCreationTime)
- }
-
- /// Return the last access time, if one exists.
- ///
- /// This corresponds to `ftLastAccessTime`.
- pub fn last_access_time(&self) -> Option<u64> {
- filetime_to_u64(self.0.ftLastAccessTime)
- }
-
- /// Return the last write time, if one exists.
- ///
- /// This corresponds to `ftLastWriteTime`.
- pub fn last_write_time(&self) -> Option<u64> {
- filetime_to_u64(self.0.ftLastWriteTime)
- }
-
- /// Return the serial number of the volume that the file is on.
- ///
- /// This corresponds to `dwVolumeSerialNumber`.
- pub fn volume_serial_number(&self) -> u64 {
- self.0.dwVolumeSerialNumber as u64
- }
-
- /// Return the file size, in bytes.
- ///
- /// This corresponds to `nFileSizeHigh` and `nFileSizeLow`.
- pub fn file_size(&self) -> u64 {
- ((self.0.nFileSizeHigh as u64) << 32) | (self.0.nFileSizeLow as u64)
- }
-
- /// Return the number of links to this file.
- ///
- /// This corresponds to `nNumberOfLinks`.
- pub fn number_of_links(&self) -> u64 {
- self.0.nNumberOfLinks as u64
- }
-
- /// Return the index of this file. The index of a file is a purpotedly
- /// unique identifier for a file within a particular volume.
- pub fn file_index(&self) -> u64 {
- ((self.0.nFileIndexHigh as u64) << 32) | (self.0.nFileIndexLow as u64)
- }
-}
-
-/// Represents a Windows file type.
-///
-/// This wraps the result of [`GetFileType`].
-///
-/// [`GetFileType`]: https://docs.microsoft.com/en-us/windows/desktop/api/fileapi/nf-fileapi-getfiletype
-#[derive(Clone)]
-pub struct Type(u32);
-
-impl Type {
- /// Returns true if this type represents a character file, which is
- /// typically an LPT device or a console.
- pub fn is_char(&self) -> bool {
- self.0 == ::winapi::um::winbase::FILE_TYPE_CHAR
- }
-
- /// Returns true if this type represents a disk file.
- pub fn is_disk(&self) -> bool {
- self.0 == ::winapi::um::winbase::FILE_TYPE_DISK
- }
-
- /// Returns true if this type represents a sock, named pipe or an
- /// anonymous pipe.
- pub fn is_pipe(&self) -> bool {
- self.0 == ::winapi::um::winbase::FILE_TYPE_PIPE
- }
-
- /// Returns true if this type is not known.
- ///
- /// Note that this never corresponds to a failure.
- pub fn is_unknown(&self) -> bool {
- self.0 == ::winapi::um::winbase::FILE_TYPE_UNKNOWN
- }
-}
-
-fn filetime_to_u64(t: FILETIME) -> Option<u64> {
- let v = ((t.dwHighDateTime as u64) << 32) | (t.dwLowDateTime as u64);
- if v == 0 {
- None
- } else {
- Some(v)
- }
-}
diff --git a/vendor/winapi-util/src/lib.rs b/vendor/winapi-util/src/lib.rs
deleted file mode 100644
index 0bb259dba..000000000
--- a/vendor/winapi-util/src/lib.rs
+++ /dev/null
@@ -1,32 +0,0 @@
-/*!
-This crate provides a smattering of safe routines for parts of winapi. The
-primary purpose of this crate is to serve as a dumping ground for various
-utility functions that make interactions with winapi safe. This permits the
-centralization of `unsafe` when dealing with Windows APIs, and thus makes it
-easier to audit.
-
-A key abstraction in this crate is the combination of the
-[`Handle`](struct.Handle.html)
-and
-[`HandleRef`](struct.HandleRef.html)
-types. Both represent a valid Windows handle to an I/O-like object, where
-`Handle` is owned (the resource is closed when the handle is dropped) and
-`HandleRef` is borrowed (the resource is not closed when the handle is
-dropped). Many of the routines in this crate work on handles and accept
-anything that can be safely converted into a `HandleRef`. This includes
-standard library types such as `File`, `Stdin`, `Stdout` and `Stderr`.
-
-Note that this crate is completely empty on non-Windows platforms.
-*/
-
-#[cfg(windows)]
-pub use win::*;
-
-/// Safe routines for dealing with the Windows console.
-#[cfg(windows)]
-pub mod console;
-/// Safe routines for dealing with files and handles on Windows.
-#[cfg(windows)]
-pub mod file;
-#[cfg(windows)]
-mod win;
diff --git a/vendor/winapi-util/src/win.rs b/vendor/winapi-util/src/win.rs
deleted file mode 100644
index 9c77c0da6..000000000
--- a/vendor/winapi-util/src/win.rs
+++ /dev/null
@@ -1,246 +0,0 @@
-use std::fs::File;
-use std::io;
-use std::os::windows::io::{
- AsRawHandle, FromRawHandle, IntoRawHandle, RawHandle,
-};
-use std::path::Path;
-use std::process;
-
-/// A handle represents an owned and valid Windows handle to a file-like
-/// object.
-///
-/// When an owned handle is dropped, then the underlying raw handle is closed.
-/// To get a borrowed handle, use `HandleRef`.
-#[derive(Debug)]
-pub struct Handle(File);
-
-impl AsRawHandle for Handle {
- fn as_raw_handle(&self) -> RawHandle {
- self.0.as_raw_handle()
- }
-}
-
-impl FromRawHandle for Handle {
- unsafe fn from_raw_handle(handle: RawHandle) -> Handle {
- Handle(File::from_raw_handle(handle))
- }
-}
-
-impl IntoRawHandle for Handle {
- fn into_raw_handle(self) -> RawHandle {
- self.0.into_raw_handle()
- }
-}
-
-impl Handle {
- /// Create an owned handle to the given file.
- ///
- /// When the returned handle is dropped, the file is closed.
- ///
- /// Note that if the given file represents a handle to a directory, then
- /// it is generally required that it have been opened with the
- /// [`FILE_FLAG_BACKUP_SEMANTICS`] flag in order to use it in various
- /// calls such as `information` or `typ`. To have this done automatically
- /// for you, use the `from_path_any` constructor.
- ///
- /// [`FILE_FLAG_BACKUP_SEMANTICS`]: https://docs.microsoft.com/en-us/windows/desktop/api/FileAPI/nf-fileapi-createfilea
- pub fn from_file(file: File) -> Handle {
- Handle(file)
- }
-
- /// Open a file to the given file path, and return an owned handle to that
- /// file.
- ///
- /// When the returned handle is dropped, the file is closed.
- ///
- /// If there was a problem opening the file, then the corresponding error
- /// is returned.
- pub fn from_path<P: AsRef<Path>>(path: P) -> io::Result<Handle> {
- Ok(Handle::from_file(File::open(path)?))
- }
-
- /// Like `from_path`, but supports opening directory handles as well.
- ///
- /// If you use `from_path` on a directory, then subsequent queries using
- /// that handle will fail.
- pub fn from_path_any<P: AsRef<Path>>(path: P) -> io::Result<Handle> {
- use std::fs::OpenOptions;
- use std::os::windows::fs::OpenOptionsExt;
- use winapi::um::winbase::FILE_FLAG_BACKUP_SEMANTICS;
-
- let file = OpenOptions::new()
- .read(true)
- .custom_flags(FILE_FLAG_BACKUP_SEMANTICS)
- .open(path)?;
- Ok(Handle::from_file(file))
- }
-
- /// Return this handle as a standard `File` reference.
- pub fn as_file(&self) -> &File {
- &self.0
- }
-
- /// Return this handle as a standard `File` mutable reference.
- pub fn as_file_mut(&mut self) -> &mut File {
- &mut self.0
- }
-}
-
-/// Represents a borrowed and valid Windows handle to a file-like object, such
-/// as stdin/stdout/stderr or an actual file.
-///
-/// When a borrowed handle is dropped, then the underlying raw handle is
-/// **not** closed. To get an owned handle, use `Handle`.
-#[derive(Debug)]
-pub struct HandleRef(HandleRefInner);
-
-/// The representation of a HandleRef, on which we define a custom Drop impl
-/// that avoids closing the underlying raw handle.
-#[derive(Debug)]
-struct HandleRefInner(Option<File>);
-
-impl Drop for HandleRefInner {
- fn drop(&mut self) {
- self.0.take().unwrap().into_raw_handle();
- }
-}
-
-impl AsRawHandle for HandleRef {
- fn as_raw_handle(&self) -> RawHandle {
- self.as_file().as_raw_handle()
- }
-}
-
-impl Clone for HandleRef {
- fn clone(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl HandleRef {
- /// Create a borrowed handle to stdin.
- ///
- /// When the returned handle is dropped, stdin is not closed.
- pub fn stdin() -> HandleRef {
- unsafe { HandleRef::from_raw_handle(io::stdin().as_raw_handle()) }
- }
-
- /// Create a handle to stdout.
- ///
- /// When the returned handle is dropped, stdout is not closed.
- pub fn stdout() -> HandleRef {
- unsafe { HandleRef::from_raw_handle(io::stdout().as_raw_handle()) }
- }
-
- /// Create a handle to stderr.
- ///
- /// When the returned handle is dropped, stderr is not closed.
- pub fn stderr() -> HandleRef {
- unsafe { HandleRef::from_raw_handle(io::stderr().as_raw_handle()) }
- }
-
- /// Create a borrowed handle to the given file.
- ///
- /// When the returned handle is dropped, the file is not closed.
- pub fn from_file(file: &File) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(file.as_raw_handle()) }
- }
-
- /// Create a borrowed handle from the given raw handle.
- ///
- /// Note that unlike the `FromRawHandle` trait, this constructor does
- /// **not** consume ownership of the given handle. That is, when the
- /// borrowed handle created by this constructor is dropped, the underlying
- /// handle will not be closed.
- ///
- /// # Safety
- ///
- /// This is unsafe because there is no guarantee that the given raw handle
- /// is a valid handle. The caller must ensure this is true before invoking
- /// this constructor.
- pub unsafe fn from_raw_handle(handle: RawHandle) -> HandleRef {
- HandleRef(HandleRefInner(Some(File::from_raw_handle(handle))))
- }
-
- /// Return this handle as a standard `File` reference.
- pub fn as_file(&self) -> &File {
- (self.0).0.as_ref().unwrap()
- }
-
- /// Return this handle as a standard `File` mutable reference.
- pub fn as_file_mut(&mut self) -> &mut File {
- (self.0).0.as_mut().unwrap()
- }
-}
-
-/// Construct borrowed and valid Windows handles from file-like objects.
-pub trait AsHandleRef {
- /// A borrowed handle that wraps the raw handle of the `Self` object.
- fn as_handle_ref(&self) -> HandleRef;
-
- /// A convenience routine for extracting a `HandleRef` from `Self`, and
- /// then extracting a raw handle from the `HandleRef`.
- fn as_raw(&self) -> RawHandle {
- self.as_handle_ref().as_raw_handle()
- }
-}
-
-impl<'a, T: AsHandleRef> AsHandleRef for &'a T {
- fn as_handle_ref(&self) -> HandleRef {
- (**self).as_handle_ref()
- }
-}
-
-impl AsHandleRef for Handle {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for HandleRef {
- fn as_handle_ref(&self) -> HandleRef {
- self.clone()
- }
-}
-
-impl AsHandleRef for File {
- fn as_handle_ref(&self) -> HandleRef {
- HandleRef::from_file(self)
- }
-}
-
-impl AsHandleRef for io::Stdin {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for io::Stdout {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for io::Stderr {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for process::ChildStdin {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for process::ChildStdout {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}
-
-impl AsHandleRef for process::ChildStderr {
- fn as_handle_ref(&self) -> HandleRef {
- unsafe { HandleRef::from_raw_handle(self.as_raw_handle()) }
- }
-}