Wenn ein entschlossener Gegner vor Ihrer Haustür steht und bereit ist, sich Ihren Computer zu schnappen oder einen ausgeklügelten Cyberangriff zu starten, hängt das Ergebnis davon ab, ob Sie über einen schriftlichen Notfallplan verfügen. Ein gut ausgearbeiteter “Kill‑Switch”, der das Gerät sofort isoliert, das gesamte kryptografische Material dreht und neue Geheimnisse auf ein verschlüsseltes Offline-Medium auslagert, kann einen potenziell katastrophalen Angriff in ein überschaubares, überprüfbares Ereignis verwandeln. Dieser Artikel führt Sie durch die warumdie wieund die best‑practice Sicherheitsvorkehrungen die Sie brauchen, um opportunistische Diebe und staatliche Akteure zu überleben.
Zusammen schaffen diese Vorteile eine defensive Tiefe, die selbst ein gut finanzierter Gegner nur schwer überwinden kann.
Dedizierte Hardware-Taste – Ein diskretes USB‑Relais oder ein Raspberry Pi HAT, das mit einem physischen Knopf verbunden ist, führt das Kill‑Switch-Skript aus.
Tastaturkürzel – Karte einer seltenen Kombination (z.B., Ctrl+Alt+Shift+Esc) auf systemd-run --on-active=1 /usr/local/sbin/door_kill_switch.
#!/usr/bin/env bash
#
# kill‑switch.sh – Isolieren Sie den Rechner, wechseln Sie die Anmeldedaten,
# exportieren Sie sie auf einen verschlüsselten USB-Stick, und räumen Sie dann auf.
#
# Verwendung:
# ./kill-switch.sh # normaler Betrieb (erfordert sudo)
# ./kill-switch.sh –test # dry‑run – nur Schlüssel erzeugen, keine Systemänderungen
#
# Optionale Tastenkombination: Drücken Sie Strg‑Alt‑K, während das Terminalfenster den Fokus hat
# (bindet das gleiche “–test” Verhalten über eine Trap).
set -euo pipefail # strikte Fehlerbehandlung
IFS=$’nt’ # vernünftige Feldaufteilung
# Konfiguration (bearbeiten Sie diese, falls Ihre Umgebung abweicht)
USB_LABEL=”KILL_USB” # Bezeichnung des vorbereiteten LUKS USB-Sticks
CRYPT_NAME=”kill_usb” # Name für den LUKS-Mapper
MNT_POINT=”/mnt/killswitch” # Einhängepunkt für das geöffnete Volume
TEST_MODE=false # wird durch –test oder shortcut umgeschaltet
# Hilfsfunktionen
log() { printf ‘[%s] %sn’ “$(Datum ‘+%H:%M:%S’)” “$*”; }
die() { log “FEHLER: $*” >&2; exit 1; }
# Erkennen Sie das optionale “test” Flag
while (( $# ))); do
case “$1” in
–test) TEST_MODE=true; shift ;;
*) break ;;
esac
erledigt
# Binden Sie Strg‑Alt‑K, um den Testmodus auszulösen (funktioniert in den meisten modernen Terminals)
if ! $TEST_MODE; then
trap ‘TEST_MODE=true; log “Testmodus per Tastendruck aktiviert”;’ INT
fi
# 1️⃣ Isolierung des Netzes
if ! $TEST_MODE; then
log “🔒 1️⃣ Netzwerk isolieren…”
# Jede Schnittstelle herunterfahren (Fehler ignorieren, z.B. lo)
for dev in $(ls /sys/class/net/); do
sudo ip link set “$dev” down 2>/dev/null || true
done
sudo ip route flush table main
sudo iptables -P OUTPUT DROP
sudo iptables -P FORWARD DROP
if command -v nft >/dev/null; then
sudo nft add rule ip filter output drop
fi
sonst
log “[TEST] Überspringen der Netzwerkisolierung.”
fi
# Caches verwerfen (nur im Real-Modus)
if ! $TEST_MODE; then
log “🧹 2️⃣ Dropping page‑cache, dentries, and inodes…”
synchronisieren
echo 3 | sudo tee /proc/sys/vm/drop_caches > /dev/null
sonst
log “[TEST] Überspringen des Cache Drop.”
fi
# Credential Rotation & Export auf verschlüsselten USB
log “🔑 3️⃣ Verschlüsselten USB vorbereiten…”
# Das USB-Gerät anhand seiner Bezeichnung auflösen
USB_DEV=”/dev/disk/by-label/${USB_LABEL}”
[[ -e “$USB_DEV” ]]|| die “USB-Gerät mit Label ‘${USB_LABEL}’ nicht gefunden bei $USB_DEV”
# Öffnen Sie den LUKS-Container (fragt nach der Passphrase)
if ! $TEST_MODE; then
sudo cryptsetup open “$USB_DEV” “$CRYPT_NAME”
sonst
log “[TEST] Öffnen des LUKS-Containers (keine Passphrase-Abfrage im Testmodus)…”
sudo cryptsetup open “$USB_DEV” “$CRYPT_NAME” <</dev/null
# Vorhandene Schlüssel archivieren
mkdir -p “${SSH_DIR}/archived”
mv “${SSH_DIR}/id_ed25519″* “${SSH_DIR}/archived/” 2>/dev/null || true
# Zeigen Sie die Standard-Dateinamen auf den neuen Schlüssel
ln -sf “$NEW_SSH” “${SSH_DIR}/id_ed25519”
ln -sf “${NEW_SSH}.pub” “${SSH_DIR}/id_ed25519.pub”
# Back‑up to USB
mkdir -p “${MNT_POINT}/ssh”
cp “${SSH_DIR}/id_ed25519″* “${MNT_POINT}/ssh/”
# GPG-Schlüsselerzeugung
log ” ↳ GPG-Schlüssel generieren…”
NEW_GPG_FPR=$(gpg –batch –quick-generate-key
“Benutzer ” ed25519 sign,encrypt,auth 2y
–pinentry-mode loopback –passphrase ” 2>/dev/null)
# Schlüssel auf den USB exportieren (ASCII‑gepanzert)
gpg –armor –export-secret-keys “$NEW_GPG_FPR” > “${MNT_POINT}/gpg_secret.asc”
gpg –armor –export “$NEW_GPG_FPR” > “${MNT_POINT}/gpg_public.asc”
# WireGuard Schlüsselrotation
log ” ↳ Drehung der WireGuard-Schlüssel…”
WG_PRIV=$(wg genkey)
WG_PUB=$(printf “%s” “$WG_PRIV” | wg pubkey)
# Auf USB speichern
printf “%sn” “$WG_PRIV” > “${MNT_POINT}/wg_private.key”
printf “%sn” “$WG_PUB” > “${MNT_POINT}/wg_public.key”
# Aktualisieren Sie die Hostkonfiguration *nur* im realen Modus.
if ! $TEST_MODE; then
sudo sed -i “s|^PrivateKey = .*|PrivateKey = $WG_PRIV|” /etc/wireguard/wg0.conf
sudo systemctl restart wg-quick@wg0
sonst
log “[TEST] Überspringen der Aktualisierung der wg0.conf und des Neustarts des Dienstes.”
fi
# Verschiedene Geheimnisse (API-Token, DB-Passwort)
log ” ↳ Erstellen diverser Geheimnisse…”
TMP_SECRETS=”$(mktemp /tmp/tmp_secrets.XXXXXX.yaml)”
cat < “$TMP_SECRETS”
api_token: “$(openssl rand -hex 16)”
db_password: “$(openssl rand -base64 32)”
EOF
# Verschlüsseln mit dem *ersten* öffentlichen Schlüssel im Schlüsselbund (oder dem neu erstellten)
RECIPIENT=$(gpg –list-keys –with-colons |
awk -F: ‘/^pub/ {print $10; exit}’)
[[ -n “$RECIPIENT” ]]|| die “No GPG public key found for encryption”
gpg –yes –batch –output “${MNT_POINT}/secrets.yaml.gpg”
–encrypt –recipient “$RECIPIENT” “$TMP_SECRETS”
rm -f “$TMP_SECRETS”
# 4️⃣ Finalize – unmount & close USB
log “✅ 4️⃣ Abschließen…”
sync
sudo umount “$MNT_POINT”
sudo cryptsetup close “$CRYPT_NAME”
log “=== AT‑THE‑DOOR KILL SWITCH COMPLETE ===”

