Back to skill

Security audit

modelscope_img_generator

Security checks for vulnerabilities and agentic risk

Overview

This image-generation skill appears purpose-aligned, but its API-key handling and actual network behavior are under-scoped enough to require review before installation.

Review before installing. Prefer setting MODELSCOPE_API_KEY through a protected environment or secret mechanism rather than pasting the key into chat or using --api-key. Use only trusted ModelScope models and LoRAs, and be aware that prompts and input images are sent to ModelScope. The publisher should tighten the network boundary by validating result-image URLs, update the fixed-endpoint claims, and pin dependencies.

Vulnerability Patterns
  • Insecure DependenciesIntroduces malicious components through unsafe dependency sources
  • 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
Findings (3)

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/generate_img.py:251
Finding

Unvalidated Server-Provided URL Enables Arbitrary Network Requests

Content
View full analysis
Remediation
View remediation

T09 · Insecure Skill Coding Practices

Warning
Location
scripts/generate_img.py:166
Finding

API Credential Can Be Exposed Through Command-Line Arguments

Content
View full analysis
str | None: """Get API key from argument first, then environment.""" if provided_key: return provided_key return os.environ.get("MODELSCOPE_API_KEY") ``` ### Technical Analysis The Skill accepts the ModelScope API key directly in the command line. Command-line secrets may be exposed through: - Shell history - Process listings and process-inspection interfaces - Agent command transcripts - Terminal session logs - Monitoring and audit systems - Error reports that capture command invocations `SKILL.md` also documents and recommends the `--api-key` method, including its use when a key is supplied in chat. This increases the likelihood that a credential will be copied into persistent logs or execution records. The key is legitimately required for the declared image-generation functionality, and the code sends it only to the ModelScope submission and polling endpoints. The finding concerns the unsafe credential-input mechanism rather than intentional credential exfiltration. ### Attack Path 1. A user or Agent invokes the documented command with `--api-key `. 2. The complete command is stored in shell history, an Agent transcript, process telemetry, or an execution log. 3. Another local user, administrator, support operator, or log reader accesses that record. 4. The exposed key is reused to authenticate to ModelScope. 5. The attacker performs unauthorized operations within the permissions and quota assigned to that API key. ### Impact Assessment Exposure could permit ...[truncated 399 chars]
Remediation
View remediation

T08 · Insecure Dependencies

Note
Location
scripts/generate_img.py:3
Finding

Unpinned Runtime Dependencies Create Supply-Chain and Reproducibility Risk

Content
View full analysis
=3.10" # dependencies = [ # "requests>=2.31.0", # "pillow>=10.0.0", # ] # /// ``` The same floating dependency constraints are declared in `manifest.yaml`: ```yaml dependencies: - requests>=2.31.0 - pillow>=10.0.0 ``` ### Technical Analysis The Skill uses lower-bound-only version constraints and provides no reviewed lockfile or package hashes. Running the script through `uv` can therefore resolve and install dependency releases published after the Skill was audited. No evidence of typosquatting, dependency confusion, or intentionally malicious package selection was found: `requests` and `pillow` are established packages. The risk arises because the exact code executed at runtime is not fixed and can change independently of this Skill package. ### Attack Path 1. A future dependency version is compromised, maliciously published, or contains a newly introduced vulnerability. 2. The Skill is executed in an environment without an existing locked dependency resolution. 3. `uv` resolves a version satisfying the broad `>=` constraint. 4. The package is installed and imported into the Skill process. 5. Its initialization or runtime code executes with the same filesystem, network, environment-variable, and process privileges as the Skill. ### Impact Assessment A compromised dependency would execute within the Skill process and could potentially: - Read the `MODELSCOPE_API_KEY` environment variable - Access prompts and input images processed by the Skill - Read or modify files available to the invoking user - Make network requests from the Agent environment - Alter generated output or application behavior This is a supply-chain hardening issue rather than evidence that the currently named dependencies are malic ...[truncated 9 chars]
Remediation
View remediation
Vulnerability Patterns
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Memory PoisoningPersistent Context Injection, Context Window Stuffing, Memory Manipulation
  • Rogue AgentSelf-Modification, Session Persistence
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
  • MCP Least PrivilegeUnderdeclared Capability, Wildcard Permission, Missing Permission Declaration
