Back to skill

Security audit

Stock Prediction

Security checks for vulnerabilities and agentic risk

Overview

The skill matches a local stock-prediction workflow, but it needs review because it can automatically start local services and contains an unsafe command-building path that could run unintended commands.

Install only in a trusted local Kronos environment. Before using it, require confirmation before starting the backend or switching models, run it under a low-privilege account, and fix run_prediction.py to validate dates and call the prediction script with an argument list instead of a PowerShell command string.

Vulnerability Patterns
  • Insecure Skill Coding PracticesFinds exploitable flaws such as hardcoded secrets or command injection
  • Skill Instruction HijackingAlters the agent's session goals or safety constraints when the skill loads
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (1)

T09 · Insecure Skill Coding Practices

Error
Location
scripts/run_prediction.py:22
Finding
PowerShell Command Injection Through Unvalidated Prediction Date<![CDATA[ ## Vulnerability Details **File Location**: `scripts/run_prediction.py`, lines 22–38 **Vulnerability Type**: OS command injection through unsafe PowerShell command construction **Risk Level**: High ### Vulnerable Code ```python def run_prediction(start_date: str, samples: int, output_dir: str): """ Execute batch prediction. Args: start_date: Prediction start date (YYYY-MM-DD) samples: Number of samples output_dir: Output directory used to locate the input file """ # Build command cmd = f'conda activate {CONDA_ENV} && python .\\batch_predict.py --start_date {start_date} --samples {samples}' print(f"执行预测: {cmd}") print(f"工作目录: {PREDICT_DIR}") result = subprocess.run( ['powershell', '-Command', cmd], cwd=PREDICT_DIR, capture_output=True, text=True ) ``` The externally supplied value originates from the command-line interface: ```python parser.add_argument('--start_date', required=True, help='预测开始日期 (YYYY-MM-DD)') parser.add_argument('--samples', type=int, required=True, help='采样次数') parser.add_argument('--output_dir', required=True, help='输出目录') parser.add_argument('--input_file', required=True, help='输入文件名') args = parser.parse_args() success = run_prediction(args.start_date, args.samples, args.output_dir) ``` ### Technical Analysis The `start_date` parameter is accepted as an unrestricted string. Although its help text states that the expected format is `YYYY-MM-DD`, the script does not parse or validate it as a date. The value is interpolated directly into `cmd`, which is then passed to `powershell -Command`. PowerShell interprets command separators, pipelines, redirections, subexpressions, and other shell metacharacters contained in that string. Consequently, a caller who can control `--start_date` can terminate or alter the intended `batch_predict.py` invocation and append additional PowerShell operations. The `samples` parameter is converted ...[truncated 1961 chars]
Remediation
<![CDATA[ ## Remediation Suggestions 1. **Strictly validate and canonicalize the date** Parse the value with `datetime.strptime()` and reject any value that is not exactly in canonical `YYYY-MM-DD` format: ```python from datetime import datetime def validate_date(value: str) -> str: try: parsed = datetime.strptime(value, "%Y-%m-%d") except ValueError as exc: raise ValueError("start_date must use YYYY-MM-DD format") from exc canonical = parsed.strftime("%Y-%m-%d") if value != canonical: raise ValueError("start_date must use canonical YYYY-MM-DD format") return canonical ``` 2. **Avoid constructing a PowerShell command string** Resolve the intended Python executable or use `conda run`, then pass every argument as a separate list element without shell interpretation: ```python validated_date = validate_date(start_date) if not 1 <= samples <= 10000: raise ValueError("samples is outside the permitted range") result = subprocess.run( [ "conda", "run", "-n", CONDA_ENV, "python", ".\\batch_predict.py", "--start_date", validated_date, "--samples", str(samples), ], cwd=PREDICT_DIR, capture_output=True, text=True, shell=False, check=False, ) ``` 3. **Apply explicit bounds to numeric inputs** Although `samples` is parsed as an integer, enforce a reasonable minimum and maximum to prevent resource exhaustion or accidental denial of service. 4. **Do not rely on quoting as the primary defense** PowerShell escaping is complex and context-sensitive. Input validation and argument-array execution without a command shell should be used instead of attempting to escape attacker-controlled text. 5. **Limit execution privileges** Run the prediction process under a dedicated, non-administrative account ...[truncated 343 chars]
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
Findings (12)

Lp3

Medium
Category
MCP Least Privilege
Confidence
96% confidence
Finding
The skill performs sensitive actions including local file writes, HTTP requests to a local service, and shell execution, but it declares no explicit tool scope or permission boundary. This creates an unsafe mismatch between what the skill advertises and what it can do, increasing the risk of unintended command execution, service manipulation, or data exposure when the skill is triggered.

Missing User Warnings

Medium
Confidence
93% confidence
Finding
The skill writes extracted stock codes and generated prediction results to local disk, but the user-facing description does not clearly disclose this persistence behavior. Undisclosed storage can expose sensitive financial interests, leave residual data on shared systems, and prevent users from making an informed consent decision.

Missing User Warnings

Medium
Confidence
95% confidence
Finding
The skill can automatically start a backend service and run shell commands if a health check fails, but this behavior is not clearly disclosed in the skill description. Auto-healing via shell execution is dangerous because it expands the effect of a simple user request into local process creation and command execution on the host.

External Transmission

Medium
Category
Data Exfiltration
Content
**切换逻辑:**
若当前模型不是 `kronos-base`,调用:
```bash
curl -X 'POST' 'http://localhost:8000/model/switch' \
  -H 'Content-Type: application/json' \
  -d '{"model_name": "kronos-base"}'
```
Confidence
60% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Missing User Warnings

Medium
Confidence
95% confidence
Finding
This script automatically starts a local backend service whenever the health check fails, without user confirmation, policy gating, or trust verification of the target code directory. In an agent skill context, that behavior is more dangerous because a simple trigger can cause local code execution and persistent service startup on the host, expanding the attack surface beyond passive analysis.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
cmd = f'conda activate {CONDA_ENV} && python .\\main.py'
    
    # 使用 PowerShell 启动
    subprocess.Popen(
        ['powershell', '-Command', cmd],
        cwd=BACKEND_DIR,
        creationflags=subprocess.CREATE_NEW_CONSOLE
Confidence
70% confidence
Finding
subprocess module calls execute external commands. Without careful input validation, this enables command injection.

Natural-Language Policy Violations

Medium
Confidence
91% confidence
Finding
This code includes natural-language docstrings and console messages only in Chinese, such as the module description and status output. Because the file provides no opt-in or alternative locale, it imposes a specific language on users and operators, which matches the language/locale policy violation criteria.

Internal Network Request

Medium
Category
Server-Side Request Forgery
Content
else:
        # 如果没有参数,先检查健康状态
        import urllib.request
        req = urllib.request.Request("http://localhost:8000/health", method='GET')
        with urllib.request.urlopen(req, timeout=5) as response:
            health_data = json.loads(response.read().decode('utf-8'))
Confidence
70% confidence
Finding
Code issues a request to a loopback, link-local, or private-range host. This can reach internal services not meant to be exposed and is a common SSRF pivot.

Natural-Language Policy Violations

Medium
Confidence
92% confidence
Finding
This code file contains natural-language strings and documentation exclusively in Chinese, including the module docstring, function docstrings, and command-line help text. Under the policy rule, forcing a specific language without opt-in or documented justification is a language/locale policy violation.

subprocess module call

Medium
Category
Dangerous Code Execution
Content
print(f"执行预测: {cmd}")
    print(f"工作目录: {PREDICT_DIR}")
    
    result = subprocess.run(
        ['powershell', '-Command', cmd],
        cwd=PREDICT_DIR,
        capture_output=True,
Confidence
96% confidence
Finding
The script builds a PowerShell command string using externally supplied CLI arguments (`start_date` and `samples`) and executes it via `powershell -Command`. Passing a composed string into a shell introduces command-injection risk if validation is bypassed or expanded in future changes; in this skill context, user-driven workflow parameters make that risk more concerning because the agent may process untrusted inputs automatically.

Missing User Warnings

Low
Confidence
88% confidence
Finding
The skill may automatically switch the active model by POSTing to a local API, but this state-changing behavior is not clearly communicated to the user. Silent model switching can alter other workflows, break expectations, or interfere with co-hosted services that depend on the current model selection.

Natural-Language Policy Violations

Low
Confidence
91% confidence
Finding
The module docstring and multiple user-facing print messages are written only in Chinese, which imposes a fixed language on users without opt-in or alternative locale handling. The policy allows fixed locale behavior only when explicitly justified or when users are given a choice.

Static analysis

No suspicious patterns detected.