Back to skill

Security audit

Model Verify Flagos

Security checks for vulnerabilities and agentic risk

Overview

The skill is a coherent model-verification tool, but it can download user-selected remote models and run their trusted custom code inside Docker without strong warnings or scoping.

Install only if you intend to run this in a disposable, tightly scoped container with no secrets, no sensitive host mounts, and trusted or pinned model sources. Treat any remote model ID as code, not just data, and review or remove --trust-remote-code unless the model genuinely requires it.

Vulnerability Patterns
  • Remote Payload Retrieval and ExecutionFetches external code whose behavior can change after review
  • 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
  • Embedded Malicious CodeShips malicious scripts inside the skill and executes them locally
Findings (2)

T03 · Remote Payload Retrieval and Execution

Error
Location
SKILL.md:53
Finding
Unpinned Remote Model Code Is Downloaded and Executed## Vulnerability Details **File Location**: `SKILL.md:53-59`, `SKILL.md:69-80`, `SKILL.md:84-93`, `SKILL.md:107-118`, and `SKILL.md:122-131` **Vulnerability Type**: Untrusted remote payload retrieval and execution **Risk Level**: High ### Vulnerable Code ```bash docker exec <CONTAINER> python3 -c " from modelscope import snapshot_download snapshot_download('<MODEL_ID>', local_dir='/data/models/<MODEL_NAME>') " ``` The downloaded model is subsequently loaded with remote code explicitly trusted: ```bash docker exec <CONTAINER> bash -c ' export USE_FLAGGEMS=0 unset FLAGCX_PATH timeout 300 python3 /tmp/run_offline_inference.py \ --model <MODEL_PATH> \ --tp <TP_SIZE> \ --trust-remote-code ' > /tmp/run_a_offline.json ``` The same `--trust-remote-code` option is present in the Run A serve command and both Run B commands. ### Technical Analysis A model identified by a user-provided remote ID is downloaded from ModelScope without an immutable revision, expected cryptographic digest, or signature verification. The verification commands then use `--trust-remote-code`, which permits custom Python code supplied by the model repository to execute during model loading. Consequently, the effective executable payload can change after this Skill has been reviewed. A repository owner, compromised account, registry compromise, or attacker-controlled model ID could supply malicious custom model code. This is not merely model-data processing: trusted remote model implementations can execute Python with the permissions of the inference process. ### Attack Path 1. An attacker publishes a model repository containing malicious custom Python model code, or compromises an otherwise trusted repository. 2. The attacker supplies that repository ID as the requested model, or waits for an unpinned repository revision to be replaced. 3. The Skill downloads the current repository ...[truncated 925 chars]
Remediation
## Remediation Suggestions 1. Disable remote model code by default and remove `--trust-remote-code` unless the selected model has a documented and reviewed requirement for it. 2. Require explicit, informed user approval before executing custom code from a model repository. 3. Restrict downloads to an allowlist of approved registries, namespaces, and repositories. 4. Pin every remote model to an immutable commit or revision rather than downloading the current mutable state. 5. Verify repository signatures or cryptographic hashes before model loading. 6. Review and locally vendor any required custom model implementation instead of executing mutable repository code. 7. Run model loading as a dedicated non-root user in a hardened, disposable container. 8. Remove sensitive mounts, credentials, host-control sockets, and unnecessary Linux capabilities from the container. 9. Disable outbound network access during model loading and inference unless it is strictly required. 10. Record the source repository, immutable revision, and verified digest in the generated report for auditability.

T09 · Insecure Skill Coding Practices

