95 lines
3.0 KiB
Rust
95 lines
3.0 KiB
Rust
pub use crate::message::*;
|
|
pub use crate::monitor::*;
|
|
use serde::Deserialize;
|
|
|
|
extern crate regex;
|
|
// use regex::Regex;
|
|
extern crate chrono;
|
|
// use chrono::Local;
|
|
|
|
#[derive(Debug)]
|
|
pub struct NmapScanner {
|
|
config: NmapScannerConfig,
|
|
}
|
|
#[derive(Debug, PartialEq, Deserialize)]
|
|
struct NmapScannerConfig {
|
|
#[serde(default)]
|
|
args: Vec<String>,
|
|
#[serde(default)]
|
|
ip_range: Option<String>,
|
|
#[serde(default)]
|
|
period: Option<f64>,
|
|
}
|
|
|
|
impl Monitor for NmapScanner {
|
|
fn new(config: serde_yaml::Value) -> Result<Self, Box<dyn std::error::Error>> {
|
|
let mut config: NmapScannerConfig = serde_yaml::from_value(config)?;
|
|
|
|
if config.ip_range.is_none() {
|
|
// Detect current subnet
|
|
|
|
config.ip_range = Some("192.168.0.1-254".to_owned());
|
|
}
|
|
|
|
// Regex compilation
|
|
// let rgx_lease = Regex::new(r"(?s)lease\s+(\d+(?:\.\d+){3})\s*\{\n?(.*?)\}").unwrap();
|
|
// let rgx_mac =
|
|
// Regex::new(r"(?m)^\s*hardware\s+ethernet\s([a-f0-9]{2}(?::[a-f0-9]{2}){5})\s*;")
|
|
// .unwrap();
|
|
// let rgx_date_start = Regex::new(r"(?m)^\s*starts\s+\d+\s+(.*?)\s*;").unwrap();
|
|
// let rgx_date_ends = Regex::new(r"(?m)^\s*ends\s+\d+\s+(.*?)\s*;").unwrap();
|
|
|
|
Ok(NmapScanner { config: config })
|
|
}
|
|
fn run(&mut self, sender: &mpsc::Sender<Message>) {
|
|
// ex: nmap -sV -T4 -O -F --version-light 192.168.0.1-254
|
|
use std::process::{Command, Stdio};
|
|
let res = Command::new("nmap")
|
|
.args(&self.config.args)
|
|
.arg(&self.config.ip_range.clone().unwrap())
|
|
.args(vec!["-oX", "-"])
|
|
.stderr(Stdio::inherit())
|
|
.output()
|
|
.expect("failed to execute process");
|
|
|
|
if res.status.success() {
|
|
let output = std::str::from_utf8(&res.stdout).expect("UTF-8 decoding error");
|
|
// println!("{}", output);
|
|
|
|
use serde_xml::value::{Content, Element};
|
|
let xml: Element = serde_xml::de::from_str(&output).expect("Bad XML format");
|
|
|
|
if let Content::Members(nodes) = xml.members {
|
|
if let Some(hosts) = nodes.get("host") {
|
|
for host_node in hosts {
|
|
if let Content::Members(host) = &host_node.members {
|
|
let address_nodes = host.get("address").unwrap();
|
|
let address = &address_nodes[0].attributes.get("addr").unwrap()[0];
|
|
let address_nodes = host.get("address").unwrap();
|
|
|
|
println!("address={:?}", address);
|
|
}
|
|
}
|
|
}
|
|
}
|
|
// println!("{:?}", );
|
|
}
|
|
|
|
std::thread::sleep(std::time::Duration::from_millis(
|
|
(self.config.period.unwrap_or(60.0) * 1000.0) as u64,
|
|
));
|
|
}
|
|
}
|
|
|
|
/*
|
|
|
|
lease 192.168.0.26 {
|
|
starts 4 2018/08/16 22:31:22;
|
|
ends 4 2018/08/16 23:01:22;
|
|
tstp 4 2018/08/16 23:01:22;
|
|
cltt 4 2018/08/16 22:31:22;
|
|
binding state free;
|
|
hardware ethernet 84:4b:f5:16:f4:94;
|
|
}
|
|
*/
|