diff --git a/Cargo.lock b/Cargo.lock
index c2eaad3..8f10e85 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -3291,9 +3291,9 @@ dependencies = [
 
 [[package]]
 name = "rustversion"
-version = "1.0.10"
+version = "1.0.11"
 source = "registry+https://github.com/rust-lang/crates.io-index"
-checksum = "4378ea89513870b6e2303ec50618e97da0fa43cdd9ded83ad3b6bad2693c08c6"
+checksum = "5583e89e108996506031660fe09baa5011b9dd0341b89029313006d1fb508d70"
 
 [[package]]
 name = "ryu"
diff --git a/src/constants.rs b/src/constants.rs
index a4e0404..f28a082 100644
--- a/src/constants.rs
+++ b/src/constants.rs
@@ -310,7 +310,7 @@ mod test {
 	}
 
 	#[test]
-	fn git_commit_is_41_chars() {
-		assert_eq!(crate::COMMIT.len(), 41);
+	fn git_commit_eq_or_gt_40_chars() {
+		assert!(crate::COMMIT.len() >= 40);
 	}
 }
diff --git a/src/disk.rs b/src/disk.rs
index a115128..b4c6299 100644
--- a/src/disk.rs
+++ b/src/disk.rs
@@ -248,7 +248,7 @@ impl State {
 	// leaving behind old keys+values and updating [default] with old valid ones.
 	pub fn merge(old: &str) -> Result<Self, TomlError> {
 		let default = toml::ser::to_string(&Self::new()).unwrap();
-		let new: Self = match Figment::from(Toml::string(&default)).merge(Toml::string(&old)).extract() {
+		let new: Self = match Figment::from(Toml::string(&default)).merge(Toml::string(old)).extract() {
 			Ok(new) => { info!("State | TOML merge ... OK"); new },
 			Err(err) => { error!("State | Couldn't merge default + old TOML"); return Err(TomlError::Merge(err)) },
 		};
@@ -696,7 +696,7 @@ impl Default for P2pool {
 }
 impl Xmrig {
 	fn with_threads(max_threads: usize, current_threads: usize) -> Self {
-		let mut xmrig = Self::default();
+		let xmrig = Self::default();
 		Self {
 			max_threads,
 			current_threads,
diff --git a/src/helper.rs b/src/helper.rs
index 4484948..623dafd 100644
--- a/src/helper.rs
+++ b/src/helper.rs
@@ -1116,7 +1116,7 @@ impl Helper {
 // Code taken from [https://docs.rs/humantime/] and edited to remove sub-second time, change spacing and some words.
 use std::time::Duration;
 
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Eq, PartialEq)]
 pub struct HumanTime(Duration);
 
 impl Default for HumanTime {
@@ -1186,7 +1186,7 @@ impl std::fmt::Display for HumanTime {
 // Percent  | [0.001]  -> [0%]                        | Rounds down, removes redundant zeros
 // Hashrate | [123.0, 311.2, null] -> [123, 311, ???] | Casts, replaces null with [???]
 // CPU Load | [12.0, 11.4, null] -> [12.0, 11.4, ???] | No change, just into [String] form
-#[derive(Debug, Clone)]
+#[derive(Debug, Clone, Eq, PartialEq)]
 pub struct HumanNumber(String);
 
 impl std::fmt::Display for HumanNumber {
@@ -1216,11 +1216,6 @@ impl HumanNumber {
 		buf.write_formatted(&(f as u128), &LOCALE);
 		Self(buf.as_str().to_string())
 	}
-	fn from_u8(u: u8) -> Self {
-		let mut buf = num_format::Buffer::new();
-		buf.write_formatted(&u, &LOCALE);
-		Self(buf.as_str().to_string())
-	}
 	fn from_u16(u: u16) -> Self {
 		let mut buf = num_format::Buffer::new();
 		buf.write_formatted(&u, &LOCALE);
@@ -1272,7 +1267,7 @@ impl HumanNumber {
 		let mut n = 0;
 		for i in array {
 			match i {
-				Some(f) => string.push_str(format!("{}", f).as_str()),
+				Some(f) => string.push_str(format!("{:.2}", f).as_str()),
 				None => string.push_str("???"),
 			}
 			if n != 2 {
@@ -1336,6 +1331,12 @@ pub struct ImgP2pool {
 	pub log_level: String, // What log level?
 }
 
+impl Default for ImgP2pool {
+	fn default() -> Self {
+		Self::new()
+	}
+}
+
 impl ImgP2pool {
 	pub fn new() -> Self {
 		Self {
@@ -1554,6 +1555,12 @@ pub struct ImgXmrig {
 	pub url: String,
 }
 
+impl Default for ImgXmrig {
+	fn default() -> Self {
+		Self::new()
+	}
+}
+
 impl ImgXmrig {
 	pub fn new() -> Self {
 		Self {
@@ -1717,6 +1724,90 @@ impl Hashrate {
 //---------------------------------------------------------------------------------------------------- TESTS
 #[cfg(test)]
 mod test {
+	#[test]
+	fn human_number() {
+		use crate::HumanNumber;
+		assert!(HumanNumber::to_percent(0.001).to_string() == "0%");
+		assert!(HumanNumber::to_percent(12.123123123123).to_string() == "12.12%");
+		assert!(HumanNumber::from_hashrate([Some(123.1), Some(11111.1), None]).to_string() == "[123 H/s, 11,111 H/s, ??? H/s]");
+		assert!(HumanNumber::from_hashrate([None, Some(1.123), Some(123123.312)]).to_string() == "[??? H/s, 1 H/s, 123,123 H/s]");
+		assert!(HumanNumber::from_load([Some(123.1234), Some(321.321), None]).to_string() == "[123.12, 321.32, ???]");
+		assert!(HumanNumber::from_load([None, Some(4321.43), Some(1234.1)]).to_string() == "[???, 4321.43, 1234.10]");
+		assert!(HumanNumber::from_f32(123_123.123123123).to_string() == "123,123");
+		assert!(HumanNumber::from_f64(123_123_123.123123123123123).to_string() == "123,123,123");
+		assert!(HumanNumber::from_u16(1_000).to_string() == "1,000");
+		assert!(HumanNumber::from_u16(65_535).to_string() == "65,535");
+		assert!(HumanNumber::from_u32(65_536).to_string() == "65,536");
+		assert!(HumanNumber::from_u32(100_000).to_string() == "100,000");
+		assert!(HumanNumber::from_u32(1_000_000).to_string() == "1,000,000");
+		assert!(HumanNumber::from_u32(10_000_000).to_string() == "10,000,000");
+		assert!(HumanNumber::from_u32(100_000_000).to_string() == "100,000,000");
+		assert!(HumanNumber::from_u32(1_000_000_000).to_string() == "1,000,000,000");
+		assert!(HumanNumber::from_u32(4_294_967_295).to_string() == "4,294,967,295");
+		assert!(HumanNumber::from_u64(4_294_967_296).to_string() == "4,294,967,296");
+		assert!(HumanNumber::from_u64(10_000_000_000).to_string() == "10,000,000,000");
+		assert!(HumanNumber::from_u64(100_000_000_000).to_string() == "100,000,000,000");
+		assert!(HumanNumber::from_u64(1_000_000_000_000).to_string() == "1,000,000,000,000");
+		assert!(HumanNumber::from_u64(10_000_000_000_000).to_string() == "10,000,000,000,000");
+		assert!(HumanNumber::from_u64(100_000_000_000_000).to_string() == "100,000,000,000,000");
+		assert!(HumanNumber::from_u64(1_000_000_000_000_000).to_string() == "1,000,000,000,000,000");
+		assert!(HumanNumber::from_u64(10_000_000_000_000_000).to_string() == "10,000,000,000,000,000");
+		assert!(HumanNumber::from_u64(18_446_744_073_709_551_615).to_string() == "18,446,744,073,709,551,615");
+		assert!(HumanNumber::from_u128(18_446_744_073_709_551_616).to_string() == "18,446,744,073,709,551,616");
+		assert!(HumanNumber::from_u128(100_000_000_000_000_000_000).to_string() == "100,000,000,000,000,000,000");
+		assert_eq!(
+			HumanNumber::from_u128(340_282_366_920_938_463_463_374_607_431_768_211_455).to_string(),
+			"340,282,366,920,938,463,463,374,607,431,768,211,455",
+		);
+	}
+
+	#[test]
+	fn human_time() {
+		use crate::HumanTime;
+		use std::time::Duration;
+		assert!(HumanTime::into_human(Duration::from_secs(0)).to_string()        == "0 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(1)).to_string()        == "1 second");
+		assert!(HumanTime::into_human(Duration::from_secs(2)).to_string()        == "2 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(59)).to_string()       == "59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(60)).to_string()       == "1 minute");
+		assert!(HumanTime::into_human(Duration::from_secs(61)).to_string()       == "1 minute, 1 second");
+		assert!(HumanTime::into_human(Duration::from_secs(62)).to_string()       == "1 minute, 2 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(120)).to_string()      == "2 minutes");
+		assert!(HumanTime::into_human(Duration::from_secs(121)).to_string()      == "2 minutes, 1 second");
+		assert!(HumanTime::into_human(Duration::from_secs(122)).to_string()      == "2 minutes, 2 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(179)).to_string()      == "2 minutes, 59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(3599)).to_string()     == "59 minutes, 59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(3600)).to_string()     == "1 hour");
+		assert!(HumanTime::into_human(Duration::from_secs(3601)).to_string()     == "1 hour, 1 second");
+		assert!(HumanTime::into_human(Duration::from_secs(3602)).to_string()     == "1 hour, 2 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(3660)).to_string()     == "1 hour, 1 minute");
+		assert!(HumanTime::into_human(Duration::from_secs(3720)).to_string()     == "1 hour, 2 minutes");
+		assert!(HumanTime::into_human(Duration::from_secs(86399)).to_string()    == "23 hours, 59 minutes, 59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(86400)).to_string()    == "1 day");
+		assert!(HumanTime::into_human(Duration::from_secs(86401)).to_string()    == "1 day, 1 second");
+		assert!(HumanTime::into_human(Duration::from_secs(86402)).to_string()    == "1 day, 2 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(86460)).to_string()    == "1 day, 1 minute");
+		assert!(HumanTime::into_human(Duration::from_secs(86520)).to_string()    == "1 day, 2 minutes");
+		assert!(HumanTime::into_human(Duration::from_secs(90000)).to_string()    == "1 day, 1 hour");
+		assert!(HumanTime::into_human(Duration::from_secs(93600)).to_string()    == "1 day, 2 hours");
+		assert!(HumanTime::into_human(Duration::from_secs(604799)).to_string()   == "6 days, 23 hours, 59 minutes, 59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(604800)).to_string()   == "7 days");
+		assert!(HumanTime::into_human(Duration::from_secs(2630016)).to_string()  == "1 month");
+		assert!(HumanTime::into_human(Duration::from_secs(3234815)).to_string()  == "1 month, 6 days, 23 hours, 59 minutes, 59 seconds");
+		assert!(HumanTime::into_human(Duration::from_secs(5260032)).to_string()  == "2 months");
+		assert!(HumanTime::into_human(Duration::from_secs(31557600)).to_string() == "1 year");
+		assert!(HumanTime::into_human(Duration::from_secs(63115200)).to_string() == "2 years");
+		assert_eq!(
+			HumanTime::into_human(Duration::from_secs(18446744073709551615)).to_string(),
+			"584542046090 years, 7 months, 15 days, 17 hours, 5 minutes, 3 seconds",
+		);
+	}
+
+	#[test]
+	fn build_p2pool_regex() {
+		crate::helper::P2poolRegex::new();
+	}
+
 	#[test]
 	fn calc_payouts_and_xmr_from_output_p2pool() {
 		use crate::helper::{PubP2poolApi,P2poolRegex};
diff --git a/src/main.rs b/src/main.rs
index 9937cc2..12deba5 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1222,7 +1222,7 @@ impl eframe::App for App {
 							let color = if hide { BLACK } else { BRIGHT_YELLOW };
 							if ui.add_sized([box_width, height], Button::new(RichText::new("👁").color(color))).on_hover_text(PASSWORD_HIDE).clicked() { sudo.hide = !sudo.hide; }
 						});
-						if (key.is_esc() && !sudo.testing) || ui.add_sized([width, height*4.0], Button::new("Leave")).clicked() { self.error_state.reset(); };
+						if (key.is_esc() && !sudo.testing) || ui.add_sized([width, height*4.0], Button::new("Leave")).on_hover_text(PASSWORD_LEAVE).clicked() { self.error_state.reset(); };
 						// If [test_sudo()] finished, reset error state.
 						if sudo.success {
 							self.error_state.reset();
@@ -1571,7 +1571,21 @@ mod test {
 
 	#[test]
 	fn build_regex() {
-		crate::Regexes::new();
+		use regex::Regex;
+		let r = crate::Regexes::new();
+		assert!(Regex::is_match(&r.name, "_this_ is... a n-a-m-e."));
+		assert!(Regex::is_match(&r.address, "44hintoFpuo3ugKfcqJvh5BmrsTRpnTasJmetKC4VXCt6QDtbHVuixdTtsm6Ptp7Y8haXnJ6j8Gj2dra8CKy5ewz7Vi9CYW"));
+		assert!(Regex::is_match(&r.ipv4, "192.168.1.2"));
+		assert!(Regex::is_match(&r.ipv4, "127.0.0.1"));
+		assert!(Regex::is_match(&r.domain, "my.node.com"));
+		assert!(Regex::is_match(&r.domain, "my.monero-node123.net"));
+		assert!(Regex::is_match(&r.domain, "www.my-node.org"));
+		assert!(Regex::is_match(&r.domain, "www.my-monero-node123.io"));
+		for i in 1..=65535 {
+			assert!(Regex::is_match(&r.port, &i.to_string()));
+		}
+		assert!(!Regex::is_match(&r.port, "0"));
+		assert!(!Regex::is_match(&r.port, "65536"));
 	}
 
 	#[test]
diff --git a/src/update.rs b/src/update.rs
index 1e84423..98fd544 100644
--- a/src/update.rs
+++ b/src/update.rs
@@ -412,7 +412,7 @@ impl Update {
 		*update.lock().unwrap().prog.lock().unwrap() = 5.0;
 
 		// Create Tor/HTTPS client
-		let mut lock = update.lock().unwrap();
+		let lock = update.lock().unwrap();
 		let tor = lock.tor;
 		if tor {
 			let msg = MSG_TOR.to_string();