Error
Location
SKILL.md:47
Finding
Unvalidated Values Are Interpolated into Shell and Python Commands## Vulnerability Details **File Location**: `SKILL.md:47-49`, `SKILL.md:53-59`, `SKILL.md:62-64`, `SKILL.md:69-80`, `SKILL.md:84-93`, `SKILL.md:107-118`, `SKILL.md:122-131`, and `SKILL.md:140-143` **Vulnerability Type**: Shell and embedded-Python command injection **Risk Level**: High ### Vulnerable Code User- or context-derived values are inserted directly into shell commands: ```bash docker exec <CONTAINER> test -f <MODEL_PATH>/config.json ``` Values are also embedded into Python source enclosed by a shell command: ```bash docker exec <CONTAINER> python3 -c " from modelscope import snapshot_download snapshot_download('<MODEL_ID>', local_dir='/data/models/<MODEL_NAME>') " ``` Model paths and tensor-parallel values are interpolated into nested `bash -c` command strings: ```bash docker exec <CONTAINER> bash -c ' export USE_FLAGGEMS=0 unset FLAGCX_PATH timeout 300 python3 /tmp/run_offline_inference.py \ --model <MODEL_PATH> \ --tp <TP_SIZE> \ --trust-remote-code ' > /tmp/run_a_offline.json ``` Container names are similarly inserted into copy and execution commands: ```bash docker cp <SKILL_DIR>/scripts/diff_analysis.py <CONTAINER>:/tmp/ docker exec <CONTAINER> python3 /tmp/diff_analysis.py \ --run-a /tmp/run_a_offline.json \ --run-b /tmp/run_b_offline.json ``` ### Technical Analysis The Skill instructs the Agent to substitute the container name, model ID, model name, model path, tensor-parallel size, and Skill directory directly into command templates. No strict validation or argument-safe construction is specified. Shell metacharacters, whitespace, command substitutions, redirection operators, or quote characters in a substituted value can change the syntax of the generated command. The nested `bash -c` construction creates an additional interpretation layer. The download command also embeds t ...[truncated 1966 chars]
Remediation
## Remediation Suggestions 1. Do not construct commands by replacing placeholders in shell strings. Invoke processes using argument arrays so each value remains a single argument. 2. Avoid nested `bash -c` commands. Use `docker exec` with explicit environment options and argument boundaries, for example by passing environment variables through supported Docker arguments. 3. Pass model IDs and destination paths to a fixed Python script through `sys.argv` or environment variables instead of embedding them into `python3 -c` source. 4. Validate container names against Docker's expected identifier or name syntax before use. 5. Parse the tensor-parallel size as an integer and enforce a safe range based on the available GPU count. 6. Canonicalize local model paths and require them to reside beneath an approved model root. 7. Validate remote model IDs against a strict registry-specific format and reject quotes, control characters, whitespace, shell metacharacters, and path traversal. 8. Quote arguments with a proven shell-escaping routine if shell execution is unavoidable; do not rely on manual quotation. 9. Treat additional vLLM arguments as a structured allowlisted collection rather than a raw command-line fragment. 10. Run Docker operations through a minimal wrapper that accepts typed fields and constructs the final process argument vector without shell interpretation.
Vulnerability Patterns
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
Findings (4)

Missing User Warnings

High
Confidence
95% confidence
Finding
The skill omits an explicit warning that it may download untrusted third-party model artifacts and then execute model-supplied code via `--trust-remote-code`. Because this is a user-invokable verification skill, the lack of disclosure materially increases the chance that operators trigger high-risk behavior without understanding the execution and supply-chain implications.

Context-Inappropriate Capability

High
Confidence
98% confidence
Finding
The skill explicitly runs inference and serving tests with `--trust-remote-code` against a user-specified model, including remotely downloaded models. That allows arbitrary Python code supplied by the model repository to execute inside the container during verification, turning a diagnostic workflow into code execution on untrusted input.

Context-Inappropriate Capability

Medium
Confidence
90% confidence
Finding
The skill downloads a user-specified model ID from external registries as part of normal execution, which expands the trust boundary from local verification to arbitrary remote content retrieval. In context, this becomes more dangerous because the same workflow later executes model-associated code with `--trust-remote-code`, so download and execution form a risky chain.

Missing User Warnings

Medium
Confidence
78% confidence
Finding
The skill writes scripts and output artifacts into `/tmp` paths in the container and on the invoking side without warning. While less severe than remote code execution, undocumented temporary writes can overwrite existing files, leak sensitive logs or model metadata into shared locations, and create persistence or cross-run contamination risks in multi-tenant or reused containers.

Static analysis

No suspicious patterns detected.