T09 · Insecure Skill Coding Practices
Error
- Location
- tool_catalog.json:58
- Finding
- Shell Command Injection in L0 Fallback Invocation Templates<![CDATA[ ## Vulnerability Details **File Location**: `tool_catalog.json:58-64` **Vulnerability Type**: User-controlled input embedded in shell command templates **Risk Level**: High ### Vulnerable Code ```json { "name": "PubMed E-utilities", "priority": 1, "invocation": "exec: curl -s 'https://eutils.ncbi.nlm.nih.gov/entrez/eutils/esearch.fcgi?db=pubmed&retmax=20&api_key=${NCBI_API_KEY}&term=QUERY' | Then use efetch to obtain details", "strength": "Biomedical literature gold standard with complete metadata", "limitation": "Biomedical content only; no AI summary", "free": true, "notes": "API key is available in the NCBI_API_KEY environment variable" } ``` Equivalent unsafe placeholders occur in other catalog commands, including `QUERY`, `URL`, `RECIPIENT`, `SUBJECT`, `BODY`, `OUTPUT`, and `PMID`. ### Technical Analysis The catalog explicitly labels the command as an `exec` invocation and places the `QUERY` placeholder inside a shell command string. It does not define URL encoding, shell escaping, argument validation, or an argument-array execution contract. If an external catalog runner performs direct string replacement and passes the resulting command to a shell, a query containing a single quote and shell metacharacters can terminate the quoted URL and append another command. Similar issues affect email fields, download URLs, output paths, and JSON bodies elsewhere in the catalog. The project does not contain the catalog executor, so the vulnerable operation depends on the surrounding Agent framework interpreting the documented `exec:` template. Nevertheless, the template instructs the framework to construct an unsafe shell command from user-controlled data. ### Attack Path 1. An attacker submits a query containing shell syntax designed to terminate the single-quoted URL. 2. The router rejects the request at the L1 Skill-routing layer and sends it to the L0 fallback layer. 3. The fallback implementation selects the PubMed or another `ex ...[truncated 947 chars]
- Remediation
- <![CDATA[ ## Remediation Suggestions 1. Replace shell-form command templates with structured invocation definitions: ```json { "method": "GET", "url": "https://eutils.ncbi.nlm.nih.gov/entrez/eutils/esearch.fcgi", "query_parameters": { "db": "pubmed", "retmax": 20, "api_key_env": "NCBI_API_KEY", "term_input": "QUERY" } } ``` 2. Use a native HTTP client or a structured tool API rather than `curl`. 3. If a subprocess is unavoidable, call it with an argument array and `shell=False`. 4. Apply URL encoding and JSON serialization through standard libraries rather than string concatenation. 5. Validate PMIDs, email recipients, URLs, and output paths against strict schemas. 6. Restrict network destinations to an explicit allowlist. 7. Never expose expanded commands containing API keys in logs or model context. 8. Require user confirmation before transmitting potentially sensitive medical or personal queries. ]]>
