initial commit w/ linux injector

Signed-off-by: Erik Hollensbe <git@hollensbe.org>
This commit is contained in:
Erik Hollensbe
2022-02-22 11:55:19 -08:00
commit 0ce554c329
4 changed files with 133 additions and 0 deletions
+2
View File
@@ -0,0 +1,2 @@
/target
Cargo.lock
+9
View File
@@ -0,0 +1,9 @@
[package]
name = "ca_injector"
version = "0.1.0"
edition = "2021"
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
[dependencies]
anyhow = "^1"
+27
View File
@@ -0,0 +1,27 @@
#[cfg(target_os = "linux")]
mod linux;
pub fn install_ca(filename: &str) -> Result<(), anyhow::Error> {
#[cfg(target_os = "linux")]
return crate::linux::install_ca(filename);
#[cfg(not(target_os = "linux"))]
Err(anyhow::anyhow!(
"Unable to install CA certificate '{}' on this platform",
filename
))
}
pub fn uninstall_ca(filename: &str) -> Result<(), anyhow::Error> {
#[cfg(target_os = "linux")]
return crate::linux::uninstall_ca(filename);
#[cfg(not(target_os = "linux"))]
Err(anyhow::anyhow!(
"Unable to uninstall CA certificate '{}' on this platform",
filename
))
}
#[cfg(test)]
mod tests {}
+95
View File
@@ -0,0 +1,95 @@
use std::{path::PathBuf, str::FromStr};
use anyhow::anyhow;
#[derive(Debug, Clone)]
struct TrustStoreMetadata {
dir: &'static str,
bin: &'static str,
args: Vec<&'static str>,
}
fn get_trust_store_command() -> Result<TrustStoreMetadata, anyhow::Error> {
if let Ok(md) = std::fs::metadata("/etc/pki/ca-trust/source/anchors") {
if md.is_dir() {
return Ok(TrustStoreMetadata {
dir: "/etc/pki/ca-trust/source/anchors",
bin: "update-ca-trust",
args: vec!["extract"],
});
}
}
if let Ok(md) = std::fs::metadata("/usr/local/share/ca-certificates") {
if md.is_dir() {
return Ok(TrustStoreMetadata {
dir: "/usr/local/share/ca-certificates",
bin: "update-ca-certificates",
args: vec![],
});
}
}
if let Ok(md) = std::fs::metadata("/etc/ca-certificates/trust-source/anchors") {
if md.is_dir() {
return Ok(TrustStoreMetadata {
dir: "/etc/ca-certificates/trust-source/anchors",
bin: "trust",
args: vec!["extract-compat"],
});
}
}
if let Ok(md) = std::fs::metadata("/usr/share/pki/trust/anchors") {
if md.is_dir() {
return Ok(TrustStoreMetadata {
dir: "/usr/share/pki/trust/anchors",
bin: "update-ca-certificates",
args: vec![],
});
}
}
Err(anyhow!("CA location could not be determined"))
}
fn template_filename(filename: &str, tsc: &TrustStoreMetadata) -> Result<PathBuf, anyhow::Error> {
let pb = PathBuf::from_str(tsc.dir)?;
Ok(pb.join(filename.replace(" ", "_").replace(".crt", ".pem")))
}
fn update(tsc: &TrustStoreMetadata) -> Result<std::process::ExitStatus, anyhow::Error> {
Ok(std::process::Command::new(tsc.bin)
.args(tsc.args.clone())
.env_clear()
.stdin(std::process::Stdio::null())
.stdout(std::process::Stdio::null())
.stderr(std::process::Stdio::null())
.status()?)
}
pub fn install_ca(filename: &str) -> Result<(), anyhow::Error> {
let tsc = get_trust_store_command()?;
std::fs::copy(filename, template_filename(filename, &tsc)?)?;
let res = update(&tsc)?;
if !res.success() {
return Err(anyhow!("Unable to install CA certificate"));
}
Ok(())
}
pub fn uninstall_ca(filename: &str) -> Result<(), anyhow::Error> {
let tsc = get_trust_store_command()?;
std::fs::remove_file(template_filename(filename, &tsc)?)?;
let res = update(&tsc)?;
if !res.success() {
return Err(anyhow!("Unable to uninstall CA certificate"));
}
Ok(())
}