From 5d241da7ca71070544c72d418865bd8fad984987 Mon Sep 17 00:00:00 2001 From: Alex Lyon Date: Sun, 4 Mar 2018 17:58:16 -0800 Subject: [PATCH] arch: add support for building on Windows --- Cargo.toml | 3 +- src/arch/arch.rs | 2 +- src/uname/uname.rs | 2 +- src/uucore/Cargo.toml | 3 +- src/uucore/lib.rs | 4 +- src/uucore/utsname.rs | 120 +++++++++++++++++++++++++++++------------- 6 files changed, 90 insertions(+), 44 deletions(-) diff --git a/Cargo.toml b/Cargo.toml index ec9a6a92b..1b8b0c84c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,7 +6,6 @@ build = "build.rs" [features] unix = [ - "arch", "chgrp", "chmod", "chown", @@ -44,7 +43,6 @@ unix = [ # all utilities in that feature. fuchsia = [ # unix utilities - "arch", "chgrp", "chmod", "chown", @@ -67,6 +65,7 @@ fuchsia = [ "generic" ] generic = [ + "arch", "cat", "hashsum", "join", diff --git a/src/arch/arch.rs b/src/arch/arch.rs index 7c13f8024..d2c859727 100644 --- a/src/arch/arch.rs +++ b/src/arch/arch.rs @@ -19,7 +19,7 @@ static LONG_HELP: &'static str = ""; pub fn uumain(args: Vec) -> i32 { new_coreopts!(SYNTAX, SUMMARY, LONG_HELP).parse(args); - let uts = Uname::new(); + let uts = return_if_err!(1, Uname::new()); println!("{}", uts.machine().trim()); 0 } diff --git a/src/uname/uname.rs b/src/uname/uname.rs index 16105442d..3c560e494 100644 --- a/src/uname/uname.rs +++ b/src/uname/uname.rs @@ -92,7 +92,7 @@ pub fn uumain(args: Vec) -> i32 { .get_matches_from(&args); let argc = args.len(); - let uname = Uname::new(); + let uname = return_if_err!(1, Uname::new()); let mut output = String::new(); if matches.is_present(OPT_KERNELNAME) || matches.is_present(OPT_ALL) || argc == 1 { diff --git a/src/uucore/Cargo.toml b/src/uucore/Cargo.toml index c0801d925..90be15c92 100644 --- a/src/uucore/Cargo.toml +++ b/src/uucore/Cargo.toml @@ -8,6 +8,7 @@ getopts = "0.2.14" time = { version = "0.1.38", optional = true } data-encoding = { version = "^1.1", optional = true } libc = { version = "0.2.34", optional = true } +winapi = { version = "0.3", features = ["sysinfoapi"], optional = true } [features] fs = ["libc"] @@ -20,7 +21,7 @@ process = ["libc"] signals = [] entries = ["libc"] wide = [] -utsname = ["libc"] +utsname = ["libc", "winapi"] default = ["fs", "libc", "utf8", "utsname", "encoding", "parse_time", "mode", "utmpx", "process", "entries", "signals", "wide"] [lib] diff --git a/src/uucore/lib.rs b/src/uucore/lib.rs index c1f5b5277..14c2246d4 100644 --- a/src/uucore/lib.rs +++ b/src/uucore/lib.rs @@ -1,5 +1,7 @@ #[cfg(feature = "libc")] pub extern crate libc; +#[cfg(feature = "winapi")] +pub extern crate winapi; #[macro_use] mod macros; @@ -22,7 +24,7 @@ pub mod parse_time; pub mod mode; #[cfg(all(unix, not(target_os = "fuchsia"), feature = "utmpx"))] pub mod utmpx; -#[cfg(all(unix, feature = "utsname"))] +#[cfg(feature = "utsname")] pub mod utsname; #[cfg(all(unix, feature = "entries"))] pub mod entries; diff --git a/src/uucore/utsname.rs b/src/uucore/utsname.rs index c928c6191..a33e3fb19 100644 --- a/src/uucore/utsname.rs +++ b/src/uucore/utsname.rs @@ -6,47 +6,91 @@ // that was distributed with this source code. // -use super::libc::{uname, utsname}; -use ::std::mem; -use ::std::ffi::CStr; -use ::std::borrow::Cow; +pub use self::platform::*; -macro_rules! cstr2cow { - ($v:expr) => ( - unsafe { CStr::from_ptr($v.as_ref().as_ptr()).to_string_lossy() } - ) -} +#[cfg(unix)] +mod platform { + use super::libc::{uname, utsname}; + use ::std::mem; + use ::std::ffi::CStr; + use ::std::borrow::Cow; + use ::std::io; -pub struct Uname { - inner: utsname, -} + macro_rules! cstr2cow { + ($v:expr) => ( + unsafe { CStr::from_ptr($v.as_ref().as_ptr()).to_string_lossy() } + ) + } -impl Uname { - pub fn new() -> Self { - unsafe { - let mut uts: utsname = mem::uninitialized(); - uname(&mut uts); - Uname { inner: uts } + pub struct Uname { + inner: utsname, + } + + impl Uname { + pub fn new() -> io::Result { + unsafe { + let mut uts: utsname = mem::uninitialized(); + if uname(&mut uts) == 0 { + Ok(Uname { inner: uts }) + } else { + Err(io::Error::last_os_error()) + } + } + } + + pub fn sysname(&self) -> Cow { + cstr2cow!(self.inner.sysname) + } + + pub fn nodename(&self) -> Cow { + cstr2cow!(self.inner.nodename) + } + + pub fn release(&self) -> Cow { + cstr2cow!(self.inner.release) + } + + pub fn version(&self) -> Cow { + cstr2cow!(self.inner.version) + } + + pub fn machine(&self) -> Cow { + cstr2cow!(self.inner.machine) } } - - pub fn sysname(&self) -> Cow { - cstr2cow!(self.inner.sysname) - } - - pub fn nodename(&self) -> Cow { - cstr2cow!(self.inner.nodename) - } - - pub fn release(&self) -> Cow { - cstr2cow!(self.inner.release) - } - - pub fn version(&self) -> Cow { - cstr2cow!(self.inner.version) - } - - pub fn machine(&self) -> Cow { - cstr2cow!(self.inner.machine) - } } + +#[cfg(windows)] +mod platform { + use ::winapi::um::sysinfoapi::{SYSTEM_INFO, GetSystemInfo}; + use ::winapi::um::winnt::*; + use ::std::mem; + use ::std::borrow::Cow; + use ::std::io; + + pub struct Uname { + inner: SYSTEM_INFO + } + + impl Uname { + pub fn new() -> io::Result { + unsafe { + let mut info = mem::uninitialized(); + GetSystemInfo(&mut info); + Ok(Uname { inner: info }) + } + } + + // FIXME: need to implement more architectures (e.g. ARM) + pub fn machine(&self) -> Cow { + let arch = unsafe { + match self.inner.u.s().wProcessorArchitecture { + PROCESSOR_ARCHITECTURE_AMD64 => "x86_64", + PROCESSOR_ARCHITECTURE_INTEL => "x86", + _ => unimplemented!() + } + }; + Cow::from(arch) + } + } +} \ No newline at end of file