T06 · System Persistence
Error
- Location
- install.sh:45
- Finding
- Persistent LaunchAgent Installed and Kept Alive Without Separate Opt-In<![CDATA[ ## Vulnerability Details **File Location**: `install.sh:45-89` **Vulnerability Type**: Persistent background service registration **Risk Level**: High ### Vulnerable Code ```bash # 5. Write LaunchAgent plist echo "Writing LaunchAgent plist: $PLIST_PATH" mkdir -p "$HOME/Library/LaunchAgents" cat > "$PLIST_PATH" << 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.lobster.api-proxy</string> <key>ProgramArguments</key> <array> <string>/usr/bin/python3</string> <string>${INSTALL_DIR}/proxy.py</string> <string>--port</string> <string>${PROXY_PORT}</string> <string>--upstream</string> <string>${UPSTREAM}</string> <string>--log-dir</string> <string>${LOG_DIR}</string> </array> <key>RunAtLoad</key> <true/> <key>KeepAlive</key> <true/> <key>StandardOutPath</key> <string>${LOG_DIR}/proxy.stdout.log</string> <key>StandardErrorPath</key> <string>${LOG_DIR}/proxy.stderr.log</string> <key>WorkingDirectory</key> <string>${INSTALL_DIR}</string> </dict> </plist> EOF # 6. Load LaunchAgent launchctl unload "$PLIST_PATH" 2>/dev/null || true launchctl load "$PLIST_PATH" ``` ### Technical Analysis The installer creates a macOS LaunchAgent with both `RunAtLoad` and `KeepAlive` enabled and immediately loads it. Consequently, the API interception proxy starts automatically in future login sessions and is restarted whenever it exits. Continuous operation can be useful for transparent API logging, and the behavior is disclosed in the documentation. However, an always-on, self-restarting service is not the minimum privilege or lifetime required for an on-demand log viewer or manually operated proxy. The installer provides no separate persistence confirmation, nonpersistent installation mode, ...[truncated 1180 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions - Run the proxy in the foreground or on demand by default. - Present persistence as a separate, explicit installation option requiring informed user consent. - Do not enable `KeepAlive` unless continuous restart behavior is strictly required. - Provide a documented uninstaller that unloads and deletes the LaunchAgent and optionally removes retained logs. - Restrict the installation directory and executable so they are writable only by the owning user. - Verify the ownership and permissions of the plist, installation directory, and proxy before loading the service. - Prefer modern `launchctl bootstrap` and `bootout` commands with explicit user-domain handling. ]]>
