Add ./src/hook.rs
This commit is contained in:
+147
@@ -0,0 +1,147 @@
|
||||
use anyhow::{Context, Result};
|
||||
use std::io::Write;
|
||||
use std::path::Path;
|
||||
use tracing::{info, warn};
|
||||
|
||||
const ALPM_HOOK_PATH: &str = "/usr/share/libalpm/hooks/aegisaur-pre-install.hook";
|
||||
const HOOK_SCRIPT_PATH: &str = "/usr/share/libalpm/hooks/aegisaur-check.sh";
|
||||
|
||||
/// Installiert den ALPM-Hook für Pre-Install-Checks
|
||||
pub fn install_alpm_hook() -> Result<()> {
|
||||
// Hook-Definition
|
||||
let hook_content = r#"[Trigger]
|
||||
Operation = Install
|
||||
Operation = Upgrade
|
||||
Type = Package
|
||||
Target = *
|
||||
|
||||
[Action]
|
||||
Description = AegisAUR Security Scan
|
||||
When = PreTransaction
|
||||
Exec = /usr/share/libalpm/hooks/aegisaur-check.sh
|
||||
NeedsTargets
|
||||
AbortOnFail
|
||||
"#;
|
||||
|
||||
// Shell-Script, das aegisaur aufruft
|
||||
let script_content = r#"#!/bin/bash
|
||||
# AegisAUR Pre-Install Hook
|
||||
# Prüft Pakete vor der Installation
|
||||
|
||||
AUR_SCANNER="/usr/bin/aegisaur"
|
||||
TMPFILE=$(mktemp)
|
||||
|
||||
# Alle zu installierenden Pakete durch aegisaur prüfen
|
||||
while read -r package; do
|
||||
# Nur AUR-Pakete prüfen (Foreign packages)
|
||||
if pacman -Qi "$package" >/devdev/null 2>&1; then
|
||||
# Paket ist bereits installiert (Upgrade)
|
||||
continue
|
||||
fi
|
||||
|
||||
# Prüfe ob es ein AUR/Foreign Paket ist
|
||||
if pacman -Si "$package" >/dev/null 2>&1; then
|
||||
# Offizielles Repo-Paket, immer OK
|
||||
continue
|
||||
fi
|
||||
|
||||
# AUR Paket gefunden - scanne es
|
||||
if [[ -x "$AUR_SCANNER" ]]; then
|
||||
RESULT=$($AUR_SCANNER scan "$package" --json 2>/devnull)
|
||||
SCORE=$(echo "$RESULT" | grep -oP '"score":\s*\K\d+')
|
||||
STATUS=$(echo "$RESULT" | grep -oP '"status":\s*"\K[^"]+')
|
||||
|
||||
if [[ "$STATUS" == "IOCDetected" ]] || [[ "$STATUS" == "Dangerous" ]]; then
|
||||
echo ""
|
||||
echo "╔════════════════════════════════════════════════════════════════╗"
|
||||
echo "║ 🚨 AEGISAUR SECURITY ALERT 🚨 ║"
|
||||
echo "╚════════════════════════════════════════════════════════════════╝"
|
||||
echo ""
|
||||
echo "Paket: $package"
|
||||
echo "Status: $STATUS"
|
||||
echo "Score: $SCORE/100"
|
||||
echo ""
|
||||
echo "⚠️ DIESES PAKET IST ALS GEFÄHRLICH EINGESTUFT!"
|
||||
echo ""
|
||||
echo "Möchtest du die Installation abbrechen? (Ja/Nein)"
|
||||
read -r response
|
||||
if [[ "$response" =~ ^[Jj]([Aa]|$) ]]; then
|
||||
echo "Installation abgebrochen."
|
||||
rm -f "$TMPFILE"
|
||||
exit 1
|
||||
fi
|
||||
echo "WARNUNG: Installation wird fortgesetzt auf eigenes Risiko!"
|
||||
echo "$package ($STATUS - Score: $SCORE)" >> "$TMPFILE"
|
||||
elif [[ "$STATUS" == "Suspicious" ]] || [[ "$STATUS" == "Warning" ]]; then
|
||||
echo ""
|
||||
echo "⚠️ AegisAUR Warnung für $package: $STATUS (Score: $SCORE/100)"
|
||||
echo "$package ($STATUS - Score: $SCORE)" >> "$TMPFILE"
|
||||
fi
|
||||
fi
|
||||
done
|
||||
|
||||
# Zusammenfassung anzeigen falls Warnungen vorhanden
|
||||
if [[ -s "$TMPFILE" ]]; then
|
||||
echo ""
|
||||
echo "╔══════════════════════════════════════════════════════════════╗"
|
||||
echo "║ AegisAUR Scan Zusammenfassung ║"
|
||||
echo "╚══════════════════════════════════════════════════════════════╝"
|
||||
cat "$TMPFILE"
|
||||
echo ""
|
||||
fi
|
||||
|
||||
rm -f "$TMPFILE"
|
||||
exit 0
|
||||
"#;
|
||||
|
||||
// Hook-Datei schreiben
|
||||
info!("Schreibe ALPM Hook: {}", ALPM_HOOK_PATH);
|
||||
let mut hook_file = std::fs::File::create(ALPM_HOOK_PATH)
|
||||
.context("Konnte ALPM Hook nicht erstellen (Root-Rechte nötig)")?;
|
||||
hook_file.write_all(hook_content.as_bytes())?;
|
||||
|
||||
// Script schreiben
|
||||
info!("Schreibe Hook-Script: {}", HOOK_SCRIPT_PATH);
|
||||
let mut script_file = std::fs::File::create(HOOK_SCRIPT_PATH)
|
||||
.context("Konnte Hook-Script nicht erstellen")?;
|
||||
script_file.write_all(script_content.as_bytes())?;
|
||||
|
||||
// Script executable machen
|
||||
#[cfg(unix)]
|
||||
{
|
||||
use std::os::unix::fs::PermissionsExt;
|
||||
let mut perms = std::fs::metadata(HOOK_SCRIPT_PATH)?.permissions();
|
||||
perms.set_mode(0o755);
|
||||
std::fs::set_permissions(HOOK_SCRIPT_PATH, perms)?;
|
||||
}
|
||||
|
||||
info!("ALPM Hook erfolgreich installiert");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Entfernt den ALPM-Hook
|
||||
pub fn remove_alpm_hook() -> Result<()> {
|
||||
info!("Entferne ALPM Hook...");
|
||||
|
||||
if Path::new(ALPM_HOOK_PATH).exists() {
|
||||
std::fs::remove_file(ALPM_HOOK_PATH)?;
|
||||
info!("Hook-Datei entfernt: {}", ALPM_HOOK_PATH);
|
||||
} else {
|
||||
warn!("Hook-Datei nicht gefunden: {}", ALPM_HOOK_PATH);
|
||||
}
|
||||
|
||||
if Path::new(HOOK_SCRIPT_PATH).exists() {
|
||||
std::fs::remove_file(HOOK_SCRIPT_PATH)?;
|
||||
info!("Script entfernt: {}", HOOK_SCRIPT_PATH);
|
||||
} else {
|
||||
warn!("Script nicht gefunden: {}", HOOK_SCRIPT_PATH);
|
||||
}
|
||||
|
||||
info!("ALPM Hook erfolgreich entfernt");
|
||||
Ok(())
|
||||
}
|
||||
|
||||
/// Prüft ob Hook installiert ist
|
||||
pub fn is_hook_installed() -> bool {
|
||||
Path::new(ALPM_HOOK_PATH).exists() && Path::new(HOOK_SCRIPT_PATH).exists()
|
||||
}
|
||||
Reference in New Issue
Block a user