diff --git a/src/linux.rs b/src/linux.rs index 0fdd410..6dd3342 100644 --- a/src/linux.rs +++ b/src/linux.rs @@ -1,5 +1,7 @@ #[cfg(target_os = "linux")] use std::collections::HashSet; +#[cfg(target_os = "linux")] +use std::fs; #[cfg(target_os = "linux")] use crate::errors::MIDError; @@ -9,15 +11,14 @@ use crate::utils::run_shell_command; #[cfg(target_os = "linux")] pub(crate) fn get_mid_result() -> Result { - let machine_output = run_shell_command( - "sh", - [ - "-c", - r#"hostnamectl status | awk '/Machine ID:/ {print $3}'; cat /var/lib/dbus/machine-id || true; cat /etc/machine-id || true"#, - ], - )?; + let hostnamectl_status = run_shell_command("hostnamectl", ["status"]) + .ok() + .and_then(parse_mid); + + let dbus_mid = fs::read_to_string("/var/lib/dbus/machine-id").ok(); + let etc_mid = fs::read_to_string("/etc/machine-id").ok(); - let combined_string = process_output(&machine_output); + let combined_string = process_output([hostnamectl_status, dbus_mid, etc_mid]); if combined_string.is_empty() { return Err(MIDError::ResultMidError); @@ -27,12 +28,12 @@ pub(crate) fn get_mid_result() -> Result { } #[cfg(target_os = "linux")] -fn process_output(output_str: &str) -> String { +fn process_output(output: [Option; 3]) -> String { let mut md5_hashes = HashSet::new(); - for line in output_str.to_lowercase().lines() { - if line.len() == 32 && line.chars().all(|c| c.is_ascii_hexdigit()) { - md5_hashes.insert(line.to_string()); + for hash in output.into_iter().flatten() { + if hash.len() == 32 && hash.chars().all(|c| c.is_ascii_hexdigit()) { + md5_hashes.insert(hash); } } @@ -44,3 +45,13 @@ fn process_output(output_str: &str) -> String { .trim() .to_string() } + +#[cfg(target_os = "linux")] +fn parse_mid(hostnamectl_status: String) -> Option { + const PATTERN: &str = "Machine ID: "; + + let pos = hostnamectl_status.find(PATTERN)?; + let after_pattern = hostnamectl_status.split_at(pos + PATTERN.len()).1; + + Some(after_pattern.lines().next()?.to_owned()) +}