OpenShell: Die Sicherheitslaufzeitumgebung hinter NemoClaw
Wenn NemoClaw der Sicherheits-Stack ist, dann ist OpenShell sein Fundament. Entwickelt von NVIDIAs Security-Engineering-Team über die letzten 18 Monate, bietet OpenShell Kernel-Level-Sandboxing für die Ausführung von KI-Agenten — und stellt sicher, dass selbst ein vollständig kompromittierter Agent nicht auf Ressourcen außerhalb seiner definierten Sicherheitsgrenze zugreifen kann.
Dieser Beitrag ist ein technischer Tieftauchgang in OpenShells Architektur, seine Isolationsmechanismen und wie es Sicherheitsrichtlinien mit minimalem Leistungs-Overhead durchsetzt.
Warum Isolation auf Kernel-Ebene?
Traditionelles Anwendungs-Sandboxing — Container, VMs, Isolation auf Prozessebene — wurde für Software entwickelt, die sich vorhersehbar verhält. KI-Agenten sind grundlegend anders. Sie generieren ihre eigenen Ausführungspläne zur Laufzeit, tätigen Tool-Aufrufe, die mit externen Systemen interagieren, und können neuartiges Verhalten zeigen, das keine Testsuite vorhergesehen hat.
Diese Unvorhersehbarkeit erfordert ein Sicherheitsmodell, das auf der niedrigstmöglichen Ebene arbeitet: dem Kernel. OpenShell fängt jeden Systemaufruf ab, den ein Agentenprozess tätigt, klassifiziert ihn anhand der aktiven Sicherheitsrichtlinie und trifft eine Erlauben/Verweigern-Entscheidung, bevor der Aufruf den Kernel erreicht.
Agent Process
│
▼
OpenShell eBPF Layer ←── Policy Engine
│
├── ALLOW → System Call → Kernel
│
├── DENY → Error returned to agent
│
└── ESCALATE → Human approval queue
eBPF: Die Technologie hinter OpenShell
OpenShell basiert auf eBPF (extended Berkeley Packet Filter), einer Linux-Kernel-Technologie, die es ermöglicht, benutzerdefinierte Programme im Kernel-Bereich auszuführen, ohne den Kernel selbst zu modifizieren. NVIDIAs Team hat eine Suite von eBPF-Programmen geschrieben, die speziell für KI-Agenten-Workloads optimiert sind:
Syscall-Interceptor
Der Syscall-Interceptor hängt sich an den sys_enter-Tracepoint an und bewertet jeden Systemaufruf anhand der aktiven Richtlinie:
// Simplified OpenShell eBPF syscall interceptor
SEC("tracepoint/raw_syscalls/sys_enter")
int openshell_syscall_enter(struct trace_event_raw_sys_enter *ctx) {
u32 pid = bpf_get_current_pid_tgid() >> 32;
struct sandbox_policy *policy = bpf_map_lookup_elem(&sandbox_policies, &pid);
if (!policy)
return 0; // Not a sandboxed process
long syscall_nr = ctx->id;
int decision = evaluate_policy(policy, syscall_nr, ctx->args);
if (decision == DENY) {
// Send event to userspace audit log
emit_security_event(pid, syscall_nr, DENY);
// Override return value to -EPERM
bpf_override_return(ctx, -EPERM);
} else if (decision == ESCALATE) {
// Pause the process and notify approval queue
emit_approval_request(pid, syscall_nr, ctx->args);
send_signal(pid, SIGSTOP);
}
return 0;
}
Dateisystem-Wächter
Der Dateisystem-Wächter beschränkt, auf welche Dateien und Verzeichnisse ein Agent zugreifen kann. Er arbeitet auf VFS-Operationen (Virtual Filesystem) und fängt open-, read-, write-, unlink- und rename-Aufrufe ab:
# Filesystem policy for a customer support agent
filesystem:
# Agent can read its own configuration
- path: "/etc/nemoclaw/agent.yaml"
permissions: [read]
# Agent can read/write to its workspace
- path: "/var/nemoclaw/workspace/**"
permissions: [read, write, create]
# Agent can read shared data
- path: "/var/nemoclaw/shared/**"
permissions: [read]
# Everything else is denied by default
defaultAction: deny
Netzwerk-Wächter
Der Netzwerk-Wächter hakt sich in Socket-Operationen ein, um den Netzwerkzugang des Agenten auf Verbindungsebene zu kontrollieren:
SEC("cgroup/connect4")
int openshell_connect4(struct bpf_sock_addr *ctx) {
u32 pid = bpf_get_current_pid_tgid() >> 32;
struct network_policy *policy = bpf_map_lookup_elem(&net_policies, &pid);
if (!policy)
return 1; // Allow non-sandboxed processes
__be32 dst_ip = ctx->user_ip4;
__be16 dst_port = ctx->user_port;
if (!is_allowed_destination(policy, dst_ip, dst_port)) {
emit_security_event(pid, NETWORK_BLOCKED, dst_ip, dst_port);
return 0; // Block connection
}
return 1; // Allow connection
}
Architektur der Richtliniendurchsetzung
OpenShell-Richtlinien werden in eBPF-Bytecode kompiliert, um maximale Durchsetzungsgeschwindigkeit zu erreichen. Die Kompilierungspipeline funktioniert wie folgt:
- 1.YAML-Richtliniendateien werden von Sicherheitsteams in einem menschenlesbaren Format geschrieben
- 2.Richtlinien-Compiler wandelt YAML in eine Zwischendarstellung (IR) um
- 3.Nemotron-Richtlinienvalidator prüft die IR auf logische Konsistenz und Konflikte
- 4.eBPF-Compiler generiert verifizierten Bytecode, der in den Kernel geladen wird
- 5.Laufzeit-Verifizierer stellt sicher, dass die eBPF-Programme terminieren und speichersicher sind
Die gesamte Kompilierungspipeline läuft in unter 2 Sekunden für typische Richtliniensets, und Richtlinien können ohne Neustart des Agenten hot-reloaded werden.
# Compile and load a policy
nemoclaw policy compile policies/customer-support.yaml
nemoclaw policy load customer-support
# Hot-reload a modified policy (no agent restart required)
nemoclaw policy reload customer-support
# Verify policy is active
nemoclaw policy status
# Output:
# POLICY STATUS LOADED AT RULES
# customer-support active 2026-03-19 14:30:01 47
# network-default active 2026-03-19 14:30:01 12
# filesystem-strict active 2026-03-19 14:30:01 23
Operator-Genehmigungsworkflows
Eine der markantesten Funktionen von OpenShell ist das integrierte Operator-Genehmigungssystem. Wenn ein Agent eine Aktion versucht, die als hochriskant eingestuft wird, pausiert OpenShell die Ausführung des Agenten und leitet die Genehmigungsanfrage an einen menschlichen Operator weiter.
Wie die Genehmigung funktioniert
- 1.Agent versucht einen Hochrisiko-Syscall (z. B. Schreiben in eine geschützte Datei, Verbindung zu einem nicht genehmigten Endpunkt)
- 2.OpenShells eBPF-Programm sendet SIGSTOP an den Agentenprozess
- 3.Eine Genehmigungsanfrage wird generiert und über den konfigurierten Kanal gesendet (Slack, Teams, PagerDuty, E-Mail)
- 4.Der Operator überprüft den Anfragekontext und genehmigt oder lehnt ab
- 5.Bei Genehmigung sendet OpenShell SIGCONT, um den Agenten fortzusetzen; bei Ablehnung wird EPERM zurückgegeben
Die Genehmigungsanfrage enthält den vollständigen Kontext:
{
"request_id": "apr-2026031914-00042",
"agent": "customer-support-agent-01",
"action": "email.send",
"target": "[email protected]",
"context": {
"ticket_id": "TKT-12345",
"customer_name": "[REDACTED]",
"reason": "Agent wants to send a follow-up email to the customer regarding their refund request",
"email_preview": "Dear Customer, your refund of $250 has been processed..."
},
"risk_level": "medium",
"policy_rule": "external-communication-requires-approval",
"timestamp": "2026-03-19T14:30:42Z"
}
Genehmigungstimeout und Standardaktionen
Operatoren können konfigurieren, was bei einem Genehmigungstimeout passiert:
approvalConfig:
timeout: 15m
onTimeout: deny # deny | allow | escalate
onEscalate:
target: security-team
channel: pagerduty
maxPendingApprovals: 10 # Queue limit per agent
autoApprove:
# Automatically approve if the same action was approved
# 3 times in the past 24 hours for this agent
repeatThreshold: 3
repeatWindow: 24h
Leistungscharakteristiken
OpenShell ist für Produktions-Workloads konzipiert, bei denen Latenz wichtig ist. Hier sind die gemessenen Overheads auf einem DGX Spark:
| Operation | Overhead |
|---|---|
| Syscall-Interception (erlaubt) | 8 Mikrosekunden |
| Syscall-Interception (verweigert) | 12 Mikrosekunden |
| Dateisystemprüfung | 15 Mikrosekunden |
| Netzwerkverbindungsprüfung | 20 Mikrosekunden |
| Richtlinien-Hot-Reload | < 500 Millisekunden |
| Genehmigungs-Roundtrip (Slack) | 2-30 Sekunden (menschenabhängig) |
Zum Vergleich: Ein typischer LLM-Inferenzaufruf dauert 500ms-5000ms, sodass der Overhead von OpenShell im Kontext von Agenten-Workloads vernachlässigbar ist.
Vergleich mit bestehendem Sandboxing
| Merkmal | OpenShell | Docker/OCI | gVisor | Firecracker |
|---|---|---|---|---|
| Isolationsebene | Kernel (eBPF) | Namespace | User-Space-Kernel | microVM |
| Syscall-Filterung | Pro Richtlinie, Hot-Reload | Statisches seccomp | Vollständige Interposition | Vollständige Isolation |
| Netzwerkrichtlinie | Pro Agent, L7-fähig | iptables | iptables | iptables |
| Menschliche Genehmigung | Integriert | Keine | Keine | Keine |
| KI-bewusste Richtlinien | Ja (Nemotron) | Nein | Nein | Nein |
| Overhead | ~10 Mikrosekunden | ~5 Mikrosekunden | ~50 Mikrosekunden | ~100ms Startup |
| GPU-Durchreichung | Nativ | NVIDIA CTK | Eingeschränkt | Eingeschränkt |
OpenShells wichtigster Differenzierungsfaktor ist, dass es von Grund auf für KI-Agenten-Workloads entwickelt wurde, mit integrierter Unterstützung für natürlichsprachliche Richtlinien, menschliche Genehmigungsworkflows und GPU-beschleunigte Richtlinienbewertung.
Erste Schritte mit OpenShell
OpenShell kann eigenständig verwendet werden, ohne den Rest des NemoClaw-Stacks:
# Install OpenShell standalone
curl -fsSL https://github.com/NVIDIA/OpenShell | bash
# Create a minimal sandbox policy
cat > my-policy.yaml << 'EOF'
apiVersion: openshell.nvidia.com/v1
kind: SandboxPolicy
metadata:
name: my-first-sandbox
spec:
isolation:
network: restricted
filesystem: workspace-only
syscalls: minimal
EOF
# Run any process inside the sandbox
openshell run --policy my-policy.yaml -- python my_agent.py
OpenShell ist Open Source unter Apache 2.0 und verfügbar unter nvidia/openshell auf GitHub. Im nächsten Beitrag erkunden wir reale Unternehmens-Einsatzszenarien für den vollständigen NemoClaw-Stack.