diff options
author | syn <isaqtm@gmail.com> | 2020-12-08 10:37:04 +0300 |
---|---|---|
committer | syn <isaqtm@gmail.com> | 2020-12-08 10:37:04 +0300 |
commit | eaf9228f3a43c3654eeddbd10cfbaf172e4578f4 (patch) | |
tree | 6e24fe86e7ef4e580b559e41b77c113036248a68 | |
parent | 420e77f90ba94cf9f8d3d0f7ae6395ba3ceda89f (diff) | |
download | evr-eaf9228f3a43c3654eeddbd10cfbaf172e4578f4.tar.gz |
cargo fmt
-rw-r--r-- | src/backends/clang.rs | 42 | ||||
-rw-r--r-- | src/backends/clang_c.rs | 42 | ||||
-rw-r--r-- | src/backends/mod.rs | 19 | ||||
-rw-r--r-- | src/backends/python.rs | 22 | ||||
-rw-r--r-- | src/backends/run_error.rs | 6 | ||||
-rw-r--r-- | src/conf.rs | 18 | ||||
-rw-r--r-- | src/main.rs | 52 | ||||
-rw-r--r-- | src/serde_duration.rs | 18 | ||||
-rw-r--r-- | src/wait/error.rs | 36 | ||||
-rw-r--r-- | src/wait/mod.rs | 81 | ||||
-rw-r--r-- | src/wait/rusage_ffi.rs | 5 |
11 files changed, 154 insertions, 187 deletions
diff --git a/src/backends/clang.rs b/src/backends/clang.rs index 361c759..cf42c41 100644 --- a/src/backends/clang.rs +++ b/src/backends/clang.rs @@ -1,14 +1,13 @@ +use crate::backends::{mk_tmp_dir, Backend, RunError}; +use crate::serde_duration::deserialize_duration; +use crate::wait::{wait_child, ChildExitStatus}; use serde_derive::Deserialize; -use crate::backends::{ Backend, mk_tmp_dir, RunError }; -use std::path::{ Path, PathBuf }; -use std::io::{ Result as IoResult, Error, ErrorKind }; -use std::process::{ Command }; use std::collections::hash_map::DefaultHasher; -use std::hash::{ Hash, Hasher }; -use crate::wait::{ ChildExitStatus, wait_child }; +use std::hash::{Hash, Hasher}; +use std::io::{Error, ErrorKind, Result as IoResult}; +use std::path::{Path, PathBuf}; +use std::process::Command; use std::time::Duration; -use crate::serde_duration::deserialize_duration; - #[derive(Debug, Deserialize, Default)] pub struct ClangBackend { @@ -21,10 +20,9 @@ pub struct ClangBackend { cc: String, #[serde(default = "default_timeout", deserialize_with = "deserialize_duration")] - timeout: Duration + timeout: Duration, } - fn default_cc() -> String { "clang++".to_string() } @@ -33,39 +31,35 @@ fn default_timeout() -> Duration { Duration::from_secs(1) } - fn get_binary_by_filename(fname: &Path) -> IoResult<PathBuf> { let hashed_fname = { let mut hasher = DefaultHasher::new(); fname.hash(&mut hasher); format!("{:x}", hasher.finish()) }; - + Ok(mk_tmp_dir()?.join(hashed_fname)) } - impl ClangBackend { fn build(&self, fname: &Path) -> IoResult<PathBuf> { let binary_fname = get_binary_by_filename(fname)?; - let get_mtime = |file| { - std::fs::metadata(file)? - .modified() - }; + let get_mtime = |file| std::fs::metadata(file)?.modified(); let src_mod = get_mtime(fname); let binary_mod = get_mtime(&binary_fname); if src_mod.is_err() || binary_mod.is_err() || src_mod.unwrap() > binary_mod.unwrap() { let clang_status = Command::new(&self.cc) - .arg("-x").arg("c++") + .arg("-x") + .arg("c++") .arg(fname.as_os_str()) - .arg("-o").arg(&binary_fname) + .arg("-o") + .arg(&binary_fname) .args(&self.args) .status()?; if !clang_status.success() { - return Err(Error::new(ErrorKind::Other, - "could not compile")); + return Err(Error::new(ErrorKind::Other, "could not compile")); } } @@ -73,20 +67,18 @@ impl ClangBackend { } } - impl Backend for ClangBackend { fn get_template(&self) -> Option<&str> { match self.template { Some(ref t) => Some(t), - None => None + None => None, } } fn run(&self, fname: &Path) -> Result<ChildExitStatus, RunError> { let binary_fname = self.build(fname)?; - let proc = Command::new(&binary_fname) - .spawn()?; + let proc = Command::new(&binary_fname).spawn()?; Ok(wait_child(proc, self.timeout, std::time::Instant::now())?) } diff --git a/src/backends/clang_c.rs b/src/backends/clang_c.rs index 1aa39e4..7ee5161 100644 --- a/src/backends/clang_c.rs +++ b/src/backends/clang_c.rs @@ -1,14 +1,13 @@ +use crate::backends::{mk_tmp_dir, Backend, RunError}; +use crate::serde_duration::deserialize_duration; +use crate::wait::{wait_child, ChildExitStatus}; use serde_derive::Deserialize; -use crate::backends::{ Backend, mk_tmp_dir, RunError }; -use std::path::{ Path, PathBuf }; -use std::io::{ Result as IoResult, Error, ErrorKind }; -use std::process::Command; use std::collections::hash_map::DefaultHasher; -use std::hash::{ Hash, Hasher }; -use crate::wait::{ ChildExitStatus, wait_child }; +use std::hash::{Hash, Hasher}; +use std::io::{Error, ErrorKind, Result as IoResult}; +use std::path::{Path, PathBuf}; +use std::process::Command; use std::time::Duration; -use crate::serde_duration::deserialize_duration; - #[derive(Debug, Deserialize, Default)] pub struct ClangCBackend { @@ -21,10 +20,9 @@ pub struct ClangCBackend { cc: String, #[serde(default = "default_timeout", deserialize_with = "deserialize_duration")] - timeout: Duration + timeout: Duration, } - fn default_cc() -> String { "clang".to_string() } @@ -33,40 +31,36 @@ fn default_timeout() -> Duration { Duration::from_secs(1) } - fn get_binary_by_filename(fname: &Path) -> IoResult<PathBuf> { let hashed_fname = { let mut hasher = DefaultHasher::new(); fname.hash(&mut hasher); format!("{:x}", hasher.finish()) }; - + Ok(mk_tmp_dir()?.join(hashed_fname)) } - impl ClangCBackend { fn build(&self, fname: &Path) -> IoResult<PathBuf> { let binary_fname = get_binary_by_filename(fname)?; - let get_mtime = |file| { - std::fs::metadata(file)? - .modified() - }; + let get_mtime = |file| std::fs::metadata(file)?.modified(); let src_mod = get_mtime(fname); let binary_mod = get_mtime(&binary_fname); if src_mod.is_err() || binary_mod.is_err() || src_mod.unwrap() > binary_mod.unwrap() { let clang_status = Command::new(&self.cc) - .arg("-x").arg("c") + .arg("-x") + .arg("c") .arg(fname.clone().as_os_str()) - .arg("-o").arg(&binary_fname) + .arg("-o") + .arg(&binary_fname) .args(&self.args) .status()?; if !clang_status.success() { - return Err(Error::new(ErrorKind::Other, - "could not compile")); + return Err(Error::new(ErrorKind::Other, "could not compile")); } } @@ -74,20 +68,18 @@ impl ClangCBackend { } } - impl Backend for ClangCBackend { fn get_template(&self) -> Option<&str> { match self.template { Some(ref t) => Some(t), - None => None + None => None, } } fn run(&self, fname: &Path) -> Result<ChildExitStatus, RunError> { let binary_fname = self.build(fname)?; - let proc = Command::new(&binary_fname) - .spawn()?; + let proc = Command::new(&binary_fname).spawn()?; Ok(wait_child(proc, self.timeout, std::time::Instant::now())?) } diff --git a/src/backends/mod.rs b/src/backends/mod.rs index 50bef36..6d402af 100644 --- a/src/backends/mod.rs +++ b/src/backends/mod.rs @@ -1,21 +1,20 @@ -use std::path::{ Path, PathBuf }; -use std::env::temp_dir; -use lazy_static::lazy_static; -use std::io::{ Error, ErrorKind }; use crate::wait::ChildExitStatus; +use lazy_static::lazy_static; +use std::env::temp_dir; +use std::io::{Error, ErrorKind}; +use std::path::{Path, PathBuf}; -pub mod python; pub mod clang; pub mod clang_c; +pub mod python; -pub use python::PythonBackend; pub use clang::ClangBackend; pub use clang_c::ClangCBackend; +pub use python::PythonBackend; pub mod run_error; pub use run_error::RunError; - lazy_static! { static ref EVR_TMP_DIR: PathBuf = temp_dir().join("evr-tmp"); } @@ -31,8 +30,10 @@ fn mk_tmp_dir() -> std::io::Result<&'static std::path::PathBuf> { std::fs::create_dir(&*EVR_TMP_DIR)?; } else { if !EVR_TMP_DIR.is_dir() { - return Err(Error::new(ErrorKind::AlreadyExists, - "tmp dir already exists and not a directory")) + return Err(Error::new( + ErrorKind::AlreadyExists, + "tmp dir already exists and not a directory", + )); } } Ok(&*EVR_TMP_DIR) diff --git a/src/backends/python.rs b/src/backends/python.rs index 7e0dac1..57bd624 100644 --- a/src/backends/python.rs +++ b/src/backends/python.rs @@ -1,9 +1,9 @@ +use crate::backends::{Backend, RunError}; +use crate::serde_duration::deserialize_duration; +use crate::wait::{wait_child, ChildExitStatus}; use serde_derive::Deserialize; -use crate::backends::{ Backend, RunError }; -use std::process::{ Command }; use std::path::Path; -use crate::wait::{ wait_child, ChildExitStatus }; -use crate::serde_duration::deserialize_duration; +use std::process::Command; use std::time::Duration; #[derive(Debug, Deserialize, Default)] @@ -15,29 +15,21 @@ pub struct PythonBackend { timeout: Duration, } - fn default_timeout() -> Duration { Duration::from_secs(1) } - impl PythonBackend { fn get_interpreter(&self) -> String { - format!( - "python{}", - self.version - .as_ref() - .unwrap_or(&String::new()) - ) + format!("python{}", self.version.as_ref().unwrap_or(&String::new())) } } - impl Backend for PythonBackend { fn get_template(&self) -> Option<&str> { match self.template { Some(ref t) => Some(t), - None => None + None => None, } } @@ -50,4 +42,4 @@ impl Backend for PythonBackend { Ok(wait_child(child, self.timeout, timer)?) } -}
\ No newline at end of file +} diff --git a/src/backends/run_error.rs b/src/backends/run_error.rs index 6203bbe..0681ea8 100644 --- a/src/backends/run_error.rs +++ b/src/backends/run_error.rs @@ -4,7 +4,7 @@ use std::io::Error as IoError; #[derive(Debug)] pub enum RunError { IoError(std::io::Error), - WaitError(WaitError) + WaitError(WaitError), } impl From<IoError> for RunError { @@ -32,7 +32,7 @@ impl std::error::Error for RunError { fn source(&self) -> Option<&(dyn std::error::Error + 'static)> { match *self { RunError::IoError(ref e) => Some(e), - RunError::WaitError(ref e) => Some(e) + RunError::WaitError(ref e) => Some(e), } } -}
\ No newline at end of file +} diff --git a/src/conf.rs b/src/conf.rs index 3649a50..0a343bb 100644 --- a/src/conf.rs +++ b/src/conf.rs @@ -1,17 +1,11 @@ use serde_derive::Deserialize; -use std::path::{ PathBuf, Path }; +use std::path::{Path, PathBuf}; use toml::de; type Error = std::io::Error; use std::io::ErrorKind; -use crate::backends::{ - Backend, - PythonBackend, - ClangBackend, - ClangCBackend, -}; - +use crate::backends::{Backend, ClangBackend, ClangCBackend, PythonBackend}; #[derive(Debug, Deserialize)] pub struct Conf { @@ -28,7 +22,6 @@ pub struct Conf { clang_c: ClangCBackend, } - impl Conf { pub fn get_template(&self, fname: &Path) -> &str { self.get_backend(fname) @@ -37,20 +30,17 @@ impl Conf { } pub fn get_backend(&self, fname: &Path) -> Option<Box<&dyn Backend>> { - let ext = fname.extension() - .and_then(|ext| ext.to_str()) - .unwrap_or(""); + let ext = fname.extension().and_then(|ext| ext.to_str()).unwrap_or(""); match ext { "py" => Some(Box::new(&self.python)), "cc" | "cpp" | "cxx" => Some(Box::new(&self.clang)), "c" => Some(Box::new(&self.clang_c)), - _ => None + _ => None, } } } - pub fn get_conf() -> Result<Conf, Error> { let mut current = std::env::current_dir()?; let path = loop { diff --git a/src/main.rs b/src/main.rs index 0d54445..b14bad7 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,14 +1,14 @@ extern crate lazy_static; -use clap::{ AppSettings, App, Arg }; +use clap::{App, AppSettings, Arg}; use env_logger; -use log::{ error }; +use log::error; use std::io::prelude::*; -mod conf; mod backends; -mod wait; +mod conf; mod serde_duration; +mod wait; fn main() { let matches = App::new("evr") @@ -16,31 +16,29 @@ fn main() { .author("syn") .setting(AppSettings::ColoredHelp) .setting(AppSettings::UnifiedHelpMessage) - .arg(Arg::with_name("src") - .required(true) - .index(1) - .help("source file") + .arg( + Arg::with_name("src") + .required(true) + .index(1) + .help("source file"), ) - .arg(Arg::with_name("time") - .short("t") - .long("time") - .help("show wall time") + .arg( + Arg::with_name("time") + .short("t") + .long("time") + .help("show wall time"), ) - .arg(Arg::with_name("mem") - .short("m") - .long("mem") - .help("show mem usage (rss)") + .arg( + Arg::with_name("mem") + .short("m") + .long("mem") + .help("show mem usage (rss)"), ) .get_matches(); + env_logger::builder().format_timestamp(None).init(); - env_logger::builder() - .format_timestamp(None) - .init(); - - let src_path: std::path::PathBuf = matches.value_of("src") - .expect("src is required") - .into(); + let src_path: std::path::PathBuf = matches.value_of("src").expect("src is required").into(); let config = match conf::get_conf() { Ok(c) => c, @@ -61,8 +59,8 @@ fn main() { if matches.is_present("mem") { eprintln!("rss: {}K", status.usage.get_rss_bytes() / 1000); } - }, - Err(err) => error!("{}", err) + } + Err(err) => error!("{}", err), }; } else { error!("could not match backend"); @@ -70,8 +68,8 @@ fn main() { } else { let template = config.get_template(&src_path).as_bytes(); if let Err(err) = - std::fs::File::create(&src_path) - .and_then(|mut file| file.write_all(template)) { + std::fs::File::create(&src_path).and_then(|mut file| file.write_all(template)) + { error!("{}", err); } }; diff --git a/src/serde_duration.rs b/src/serde_duration.rs index 50076b0..5a54408 100644 --- a/src/serde_duration.rs +++ b/src/serde_duration.rs @@ -1,28 +1,28 @@ -use serde::de::{ Visitor, Error, Deserializer }; -use std::time::Duration; +use serde::de::{Deserializer, Error, Visitor}; use std::fmt; +use std::time::Duration; pub fn deserialize_duration<'de, D>(deserializer: D) -> Result<Duration, D::Error> where - D: Deserializer<'de> + D: Deserializer<'de>, { struct DurationVisitor; impl<'de> Visitor<'de> for DurationVisitor { type Value = Duration; - + fn expecting(&self, f: &mut fmt::Formatter) -> fmt::Result { write!(f, "duration in secs") } - - fn visit_f32<E: Error> (self, v: f32) -> Result<Self::Value, E> { + + fn visit_f32<E: Error>(self, v: f32) -> Result<Self::Value, E> { Ok(Duration::from_secs_f32(v)) } - - fn visit_f64<E: Error> (self, v: f64) -> Result<Self::Value, E> { + + fn visit_f64<E: Error>(self, v: f64) -> Result<Self::Value, E> { Ok(Duration::from_secs_f64(v)) } } - + deserializer.deserialize_any(DurationVisitor) } diff --git a/src/wait/error.rs b/src/wait/error.rs index 169097d..fb489f5 100644 --- a/src/wait/error.rs +++ b/src/wait/error.rs @@ -5,7 +5,7 @@ use std::time::Duration; pub struct ProcessSignalInfo { pub pid: nix::unistd::Pid, pub signal: nix::sys::signal::Signal, - pub coredump: bool + pub coredump: bool, } #[derive(Debug)] @@ -14,10 +14,9 @@ pub enum WaitError { ReturnNonZero(i32, nix::unistd::Pid), Signaled(ProcessSignalInfo), OsError(nix::Error), - NotExited + NotExited, } - impl From<nix::Error> for WaitError { fn from(err: nix::Error) -> Self { WaitError::OsError(err) @@ -28,13 +27,20 @@ impl std::fmt::Display for WaitError { fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { match *self { WaitError::TimedOut(dur) => write!(f, "process timed out in {:?}", dur), - WaitError::ReturnNonZero(ret, pid) => - write!(f, "process exited with non-zero exit code ({}). was {}", ret, pid), - WaitError::Signaled(ref info) => - write!(f, "process killed by {} {}. was {}", - info.signal, if info.coredump {"(core dumped)"} else {""}, info.pid), + WaitError::ReturnNonZero(ret, pid) => write!( + f, + "process exited with non-zero exit code ({}). was {}", + ret, pid + ), + WaitError::Signaled(ref info) => write!( + f, + "process killed by {} {}. was {}", + info.signal, + if info.coredump { "(core dumped)" } else { "" }, + info.pid + ), WaitError::OsError(err) => err.fmt(f), - WaitError::NotExited => write!(f, "process signaled, but not exited") + WaitError::NotExited => write!(f, "process signaled, but not exited"), } } } @@ -42,11 +48,11 @@ impl std::fmt::Display for WaitError { impl std::error::Error for WaitError { fn source(&self) -> Option<&(dyn std::error::Error + 'static)> { match *self { - WaitError::TimedOut(_) | - WaitError::ReturnNonZero(_, _) | - WaitError::Signaled(_) | - WaitError::NotExited => None, - WaitError::OsError(ref e) => Some(e) + WaitError::TimedOut(_) + | WaitError::ReturnNonZero(_, _) + | WaitError::Signaled(_) + | WaitError::NotExited => None, + WaitError::OsError(ref e) => Some(e), } } -}
\ No newline at end of file +} diff --git a/src/wait/mod.rs b/src/wait/mod.rs index 1a699a0..f87b954 100644 --- a/src/wait/mod.rs +++ b/src/wait/mod.rs @@ -1,33 +1,29 @@ use nix::libc::{self, c_int}; -use nix::{ - errno::Errno, - sys::wait::WaitStatus, - unistd::Pid -}; -use std::time::{ Instant, Duration }; +use nix::{errno::Errno, sys::wait::WaitStatus, unistd::Pid}; +use std::convert::{TryFrom, TryInto}; use std::process::Child; -use std::thread; use std::sync::mpsc; -use std::convert::{ TryFrom, TryInto }; +use std::thread; +use std::time::{Duration, Instant}; mod error; mod rusage_ffi; pub use rusage_ffi::Rusage; -pub use error::WaitError; use error::ProcessSignalInfo; +pub use error::WaitError; #[derive(Debug)] struct WaitInfo { pub status: WaitStatus, pub usage: Rusage, - pub wall_time: Duration + pub wall_time: Duration, } #[derive(Debug)] pub struct ChildExitStatus { pub usage: Rusage, - pub wall_time: Duration + pub wall_time: Duration, } impl TryFrom<WaitInfo> for ChildExitStatus { @@ -35,38 +31,43 @@ impl TryFrom<WaitInfo> for ChildExitStatus { fn try_from(info: WaitInfo) -> Result<Self, Self::Error> { match info.status { - WaitStatus::Exited(pid, ret) => - match ret { - 0 => Ok(ChildExitStatus { usage: info.usage, wall_time: info.wall_time }), - _ => Err(WaitError::ReturnNonZero(ret, pid)) - }, - WaitStatus::Signaled(pid, signal, coredump) => - Err(WaitError::Signaled(ProcessSignalInfo { pid, signal, coredump })), - _ => Err(WaitError::NotExited) + WaitStatus::Exited(pid, ret) => match ret { + 0 => Ok(ChildExitStatus { + usage: info.usage, + wall_time: info.wall_time, + }), + _ => Err(WaitError::ReturnNonZero(ret, pid)), + }, + WaitStatus::Signaled(pid, signal, coredump) => { + Err(WaitError::Signaled(ProcessSignalInfo { + pid, + signal, + coredump, + })) + } + _ => Err(WaitError::NotExited), } } } - #[cfg(target_os = "macos")] #[link(name = "c")] -extern { +extern "C" { fn wait4( - pid: libc::pid_t, - status: *mut c_int, - options: c_int, - rusage: *mut libc::rusage + pid: libc::pid_t, + status: *mut c_int, + options: c_int, + rusage: *mut libc::rusage, ) -> libc::pid_t; } #[cfg(target_os = "linux")] use libc::wait4; - fn wait4_pid( pid: Pid, chan: mpsc::Sender<std::result::Result<WaitInfo, nix::Error>>, - timer: Instant + timer: Instant, ) { let mut status: c_int = 0; let mut usg: libc::rusage; @@ -77,26 +78,23 @@ fn wait4_pid( wait_ret = wait4(pid.as_raw(), &mut status, 0 as c_int, &mut usg); } - #[allow(unused_must_use)] { + #[allow(unused_must_use)] + { chan.send(match wait_ret { -1 => Err(nix::Error::Sys(Errno::last())), - _ => WaitStatus::from_raw(pid, status).map(|nix_status| { - WaitInfo { - status: nix_status, - usage: usg.into(), - wall_time: timer.elapsed() - } - } - ) + _ => WaitStatus::from_raw(pid, status).map(|nix_status| WaitInfo { + status: nix_status, + usage: usg.into(), + wall_time: timer.elapsed(), + }), }); }; } - pub fn wait_child( mut child: Child, timeout: Duration, - timer: Instant + timer: Instant, ) -> Result<ChildExitStatus, WaitError> { let pid = Pid::from_raw(child.id() as i32); let (send, recv) = mpsc::channel(); @@ -110,12 +108,13 @@ pub fn wait_child( drop(recv); drop(thr); - #[allow(unused_must_use)] { + #[allow(unused_must_use)] + { child.kill(); } Err(WaitError::TimedOut(timeout)) - }, - Err(mpsc::RecvTimeoutError::Disconnected) => unreachable!() + } + Err(mpsc::RecvTimeoutError::Disconnected) => unreachable!(), } } diff --git a/src/wait/rusage_ffi.rs b/src/wait/rusage_ffi.rs index d77884e..4ac68ec 100644 --- a/src/wait/rusage_ffi.rs +++ b/src/wait/rusage_ffi.rs @@ -25,10 +25,7 @@ impl From<libc::rusage> for Rusage { fn from(usg: libc::rusage) -> Rusage { const MICROS_IN_SEC: u64 = 1_000_000; let convert_timeval = |tv: libc::timeval| { - Duration::from_micros( - tv.tv_sec as u64 * MICROS_IN_SEC + - tv.tv_usec as u64 - ) + Duration::from_micros(tv.tv_sec as u64 * MICROS_IN_SEC + tv.tv_usec as u64) }; Rusage { |