T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/scan_gitcode_issues.py:294
- Finding
- Shell Command Injection in Generated Issue-Closing Scripts<![CDATA[ ## Vulnerability Details **File Location**: `scripts/scan_gitcode_issues.py`, lines 294–325 **Vulnerability Type**: Shell command injection through unsafe script generation **Risk Level**: High ### Vulnerable Code PowerShell script generation: ```python return f'''# Generated GitCode Issue close script. Review before running. $ErrorActionPreference = "Stop" $gitcode = "{gitcode_command}" $repo = "{repo}" $targetBranch = "{target_branch}" $issues = @({",".join(str(number) for number in numbers)}) ``` Bash script generation: ```python return f'''#!/usr/bin/env bash # Generated GitCode Issue close script. Review before running. set -euo pipefail gitcode_cmd="{gitcode_command}" repo="{repo}" target_branch="{target_branch}" issues=({number_text}) ``` ### Technical Analysis The `repo`, `target_branch`, and `gitcode_command` values are embedded directly into executable Bash or PowerShell source code. No validation or shell-specific escaping is applied before these values are placed inside double-quoted assignments. Double quotes do not make untrusted values safe in either supported shell: - In Bash, command substitution such as `$(command)` remains active inside double quotes. - In PowerShell, a value containing a double quote can terminate the string and append additional statements. - Newline and other shell metacharacters can alter the structure of the generated script. The live scan invokes the GitCode CLI through an argument array and is not itself vulnerable to conventional shell injection. The vulnerability occurs when the generated close script is subsequently executed. The target branch is the most direct injection vector because it is used during local classification and then inserted into the generated script without being required to identify a valid executable. For example, a Bash target branch resembling the following would produce an executable command substitution in the generated assignment: ```text $(touch /tmp/s ...[truncated 2203 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions 1. **Apply strict input validation** - Validate repository identifiers against the exact GitCode `owner/repository` grammar. - Reject carriage returns, newlines, null bytes, and shell metacharacters. - Validate target branch names using a conservative allowlist or Git-compatible reference validation. - Do not accept an arbitrary command expression for `--gitcode-command`; resolve it to a verified executable path. 2. **Use shell-specific literal encoding** - For Bash, emit single-quoted literals and replace each embedded apostrophe using the standard safe sequence. - For PowerShell, use single-quoted literals and escape embedded apostrophes by doubling them. - Do not rely on double quotes for untrusted values. 3. **Prefer runtime parameters over source interpolation** - Generate a static script that receives the repository and target branch as validated command-line parameters. - Keep issue numbers as integers and validate all arguments before invoking the GitCode CLI. 4. **Separate executable selection from generated data** - Resolve the GitCode executable with `shutil.which`. - Require a regular executable file. - Store or pass the resolved absolute path using safe literal encoding. 5. **Add security regression tests** - Test values containing `$(...)`, backticks, quotes, semicolons, dollar signs, PowerShell subexpressions, carriage returns, and newlines. - Parse or execute generated scripts in an isolated environment and verify that input values cannot create additional commands. 6. **Retain defense-in-depth controls** - Continue requiring manual review and revalidation before closing issues. - Clearly mark generated scripts as containing potentially sensitive repository operations. - Avoid automatically executing or sourcing generated files. ]]>
