T09 · Insecure Skill Coding Practices
Error
- Location
- scripts/transcribe.sh:117
- Finding
- Python Code Injection Through the User-Controlled Output Path<![CDATA[ ## Vulnerability Details **File Location**: `scripts/transcribe.sh:117-153` **Vulnerability Type**: Python source-code injection **Risk Level**: High ### Vulnerable Code ```bash python3 -c " import re, sys with open('$SUB_FILE', 'r') as f: content = f.read() # Remove VTT header content = re.sub(r'^WEBVTT.*?\n\n', '', content, flags=re.DOTALL) # Remove timestamps and cue metadata lines = [] seen = set() for line in content.split('\n'): line = line.strip() # Skip timestamp lines if re.match(r'^\d{2}:\d{2}', line): continue # Skip empty lines and position metadata if not line or line.startswith('align:') or line.startswith('position:'): continue # Remove inline timestamps line = re.sub(r'<\d{2}:\d{2}:\d{2}\.\d{3}>', '', line) # Remove HTML tags line = re.sub(r'<[^>]+>', '', line) # Deduplicate if line not in seen: seen.add(line) lines.append(line) text = ' '.join(lines) # Clean up whitespace text = re.sub(r'\s+', ' ', text).strip() with open('$OUT_FILE', 'w') as f: f.write(text + '\n') print(f'Transcript saved ({len(text)} chars)', file=sys.stderr) " 2>&1 ``` ### Technical Analysis The `--out` option is accepted as user-controlled input and stored in `OUT_FILE`. The value is subsequently interpolated directly into the source text passed to `python3 -c`. Shell quoting does not make this value safe in the generated Python program. An output path containing a single quote and additional Python syntax can terminate the string literal in: ```python with open('$OUT_FILE', 'w') as f: ``` The remainder of the supplied value can then introduce arbitrary Python statements. The injected Python runs with the same operating-system identity, filesystem permissions, environment, and network access as the transcription script. The vulnerability is reached when the subtitle fast path successfully downloads a nonempty VTT file. It does not require the OpenAI fallback path. ### ...[truncated 1016 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions Do not interpolate paths or other external data into dynamically generated Python source. Pass both paths as positional arguments: ```bash python3 - "$SUB_FILE" "$OUT_FILE" <<'PY' import re import sys sub_file = sys.argv[1] out_file = sys.argv[2] with open(sub_file, "r", encoding="utf-8") as f: content = f.read() # Process the subtitle content here. with open(out_file, "w", encoding="utf-8") as f: f.write(content) PY ``` Additional hardening should include: 1. Validate that `--out` has an associated argument before shifting command-line parameters. 2. Use explicit text encodings and controlled error handling. 3. If output must be restricted to an approved directory, canonicalize the path and verify that it remains inside that directory. 4. Add regression tests containing quotes, newlines, command substitutions, spaces, and other metacharacters in output filenames. ]]>
