From 1fcf025a062b63abfbfb877c648c47d6fefc573d Mon Sep 17 00:00:00 2001 From: kazuminn Date: Sat, 31 Oct 2020 22:36:52 +0900 Subject: [PATCH 01/20] fix decode's optional --- src/detections/utils.rs | 26 ++++++++++++-------------- 1 file changed, 12 insertions(+), 14 deletions(-) diff --git a/src/detections/utils.rs b/src/detections/utils.rs index deae75df..fc63bd0d 100644 --- a/src/detections/utils.rs +++ b/src/detections/utils.rs @@ -61,22 +61,20 @@ pub fn check_command( .unwrap() .is_match(commandline) { - /* - if let decoded = base64::decode(&base64) { - let mut d = GzDecoder::new(decoded.as_slice()); - let mut uncompressed = String::new(); - d.read_to_string(&mut uncompressed).unwrap(); - println!("Decoded : {}", uncompressed); - text.push_str("Base64-encoded and compressed function\n"); - + if let Ok(decoded) = base64::decode(&base64) { + let mut d = GzDecoder::new(decoded.as_slice()); + let mut uncompressed = String::new(); + d.read_to_string(&mut uncompressed).unwrap(); + println!("Decoded : {}", uncompressed); + text.push_str("Base64-encoded and compressed function\n"); } - */ } else { - let decoded = base64::decode(base64).unwrap(); - println!("Decoded : {}", str::from_utf8(decoded.as_slice()).unwrap()); - text.push_str("Base64-encoded function\n"); - text.push_str(&check_obfu(str::from_utf8(decoded.as_slice()).unwrap())); - text.push_str(&check_regex(str::from_utf8(decoded.as_slice()).unwrap(), 0)); + if let Ok(decoded) = base64::decode(&base64) { + println!("Decoded : {}", str::from_utf8(decoded.as_slice()).unwrap()); + text.push_str("Base64-encoded function\n"); + text.push_str(&check_obfu(str::from_utf8(decoded.as_slice()).unwrap())); + text.push_str(&check_regex(str::from_utf8(decoded.as_slice()).unwrap(), 0)); + } } } if !text.is_empty() { From 73fa8090f00a4165f255084725de0d4b344c8ff9 Mon Sep 17 00:00:00 2001 From: kazuminn Date: Mon, 2 Nov 2020 16:15:44 +0900 Subject: [PATCH 02/20] =?UTF-8?q?=E6=8C=87=E6=91=98=E3=81=95=E3=82=8C?= =?UTF-8?q?=E3=81=9F=E3=81=A8=E3=81=93=E3=82=8D?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- src/detections/utils.rs | 16 +++++++--------- 1 file changed, 7 insertions(+), 9 deletions(-) diff --git a/src/detections/utils.rs b/src/detections/utils.rs index fc63bd0d..2e7026e0 100644 --- a/src/detections/utils.rs +++ b/src/detections/utils.rs @@ -56,20 +56,18 @@ pub fn check_command( let re = Regex::new(r"'.*$").unwrap(); base64.push_str(&re.replace_all(&base64.to_string(), "")); } - if !base64.is_empty() { - if Regex::new(r"Compression.GzipStream.*Decompress") - .unwrap() - .is_match(commandline) - { - if let Ok(decoded) = base64::decode(&base64) { + if let Ok(decoded) = base64::decode(&base64) { + if !base64.is_empty() { + if Regex::new(r"Compression.GzipStream.*Decompress") + .unwrap() + .is_match(commandline) + { let mut d = GzDecoder::new(decoded.as_slice()); let mut uncompressed = String::new(); d.read_to_string(&mut uncompressed).unwrap(); println!("Decoded : {}", uncompressed); text.push_str("Base64-encoded and compressed function\n"); - } - } else { - if let Ok(decoded) = base64::decode(&base64) { + } else { println!("Decoded : {}", str::from_utf8(decoded.as_slice()).unwrap()); text.push_str("Base64-encoded function\n"); text.push_str(&check_obfu(str::from_utf8(decoded.as_slice()).unwrap())); From f9672b17f94abb34c4810f1e1319742a59b56794 Mon Sep 17 00:00:00 2001 From: kazuminn Date: Tue, 3 Nov 2020 17:31:22 +0900 Subject: [PATCH 03/20] windows crossconpile --- Cargo.toml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/Cargo.toml b/Cargo.toml index b28772bf..1f5786f4 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,3 +18,9 @@ csv = "1.1" base64 = "*" flate2 = "1.0" toml = "0.5" + +[target.x86_64-pc-windows-gnu] +linker = "x86_64-w64-mingw32-gcc" + +[target.i686-pc-windows-gnu] +linker = "i686-w64-mingw32-gcc" \ No newline at end of file From 692f4710049b91bbd231a3b51d77b0c7d8b4e96b Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 22 Oct 2020 18:02:26 +0900 Subject: [PATCH 04/20] Add: ErrorMessage struct for print in appropriate language --- src/detections/mod.rs | 1 + src/detections/print.rs | 78 +++++++++++++++++++++++++++++++++++++++++ 2 files changed, 79 insertions(+) create mode 100644 src/detections/print.rs diff --git a/src/detections/mod.rs b/src/detections/mod.rs index ad3011e6..d1996a94 100644 --- a/src/detections/mod.rs +++ b/src/detections/mod.rs @@ -4,6 +4,7 @@ mod common; mod configs; pub mod detection; mod powershell; +mod print; mod security; mod sysmon; mod system; diff --git a/src/detections/print.rs b/src/detections/print.rs new file mode 100644 index 00000000..6f131ee5 --- /dev/null +++ b/src/detections/print.rs @@ -0,0 +1,78 @@ +use std::collections::HashMap; + +#[derive(Debug)] +pub enum Lang { + ja, + en, +} + +#[derive(Debug)] +pub struct MessageLanguages { + ja: String, + en: String, +} + +#[derive(Debug)] +pub struct ErrorMessage { + map: HashMap, +} + +impl ErrorMessage { + pub fn new() -> Self { + let mut messages: HashMap = HashMap::new(); + messages.insert( + "undefined".to_string(), + MessageLanguages { + ja: "未設定".to_string(), + en: "Undefined".to_string(), + }, + ); + ErrorMessage { map: messages } + } + + /// エラーメッセージを設定 + pub fn insert_rule(&mut self, error_code: String, message: MessageLanguages) { + self.map.insert(error_code, message); + } + + /// エラーメッセージを指定された言語で返す + pub fn return_error_message(&self, error_num: &str, lang: Lang) -> String { + let messages = if let Some(boxed_message) = self.map.get(error_num) { + boxed_message + } else { + self.map.get("undefined").unwrap() + }; + match lang { + Lang::ja => messages.ja.clone(), + Lang::en => messages.en.clone(), + } + } +} + +#[test] +fn test_create_error_message() { + let mut error_message = ErrorMessage::new(); + + error_message.insert_rule( + "4103".to_string(), + MessageLanguages { + ja: "パイプライン実行をしています".to_string(), + en: "Execute pipeline".to_string(), + }, + ); + + let message_ja1 = error_message.return_error_message("4103", Lang::ja); + assert_eq!(message_ja1, "パイプライン実行をしています"); + let message_ja2 = error_message.return_error_message("4103", Lang::ja); + assert_eq!(message_ja2, "パイプライン実行をしています"); + + let message_en1 = error_message.return_error_message("4103", Lang::en); + assert_eq!(message_en1, "Execute pipeline"); + let message_en2 = error_message.return_error_message("4103", Lang::en); + assert_eq!(message_en2, "Execute pipeline"); + + let undef_ja = error_message.return_error_message("HOGE", Lang::ja); + assert_eq!(undef_ja, "未設定"); + let undef_en = error_message.return_error_message("HOGE", Lang::en); + assert_eq!(undef_en, "Undefined"); +} From 5b47ba397dc1f4b44ecd478287d6fff142a11b30 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 22 Oct 2020 18:47:59 +0900 Subject: [PATCH 05/20] Solve threads --- src/detections/print.rs | 52 +++++++++++++++++++---------------------- 1 file changed, 24 insertions(+), 28 deletions(-) diff --git a/src/detections/print.rs b/src/detections/print.rs index 6f131ee5..64b40923 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -2,77 +2,73 @@ use std::collections::HashMap; #[derive(Debug)] pub enum Lang { - ja, - en, + Ja, + En, } #[derive(Debug)] -pub struct MessageLanguages { +pub struct MessageText { ja: String, en: String, } #[derive(Debug)] -pub struct ErrorMessage { - map: HashMap, +pub struct Message { + map: HashMap, } -impl ErrorMessage { +impl Message { pub fn new() -> Self { - let mut messages: HashMap = HashMap::new(); + let mut messages: HashMap = HashMap::new(); messages.insert( "undefined".to_string(), - MessageLanguages { + MessageText { ja: "未設定".to_string(), en: "Undefined".to_string(), }, ); - ErrorMessage { map: messages } + Message { map: messages } } - /// エラーメッセージを設定 - pub fn insert_rule(&mut self, error_code: String, message: MessageLanguages) { + /// メッセージを設定 + pub fn insert_message(&mut self, error_code: String, message: MessageText) { self.map.insert(error_code, message); } - /// エラーメッセージを指定された言語で返す + /// メッセージを指定された言語で返す pub fn return_error_message(&self, error_num: &str, lang: Lang) -> String { - let messages = if let Some(boxed_message) = self.map.get(error_num) { - boxed_message - } else { - self.map.get("undefined").unwrap() - }; + let messages = self.map.get(error_num).unwrap_or(self.map.get("undefined").unwrap()); match lang { - Lang::ja => messages.ja.clone(), - Lang::en => messages.en.clone(), + Lang::Ja => messages.ja.clone(), + Lang::En => messages.en.clone(), } } } #[test] fn test_create_error_message() { - let mut error_message = ErrorMessage::new(); + let mut error_message = Message::new(); - error_message.insert_rule( + error_message.insert_message( "4103".to_string(), - MessageLanguages { + MessageText { ja: "パイプライン実行をしています".to_string(), en: "Execute pipeline".to_string(), }, ); - let message_ja1 = error_message.return_error_message("4103", Lang::ja); + let message_ja1 = error_message.return_error_message("4103", Lang::Ja); assert_eq!(message_ja1, "パイプライン実行をしています"); - let message_ja2 = error_message.return_error_message("4103", Lang::ja); + let message_ja2 = error_message.return_error_message("4103", Lang::Ja); assert_eq!(message_ja2, "パイプライン実行をしています"); - let message_en1 = error_message.return_error_message("4103", Lang::en); + let message_en1 = error_message.return_error_message("4103", Lang::En); assert_eq!(message_en1, "Execute pipeline"); - let message_en2 = error_message.return_error_message("4103", Lang::en); + let message_en2 = error_message.return_error_message("4103", Lang::En); assert_eq!(message_en2, "Execute pipeline"); - let undef_ja = error_message.return_error_message("HOGE", Lang::ja); + let undef_ja = error_message.return_error_message("HOGE", Lang::Ja); assert_eq!(undef_ja, "未設定"); - let undef_en = error_message.return_error_message("HOGE", Lang::en); + let undef_en = error_message.return_error_message("HOGE", Lang::En); assert_eq!(undef_en, "Undefined"); } From 8e84535e7bfa241d84595b56f53b662efb697dd9 Mon Sep 17 00:00:00 2001 From: itiB Date: Sun, 25 Oct 2020 12:11:55 +0900 Subject: [PATCH 06/20] WIP: collect args to singleton --- src/detections/configs.rs | 36 +++++++++++++++++++++++++++++++++++- src/detections/mod.rs | 2 +- src/main.rs | 5 ++++- 3 files changed, 40 insertions(+), 3 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index 1862e2d4..86019b44 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -1,22 +1,49 @@ use std::fs::File; use std::io::prelude::*; use std::sync::Once; +use clap::ArgMatches; #[derive(Clone)] pub struct SingletonReader { pub regex: Vec>, pub whitelist: Vec>, + pub args: Config<'static>, } -pub fn singleton() -> Box { +#[derive(Debug, Clone)] +pub struct Config<'a> { + pub filepath: Option<&'a str>, + pub attackhunt: Option<&'a str>, + pub csv_timeline: Option<&'a str>, + pub human_readable_timeline: Option<&'a str>, + pub lang: Option<&'a str>, + pub timezone: Option<&'a str>, +} + +impl<'a> Config<'a> { + fn new(args: ArgMatches<'a>) -> Self { + Config { + filepath: args.value_of("filepath"), + attackhunt: args.value_of("attackhunt"), + csv_timeline: args.value_of("csv-timeline"), + human_readable_timeline: args.value_of("human-readable-timeline"), + lang: args.value_of("lang"), + timezone: args.value_of("timezone"), + } + } +} + +pub fn init_singleton(args: ArgMatches<'static>) -> Box { static mut SINGLETON: Option> = Option::None; static ONCE: Once = Once::new(); + static CONFIG: Config = Config::new(args); unsafe { ONCE.call_once(|| { let singleton = SingletonReader { regex: read_csv("regexes.txt"), whitelist: read_csv("whitelist.txt"), + args: CONFIG, }; SINGLETON = Some(Box::new(singleton)); @@ -26,6 +53,13 @@ pub fn singleton() -> Box { } } +pub fn singleton() -> Box { + static mut SINGLETON: Option> = Option::None; + unsafe { + return SINGLETON.clone().unwrap(); + } +} + fn read_csv(filename: &str) -> Vec> { let mut f = File::open(filename).expect("file not found!!!"); let mut contents: String = String::new(); diff --git a/src/detections/mod.rs b/src/detections/mod.rs index d1996a94..30eac958 100644 --- a/src/detections/mod.rs +++ b/src/detections/mod.rs @@ -1,7 +1,7 @@ mod application; mod applocker; mod common; -mod configs; +pub mod configs; pub mod detection; mod powershell; mod print; diff --git a/src/main.rs b/src/main.rs index fe8ffba4..b4ea6830 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,6 +5,7 @@ use clap::{App, AppSettings, Arg}; use evtx::EvtxParser; use quick_xml::de::DeError; use std::{fs, path::PathBuf, process}; +use yamato_event_analyzer::detections::configs; use yamato_event_analyzer::detections::detection; use yamato_event_analyzer::omikuji::Omikuji; use yamato_event_analyzer::toml; @@ -39,7 +40,9 @@ fn build_app() -> clap::App<'static, 'static> { fn main() -> Result<(), DeError> { let args = build_app().get_matches(); - let filepath: Option<&str> = args.value_of("filepath"); + configs::init_singleton(&args); + + let filepath: Option<&str> = configs::singleton().args.filepath; if let Some(filepath) = filepath { parse_file(filepath); From c53b4b6f469ce5db82f8bff4babc1f443aec73ca Mon Sep 17 00:00:00 2001 From: itiB Date: Mon, 26 Oct 2020 00:26:54 +0900 Subject: [PATCH 07/20] feat: switch lang from args --- src/detections/configs.rs | 74 +++++++++++++++++++++++---------------- src/detections/mod.rs | 2 +- src/detections/print.rs | 48 +++++++++++-------------- src/main.rs | 45 +++++------------------- 4 files changed, 73 insertions(+), 96 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index 86019b44..cbd02fe4 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -1,49 +1,30 @@ +use clap::{App, AppSettings, Arg, ArgMatches}; use std::fs::File; use std::io::prelude::*; use std::sync::Once; -use clap::ArgMatches; #[derive(Clone)] pub struct SingletonReader { pub regex: Vec>, pub whitelist: Vec>, - pub args: Config<'static>, + pub args: ArgMatches<'static>, } -#[derive(Debug, Clone)] -pub struct Config<'a> { - pub filepath: Option<&'a str>, - pub attackhunt: Option<&'a str>, - pub csv_timeline: Option<&'a str>, - pub human_readable_timeline: Option<&'a str>, - pub lang: Option<&'a str>, - pub timezone: Option<&'a str>, +pub enum Lang { + Ja, + En, } -impl<'a> Config<'a> { - fn new(args: ArgMatches<'a>) -> Self { - Config { - filepath: args.value_of("filepath"), - attackhunt: args.value_of("attackhunt"), - csv_timeline: args.value_of("csv-timeline"), - human_readable_timeline: args.value_of("human-readable-timeline"), - lang: args.value_of("lang"), - timezone: args.value_of("timezone"), - } - } -} - -pub fn init_singleton(args: ArgMatches<'static>) -> Box { +pub fn singleton() -> Box { static mut SINGLETON: Option> = Option::None; static ONCE: Once = Once::new(); - static CONFIG: Config = Config::new(args); unsafe { ONCE.call_once(|| { let singleton = SingletonReader { regex: read_csv("regexes.txt"), whitelist: read_csv("whitelist.txt"), - args: CONFIG, + args: build_app().get_matches(), }; SINGLETON = Some(Box::new(singleton)); @@ -53,11 +34,31 @@ pub fn init_singleton(args: ArgMatches<'static>) -> Box { } } -pub fn singleton() -> Box { - static mut SINGLETON: Option> = Option::None; - unsafe { - return SINGLETON.clone().unwrap(); - } +fn build_app() -> clap::App<'static, 'static> { + let program = std::env::args() + .nth(0) + .and_then(|s| { + std::path::PathBuf::from(s) + .file_stem() + .map(|s| s.to_string_lossy().into_owned()) + }) + .unwrap(); + + App::new(program) + .about("Yea! (Yamato Event Analyzer). Aiming to be the world's greatest Windows event log analysis tool!") + .version("0.0.1") + .author("Author name ") + .setting(AppSettings::VersionlessSubcommands) + .arg(Arg::from_usage("-f --filepath=[FILEPATH] 'event file path'")) + .arg(Arg::from_usage("--attackhunt=[ATTACK_HUNT] 'Attack Hunt'")) + .arg(Arg::from_usage("--csv-timeline=[CSV_TIMELINE] 'csv output timeline'")) + .arg(Arg::from_usage("--human-readable-timeline=[HUMAN_READABLE_TIMELINE] 'human readable timeline'")) + .arg(Arg::from_usage("-l --lang=[LANG] 'output language'")) + .arg(Arg::from_usage("-t --timezone=[TIMEZONE] 'timezone setting'")) + .arg(Arg::from_usage("-d --directory 'event log files directory'")) + .arg(Arg::from_usage("-s --statistics 'event statistics'")) + .arg(Arg::from_usage("-u --update 'signature update'")) + .arg(Arg::from_usage("--credits 'Zachary Mathis, Akira Nishikawa'")) } fn read_csv(filename: &str) -> Vec> { @@ -82,3 +83,14 @@ fn read_csv(filename: &str) -> Vec> { return ret; } + +/// Argsから言語情報を読み取り Lang を返す +pub fn get_lang() -> Lang { + let lang: String = singleton().args.value_of("lang").unwrap_or("").to_string(); + + match &*lang { + "Ja" | "ja" => Lang::Ja, + "En" | "en" => Lang::En, + _ => Lang::En, + } +} diff --git a/src/detections/mod.rs b/src/detections/mod.rs index 30eac958..4aaee9ff 100644 --- a/src/detections/mod.rs +++ b/src/detections/mod.rs @@ -4,7 +4,7 @@ mod common; pub mod configs; pub mod detection; mod powershell; -mod print; +pub mod print; mod security; mod sysmon; mod system; diff --git a/src/detections/print.rs b/src/detections/print.rs index 64b40923..c950f9a5 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,15 +1,11 @@ +use crate::detections::configs::{get_lang, Lang}; use std::collections::HashMap; - -#[derive(Debug)] -pub enum Lang { - Ja, - En, -} +use std::fmt; #[derive(Debug)] pub struct MessageText { - ja: String, - en: String, + pub ja: String, + pub en: String, } #[derive(Debug)] @@ -35,18 +31,25 @@ impl Message { self.map.insert(error_code, message); } - /// メッセージを指定された言語で返す - pub fn return_error_message(&self, error_num: &str, lang: Lang) -> String { - let messages = self.map.get(error_num).unwrap_or(self.map.get("undefined").unwrap()); - match lang { - Lang::Ja => messages.ja.clone(), - Lang::En => messages.en.clone(), + /// メッセージを返す + pub fn return_message(&self, message_num: &str) -> &MessageText { + self.map.get(message_num).unwrap_or(self.map.get("undefined").unwrap()) + } +} + +/// メッセージテキストを言語設定に合わせて返す +/// println!("{}", ) とすると今の言語設定で出力される +impl fmt::Display for MessageText { + fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { + match get_lang() { + Lang::Ja => write!(f, "{}", self.ja), + Lang::En => write!(f, "{}", self.en), } } } #[test] -fn test_create_error_message() { +fn test_create_and_read_message() { let mut error_message = Message::new(); error_message.insert_message( @@ -57,18 +60,7 @@ fn test_create_error_message() { }, ); - let message_ja1 = error_message.return_error_message("4103", Lang::Ja); - assert_eq!(message_ja1, "パイプライン実行をしています"); - let message_ja2 = error_message.return_error_message("4103", Lang::Ja); - assert_eq!(message_ja2, "パイプライン実行をしています"); + let display = format!("{}", format_args!("{}", error_message.return_message("4103"))); - let message_en1 = error_message.return_error_message("4103", Lang::En); - assert_eq!(message_en1, "Execute pipeline"); - let message_en2 = error_message.return_error_message("4103", Lang::En); - assert_eq!(message_en2, "Execute pipeline"); - - let undef_ja = error_message.return_error_message("HOGE", Lang::Ja); - assert_eq!(undef_ja, "未設定"); - let undef_en = error_message.return_error_message("HOGE", Lang::En); - assert_eq!(undef_en, "Undefined"); + assert_eq!(display, "Execute pipeline") } diff --git a/src/main.rs b/src/main.rs index b4ea6830..79a27530 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,51 +1,24 @@ -extern crate clap; extern crate serde; -use clap::{App, AppSettings, Arg}; use evtx::EvtxParser; use quick_xml::de::DeError; use std::{fs, path::PathBuf, process}; use yamato_event_analyzer::detections::configs; use yamato_event_analyzer::detections::detection; +use yamato_event_analyzer::detections::print; use yamato_event_analyzer::omikuji::Omikuji; use yamato_event_analyzer::toml; -fn build_app() -> clap::App<'static, 'static> { - let program = std::env::args() - .nth(0) - .and_then(|s| { - std::path::PathBuf::from(s) - .file_stem() - .map(|s| s.to_string_lossy().into_owned()) - }) - .unwrap(); - - App::new(program) - .about("Yea! (Yamato Event Analyzer). Aiming to be the world's greatest Windows event log analysis tool!") - .version("0.0.1") - .author("Author name ") - .setting(AppSettings::VersionlessSubcommands) - .arg(Arg::from_usage("-f --filepath=[FILEPATH] 'event file path'")) - .arg(Arg::from_usage("--attackhunt=[ATTACK_HUNT] 'Attack Hunt'")) - .arg(Arg::from_usage("--csv-timeline=[CSV_TIMELINE] 'csv output timeline'")) - .arg(Arg::from_usage("--human-readable-timeline=[HUMAN_READABLE_TIMELINE] 'human readable timeline'")) - .arg(Arg::from_usage("-l --lang=[LANG] 'output language'")) - .arg(Arg::from_usage("-t --timezone=[TIMEZONE] 'timezone setting'")) - .arg(Arg::from_usage("-d --directory 'event log files directory'")) - .arg(Arg::from_usage("-s --statistics 'event statistics'")) - .arg(Arg::from_usage("-u --update 'signature update'")) - .arg(Arg::from_usage("-o --omikuji 'output with omikuji'")) - .arg(Arg::from_usage("--credits 'Zachary Mathis, Akira Nishikawa'")) -} - fn main() -> Result<(), DeError> { - let args = build_app().get_matches(); - configs::init_singleton(&args); + configs::singleton(); - let filepath: Option<&str> = configs::singleton().args.filepath; - - if let Some(filepath) = filepath { - parse_file(filepath); + let filepath: String = configs::singleton() + .args + .value_of("filepath") + .unwrap_or("") + .to_string(); + if filepath != "" { + parse_file(&filepath); } Ok(()) From 1d8a9c19d2ff698fb2134a382db8715b81235abe Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 29 Oct 2020 23:00:55 +0900 Subject: [PATCH 08/20] Update: read messages from rules/**.toml --- Cargo.lock | 1 + Cargo.toml | 1 + .../powershell/powershell4103.toml | 6 +++++ .../powershell/powershell4104.toml | 6 +++++ src/detections/powershell.rs | 9 +++++++- src/detections/print.rs | 23 ++++++++++++------- src/main.rs | 18 ++++++++++++++- src/models/rule.rs | 7 ++++++ 8 files changed, 61 insertions(+), 10 deletions(-) create mode 100644 rules/deep_blue_cli/powershell/powershell4103.toml create mode 100644 rules/deep_blue_cli/powershell/powershell4104.toml diff --git a/Cargo.lock b/Cargo.lock index ab932e6f..990cbd86 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1191,6 +1191,7 @@ dependencies = [ "csv", "evtx", "flate2", + "lazy_static", "quick-xml 0.17.2", "regex", "serde", diff --git a/Cargo.toml b/Cargo.toml index b28772bf..435c9cf2 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -18,3 +18,4 @@ csv = "1.1" base64 = "*" flate2 = "1.0" toml = "0.5" +lazy_static = "1.4.0" diff --git a/rules/deep_blue_cli/powershell/powershell4103.toml b/rules/deep_blue_cli/powershell/powershell4103.toml new file mode 100644 index 00000000..dcd22977 --- /dev/null +++ b/rules/deep_blue_cli/powershell/powershell4103.toml @@ -0,0 +1,6 @@ +[rule] +severity = "high" +name = "4103" +messages = [ + ["4103", { ja = "パイプライン実行をしています", en = "Execute Pipeline" }] +] \ No newline at end of file diff --git a/rules/deep_blue_cli/powershell/powershell4104.toml b/rules/deep_blue_cli/powershell/powershell4104.toml new file mode 100644 index 00000000..83bba2ce --- /dev/null +++ b/rules/deep_blue_cli/powershell/powershell4104.toml @@ -0,0 +1,6 @@ +[rule] +severity = "high" +name = "4104" +messages = [ + ["4104", { ja = "リモートコマンドを実行します", en = "Excute Remote Command" }] +] \ No newline at end of file diff --git a/src/detections/powershell.rs b/src/detections/powershell.rs index c628a011..e9bfc05e 100644 --- a/src/detections/powershell.rs +++ b/src/detections/powershell.rs @@ -1,8 +1,8 @@ use crate::detections::utils; use crate::models::event; +use crate::detections::print::MESSAGES; use regex::Regex; use std::collections::HashMap; -extern crate csv; pub struct PowerShell {} @@ -25,6 +25,10 @@ impl PowerShell { if event_id != "4103" { return; } + + let message = MESSAGES.lock().unwrap(); + println!("{}", message.return_message("4103")); + let default = String::from(""); let commandline = event_data.get("ContextInfo").unwrap_or(&default); @@ -48,6 +52,9 @@ impl PowerShell { if event_id != "4104" { return; } + let message = MESSAGES.lock().unwrap(); + println!("{}", message.return_message("4104")); + let default = String::from(""); let path = event_data.get("Path").unwrap().to_string(); if path == "".to_string() { diff --git a/src/detections/print.rs b/src/detections/print.rs index c950f9a5..3fb83fbe 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,18 +1,20 @@ +extern crate lazy_static; use crate::detections::configs::{get_lang, Lang}; use std::collections::HashMap; +use crate::models::rule::MessageText; +use lazy_static::lazy_static; use std::fmt; - -#[derive(Debug)] -pub struct MessageText { - pub ja: String, - pub en: String, -} +use std::sync::Mutex; #[derive(Debug)] pub struct Message { map: HashMap, } +lazy_static! { + pub static ref MESSAGES: Mutex = Mutex::new(Message::new()); +} + impl Message { pub fn new() -> Self { let mut messages: HashMap = HashMap::new(); @@ -33,7 +35,9 @@ impl Message { /// メッセージを返す pub fn return_message(&self, message_num: &str) -> &MessageText { - self.map.get(message_num).unwrap_or(self.map.get("undefined").unwrap()) + self.map + .get(message_num) + .unwrap_or(self.map.get("undefined").unwrap()) } } @@ -60,7 +64,10 @@ fn test_create_and_read_message() { }, ); - let display = format!("{}", format_args!("{}", error_message.return_message("4103"))); + let display = format!( + "{}", + format_args!("{}", error_message.return_message("4103")) + ); assert_eq!(display, "Execute pipeline") } diff --git a/src/main.rs b/src/main.rs index 79a27530..84325960 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,12 +5,28 @@ use quick_xml::de::DeError; use std::{fs, path::PathBuf, process}; use yamato_event_analyzer::detections::configs; use yamato_event_analyzer::detections::detection; -use yamato_event_analyzer::detections::print; +use yamato_event_analyzer::detections::print::MESSAGES; use yamato_event_analyzer::omikuji::Omikuji; use yamato_event_analyzer::toml; fn main() -> Result<(), DeError> { configs::singleton(); + let mut toml = toml::ParseToml::new(); + &toml.read_dir("rules".to_string()); + + for rule in toml.rules { + match rule { + Ok(_rule) => { + let mut message = MESSAGES.lock().unwrap(); + if let Some(messages) = _rule.rule.messages { + for (key, texts) in messages { + message.insert_message(key, texts); + } + } + } + Err(_) => (), + } + } let filepath: String = configs::singleton() .args diff --git a/src/models/rule.rs b/src/models/rule.rs index 550bdc65..66f77e4a 100644 --- a/src/models/rule.rs +++ b/src/models/rule.rs @@ -5,6 +5,13 @@ use serde::Deserialize; pub struct Rule { pub severity: Option, pub name: Option, + pub messages: Option>, +} + +#[derive(Debug, Deserialize)] +pub struct MessageText { + pub ja: String, + pub en: String, } #[derive(Debug, Deserialize)] From 352ad7bb0945d96e6af9e00323a58302a14786b8 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 29 Oct 2020 23:02:37 +0900 Subject: [PATCH 09/20] cargo fmt --all --- src/detections/powershell.rs | 2 +- src/detections/print.rs | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/detections/powershell.rs b/src/detections/powershell.rs index e9bfc05e..74cef1a6 100644 --- a/src/detections/powershell.rs +++ b/src/detections/powershell.rs @@ -1,6 +1,6 @@ +use crate::detections::print::MESSAGES; use crate::detections::utils; use crate::models::event; -use crate::detections::print::MESSAGES; use regex::Regex; use std::collections::HashMap; diff --git a/src/detections/print.rs b/src/detections/print.rs index 3fb83fbe..c796c41c 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,8 +1,8 @@ extern crate lazy_static; use crate::detections::configs::{get_lang, Lang}; -use std::collections::HashMap; use crate::models::rule::MessageText; use lazy_static::lazy_static; +use std::collections::HashMap; use std::fmt; use std::sync::Mutex; From 96e379cc52c85a8fbe3905cba5dbebd33f1df1a9 Mon Sep 17 00:00:00 2001 From: itiB Date: Sat, 31 Oct 2020 20:25:22 +0900 Subject: [PATCH 10/20] solve threads... --- src/detections/configs.rs | 11 ----------- src/detections/powershell.rs | 4 ++-- src/detections/print.rs | 24 ++++++++++++++++-------- src/main.rs | 2 +- 4 files changed, 19 insertions(+), 22 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index cbd02fe4..ab5dc0c7 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -83,14 +83,3 @@ fn read_csv(filename: &str) -> Vec> { return ret; } - -/// Argsから言語情報を読み取り Lang を返す -pub fn get_lang() -> Lang { - let lang: String = singleton().args.value_of("lang").unwrap_or("").to_string(); - - match &*lang { - "Ja" | "ja" => Lang::Ja, - "En" | "en" => Lang::En, - _ => Lang::En, - } -} diff --git a/src/detections/powershell.rs b/src/detections/powershell.rs index 74cef1a6..9a4a8c5d 100644 --- a/src/detections/powershell.rs +++ b/src/detections/powershell.rs @@ -27,7 +27,7 @@ impl PowerShell { } let message = MESSAGES.lock().unwrap(); - println!("{}", message.return_message("4103")); + println!("{}", message.get("4103")); let default = String::from(""); let commandline = event_data.get("ContextInfo").unwrap_or(&default); @@ -53,7 +53,7 @@ impl PowerShell { return; } let message = MESSAGES.lock().unwrap(); - println!("{}", message.return_message("4104")); + println!("{}", message.get("4104")); let default = String::from(""); let path = event_data.get("Path").unwrap().to_string(); diff --git a/src/detections/print.rs b/src/detections/print.rs index c796c41c..c91adb26 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,5 +1,5 @@ extern crate lazy_static; -use crate::detections::configs::{get_lang, Lang}; +use crate::detections::configs::{singleton, Lang}; use crate::models::rule::MessageText; use lazy_static::lazy_static; use std::collections::HashMap; @@ -29,12 +29,12 @@ impl Message { } /// メッセージを設定 - pub fn insert_message(&mut self, error_code: String, message: MessageText) { + pub fn insert(&mut self, error_code: String, message: MessageText) { self.map.insert(error_code, message); } /// メッセージを返す - pub fn return_message(&self, message_num: &str) -> &MessageText { + pub fn get(&self, message_num: &str) -> &MessageText { self.map .get(message_num) .unwrap_or(self.map.get("undefined").unwrap()) @@ -52,11 +52,22 @@ impl fmt::Display for MessageText { } } +/// Argsから言語情報を読み取り Lang を返す +pub fn get_lang() -> Lang { + let lang: String = singleton().args.value_of("lang").unwrap_or("").to_string(); + + match &*lang { + "Ja" | "ja" => Lang::Ja, + "En" | "en" => Lang::En, + _ => Lang::En, + } +} + #[test] fn test_create_and_read_message() { let mut error_message = Message::new(); - error_message.insert_message( + error_message.insert( "4103".to_string(), MessageText { ja: "パイプライン実行をしています".to_string(), @@ -64,10 +75,7 @@ fn test_create_and_read_message() { }, ); - let display = format!( - "{}", - format_args!("{}", error_message.return_message("4103")) - ); + let display = format!("{}", format_args!("{}", error_message.get("4103"))); assert_eq!(display, "Execute pipeline") } diff --git a/src/main.rs b/src/main.rs index 84325960..46327208 100644 --- a/src/main.rs +++ b/src/main.rs @@ -20,7 +20,7 @@ fn main() -> Result<(), DeError> { let mut message = MESSAGES.lock().unwrap(); if let Some(messages) = _rule.rule.messages { for (key, texts) in messages { - message.insert_message(key, texts); + message.insert(key, texts); } } } From 0f6d53582e88be6a6f04f363aa064161ad84bb3f Mon Sep 17 00:00:00 2001 From: itiB Date: Sat, 31 Oct 2020 20:51:28 +0900 Subject: [PATCH 11/20] Add: Message.print() --- src/detections/print.rs | 5 +++++ 1 file changed, 5 insertions(+) diff --git a/src/detections/print.rs b/src/detections/print.rs index c91adb26..d83480f3 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -39,6 +39,11 @@ impl Message { .get(message_num) .unwrap_or(self.map.get("undefined").unwrap()) } + + /// MessageMaoのなかに入っているメッセージすべてを表示する + pub fn print(&self) { + println!("{:?}", self.map); + } } /// メッセージテキストを言語設定に合わせて返す From b42ab6a0d538e07aab73660f8e54054b759496d5 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 04:18:44 +0900 Subject: [PATCH 12/20] Update: Collect result message to print.rs-Message --- Cargo.lock | 7 ++-- Cargo.toml | 1 + src/detections/powershell.rs | 6 ---- src/detections/print.rs | 62 +++++++++++++++++++----------------- 4 files changed, 38 insertions(+), 38 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 990cbd86..b2f1632f 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -139,14 +139,16 @@ checksum = "4785bdd1c96b2a846b2bd7cc02e86b6b3dbf14e7e53446c4f54c92a361040822" [[package]] name = "chrono" -version = "0.4.15" +version = "0.4.19" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "942f72db697d8767c22d46a598e01f2d3b475501ea43d0db4f16d90259182d0b" +checksum = "670ad68c9088c2a963aaa298cb369688cf3f9465ce5e2d4ca10e6e0098a1ce73" dependencies = [ + "libc", "num-integer", "num-traits", "serde", "time", + "winapi", ] [[package]] @@ -1187,6 +1189,7 @@ name = "yamato_event_analyzer" version = "0.1.0" dependencies = [ "base64", + "chrono", "clap", "csv", "evtx", diff --git a/Cargo.toml b/Cargo.toml index 435c9cf2..06fbd18d 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -19,3 +19,4 @@ base64 = "*" flate2 = "1.0" toml = "0.5" lazy_static = "1.4.0" +chrono = "0.4.19" diff --git a/src/detections/powershell.rs b/src/detections/powershell.rs index 9a4a8c5d..4fa956b0 100644 --- a/src/detections/powershell.rs +++ b/src/detections/powershell.rs @@ -1,4 +1,3 @@ -use crate::detections::print::MESSAGES; use crate::detections::utils; use crate::models::event; use regex::Regex; @@ -26,9 +25,6 @@ impl PowerShell { return; } - let message = MESSAGES.lock().unwrap(); - println!("{}", message.get("4103")); - let default = String::from(""); let commandline = event_data.get("ContextInfo").unwrap_or(&default); @@ -52,8 +48,6 @@ impl PowerShell { if event_id != "4104" { return; } - let message = MESSAGES.lock().unwrap(); - println!("{}", message.get("4104")); let default = String::from(""); let path = event_data.get("Path").unwrap().to_string(); diff --git a/src/detections/print.rs b/src/detections/print.rs index d83480f3..fb8a34c8 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,14 +1,16 @@ +extern crate chrono; extern crate lazy_static; use crate::detections::configs::{singleton, Lang}; -use crate::models::rule::MessageText; +use chrono::prelude::*; +use chrono::{DateTime, Utc}; use lazy_static::lazy_static; -use std::collections::HashMap; +use std::collections::BTreeMap; use std::fmt; use std::sync::Mutex; #[derive(Debug)] pub struct Message { - map: HashMap, + map: BTreeMap, Vec>, } lazy_static! { @@ -17,31 +19,33 @@ lazy_static! { impl Message { pub fn new() -> Self { - let mut messages: HashMap = HashMap::new(); - messages.insert( - "undefined".to_string(), - MessageText { - ja: "未設定".to_string(), - en: "Undefined".to_string(), - }, - ); + let mut messages: BTreeMap, Vec> = BTreeMap::new(); Message { map: messages } } /// メッセージを設定 - pub fn insert(&mut self, error_code: String, message: MessageText) { - self.map.insert(error_code, message); + pub fn insert(&mut self, time: DateTime, message: String) { + match self.map.get_mut(&time) { + Some(v) => { + v.push(message.to_string()); + } + None => { + let m = vec![message.to_string(); 1]; + self.map.insert(time, m); + } + } } /// メッセージを返す - pub fn get(&self, message_num: &str) -> &MessageText { - self.map - .get(message_num) - .unwrap_or(self.map.get("undefined").unwrap()) + pub fn get(&self, time: DateTime) -> Vec { + match self.map.get(&time) { + Some(v) => (&v).to_vec(), + None => Vec::new(), + } } /// MessageMaoのなかに入っているメッセージすべてを表示する - pub fn print(&self) { + pub fn debug(&self) { println!("{:?}", self.map); } } @@ -69,18 +73,16 @@ pub fn get_lang() -> Lang { } #[test] -fn test_create_and_read_message() { - let mut error_message = Message::new(); +fn test_create_and_append_message() { + let mut message = Message::new(); + let poke = Utc.ymd(1996, 2, 27).and_hms(1, 5, 1); + let taka = Utc.ymd(2000, 1, 21).and_hms(9, 6, 1); - error_message.insert( - "4103".to_string(), - MessageText { - ja: "パイプライン実行をしています".to_string(), - en: "Execute pipeline".to_string(), - }, - ); + message.insert(poke, "TEST".to_string()); + message.insert(poke, "TEST2".to_string()); + message.insert(taka, "TEST3".to_string()); - let display = format!("{}", format_args!("{}", error_message.get("4103"))); - - assert_eq!(display, "Execute pipeline") + let display = format!("{}", format_args!("{:?}", message)); + let expect = "Message { map: {1996-02-27T01:05:01Z: [\"TEST\", \"TEST2\"], 2000-01-21T09:06:01Z: [\"TEST3\"]} }"; + assert_eq!(display, expect); } From e8c0ec44f81f4d40ebcaa74890220d47716eede4 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 04:19:44 +0900 Subject: [PATCH 13/20] rm: unnecessary MessageText struct --- src/detections/print.rs | 11 ----------- src/main.rs | 15 --------------- src/models/rule.rs | 8 +------- 3 files changed, 1 insertion(+), 33 deletions(-) diff --git a/src/detections/print.rs b/src/detections/print.rs index fb8a34c8..2850f0ef 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -50,17 +50,6 @@ impl Message { } } -/// メッセージテキストを言語設定に合わせて返す -/// println!("{}", ) とすると今の言語設定で出力される -impl fmt::Display for MessageText { - fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result { - match get_lang() { - Lang::Ja => write!(f, "{}", self.ja), - Lang::En => write!(f, "{}", self.en), - } - } -} - /// Argsから言語情報を読み取り Lang を返す pub fn get_lang() -> Lang { let lang: String = singleton().args.value_of("lang").unwrap_or("").to_string(); diff --git a/src/main.rs b/src/main.rs index 46327208..5eb2d00e 100644 --- a/src/main.rs +++ b/src/main.rs @@ -5,7 +5,6 @@ use quick_xml::de::DeError; use std::{fs, path::PathBuf, process}; use yamato_event_analyzer::detections::configs; use yamato_event_analyzer::detections::detection; -use yamato_event_analyzer::detections::print::MESSAGES; use yamato_event_analyzer::omikuji::Omikuji; use yamato_event_analyzer::toml; @@ -14,20 +13,6 @@ fn main() -> Result<(), DeError> { let mut toml = toml::ParseToml::new(); &toml.read_dir("rules".to_string()); - for rule in toml.rules { - match rule { - Ok(_rule) => { - let mut message = MESSAGES.lock().unwrap(); - if let Some(messages) = _rule.rule.messages { - for (key, texts) in messages { - message.insert(key, texts); - } - } - } - Err(_) => (), - } - } - let filepath: String = configs::singleton() .args .value_of("filepath") diff --git a/src/models/rule.rs b/src/models/rule.rs index 66f77e4a..54fc41de 100644 --- a/src/models/rule.rs +++ b/src/models/rule.rs @@ -5,13 +5,7 @@ use serde::Deserialize; pub struct Rule { pub severity: Option, pub name: Option, - pub messages: Option>, -} - -#[derive(Debug, Deserialize)] -pub struct MessageText { - pub ja: String, - pub en: String, + pub messages: Option>, } #[derive(Debug, Deserialize)] From 66f088627392ceb08bbf5d7dee797743c26e354a Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 14:28:01 +0900 Subject: [PATCH 14/20] Solve warnings --- src/detections/print.rs | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-) diff --git a/src/detections/print.rs b/src/detections/print.rs index 2850f0ef..670a6f7c 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,11 +1,9 @@ extern crate chrono; extern crate lazy_static; use crate::detections::configs::{singleton, Lang}; -use chrono::prelude::*; -use chrono::{DateTime, Utc}; +use chrono::{DateTime, TimeZone, Utc}; use lazy_static::lazy_static; use std::collections::BTreeMap; -use std::fmt; use std::sync::Mutex; #[derive(Debug)] @@ -19,7 +17,7 @@ lazy_static! { impl Message { pub fn new() -> Self { - let mut messages: BTreeMap, Vec> = BTreeMap::new(); + let messages: BTreeMap, Vec> = BTreeMap::new(); Message { map: messages } } From 77df2fcc9c3ac4206501c3f9091fc1d470d6fe30 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 14:29:48 +0900 Subject: [PATCH 15/20] Fix: only 1 message in 1 toml file --- rules/deep_blue_cli/powershell/powershell4103.toml | 4 +--- rules/deep_blue_cli/powershell/powershell4104.toml | 4 +--- src/models/rule.rs | 2 +- 3 files changed, 3 insertions(+), 7 deletions(-) diff --git a/rules/deep_blue_cli/powershell/powershell4103.toml b/rules/deep_blue_cli/powershell/powershell4103.toml index dcd22977..d70c52bf 100644 --- a/rules/deep_blue_cli/powershell/powershell4103.toml +++ b/rules/deep_blue_cli/powershell/powershell4103.toml @@ -1,6 +1,4 @@ [rule] severity = "high" name = "4103" -messages = [ - ["4103", { ja = "パイプライン実行をしています", en = "Execute Pipeline" }] -] \ No newline at end of file +message = "Execute Pipeline" \ No newline at end of file diff --git a/rules/deep_blue_cli/powershell/powershell4104.toml b/rules/deep_blue_cli/powershell/powershell4104.toml index 83bba2ce..a4262b86 100644 --- a/rules/deep_blue_cli/powershell/powershell4104.toml +++ b/rules/deep_blue_cli/powershell/powershell4104.toml @@ -1,6 +1,4 @@ [rule] severity = "high" name = "4104" -messages = [ - ["4104", { ja = "リモートコマンドを実行します", en = "Excute Remote Command" }] -] \ No newline at end of file +message = "Excute Remote Command" \ No newline at end of file diff --git a/src/models/rule.rs b/src/models/rule.rs index 54fc41de..fa1ca510 100644 --- a/src/models/rule.rs +++ b/src/models/rule.rs @@ -5,7 +5,7 @@ use serde::Deserialize; pub struct Rule { pub severity: Option, pub name: Option, - pub messages: Option>, + pub message: Option, } #[derive(Debug, Deserialize)] From 28d5731ef083a5ec344ab4238c15b4198bb39505 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 19:40:04 +0900 Subject: [PATCH 16/20] Update: store toml rules in config.rs - Singleton --- src/detections/configs.rs | 6 ++++++ src/detections/print.rs | 1 - src/main.rs | 3 --- src/models/rule.rs | 4 ++-- src/toml.rs | 1 + 5 files changed, 9 insertions(+), 6 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index ab5dc0c7..c59eff94 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -1,3 +1,4 @@ +use crate::toml; use clap::{App, AppSettings, Arg, ArgMatches}; use std::fs::File; use std::io::prelude::*; @@ -8,6 +9,7 @@ pub struct SingletonReader { pub regex: Vec>, pub whitelist: Vec>, pub args: ArgMatches<'static>, + pub rules: toml::ParseToml, } pub enum Lang { @@ -19,12 +21,16 @@ pub fn singleton() -> Box { static mut SINGLETON: Option> = Option::None; static ONCE: Once = Once::new(); + let mut toml = toml::ParseToml::new(); + &toml.read_dir("rules".to_string()); + unsafe { ONCE.call_once(|| { let singleton = SingletonReader { regex: read_csv("regexes.txt"), whitelist: read_csv("whitelist.txt"), args: build_app().get_matches(), + rules: toml, }; SINGLETON = Some(Box::new(singleton)); diff --git a/src/detections/print.rs b/src/detections/print.rs index 670a6f7c..ac12a1d1 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -1,6 +1,5 @@ extern crate chrono; extern crate lazy_static; -use crate::detections::configs::{singleton, Lang}; use chrono::{DateTime, TimeZone, Utc}; use lazy_static::lazy_static; use std::collections::BTreeMap; diff --git a/src/main.rs b/src/main.rs index 5eb2d00e..ffbce6e9 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,12 +6,9 @@ use std::{fs, path::PathBuf, process}; use yamato_event_analyzer::detections::configs; use yamato_event_analyzer::detections::detection; use yamato_event_analyzer::omikuji::Omikuji; -use yamato_event_analyzer::toml; fn main() -> Result<(), DeError> { configs::singleton(); - let mut toml = toml::ParseToml::new(); - &toml.read_dir("rules".to_string()); let filepath: String = configs::singleton() .args diff --git a/src/models/rule.rs b/src/models/rule.rs index fa1ca510..f385e596 100644 --- a/src/models/rule.rs +++ b/src/models/rule.rs @@ -1,14 +1,14 @@ extern crate serde; use serde::Deserialize; -#[derive(Debug, Deserialize)] +#[derive(Debug, Deserialize, Clone)] pub struct Rule { pub severity: Option, pub name: Option, pub message: Option, } -#[derive(Debug, Deserialize)] +#[derive(Debug, Deserialize, Clone)] pub struct Toml { pub rule: Rule, } diff --git a/src/toml.rs b/src/toml.rs index 08482f88..94cdfce3 100644 --- a/src/toml.rs +++ b/src/toml.rs @@ -7,6 +7,7 @@ use std::io; use std::io::{BufReader, Read}; use std::path::{Path, PathBuf}; +#[derive(Clone)] pub struct ParseToml { pub rules: Vec>, } From 820a9f2ebd9d5b815190cc7f12885a3ef611c405 Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 19:41:06 +0900 Subject: [PATCH 17/20] Fix: typo... --- src/detections/print.rs | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/detections/print.rs b/src/detections/print.rs index ac12a1d1..02a15a69 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -41,7 +41,7 @@ impl Message { } } - /// MessageMaoのなかに入っているメッセージすべてを表示する + /// Messageのなかに入っているメッセージすべてを表示する pub fn debug(&self) { println!("{:?}", self.map); } From 3d78f090238d153734d790297b36a157f44619de Mon Sep 17 00:00:00 2001 From: itiB Date: Thu, 5 Nov 2020 19:41:28 +0900 Subject: [PATCH 18/20] Rm: get_lang() --- src/detections/print.rs | 11 ----------- 1 file changed, 11 deletions(-) diff --git a/src/detections/print.rs b/src/detections/print.rs index 02a15a69..793737e4 100644 --- a/src/detections/print.rs +++ b/src/detections/print.rs @@ -47,17 +47,6 @@ impl Message { } } -/// Argsから言語情報を読み取り Lang を返す -pub fn get_lang() -> Lang { - let lang: String = singleton().args.value_of("lang").unwrap_or("").to_string(); - - match &*lang { - "Ja" | "ja" => Lang::Ja, - "En" | "en" => Lang::En, - _ => Lang::En, - } -} - #[test] fn test_create_and_append_message() { let mut message = Message::new(); From 3933d839ab262072df22d51eb79e32febf2dc984 Mon Sep 17 00:00:00 2001 From: itiB Date: Fri, 6 Nov 2020 14:46:34 +0900 Subject: [PATCH 19/20] rm: enum Lang & configs::singleton() call --- src/detections/configs.rs | 5 ----- src/main.rs | 2 -- 2 files changed, 7 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index c59eff94..7297ea20 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -12,11 +12,6 @@ pub struct SingletonReader { pub rules: toml::ParseToml, } -pub enum Lang { - Ja, - En, -} - pub fn singleton() -> Box { static mut SINGLETON: Option> = Option::None; static ONCE: Once = Once::new(); diff --git a/src/main.rs b/src/main.rs index ffbce6e9..c2e44c76 100644 --- a/src/main.rs +++ b/src/main.rs @@ -8,8 +8,6 @@ use yamato_event_analyzer::detections::detection; use yamato_event_analyzer::omikuji::Omikuji; fn main() -> Result<(), DeError> { - configs::singleton(); - let filepath: String = configs::singleton() .args .value_of("filepath") From edcadea9b003b4fbe2decda09a56490c8f4814fa Mon Sep 17 00:00:00 2001 From: itiB Date: Fri, 6 Nov 2020 20:55:42 +0900 Subject: [PATCH 20/20] Fix: read toml once by singleton --- src/detections/configs.rs | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/detections/configs.rs b/src/detections/configs.rs index 7297ea20..5572542b 100644 --- a/src/detections/configs.rs +++ b/src/detections/configs.rs @@ -16,11 +16,11 @@ pub fn singleton() -> Box { static mut SINGLETON: Option> = Option::None; static ONCE: Once = Once::new(); - let mut toml = toml::ParseToml::new(); - &toml.read_dir("rules".to_string()); - unsafe { ONCE.call_once(|| { + let mut toml = toml::ParseToml::new(); + &toml.read_dir("rules".to_string()); + let singleton = SingletonReader { regex: read_csv("regexes.txt"), whitelist: read_csv("whitelist.txt"),