#![feature(plugin)]
#![plugin(clucstr)]
use std::io::Error;
use crate::display_cstr::DisplaySliceCStr;
use crate::uts_struct::UtsNameSlice;
use crate::uts_struct::UtsNameBuf;
use std::ffi::CStr;
mod hash;
pub mod uts_struct;
pub mod display_cstr;
pub use self::hash::*;
use std::fmt::Debug;
use std::fmt::Display;
use std::collections::hash_map::DefaultHasher;
use std::hash::{Hash, Hasher};
pub trait UtsName: Hash + HashVersion + Display + Debug + Hash + PartialEq + Eq + PartialOrd + Ord + Clone {
fn as_sysname(&self) -> &CStr;
fn as_nodename(&self) -> &CStr;
fn as_release(&self) -> &CStr;
fn as_version(&self) -> &CStr;
fn as_machine(&self) -> &CStr;
#[cfg(feature = "enable_domainname")]
fn as_domainname(&self) -> &CStr;
fn uname_hash(&self) -> u64 {
let mut hasher = DefaultHasher::new();
self.hash(&mut hasher);
hasher.finish()
}
fn version_hash(&self) -> u64 {
let mut hasher = DefaultHasher::new();
self.hash_version(&mut hasher);
hasher.finish()
}
#[inline]
fn display_sysname<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_sysname())
}
#[inline]
fn display_nodename<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_nodename())
}
#[inline]
fn display_release<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_release())
}
#[inline]
fn display_version<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_version())
}
#[inline]
fn display_machine<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_machine())
}
#[cfg(feature = "enable_domainname")]
#[inline]
fn display_domainname<'r>(&'r self) -> DisplaySliceCStr<'r> {
DisplaySliceCStr::new(self.as_domainname())
}
}
impl<'a, T: UtsName> UtsName for &'a T {
#[inline(always)]
fn as_sysname(&self) -> &CStr { (*self).as_sysname() }
#[inline(always)]
fn as_nodename(&self) -> &CStr { (*self).as_nodename() }
#[inline(always)]
fn as_release(&self) -> &CStr { (*self).as_release() }
#[inline(always)]
fn as_version(&self) -> &CStr { (*self).as_version() }
#[inline(always)]
fn as_machine(&self) -> &CStr { (*self).as_machine() }
#[inline(always)]
#[cfg(feature = "enable_domainname")]
fn as_domainname(&self) -> &CStr { (*self).as_domainname() }
#[inline(always)]
fn uname_hash(&self) -> u64 { (*self).uname_hash() }
#[inline(always)]
fn version_hash(&self) -> u64 { (*self).version_hash() }
#[inline(always)]
fn display_sysname<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_sysname() }
#[inline(always)]
fn display_nodename<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_nodename() }
#[inline(always)]
fn display_release<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_release() }
#[inline(always)]
fn display_version<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_version() }
#[inline(always)]
fn display_machine<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_machine() }
#[cfg(feature = "enable_domainname")]
#[inline(always)]
fn display_domainname<'r>(&'r self) -> DisplaySliceCStr<'r> { (*self).display_domainname() }
}
pub mod build {
use std::io::Error;
use crate::uts_struct::UtsNameSlice;
use crate::uts_struct::UtsNameBuf;
use std::ffi::CStr;
#[cfg(feature = "enable_domainname")]
#[inline]
pub fn custom<'a>(a1: &'a CStr, a2: &'a CStr, a3: &'a CStr, a4: &'a CStr, a5: &'a CStr, a6: &'a CStr) -> UtsNameSlice<'a> {
UtsNameSlice::new(a1, a2, a3, a4, a5, a6)
}
#[cfg(not(feature = "enable_domainname"))]
#[inline]
pub fn custom<'a>(a1: &'a CStr, a2: &'a CStr, a3: &'a CStr, a4: &'a CStr, a5: &'a CStr) -> UtsNameSlice<'a> {
UtsNameSlice::new(a1, a2, a3, a4, a5)
}
#[inline]
pub fn this_machine() -> Result<UtsNameBuf, Error> {
UtsNameBuf::this_machine()
}
pub fn linux_216_86() -> UtsNameSlice<'static> {
custom (
cstr!("Linux"),
cstr!("cluComp"),
cstr!("2.16-localhost"),
cstr!("#1 SMP PREEMPT Sat Mar 31 23:59:18 UTC 2008"),
cstr!("x86"),
#[cfg(feature = "enable_domainname")]
cstr!("(none)"),
)
}
pub fn linux_415_86_64() -> UtsNameSlice<'static> {
custom (
cstr!("Linux"),
cstr!("cluComp"),
cstr!("4.15.15-1-zen"),
cstr!("#1 ZEN SMP PREEMPT Sat Mar 31 23:59:18 UTC 2018"),
cstr!("x86_64"),
#[cfg(feature = "enable_domainname")]
cstr!("(none)"),
)
}
}
#[inline]
pub fn uname() -> Result<UtsNameBuf, Error> {
build::this_machine()
}
#[cfg(feature = "enable_domainname")]
#[inline]
pub fn custom_uname<'a>(a1: &'a CStr, a2: &'a CStr, a3: &'a CStr, a4: &'a CStr, a5: &'a CStr, a6: &'a CStr) -> UtsNameSlice<'a> {
build::custom(a1, a2, a3, a4, a5, a6)
}
#[cfg(not(feature = "enable_domainname"))]
#[inline]
pub fn custom_uname<'a>(a1: &'a CStr, a2: &'a CStr, a3: &'a CStr, a4: &'a CStr, a5: &'a CStr) -> UtsNameSlice<'a> {
build::custom(a1, a2, a3, a4, a5)
}
#[inline]
pub fn uname_hash<I: UtsName>(uts: I) -> u64 {
uts.uname_hash()
}
#[inline]
pub fn version_hash<I: UtsName>(uts: I) -> u64 {
uts.version_hash()
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
#[cfg(target_os = "linux")]
fn linux() {
if let Ok(uts) = uname() {
assert_eq!(uts.as_sysname(), cstr!("Linux"));
}
}
#[test]
fn custom() {
let uts = custom_uname (
cstr!("Linux"),
cstr!("cluComp"),
cstr!("4.15.15-1-zen"),
cstr!("#1 ZEN SMP PREEMPT Sat Mar 31 23:59:18 UTC 2018"),
cstr!("x86_64"),
#[cfg(feature = "enable_domainname")]
cstr!("(none)"),
);
assert_eq!(uts.as_sysname(), cstr!("Linux"));
assert_eq!(uts.as_nodename(), cstr!("cluComp"));
assert_eq!(uts.as_release(), cstr!("4.15.15-1-zen"));
assert_eq!(uts.as_version(), cstr!("#1 ZEN SMP PREEMPT Sat Mar 31 23:59:18 UTC 2018"));
assert_eq!(uts.as_machine(), cstr!("x86_64"));
#[cfg(feature = "enable_domainname")]
assert_eq!(uts.as_domainname(), cstr!("(none)"));
}
}