Back to skill

Security audit

soul-guardian

Security checks across malware telemetry and agentic risk

Overview

This is a disclosed local file-integrity monitor that can restore selected workspace files, with optional user-enabled scheduling and no evidence of hidden network access or malicious behavior.

Install only if you want a local guard that can overwrite protected workspace files back to approved baselines. Initialize baselines from known-good files, use --no-restore or alert-only policy if you do not want automatic restores, keep the state directory private, and enable cron or launchd only after reviewing the exact command and schedule.

SkillSpector

By NVIDIA
Vulnerability Patterns
  • Rogue AgentSelf-Modification, Session Persistence
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
Findings (9)

Lp3

Medium
Category
MCP Least Privilege
Confidence
96% confidence
Finding
The skill performs file reads/writes, shell execution, and environment-dependent operations, but does not declare permissions to match those capabilities. This creates a transparency and policy-enforcement gap: a host or reviewer may treat the skill as lower risk than it actually is, increasing the chance that destructive actions like restoring files or running helper scripts are approved implicitly.

Vague Triggers

Medium
Confidence
92% confidence
Finding
The trigger list includes broad phrases such as "workspace security," "guard files," and "integrity check" that are likely to match ordinary user requests unrelated to this specific skill. In an agent environment, overbroad triggers can cause unintended activation of a file-restoration or integrity-monitoring skill, increasing the chance of unauthorized file inspection or overwriting protected workspace content.

Session Persistence

Medium
Category
Rogue Agent
Content
ap.add_argument(
        "--label",
        default=None,
        help="launchd label (default: com.openclaw.soul-guardian.<agentId>). When using a non-legacy label, --install attempts to disable/boot out the previous com.clawdbot.soul-guardian.<agentId> job first.",
    )
    ap.add_argument(
        "--interval-seconds",
Confidence
98% confidence
Finding
launchd label (default: com.openclaw.soul-guardian.<agentId>). When using a non-legacy label, --install

Session Persistence

Medium
Category
Rogue Agent
Content
subprocess.run(["/bin/launchctl", "enable", f"gui/{uid}/{label}"], check=False)
        subprocess.run(["/bin/launchctl", "kickstart", "-k", f"gui/{uid}/{label}"], check=False)
        print("Installed + started (launchctl bootstrap/enable/kickstart).")
    else:
        print("Not installed (dry write). To load it:")
        print(f"  launchctl bootstrap gui/{uid} {plist_path}")
Confidence
98% confidence
Finding
launchctl bootstrap/enable

Session Persistence

Medium
Category
Rogue Agent
Content
ap.add_argument(
        "--install",
        action="store_true",
        help="Install+load the plist with launchctl (bootstrap). Without this flag we only write the plist.",
    )

    args = ap.parse_args(argv)
Confidence
97% confidence
Finding
plist

Session Persistence

Medium
Category
Rogue Agent
Content
ap.add_argument(
        "--install",
        action="store_true",
        help="Install+load the plist with launchctl (bootstrap). Without this flag we only write the plist.",
    )

    args = ap.parse_args(argv)
Confidence
97% confidence
Finding
plist

Session Persistence

Medium
Category
Rogue Agent
Content
plist_path.parent.mkdir(parents=True, exist_ok=True)

    if plist_path.exists() and not args.force:
        raise SystemExit(f"Refusing to overwrite existing {plist_path}. Re-run with --force.")

    with plist_path.open("wb") as f:
        plistlib.dump(plist, f, fmt=plistlib.FMT_XML, sort_keys=True)
Confidence
96% confidence
Finding
plist

Session Persistence

Medium
Category
Rogue Agent
Content
# Best-effort: remove any existing job with same label, then bootstrap.
        run_launchctl(["bootout", f"gui/{uid}", label])
        run_launchctl(["bootout", f"gui/{uid}", str(plist_path)])
        res = subprocess.run(["/bin/launchctl", "bootstrap", f"gui/{uid}", str(plist_path)], text=True, capture_output=True)
        if res.returncode != 0:
            sys.stderr.write((res.stderr or res.stdout or "").strip() + "\n")
Confidence
97% confidence
Finding
plist

Session Persistence

Medium
Category
Rogue Agent
Content
# Best-effort: remove any existing job with same label, then bootstrap.
        run_launchctl(["bootout", f"gui/{uid}", label])
        run_launchctl(["bootout", f"gui/{uid}", str(plist_path)])
        res = subprocess.run(["/bin/launchctl", "bootstrap", f"gui/{uid}", str(plist_path)], text=True, capture_output=True)
        if res.returncode != 0:
            sys.stderr.write((res.stderr or res.stdout or "").strip() + "\n")
            sys.stderr.write("Failed to bootstrap. You can try manually:\n")
Confidence
98% confidence
Finding
plist

VirusTotal

62/62 vendors flagged this skill as clean.

View on VirusTotal

Static analysis

Detected: suspicious.dynamic_code_execution

Dynamic code execution detected.

Critical
Code
suspicious.dynamic_code_execution
Location
scripts/test_install_launchd_plist.py:66