T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/install.sh:40
- Finding
- Persistent Shell Command Injection Through macOS Installer Parameters<![CDATA[ ## Vulnerability Details **File Location**: `scripts/install.sh`, lines 40-47 **Vulnerability Type**: Shell source-code injection through unsafe template substitution **Risk Level**: High ### Vulnerable Code ```bash # 1. Copy + patch watchdog script mkdir -p "$SCRIPTS_DIR" cp "$SKILL_DIR/scripts/gateway-watchdog.sh" "$WATCHDOG_SCRIPT" chmod +x "$WATCHDOG_SCRIPT" sed -i '' "s|PROBE_URL=\"http://127.0.0.1:YOUR_OC_PORT\"|PROBE_URL=\"http://127.0.0.1:${OC_PORT}\"|g" "$WATCHDOG_SCRIPT" sed -i '' "s|YOUR_TELEGRAM_ID|${TELEGRAM_ID}|g" "$WATCHDOG_SCRIPT" ``` ### Technical Analysis `OC_PORT` and `TELEGRAM_ID` are accepted from the installer environment without format validation or escaping and are substituted directly into an executable shell script. An attacker-controlled value containing a double quote followed by shell syntax can terminate the generated variable assignment and add commands to the installed watchdog. For example, a malicious Telegram identifier shaped like: ```text "; attacker_command; # ``` would cause the generated assignment to contain an additional shell command. Because the resulting script is registered with launchd, the injected command can execute repeatedly whenever the persistent watchdog runs. Shell quoting around the `sed` command does not make the generated shell source safe. It protects the installer command from immediate shell expansion, but it does not escape the value for its destination context as Bash source code. Replacement delimiters and `sed` metacharacters can also corrupt the substitution. ### Attack Path 1. An attacker convinces a user or automation workflow to run the installer with a malicious `OC_PORT` or `TELEGRAM_ID`. 2. The installer copies `gateway-watchdog.sh` into the workspace. 3. The unvalidated value is inserted into the copied executable script through `sed`. 4. The installer creates and bootstraps a launchd agent that periodically executes the modified script. 5. The injected command execute ...[truncated 604 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions - Require `OC_PORT` to contain only decimal digits, then enforce the valid TCP port range: ```bash if ! [[ "$OC_PORT" =~ ^[0-9]{1,5}$ ]] || (( OC_PORT < 1 || OC_PORT > 65535 )); then echo "ERROR: OC_PORT must be an integer from 1 to 65535." >&2 exit 1 fi ``` - Validate `TELEGRAM_ID` against the exact format supported by the Telegram integration, such as an optional signed numeric identifier if that is the required format. - Do not generate executable shell source by performing text replacement with untrusted values. - Prefer passing validated settings as launchd environment variables and reading them at runtime. - If source generation is unavoidable, serialize values with context-appropriate Bash escaping, such as `printf '%q'`, rather than using raw `sed` replacement. - Add installation tests using quotes, backslashes, delimiters, newlines, and shell metacharacters to verify that malformed input is rejected. ]]>
