diff --git a/src/lib.rs b/src/lib.rs
new file mode 100644
index 0000000..ed7ccf5
--- /dev/null
+++ b/src/lib.rs
@@ -0,0 +1,572 @@
+/*!
+This crate provides a safe and simple **cross platform** way to determine
+whether two file paths refer to the same file or directory.
+
+Most uses of this crate should be limited to the top-level [`is_same_file`]
+function, which takes two file paths and returns true if they refer to the
+same file or directory:
+
+```rust,no_run
+# use std::error::Error;
+use same_file::is_same_file;
+
+# fn try_main() -> Result<(), Box<Error>> {
+assert!(is_same_file("/bin/sh", "/usr/bin/sh")?);
+#    Ok(())
+# }
+#
+# fn main() {
+#    try_main().unwrap();
+# }
+```
+
+Additionally, this crate provides a [`Handle`] type that permits a more efficient
+equality check depending on your access pattern. For example, if one wanted to
+check whether any path in a list of paths corresponded to the process' stdout
+handle, then one could build a handle once for stdout. The equality check for
+each file in the list then only requires one stat call instead of two. The code
+might look like this:
+
+```rust,no_run
+# use std::error::Error;
+use same_file::Handle;
+
+# fn try_main() -> Result<(), Box<Error>> {
+let candidates = &[
+    "examples/is_same_file.rs",
+    "examples/is_stderr.rs",
+    "examples/stderr",
+];
+let stdout_handle = Handle::stdout()?;
+for candidate in candidates {
+    let handle = Handle::from_path(candidate)?;
+    if stdout_handle == handle {
+        println!("{:?} is stdout!", candidate);
+    } else {
+        println!("{:?} is NOT stdout!", candidate);
+    }
+}
+#    Ok(())
+# }
+#
+# fn main() {
+#     try_main().unwrap();
+# }
+```
+
+See [`examples/is_stderr.rs`] for a runnable example and compare the output of:
+
+- `cargo run --example is_stderr 2> examples/stderr` and
+- `cargo run --example is_stderr`.
+
+[`is_same_file`]: fn.is_same_file.html
+[`Handle`]: struct.Handle.html
+[`examples/is_stderr.rs`]: https://github.com/BurntSushi/same-file/blob/master/examples/is_same_file.rs
+
+*/
+
+#![allow(bare_trait_objects, unknown_lints)]
+#![deny(missing_docs)]
+
+#[cfg(test)]
+doc_comment::doctest!("../README.md");
+
+use std::fs::File;
+use std::io;
+use std::path::Path;
+
+#[cfg(any(target_os = "redox", unix))]
+use crate::unix as imp;
+#[cfg(not(any(target_os = "redox", unix, windows)))]
+use unknown as imp;
+#[cfg(windows)]
+use win as imp;
+
+#[cfg(any(target_os = "redox", unix))]
+mod unix;
+#[cfg(not(any(target_os = "redox", unix, windows)))]
+mod unknown;
+#[cfg(windows)]
+mod win;
+
+/// A handle to a file that can be tested for equality with other handles.
+///
+/// If two files are the same, then any two handles of those files will compare
+/// equal. If two files are not the same, then any two handles of those files
+/// will compare not-equal.
+///
+/// A handle consumes an open file resource as long as it exists.
+///
+/// Equality is determined by comparing inode numbers on Unix and a combination
+/// of identifier, volume serial, and file size on Windows. Note that it's
+/// possible for comparing two handles to produce a false positive on some
+/// platforms. Namely, two handles can compare equal even if the two handles
+/// *don't* point to the same file. Check the [source] for specific
+/// implementation details.
+///
+/// [source]: https://github.com/BurntSushi/same-file/tree/master/src
+#[derive(Debug, Eq, PartialEq, Hash)]
+pub struct Handle(imp::Handle);
+
+impl Handle {
+    /// Construct a handle from a path.
+    ///
+    /// Note that the underlying [`File`] is opened in read-only mode on all
+    /// platforms.
+    ///
+    /// [`File`]: https://doc.rust-lang.org/std/fs/struct.File.html
+    ///
+    /// # Errors
+    /// This method will return an [`io::Error`] if the path cannot
+    /// be opened, or the file's metadata cannot be obtained.
+    /// The most common reasons for this are: the path does not
+    /// exist, or there were not enough permissions.
+    ///
+    /// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+    ///
+    /// # Examples
+    /// Check that two paths are not the same file:
+    ///
+    /// ```rust,no_run
+    /// # use std::error::Error;
+    /// use same_file::Handle;
+    ///
+    /// # fn try_main() -> Result<(), Box<Error>> {
+    /// let source = Handle::from_path("./source")?;
+    /// let target = Handle::from_path("./target")?;
+    /// assert_ne!(source, target, "The files are the same.");
+    /// # Ok(())
+    /// # }
+    /// #
+    /// # fn main() {
+    /// #     try_main().unwrap();
+    /// # }
+    /// ```
+    pub fn from_path<P: AsRef<Path>>(p: P) -> io::Result<Handle> {
+        imp::Handle::from_path(p).map(Handle)
+    }
+
+    /// Construct a handle from a file.
+    ///
+    /// # Errors
+    /// This method will return an [`io::Error`] if the metadata for
+    /// the given [`File`] cannot be obtained.
+    ///
+    /// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+    /// [`File`]: https://doc.rust-lang.org/std/fs/struct.File.html
+    ///
+    /// # Examples
+    /// Check that two files are not in fact the same file:
+    ///
+    /// ```rust,no_run
+    /// # use std::error::Error;
+    /// # use std::fs::File;
+    /// use same_file::Handle;
+    ///
+    /// # fn try_main() -> Result<(), Box<Error>> {
+    /// let source = File::open("./source")?;
+    /// let target = File::open("./target")?;
+    ///
+    /// assert_ne!(
+    ///     Handle::from_file(source)?,
+    ///     Handle::from_file(target)?,
+    ///     "The files are the same."
+    /// );
+    /// #     Ok(())
+    /// # }
+    /// #
+    /// # fn main() {
+    /// #     try_main().unwrap();
+    /// # }
+    /// ```
+    pub fn from_file(file: File) -> io::Result<Handle> {
+        imp::Handle::from_file(file).map(Handle)
+    }
+
+    /// Construct a handle from stdin.
+    ///
+    /// # Errors
+    /// This method will return an [`io::Error`] if stdin cannot
+    /// be opened due to any I/O-related reason.
+    ///
+    /// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+    ///
+    /// # Examples
+    ///
+    /// ```rust
+    /// # use std::error::Error;
+    /// use same_file::Handle;
+    ///
+    /// # fn try_main() -> Result<(), Box<Error>> {
+    /// let stdin = Handle::stdin()?;
+    /// let stdout = Handle::stdout()?;
+    /// let stderr = Handle::stderr()?;
+    ///
+    /// if stdin == stdout {
+    ///     println!("stdin == stdout");
+    /// }
+    /// if stdin == stderr {
+    ///     println!("stdin == stderr");
+    /// }
+    /// if stdout == stderr {
+    ///     println!("stdout == stderr");
+    /// }
+    /// #
+    /// #     Ok(())
+    /// # }
+    /// #
+    /// # fn main() {
+    /// #     try_main().unwrap();
+    /// # }
+    /// ```
+    ///
+    /// The output differs depending on the platform.
+    ///
+    /// On Linux:
+    ///
+    /// ```text
+    /// $ ./example
+    /// stdin == stdout
+    /// stdin == stderr
+    /// stdout == stderr
+    /// $ ./example > result
+    /// $ cat result
+    /// stdin == stderr
+    /// $ ./example > result 2>&1
+    /// $ cat result
+    /// stdout == stderr
+    /// ```
+    ///
+    /// Windows:
+    ///
+    /// ```text
+    /// > example
+    /// > example > result 2>&1
+    /// > type result
+    /// stdout == stderr
+    /// ```
+    pub fn stdin() -> io::Result<Handle> {
+        imp::Handle::stdin().map(Handle)
+    }
+
+    /// Construct a handle from stdout.
+    ///
+    /// # Errors
+    /// This method will return an [`io::Error`] if stdout cannot
+    /// be opened due to any I/O-related reason.
+    ///
+    /// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+    ///
+    /// # Examples
+    /// See the example for [`stdin()`].
+    ///
+    /// [`stdin()`]: #method.stdin
+    pub fn stdout() -> io::Result<Handle> {
+        imp::Handle::stdout().map(Handle)
+    }
+
+    /// Construct a handle from stderr.
+    ///
+    /// # Errors
+    /// This method will return an [`io::Error`] if stderr cannot
+    /// be opened due to any I/O-related reason.
+    ///
+    /// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+    ///
+    /// # Examples
+    /// See the example for [`stdin()`].
+    ///
+    /// [`stdin()`]: #method.stdin
+    pub fn stderr() -> io::Result<Handle> {
+        imp::Handle::stderr().map(Handle)
+    }
+
+    /// Return a reference to the underlying file.
+    ///
+    /// # Examples
+    /// Ensure that the target file is not the same as the source one,
+    /// and copy the data to it:
+    ///
+    /// ```rust,no_run
+    /// # use std::error::Error;
+    /// use std::io::prelude::*;
+    /// use std::io::Write;
+    /// use std::fs::File;
+    /// use same_file::Handle;
+    ///
+    /// # fn try_main() -> Result<(), Box<Error>> {
+    /// let source = File::open("source")?;
+    /// let target = File::create("target")?;
+    ///
+    /// let source_handle = Handle::from_file(source)?;
+    /// let mut target_handle = Handle::from_file(target)?;
+    /// assert_ne!(source_handle, target_handle, "The files are the same.");
+    ///
+    /// let mut source = source_handle.as_file();
+    /// let target = target_handle.as_file_mut();
+    ///
+    /// let mut buffer = Vec::new();
+    /// // data copy is simplified for the purposes of the example
+    /// source.read_to_end(&mut buffer)?;
+    /// target.write_all(&buffer)?;
+    /// #
+    /// #    Ok(())
+    /// # }
+    /// #
+    /// # fn main() {
+    /// #    try_main().unwrap();
+    /// # }
+    /// ```
+    pub fn as_file(&self) -> &File {
+        self.0.as_file()
+    }
+
+    /// Return a mutable reference to the underlying file.
+    ///
+    /// # Examples
+    /// See the example for [`as_file()`].
+    ///
+    /// [`as_file()`]: #method.as_file
+    pub fn as_file_mut(&mut self) -> &mut File {
+        self.0.as_file_mut()
+    }
+
+    /// Return the underlying device number of this handle.
+    ///
+    /// Note that this only works on unix platforms.
+    #[cfg(any(target_os = "redox", unix))]
+    pub fn dev(&self) -> u64 {
+        self.0.dev()
+    }
+
+    /// Return the underlying inode number of this handle.
+    ///
+    /// Note that this only works on unix platforms.
+    #[cfg(any(target_os = "redox", unix))]
+    pub fn ino(&self) -> u64 {
+        self.0.ino()
+    }
+}
+
+/// Returns true if the two file paths may correspond to the same file.
+///
+/// Note that it's possible for this to produce a false positive on some
+/// platforms. Namely, this can return true even if the two file paths *don't*
+/// resolve to the same file.
+/// # Errors
+/// This function will return an [`io::Error`] if any of the two paths cannot
+/// be opened. The most common reasons for this are: the path does not exist,
+/// or there were not enough permissions.
+///
+/// [`io::Error`]: https://doc.rust-lang.org/std/io/struct.Error.html
+///
+/// # Example
+///
+/// ```rust,no_run
+/// use same_file::is_same_file;
+///
+/// assert!(is_same_file("./foo", "././foo").unwrap_or(false));
+/// ```
+pub fn is_same_file<P, Q>(path1: P, path2: Q) -> io::Result<bool>
+where
+    P: AsRef<Path>,
+    Q: AsRef<Path>,
+{
+    Ok(Handle::from_path(path1)? == Handle::from_path(path2)?)
+}
+
+#[cfg(test)]
+mod tests {
+    use std::env;
+    use std::error;
+    use std::fs::{self, File};
+    use std::io;
+    use std::path::{Path, PathBuf};
+    use std::result;
+
+    use super::is_same_file;
+
+    type Result<T> = result::Result<T, Box<error::Error + Send + Sync>>;
+
+    /// Create an error from a format!-like syntax.
+    macro_rules! err {
+        ($($tt:tt)*) => {
+            Box::<error::Error + Send + Sync>::from(format!($($tt)*))
+        }
+    }
+
+    /// A simple wrapper for creating a temporary directory that is
+    /// automatically deleted when it's dropped.
+    ///
+    /// We use this in lieu of tempfile because tempfile brings in too many
+    /// dependencies.
+    #[derive(Debug)]
+    struct TempDir(PathBuf);
+
+    impl Drop for TempDir {
+        fn drop(&mut self) {
+            fs::remove_dir_all(&self.0).unwrap();
+        }
+    }
+
+    impl TempDir {
+        /// Create a new empty temporary directory under the system's
+        /// configured temporary directory.
+        fn new() -> Result<TempDir> {
+            #![allow(deprecated)]
+
+            use std::sync::atomic::{
+                AtomicUsize, Ordering, ATOMIC_USIZE_INIT,
+            };
+
+            static TRIES: usize = 100;
+            static COUNTER: AtomicUsize = ATOMIC_USIZE_INIT;
+
+            let tmpdir = env::temp_dir();
+            for _ in 0..TRIES {
+                let count = COUNTER.fetch_add(1, Ordering::SeqCst);
+                let path = tmpdir.join("rust-walkdir").join(count.to_string());
+                if path.is_dir() {
+                    continue;
+                }
+                fs::create_dir_all(&path).map_err(|e| {
+                    err!("failed to create {}: {}", path.display(), e)
+                })?;
+                return Ok(TempDir(path));
+            }
+            Err(err!("failed to create temp dir after {} tries", TRIES))
+        }
+
+        /// Return the underlying path to this temporary directory.
+        fn path(&self) -> &Path {
+            &self.0
+        }
+    }
+
+    fn tmpdir() -> TempDir {
+        TempDir::new().unwrap()
+    }
+
+    #[cfg(unix)]
+    pub fn soft_link_dir<P: AsRef<Path>, Q: AsRef<Path>>(
+        src: P,
+        dst: Q,
+    ) -> io::Result<()> {
+        use std::os::unix::fs::symlink;
+        symlink(src, dst)
+    }
+
+    #[cfg(unix)]
+    pub fn soft_link_file<P: AsRef<Path>, Q: AsRef<Path>>(
+        src: P,
+        dst: Q,
+    ) -> io::Result<()> {
+        soft_link_dir(src, dst)
+    }
+
+    #[cfg(windows)]
+    pub fn soft_link_dir<P: AsRef<Path>, Q: AsRef<Path>>(
+        src: P,
+        dst: Q,
+    ) -> io::Result<()> {
+        use std::os::windows::fs::symlink_dir;
+        symlink_dir(src, dst)
+    }
+
+    #[cfg(windows)]
+    pub fn soft_link_file<P: AsRef<Path>, Q: AsRef<Path>>(
+        src: P,
+        dst: Q,
+    ) -> io::Result<()> {
+        use std::os::windows::fs::symlink_file;
+        symlink_file(src, dst)
+    }
+
+    // These tests are rather uninteresting. The really interesting tests
+    // would stress the edge cases. On Unix, this might be comparing two files
+    // on different mount points with the same inode number. On Windows, this
+    // might be comparing two files whose file indices are the same on file
+    // systems where such things aren't guaranteed to be unique.
+    //
+    // Alas, I don't know how to create those environmental conditions. ---AG
+
+    #[test]
+    fn same_file_trivial() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        File::create(dir.join("a")).unwrap();
+        assert!(is_same_file(dir.join("a"), dir.join("a")).unwrap());
+    }
+
+    #[test]
+    fn same_dir_trivial() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        fs::create_dir(dir.join("a")).unwrap();
+        assert!(is_same_file(dir.join("a"), dir.join("a")).unwrap());
+    }
+
+    #[test]
+    fn not_same_file_trivial() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        File::create(dir.join("a")).unwrap();
+        File::create(dir.join("b")).unwrap();
+        assert!(!is_same_file(dir.join("a"), dir.join("b")).unwrap());
+    }
+
+    #[test]
+    fn not_same_dir_trivial() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        fs::create_dir(dir.join("a")).unwrap();
+        fs::create_dir(dir.join("b")).unwrap();
+        assert!(!is_same_file(dir.join("a"), dir.join("b")).unwrap());
+    }
+
+    #[test]
+    fn same_file_hard() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        File::create(dir.join("a")).unwrap();
+        fs::hard_link(dir.join("a"), dir.join("alink")).unwrap();
+        assert!(is_same_file(dir.join("a"), dir.join("alink")).unwrap());
+    }
+
+    #[test]
+    fn same_file_soft() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        File::create(dir.join("a")).unwrap();
+        soft_link_file(dir.join("a"), dir.join("alink")).unwrap();
+        assert!(is_same_file(dir.join("a"), dir.join("alink")).unwrap());
+    }
+
+    #[test]
+    fn same_dir_soft() {
+        let tdir = tmpdir();
+        let dir = tdir.path();
+
+        fs::create_dir(dir.join("a")).unwrap();
+        soft_link_dir(dir.join("a"), dir.join("alink")).unwrap();
+        assert!(is_same_file(dir.join("a"), dir.join("alink")).unwrap());
+    }
+
+    #[test]
+    fn test_send() {
+        fn assert_send<T: Send>() {}
+        assert_send::<super::Handle>();
+    }
+
+    #[test]
+    fn test_sync() {
+        fn assert_sync<T: Sync>() {}
+        assert_sync::<super::Handle>();
+    }
+}
diff --git a/src/unix.rs b/src/unix.rs
new file mode 100644
index 0000000..fb3d19f
--- /dev/null
+++ b/src/unix.rs
@@ -0,0 +1,112 @@
+use std::fs::{File, OpenOptions};
+use std::hash::{Hash, Hasher};
+use std::io;
+use std::os::unix::fs::MetadataExt;
+use std::os::unix::io::{AsRawFd, FromRawFd, IntoRawFd, RawFd};
+use std::path::Path;
+
+#[derive(Debug)]
+pub struct Handle {
+    file: Option<File>,
+    // If is_std is true, then we don't drop the corresponding File since it
+    // will close the handle.
+    is_std: bool,
+    dev: u64,
+    ino: u64,
+}
+
+impl Drop for Handle {
+    fn drop(&mut self) {
+        if self.is_std {
+            // unwrap() will not panic. Since we were able to open an
+            // std stream successfully, then `file` is guaranteed to be Some()
+            self.file.take().unwrap().into_raw_fd();
+        }
+    }
+}
+
+impl Eq for Handle {}
+
+impl PartialEq for Handle {
+    fn eq(&self, other: &Handle) -> bool {
+        (self.dev, self.ino) == (other.dev, other.ino)
+    }
+}
+
+impl AsRawFd for crate::Handle {
+    fn as_raw_fd(&self) -> RawFd {
+        // unwrap() will not panic. Since we were able to open the
+        // file successfully, then `file` is guaranteed to be Some()
+        self.0.file.as_ref().take().unwrap().as_raw_fd()
+    }
+}
+
+impl IntoRawFd for crate::Handle {
+    fn into_raw_fd(mut self) -> RawFd {
+        // unwrap() will not panic. Since we were able to open the
+        // file successfully, then `file` is guaranteed to be Some()
+        self.0.file.take().unwrap().into_raw_fd()
+    }
+}
+
+impl Hash for Handle {
+    fn hash<H: Hasher>(&self, state: &mut H) {
+        self.dev.hash(state);
+        self.ino.hash(state);
+    }
+}
+
+impl Handle {
+    pub fn from_path<P: AsRef<Path>>(p: P) -> io::Result<Handle> {
+        Handle::from_file(OpenOptions::new().read(true).open(p)?)
+    }
+
+    pub fn from_file(file: File) -> io::Result<Handle> {
+        let md = file.metadata()?;
+        Ok(Handle {
+            file: Some(file),
+            is_std: false,
+            dev: md.dev(),
+            ino: md.ino(),
+        })
+    }
+
+    pub fn from_std(file: File) -> io::Result<Handle> {
+        Handle::from_file(file).map(|mut h| {
+            h.is_std = true;
+            h
+        })
+    }
+
+    pub fn stdin() -> io::Result<Handle> {
+        Handle::from_std(unsafe { File::from_raw_fd(0) })
+    }
+
+    pub fn stdout() -> io::Result<Handle> {
+        Handle::from_std(unsafe { File::from_raw_fd(1) })
+    }
+
+    pub fn stderr() -> io::Result<Handle> {
+        Handle::from_std(unsafe { File::from_raw_fd(2) })
+    }
+
+    pub fn as_file(&self) -> &File {
+        // unwrap() will not panic. Since we were able to open the
+        // file successfully, then `file` is guaranteed to be Some()
+        self.file.as_ref().take().unwrap()
+    }
+
+    pub fn as_file_mut(&mut self) -> &mut File {
+        // unwrap() will not panic. Since we were able to open the
+        // file successfully, then `file` is guaranteed to be Some()
+        self.file.as_mut().take().unwrap()
+    }
+
+    pub fn dev(&self) -> u64 {
+        self.dev
+    }
+
+    pub fn ino(&self) -> u64 {
+        self.ino
+    }
+}
diff --git a/src/unknown.rs b/src/unknown.rs
new file mode 100644
index 0000000..6bfbdea
--- /dev/null
+++ b/src/unknown.rs
@@ -0,0 +1,52 @@
+use std::fs::File;
+use std::io;
+use std::path::Path;
+
+static ERROR_MESSAGE: &str = "same-file is not supported on this platform.";
+// This implementation is to allow same-file to be compiled on
+// unsupported platforms in case it was incidentally included
+// as a transitive, unused dependency
+#[derive(Debug, Hash)]
+pub struct Handle;
+
+impl Eq for Handle {}
+
+impl PartialEq for Handle {
+    fn eq(&self, _other: &Handle) -> bool {
+        unreachable!(ERROR_MESSAGE);
+    }
+}
+
+impl Handle {
+    pub fn from_path<P: AsRef<Path>>(_p: P) -> io::Result<Handle> {
+        error()
+    }
+
+    pub fn from_file(_file: File) -> io::Result<Handle> {
+        error()
+    }
+
+    pub fn stdin() -> io::Result<Handle> {
+        error()
+    }
+
+    pub fn stdout() -> io::Result<Handle> {
+        error()
+    }
+
+    pub fn stderr() -> io::Result<Handle> {
+        error()
+    }
+
+    pub fn as_file(&self) -> &File {
+        unreachable!(ERROR_MESSAGE);
+    }
+
+    pub fn as_file_mut(&self) -> &mut File {
+        unreachable!(ERROR_MESSAGE);
+    }
+}
+
+fn error<T>() -> io::Result<T> {
+    Err(io::Error::new(io::ErrorKind::Other, ERROR_MESSAGE))
+}
diff --git a/src/win.rs b/src/win.rs
new file mode 100644
index 0000000..6924739
--- /dev/null
+++ b/src/win.rs
@@ -0,0 +1,172 @@
+use std::fs::File;
+use std::hash::{Hash, Hasher};
+use std::io;
+use std::os::windows::io::{AsRawHandle, IntoRawHandle, RawHandle};
+use std::path::Path;
+
+use winapi_util as winutil;
+
+// For correctness, it is critical that both file handles remain open while
+// their attributes are checked for equality. In particular, the file index
+// numbers on a Windows stat object are not guaranteed to remain stable over
+// time.
+//
+// See the docs and remarks on MSDN:
+// https://msdn.microsoft.com/en-us/library/windows/desktop/aa363788(v=vs.85).aspx
+//
+// It gets worse. It appears that the index numbers are not always
+// guaranteed to be unique. Namely, ReFS uses 128 bit numbers for unique
+// identifiers. This requires a distinct syscall to get `FILE_ID_INFO`
+// documented here:
+// https://msdn.microsoft.com/en-us/library/windows/desktop/hh802691(v=vs.85).aspx
+//
+// It seems straight-forward enough to modify this code to use
+// `FILE_ID_INFO` when available (minimum Windows Server 2012), but I don't
+// have access to such Windows machines.
+//
+// Two notes.
+//
+// 1. Java's NIO uses the approach implemented here and appears to ignore
+//    `FILE_ID_INFO` altogether. So Java's NIO and this code are
+//    susceptible to bugs when running on a file system where
+//    `nFileIndex{Low,High}` are not unique.
+//
+// 2. LLVM has a bug where they fetch the id of a file and continue to use
+//    it even after the handle has been closed, so that uniqueness is no
+//    longer guaranteed (when `nFileIndex{Low,High}` are unique).
+//    bug report: http://lists.llvm.org/pipermail/llvm-bugs/2014-December/037218.html
+//
+// All said and done, checking whether two files are the same on Windows
+// seems quite tricky. Moreover, even if the code is technically incorrect,
+// it seems like the chances of actually observing incorrect behavior are
+// extremely small. Nevertheless, we mitigate this by checking size too.
+//
+// In the case where this code is erroneous, two files will be reported
+// as equivalent when they are in fact distinct. This will cause the loop
+// detection code to report a false positive, which will prevent descending
+// into the offending directory. As far as failure modes goes, this isn't
+// that bad.
+
+#[derive(Debug)]
+pub struct Handle {
+    kind: HandleKind,
+    key: Option<Key>,
+}
+
+#[derive(Debug)]
+enum HandleKind {
+    /// Used when opening a file or acquiring ownership of a file.
+    Owned(winutil::Handle),
+    /// Used for stdio.
+    Borrowed(winutil::HandleRef),
+}
+
+#[derive(Debug, Eq, PartialEq, Hash)]
+struct Key {
+    volume: u64,
+    index: u64,
+}
+
+impl Eq for Handle {}
+
+impl PartialEq for Handle {
+    fn eq(&self, other: &Handle) -> bool {
+        // Need this branch to satisfy `Eq` since `Handle`s with
+        // `key.is_none()` wouldn't otherwise.
+        if self as *const Handle == other as *const Handle {
+            return true;
+        } else if self.key.is_none() || other.key.is_none() {
+            return false;
+        }
+        self.key == other.key
+    }
+}
+
+impl AsRawHandle for crate::Handle {
+    fn as_raw_handle(&self) -> RawHandle {
+        match self.0.kind {
+            HandleKind::Owned(ref h) => h.as_raw_handle(),
+            HandleKind::Borrowed(ref h) => h.as_raw_handle(),
+        }
+    }
+}
+
+impl IntoRawHandle for crate::Handle {
+    fn into_raw_handle(self) -> RawHandle {
+        match self.0.kind {
+            HandleKind::Owned(h) => h.into_raw_handle(),
+            HandleKind::Borrowed(h) => h.as_raw_handle(),
+        }
+    }
+}
+
+impl Hash for Handle {
+    fn hash<H: Hasher>(&self, state: &mut H) {
+        self.key.hash(state);
+    }
+}
+
+impl Handle {
+    pub fn from_path<P: AsRef<Path>>(p: P) -> io::Result<Handle> {
+        let h = winutil::Handle::from_path_any(p)?;
+        let info = winutil::file::information(&h)?;
+        Ok(Handle::from_info(HandleKind::Owned(h), info))
+    }
+
+    pub fn from_file(file: File) -> io::Result<Handle> {
+        let h = winutil::Handle::from_file(file);
+        let info = winutil::file::information(&h)?;
+        Ok(Handle::from_info(HandleKind::Owned(h), info))
+    }
+
+    fn from_std_handle(h: winutil::HandleRef) -> io::Result<Handle> {
+        match winutil::file::information(&h) {
+            Ok(info) => Ok(Handle::from_info(HandleKind::Borrowed(h), info)),
+            // In a Windows console, if there is no pipe attached to a STD
+            // handle, then GetFileInformationByHandle will return an error.
+            // We don't really care. The only thing we care about is that
+            // this handle is never equivalent to any other handle, which is
+            // accomplished by setting key to None.
+            Err(_) => Ok(Handle { kind: HandleKind::Borrowed(h), key: None }),
+        }
+    }
+
+    fn from_info(
+        kind: HandleKind,
+        info: winutil::file::Information,
+    ) -> Handle {
+        Handle {
+            kind: kind,
+            key: Some(Key {
+                volume: info.volume_serial_number(),
+                index: info.file_index(),
+            }),
+        }
+    }
+
+    pub fn stdin() -> io::Result<Handle> {
+        Handle::from_std_handle(winutil::HandleRef::stdin())
+    }
+
+    pub fn stdout() -> io::Result<Handle> {
+        Handle::from_std_handle(winutil::HandleRef::stdout())
+    }
+
+    pub fn stderr() -> io::Result<Handle> {
+        Handle::from_std_handle(winutil::HandleRef::stderr())
+    }
+
+    pub fn as_file(&self) -> &File {
+        match self.kind {
+            HandleKind::Owned(ref h) => h.as_file(),
+            HandleKind::Borrowed(ref h) => h.as_file(),
+        }
+    }
+
+    pub fn as_file_mut(&mut self) -> &mut File {
+        match self.kind {
+            HandleKind::Owned(ref mut h) => h.as_file_mut(),
+            HandleKind::Borrowed(ref mut h) => h.as_file_mut(),
+        }
+    }
+}