Findings (8)

Memory Manipulation

High
Category
Memory Poisoning
Confidence
80% confidence
Finding

Skill manipulates agent memory, state, or stored context. Memory corruption can alter personality, override safety rules, or cause unpredictable behavior.

Content

Scanner excerpt · SKILL.md (reported line 106)May include surrounding context.

md
- Prompt "A serene Japanese garden" → `2025-11-23-14-23-05-japanese-garden.jpg`
- Prompt "sunset over mountains" → `2025-11-23-15-30-12-sunset-mountains.jpg`
- Prompt "create an image of a robot" → `2025-11-23-16-45-33-robot.jpg`
- Unclear context → `2025-11-23-17-12-48-x9k2.jpg`

## Image Editing

Credential Access

High
Category
Privilege Escalation
Confidence
70% confidence
Finding

Code accesses credential files (SSH keys, AWS credentials, etc.). This could indicate credential theft attempts.

Content

Scanner excerpt · scripts/generate_img.py (reported line 44)May include surrounding context.

python
def get_api_key(provided_key: str | None) -> str | None:
    """Get API key from argument first, then environment."""
    if provided_key:
        return provided_key
    return os.environ.get("MODELSCOPE_API_KEY")

Undeclared Tool Scope

Medium
Category
MCP Least Privilege
Confidence
96% confidence
Finding

The skill documents capabilities that require access to environment variables and outbound network connections, but it does not declare any explicit tool scope such as permissions or allowed-tools. That gap weakens reviewability and policy enforcement because an agent may invoke the skill without a clear, auditable declaration of the sensitive capabilities it needs.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
84% confidence
Finding

The security notice asserts that the endpoint is fixed and cannot be redirected, but the same skill allows arbitrary --model and --lora repository identifiers that influence what remote resources the service processes. This is not direct SSRF from the local environment, but it is a misleading security claim that can cause over-trust while still permitting user-controlled remote dependency selection with possible data-handling, prompt-routing, or supply-chain implications on the provider side.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
60% confidence
Finding

Skill establishes unauthorized persistence across sessions via cron jobs, startup scripts, or state files. Session persistence allows an attacker to maintain access beyond the current interaction.

Content

Scanner excerpt · SKILL.md (reported line 105)May include surrounding context.

md
Examples:
- Prompt "A serene Japanese garden" → `2025-11-23-14-23-05-japanese-garden.jpg`
- Prompt "sunset over mountains" → `2025-11-23-15-30-12-sunset-mountains.jpg`
- Prompt "create an image of a robot" → `2025-11-23-16-45-33-robot.jpg`
- Unclear context → `2025-11-23-17-12-48-x9k2.jpg`

## Image Editing

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

The file-level security notice claims the tool only connects to the official ModelScope API endpoint, but later the script downloads the generated image from output_image_url returned by the API without validating the host. If the API, an intermediary, or a compromised upstream service returns an arbitrary URL, the tool can be induced to make outbound requests to attacker-controlled or internal network locations, contradicting the stated trust boundary.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding

The inline comments assert that using a hardcoded API endpoint prevents redirection of data or credentials, but the result-download step still performs an unrestricted GET to a URL provided by the API. This creates a misleading security guarantee and can mask a real outbound-request primitive that may enable SSRF-style access or retrieval of malicious content.

Content

No source excerpt is available for this finding.

Tainted flow: 'task_id' from requests.post (line 252, network input) → requests.get (network output)

Medium
Category
Data Flow
Confidence
65% confidence
Finding

Data from a source is assigned to a variable that is later passed to a sink, creating a variable-mediated taint flow.

Content

Scanner excerpt · scripts/generate_img.py (reported line 108)May include surrounding context.

python
for attempt in range(max_attempts):
        try:
            # SECURITY: Using hardcoded endpoint only
            result = requests.get(
                f"{_API_ENDPOINT}v1/tasks/{task_id}",
                headers={**common_headers, "X-ModelScope-Task-Type": "image_generation"},
                timeout=30