From 263ade47ba4ca15d8166f5bbd220b6ab9dc091c8 Mon Sep 17 00:00:00 2001 From: syn Date: Thu, 16 Jan 2020 14:46:18 +0300 Subject: Add c/cxx support --- src/backends/clang.rs | 73 +++++++++++++++++++++++++++++++++++++++++++++++---- 1 file changed, 68 insertions(+), 5 deletions(-) diff --git a/src/backends/clang.rs b/src/backends/clang.rs index 5a0c37f..b5f9be8 100644 --- a/src/backends/clang.rs +++ b/src/backends/clang.rs @@ -1,12 +1,68 @@ use serde_derive::{ Serialize, Deserialize }; -use crate::backends::Backend; +use crate::backends::{ Backend, mk_tmp_dir }; use std::path::Path; +use std::process::Command; +use std::collections::hash_map::DefaultHasher; +use std::hash::{Hash, Hasher}; +use log::trace; + +type Result = std::io::Result; #[derive(Debug, Serialize, Deserialize, Default)] pub struct ClangBackend { - template: Option + template: Option, + + #[serde(default)] + args: Vec, + + #[serde(default = "default_cc")] + cc: String, +} + + +fn default_cc() -> String { + "clang++".to_string() } + +fn get_binary_by_filename(fname: &Path) -> Result { + 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) -> Result { + let binary_fname = get_binary_by_filename(fname)?; + 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) + .args(&self.args) + .arg("-x").arg("c++") + .arg(fname.as_os_str()) + .arg("-o").arg(&binary_fname) + .arg("-lstdc++") + .status(); + + trace!("{:#?}", clang_status); + } + + Ok(binary_fname) + } +} + + impl Backend for ClangBackend { fn get_template(&self) -> Option<&str> { match self.template { @@ -15,7 +71,14 @@ impl Backend for ClangBackend { } } - fn run(&self, _fname: &Path) -> std::io::Result<()> { - todo!(); + fn run(&self, fname: &Path) -> std::io::Result<()> { + let binary_fname = self.build(fname)?; + + Command::new(&binary_fname) + .status() + .map(|status| { + trace!("{:#?}", status); + () + }) } -} \ No newline at end of file +} -- cgit v1.2.1-18-gbd029