Back to skill

Security audit

OpenClaw Studio

Security checks for vulnerabilities and agentic risk

Overview

The skill is a local dashboard package, but it ships an under-disclosed macOS persistence installer that starts three background LaunchAgents, including optional recovery helpers, without separate user opt-in.

Review carefully before installing. Running the normal foreground command is lower risk, but do not run install_launchd.sh unless you intentionally want persistent macOS login services for monitor, auto-heal, and watchdog behavior. Verify the missing runtime files and use the uninstall script or launchctl to remove the LaunchAgents if they were installed.

Vulnerability Patterns
  • System PersistenceInstalls backdoors, hooks, services, or scheduled tasks that survive the run
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
Findings (3)

T06 · System Persistence

Warning
Location
install_launchd.sh:13
Finding
Unconditional Installation of Persistent macOS LaunchAgents<![CDATA[ ## Vulnerability Details **File Location**: `install_launchd.sh`, lines 13-89 **Vulnerability Type**: Unnecessary and unconditional startup persistence **Risk Level**: Medium ### Vulnerable Code ```sh cat > "$MONITOR_PLIST" <<EOF <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> <plist version="1.0"> <dict> <key>Label</key><string>com.studywest.openclaw.arcade-monitor</string> <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</string> <string>$DIR/server.py</string> </array> <key>WorkingDirectory</key><string>$DIR</string> <key>RunAtLoad</key><true/> <key>KeepAlive</key><true/> <key>StandardOutPath</key><string>$DIR/launchd-monitor.out.log</string> <key>StandardErrorPath</key><string>$DIR/launchd-monitor.err.log</string> </dict> </plist> EOF cat > "$AUTOHEAL_PLIST" <<EOF <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> <plist version="1.0"> <dict> <key>Label</key><string>com.studywest.openclaw.arcade-autoheal</string> <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</string> <string>$DIR/autoheal.py</string> </array> <key>WorkingDirectory</key><string>$DIR</string> <key>RunAtLoad</key><true/> <key>KeepAlive</key><true/> <key>StandardOutPath</key><string>$DIR/launchd-autoheal.out.log</string> <key>StandardErrorPath</key><string>$DIR/launchd-autoheal.err.log</string> </dict> </plist> EOF cat > "$WATCHDOG_PLIST" <<EOF <?xml version="1.0" encoding="UTF-8"?> <!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd"> <plist version="1.0"> <dict> <key>Label</key><string>com.studywest.openclaw.app-watchdog</string> <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</ ...[truncated 3266 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Install only the dashboard monitor by default. 2. Require explicit command-line flags or interactive confirmation before installing auto-heal or watchdog components. 3. Verify that every referenced executable exists, is a regular file, has expected ownership, and is not writable by untrusted users before creating any LaunchAgent. 4. Abort installation if required files are absent instead of registering broken persistent jobs. 5. Remove `KeepAlive` unless continuous restart behavior is essential and clearly disclosed. 6. Install executable files into a dedicated directory with restrictive permissions rather than executing them from an arbitrary unpacked project directory. 7. Record file hashes or use code signing where feasible to detect replacement after installation. 8. Clearly document persistence behavior, service names, execution frequency, logs, and uninstallation steps before installation. ]]>

T09 · Insecure Skill Coding Practices

Warning
Location
stop_monitor.sh:5
Finding
Port-Based Process Identification Can Terminate an Unrelated Service<![CDATA[ ## Vulnerability Details **File Location**: `start_bg.sh`, lines 8-12, and `stop_monitor.sh`, lines 5-8 **Vulnerability Type**: Unsafe process identification and termination **Risk Level**: Medium ### Vulnerable Code From `start_bg.sh`: ```sh if lsof -nP -iTCP:"$PORT" -sTCP:LISTEN >/dev/null 2>&1; then PID=$(lsof -nP -iTCP:"$PORT" -sTCP:LISTEN -t | head -n1) echo "$PID" > monitor.pid echo "Monitor already running on $HOST:$PORT (PID $PID)" exit 0 fi ``` From `stop_monitor.sh`: ```sh if lsof -nP -iTCP:18991 -sTCP:LISTEN >/dev/null 2>&1; then PID=$(lsof -nP -iTCP:18991 -sTCP:LISTEN -t | head -n1) kill "$PID" rm -f monitor.pid echo "Stopped monitor PID $PID" exit 0 fi ``` ### Technical Analysis The scripts treat the first process listening on the selected TCP port as the dashboard process. They do not validate the process executable, command line, ownership, launch time, or relationship to the script. `start_bg.sh` writes an arbitrary listener's PID to `monitor.pid` and reports that the monitor is already running. More critically, `stop_monitor.sh` ignores `monitor.pid` and kills the first process found on hardcoded port 18991. Port ownership is not a reliable process identity mechanism because any application may legitimately or intentionally bind that port. The start script also allows a configurable `MONITOR_PORT`, while the stop script always checks port 18991, creating an additional lifecycle mismatch. ### Attack Path 1. A legitimate unrelated application, or an attacker-controlled process running as the same user, binds to TCP port 18991. 2. The user runs `start_bg.sh`; the script incorrectly identifies the existing listener as OpenClaw Studio and records its PID. 3. The user later runs `stop_monitor.sh`. 4. The stop script discovers the first listener on port 18991 and sends it `SIGTERM` without validating its identity. 5. The unrelated application is terminated, causing denial of service or loss of in-progress work. ...[truncated 639 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Capture the PID of the process actually launched by the script using `$!` immediately after background execution. 2. Write the PID file atomically and apply restrictive permissions. 3. When stopping the service, read the recorded PID and validate it with `kill -0`. 4. Verify the process command line or executable path before sending a signal, for example by checking that it is the expected Python interpreter running the expected absolute `server.py` path. 5. Detect stale PID files by comparing process identity and start time where supported. 6. Use the same configured host and port consistently across start and stop operations, but use the port only as a secondary health check—not as process identity. 7. If identity validation fails, report the conflict and refuse to terminate the process. 8. For launchd-managed operation, prefer `launchctl bootout` or `launchctl kill` using the exact service label rather than searching by network port. ]]>

T09 · Insecure Skill Coding Practices

Note
Location
install_launchd.sh:19
Finding
Unescaped Project Path Is Interpolated into LaunchAgent XML<![CDATA[ ## Vulnerability Details **File Location**: `install_launchd.sh`, lines 19-25, 40-46, and 61-67 **Vulnerability Type**: Unsafe XML generation through shell interpolation **Risk Level**: Low ### Vulnerable Code ```sh <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</string> <string>$DIR/server.py</string> </array> <key>WorkingDirectory</key><string>$DIR</string> ``` The same pattern is used for the auto-heal component: ```sh <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</string> <string>$DIR/autoheal.py</string> </array> <key>WorkingDirectory</key><string>$DIR</string> ``` And for the watchdog component: ```sh <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>-u</string> <string>$DIR/app_watchdog.py</string> </array> <key>WorkingDirectory</key><string>$DIR</string> ``` ### Technical Analysis The absolute project path stored in `$DIR` is inserted directly into XML here-documents. XML metacharacters such as `&`, `<`, and `>` are not escaped. A valid filesystem directory name can contain these characters, so installing the package from such a path can produce malformed XML or alter the generated plist structure. Shell quoting does not protect XML syntax after interpolation. Although the path is not evaluated by the shell as code during here-document expansion, it is interpreted by the plist XML parser after the file is written. The primary realistic outcome is denial of installation through malformed plist data. Carefully structured path text could also inject additional XML nodes if it results in a plist accepted by the parser. ### Attack Path 1. An attacker distributes or places the package under a directory whose name contains XML metacharacters and crafted plist markup. 2. The user runs `install_launchd.sh` from that location. 3. The script computes the crafted absolute directory path and interpolates it into multiple `<string>` ...[truncated 739 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. Do not construct plist XML through unescaped shell here-documents. 2. Generate plist files using a structured serializer such as Python's `plistlib`, which automatically escapes path values. 3. Alternatively, use a native plist-management utility that treats values as data rather than markup. 4. If shell generation cannot be avoided, apply correct XML escaping to every interpolated value, including replacing `&`, `<`, `>`, `"`, and `'` with their corresponding entities. 5. Validate generated files with `plutil -lint` before invoking `launchctl bootstrap`. 6. Write generated plists to a temporary file with restrictive permissions, validate them, and atomically move them into `~/Library/LaunchAgents`. 7. Reject installation paths containing unsupported control characters or newline characters. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Rogue AgentSelf-Modification, Session Persistence
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
Findings (38)

Tool Parameter Abuse

High
Category
Tool Misuse
Content
launchctl bootout "gui/$UID_NOW/$MONITOR_LABEL" >/dev/null 2>&1 || true
launchctl bootout "gui/$UID_NOW/$AUTOHEAL_LABEL" >/dev/null 2>&1 || true
launchctl bootout "gui/$UID_NOW/$WATCHDOG_LABEL" >/dev/null 2>&1 || true
rm -f "$LAUNCH_DIR/$MONITOR_LABEL.plist" "$LAUNCH_DIR/$AUTOHEAL_LABEL.plist" "$LAUNCH_DIR/$WATCHDOG_LABEL.plist"

echo "Uninstalled launchd services."
Confidence
95% confidence
Finding
Tool parameters are crafted to achieve unintended or unsafe behavior. Parameter abuse can bypass intended safety checks (e.g. shell=True, --force, dangerous glob patterns).

Missing User Warnings

Medium
Confidence
89% confidence
Finding
The README advertises control actions and optional auto-heal/watchdog helpers but does not clearly warn that these features can automatically intervene in a live agent session. In a local operations dashboard, missing disclosure can mislead users into enabling automation they do not fully understand, causing unintended agent actions, restarts, or workflow disruption.

Description-Behavior Mismatch

Medium
Confidence
91% confidence
Finding
The release notes advertise capabilities such as automatic prompting/automation, self-healing, and watchdog behavior that expand beyond a simple local dashboard and optional recovery-helper scope. This kind of scope drift is security-relevant because it can normalize or conceal autonomous control features that may perform actions without clear user consent, review, or corresponding documentation in the manifest.

Missing User Warnings

Medium
Confidence
94% confidence
Finding
The script creates the user's LaunchAgents directory entries and prepares persistent service definitions without any confirmation, prompt, or prior warning. Writing autorun configuration silently is risky because users may believe they are just launching a dashboard, while the system is being modified to start code automatically on future logins.

Session Persistence

Medium
Category
Rogue Agent
Content
LAUNCH_DIR="$HOME/Library/LaunchAgents"
mkdir -p "$LAUNCH_DIR"

MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"
Confidence
85% confidence
Finding
This line defines a LaunchAgent plist path under '$HOME/Library/LaunchAgents', which is the standard user-session persistence location on macOS. In context with the subsequent file writes and launchctl calls, it is part of establishing login-time persistence rather than a harmless string reference.

Session Persistence

Medium
Category
Rogue Agent
Content
LAUNCH_DIR="$HOME/Library/LaunchAgents"
mkdir -p "$LAUNCH_DIR"

MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"
Confidence
85% confidence
Finding
This line defines a LaunchAgent plist path under '$HOME/Library/LaunchAgents', which is the standard user-session persistence location on macOS. In context with the subsequent file writes and launchctl calls, it is part of establishing login-time persistence rather than a harmless string reference.

Session Persistence

Medium
Category
Rogue Agent
Content
mkdir -p "$LAUNCH_DIR"

MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
Confidence
83% confidence
Finding
This line defines another plist path in the LaunchAgents directory for a second background component. In this script's context, each additional agent increases the persisted attack surface and the amount of code that will execute automatically in the user session.

Session Persistence

Medium
Category
Rogue Agent
Content
mkdir -p "$LAUNCH_DIR"

MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
Confidence
83% confidence
Finding
This line defines another plist path in the LaunchAgents directory for a second background component. In this script's context, each additional agent increases the persisted attack surface and the amount of code that will execute automatically in the user session.

Session Persistence

Medium
Category
Rogue Agent
Content
MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
Confidence
83% confidence
Finding
This line defines a third LaunchAgent plist path, adding yet another persistent background task. For a local dashboard skill, establishing three separate login-persistent services is more dangerous than a single foreground process because it increases unnoticed background execution and maintenance burden.

Session Persistence

Medium
Category
Rogue Agent
Content
MONITOR_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-monitor.plist"
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
Confidence
83% confidence
Finding
This line defines a third LaunchAgent plist path, adding yet another persistent background task. For a local dashboard skill, establishing three separate login-persistent services is more dangerous than a single foreground process because it increases unnoticed background execution and maintenance burden.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
AUTOHEAL_PLIST="$LAUNCH_DIR/com.studywest.openclaw.arcade-autoheal.plist"
WATCHDOG_PLIST="$LAUNCH_DIR/com.studywest.openclaw.app-watchdog.plist"

cat > "$MONITOR_PLIST" <<EOF
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
<plist version="1.0">
Confidence
75% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Description-Behavior Mismatch

Medium
Confidence
95% confidence
Finding
The script installs three separate launchd LaunchAgents that automatically run at login and, for two of them, remain always-on via KeepAlive. For a skill described as helping run a local dashboard session, silently persisting multiple background services expands the trust boundary and creates ongoing execution beyond the user’s immediate intent, especially because the referenced Python files will be re-executed on future sessions.

Missing User Warnings

Medium
Confidence
96% confidence
Finding
The script unloads any existing agents, bootstraps replacement LaunchAgents, enables them, and immediately starts them without interactive consent. This makes persistent execution take effect right away and can replace prior service state in a way the user may not expect, increasing the chance of unnoticed long-lived background activity.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootout "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal" >/dev/null 2>&1 || true
launchctl bootout "gui/$UID_NOW/com.studywest.openclaw.app-watchdog" >/dev/null 2>&1 || true

launchctl bootstrap "gui/$UID_NOW" "$MONITOR_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$AUTOHEAL_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
Confidence
86% confidence
Finding
This line bootstraps the first LaunchAgent into the current GUI session, making the persisted service active. Immediate activation of a login-persistent background service raises risk because code in the local directory begins executing under launchd management without further user interaction.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootout "gui/$UID_NOW/com.studywest.openclaw.app-watchdog" >/dev/null 2>&1 || true

launchctl bootstrap "gui/$UID_NOW" "$MONITOR_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$AUTOHEAL_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
Confidence
86% confidence
Finding
This line bootstraps the second LaunchAgent, activating the autoheal background service in the current user session. Since it is intended to remain active and self-recover, loading it automatically increases the durability and opacity of background execution.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootstrap "gui/$UID_NOW" "$MONITOR_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$AUTOHEAL_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.app-watchdog"
Confidence
86% confidence
Finding
This line bootstraps the third LaunchAgent, activating the watchdog service immediately. Combined with the scheduled StartInterval behavior, it establishes recurring background execution that may continue inspecting or restarting application components beyond what a user expects from a local dashboard launcher.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootstrap "gui/$UID_NOW" "$MONITOR_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$AUTOHEAL_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.app-watchdog"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
Confidence
90% confidence
Finding
This line explicitly enables a launchd agent for future sessions, creating persistence in the user's login context. Persistent autorun is security-relevant because any compromise or unsafe behavior in the referenced Python service will recur automatically without further user action.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootstrap "gui/$UID_NOW" "$AUTOHEAL_PLIST"
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.app-watchdog"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
Confidence
90% confidence
Finding
This line enables the autoheal agent to run persistently in future sessions. Because the component is named and configured as an always-on recovery helper, it materially increases background execution and could repeatedly run code from the install directory even after the original dashboard session ends.

Session Persistence

Medium
Category
Rogue Agent
Content
launchctl bootstrap "gui/$UID_NOW" "$WATCHDOG_PLIST"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
launchctl enable "gui/$UID_NOW/com.studywest.openclaw.app-watchdog"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.arcade-monitor"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.arcade-autoheal"
launchctl kickstart -k "gui/$UID_NOW/com.studywest.openclaw.app-watchdog"
Confidence
90% confidence
Finding
This line enables the watchdog agent for future sessions, extending execution beyond a single user-invoked run. Even though it runs on an interval rather than KeepAlive, it still establishes recurring autorun behavior that can mask or perpetuate unsafe code paths in the monitored application.

Session Persistence

Medium
Category
Rogue Agent
Content
exit 0
fi

MONITOR_HOST="$HOST" MONITOR_PORT="$PORT" /usr/bin/nohup /usr/bin/python3 -u server.py </dev/null >monitor.log 2>&1 &
PID=""
for _ in {1..10}; do
  sleep 1
Confidence
65% confidence
Finding
Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Static analysis

No suspicious patterns detected.