Back to skill

Security audit

Video-based Fall Detection Skill | 跌倒检测视频版技能

Security checks for vulnerabilities and agentic risk

Overview

This skill needs review because it can mix users’ private reports, retain login credentials, and upload video despite an export-only request.

Before using private footage, ask the publisher to fix sender isolation, export-only behavior, credential destination restrictions, and token storage. Use a separate workspace and account for each user, and clarify cloud retention and report access. Do not rely on --export-env-only to prevent uploads or on this bundle alone for continuous emergency alarms. Review was static; backend behavior remains unverified. The evidence supports material security concerns, but does not establish malicious intent.

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

Warning
Location
scripts/fall_detection_video_analysis.py:55
Finding

Standard CLI discards upstream sender identity and authenticates different senders as the same fallback account

Content
View full analysis

Impact

In the stated shared-workspace configuration, a second sender can receive another sender's fall-detection reports and associated analysis data. This does not require a server-side authorization bypass: the client uses the same valid account for both senders.

Vulnerability Patterns
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Output HandlingUnvalidated Output Injection, Cross-Context Output, Unbounded Output
  • Behavioral ASTexec() Call, eval() Call, Dynamic Import
Findings (25)

Description-Behavior Mismatch

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding

The supplied chunk contains no video ingestion, target-area analysis, fall detection, or safety-monitoring logic. Its concrete functionality centers on a sys_user database containing names, email addresses, demographic information, and token fields. Although database utilities can support a larger skill, this user-account functionality is not connected to the declared fall-detection purpose in the supplied code. This assessment is limited to the provided chunk; it does not establish that the complete skill lacks fall detection or that stored data is transmitted elsewhere.

Content

No source excerpt is available for this finding.

Description-Behavior Mismatch

High
Category
MCP Tool Poisoning
Confidence
91% confidence
Finding

Ordinary utility functions and authenticated API access can support a fall-detection skill; their presence alone would not establish a mismatch. However, this chunk also implements undeclared identity provisioning and credential persistence, and its request wrapper can send configured credentials to arbitrary caller-supplied HTTP(S) destinations. These capabilities exceed the declared video-monitoring purpose. The absence of detection logic in a shared utility file is not independently evidence that the complete skill lacks fall detection. The identified behaviors occur when the relevant methods are called; the chunk does not establish that they have actually executed.

Content

No source excerpt is available for this finding.

Description-Behavior Mismatch

High
Category
MCP Tool Poisoning
Confidence
82% confidence
Finding

The code exposes history retrieval via get_output_analysis_list(open_id=...), which goes beyond the declared fall-detection function. Its primary analysis operation delegates to skill.get_output_analysis without visible fall-specific logic or continuous stream processing. Because that implementation is not supplied, fall detection and real-time stream support cannot be confirmed or ruled out from this chunk alone. API delegation and optional result-file output are supporting implementation details, not independent mismatches.

Content

No source excerpt is available for this finding.

YARA rule 'agent_skill_mcp_tool_poisoning_metadata': MCP/tool metadata poisoning indicators in tool schemas or skill manifests [agent_skills]

High
Category
YARA Match
Confidence
80% confidence
Finding

YARA rule matched a hack tool or exploit indicator (offensive tools, reconnaissance, privilege escalation, or exploit frameworks).

Content

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

md
---
name: "fall-detection-video-analysis"
description: "Detects whether anyone has fallen within a target area. Supports video stream analysis and is suitable for real-time safety monitoring of elderly people living alone. | 跌倒检测视频版技能,检测目标区域内是否有人跌倒,支持视频流检测,适用于独居老人居家安全监测"
version: "1.0.22"
license: "MIT-0"
---

# 🚨 Video-based Fall Detection Skill | 跌倒检测视频版技能
> **智能分析中枢** · 图片/视频智能分析 · 结构化报告 · 历史报告云端查询

---

## 🧭 技能概览 | Overview

| 模块 | 内容 |
|---|---|

The analysis workflow lacks a privacy warning about sending surveillance inputs to an external API.

High
Category
Output Handling
Confidence
93% confidence
Finding

Although cloud APIs are mentioned, the workflow does not clearly warn that local surveillance footage will leave the device or require informed authorization before transfer. Footage from bedrooms and bathrooms can expose intimate activities and health information about vulnerable people, making this omission particularly consequential.

Content

No source excerpt is available for this finding.

Caller-supplied external URLs receive shared service credentials and user identity automatically.

High
Category
Excessive Agency
Confidence
99% confidence
Finding

The helper accepts arbitrary absolute HTTP or HTTPS URLs and automatically adds shared access tokens, the API key, authorization credentials, and user identity. If a caller supplies an attacker-controlled endpoint, those secrets are sent directly to it; accepting HTTP also permits cleartext exposure, potentially compromising the monitoring service account.

Content

No source excerpt is available for this finding.

Skill declares no tool scope ('permissions' or 'allowed-tools') but code capabilities were detected: env, file_read, file_write, network, shell.

Medium
Category
MCP Least Privilege
Confidence
70% confidence
Finding

Without declared permissions the skill's intent is opaque and cannot be validated.

Content

No source excerpt is available for this finding.

The --export-env-only option promises not to run analysis, but does not prevent analysis.

Medium
Category
Excessive Agency
Confidence
99% confidence
Finding

The export-only flag is parsed but never checked, so supplying it alongside a video still proceeds into analysis. Users relying on the explicit promise of no analysis can unintentionally transmit sensitive home-surveillance footage to the external service.

Content

No source excerpt is available for this finding.

Whitespace Padding

Medium
Category
Prompt Injection
Confidence
70% confidence
Finding

Large whitespace padding was detected (a block of blank lines or a long run of spaces). This can push injected instructions below or to the right of the visible area so a human reviewer never sees them while the agent still reads them. Manual review of the hidden content is recommended.

Content

Scanner excerpt · skills/smyx_analysis/scripts/skill.py (reported line 28)May include surrounding context.

python
result_json = JsonUtil.parse(result_json_pure_text, result_json_pure_text)

        result_json_common_ai_response = result_json.get("commonAiResponse") if isinstance(result_json,
                                                                                           dict) else result_json
        if result_json_common_ai_response:
            result_json = result_json_common_ai_response

Whitespace Padding

Medium
Category
Prompt Injection
Confidence
70% confidence
Finding

Large whitespace padding was detected (a block of blank lines or a long run of spaces). This can push injected instructions below or to the right of the visible area so a human reviewer never sees them while the agent still reads them. Manual review of the hidden content is recommended.

Content

Scanner excerpt · skills/smyx_analysis/scripts/skill.py (reported line 33)May include surrounding context.

python
result_json = result_json_common_ai_response

        result_json_health_ai_response = result_json.get("healthAiResponse") if isinstance(result_json,
                                                                                           dict) else result_json
        if result_json_health_ai_response:
            result_json = result_json_health_ai_response

Local video contents are passed to the analysis API without disclosure that the file will be uploaded.

Medium
Category
Output Handling
Confidence
96% confidence
Finding

The function reads the complete local video into a multipart upload payload and passes it to the analysis API without a visible disclosure or authorization gate. For elderly home monitoring, this can transfer intimate footage and health-related information beyond the user's expected local-processing boundary.

Content

No source excerpt is available for this finding.

The documented export-only mode does not prevent video analysis.

Medium
Category
Excessive Agency
Confidence
99% confidence
Finding

The export-only option is accepted but never branches or terminates execution, so a valid video input still reaches analyze_video. This violates an explicit no-analysis promise and can cause unintended external processing of sensitive surveillance footage.

Content

No source excerpt is available for this finding.

The skill includes persistent user-profile and credential management unrelated to its declared video fall-detection purpose.

Medium
Category
Excessive Agency
Confidence
88% confidence
Finding

The model stores reusable token and open_token values as ordinary strings in a workspace SQLite database, without credential-specific protection shown here. Account integration is not inherently unrelated to a hosted detection service, but persisting credentials alongside personal profiles increases exposure to workspace readers, backups, or compromised skills, particularly in a sensitive home-monitoring context.

Content

No source excerpt is available for this finding.

The ai_chat docstring claims to invoke the OpenClaw agent through subprocess, but the implementation never invokes it or produces an analysis result.

Medium
Category
Excessive Agency
Confidence
99% confidence
Finding

The docstring at L26 explicitly promises a subprocess invocation, but the command and subprocess.run call are commented out. Instead, L68 creates an empty dictionary, and accessing result.stderr at L70 raises an AttributeError that is caught and suppressed, causing the method to return None without performing the documented analysis.

Content

No source excerpt is available for this finding.

FileUtil.open silently truncates existing files.

Medium
Category
Output Handling
Confidence
96% confidence
Finding

The generically named open helper always uses mode 'w', which immediately erases an existing file's contents. There is no confirmation, operation-specific log, docstring, or comment disclosing this destructive behavior; exception tracing does not disclose successful truncation.

Content

No source excerpt is available for this finding.

The request helper silently provisions remote user accounts and persists account credentials, beyond the declared fall-detection functionality.

Medium
Category
Excessive Agency
Confidence
94% confidence
Finding

An ordinary HTTP-helper invocation can trigger silent remote registration and persist returned account credentials without a separate enrollment step. A service account may support fall detection legitimately, but hiding enrollment and credential retention inside a generic request helper creates unexpected privacy and account-lifecycle side effects.

Content

No source excerpt is available for this finding.

HTTP requests can silently trigger remote account registration.

Medium
Category
Output Handling
Confidence
93% confidence
Finding

The helper submits silent=1 and register=1 to the remote login endpoint when credentials are unavailable. This makes a routine request capable of creating an account and sharing identity information without explicit enrollment, an unexpected side effect for a home-safety analysis skill.

Content

No source excerpt is available for this finding.

External Transmission

Medium
Category
Data Exfiltration
Confidence
92% confidence
Finding

This POST transmits the selected identity as both openId and mobile during implicit login or registration. The caller prioritizes ApiEnum.API_SECRET_KEY as that identity when configured, so the payload can also contain a secret key; the destination's trust and necessity for receiving these fields are not established in this source.

Content

Scanner excerpt · skills/smyx_common/scripts/util.py (reported line 561)May include surrounding context.

python
"source": ConstantEnum.DEFAULT__SKILL_HUB_NAME
            }
            try:
                _response = requests.post(_url, json=_data)
                if _response.status_code == 200:
                    _response_json = _response.json()
                    if _response_json and _response_json.get("success"):

The analysis-output heading is unconditionally rendered in Chinese without a user language choice.

Low
Category
Output Handling
Confidence
90% confidence
Finding

The output-heading method always returns a Chinese-language heading, regardless of the user's language or locale. This file provides no language opt-in or documented locale-specific justification for that fixed output language.

Content

No source excerpt is available for this finding.

Configuration loading silently creates directories and files, including during module import.

Low
Category
Output Handling
Confidence
92% confidence
Finding

YamlUtil.load creates parent directories and writes a YAML file when the requested path is missing, without a prompt, log, docstring, or explanatory comment disclosing this side effect. BaseEnum.init_subclass invokes this loader during class definition (L052–L058), so merely importing this configuration module can modify the filesystem.

Content

No source excerpt is available for this finding.

Dynamic attribute access via getattr()

Low
Category
Dangerous Code Execution
Confidence
50% confidence
Finding

Dynamic getattr() with a non-literal attribute name can access arbitrary object attributes, potentially bypassing access controls.

Content

Scanner excerpt · skills/smyx_common/scripts/dao.py (reported line 243)May include surrounding context.

python
username = getattr(model, "username", None)
            if username:
                column_names = self.__model__.__table__.columns.keys()
                update_data = {key: getattr(model, key) for key in column_names if key != "username"}
                return self.update_by_username(username, **update_data)

            return None

Dynamic attribute access via getattr()

Low
Category
Dangerous Code Execution
Confidence
50% confidence
Finding

Dynamic getattr() with a non-literal attribute name can access arbitrary object attributes, potentially bypassing access controls.

Content

Scanner excerpt · skills/smyx_common/scripts/dao.py (reported line 326)May include surrounding context.

python
if filters:
                for key, value in filters.items():
                    query = query.filter(getattr(self.__model__, key) == value)

            if offset:
                query = query.offset(offset)

Dynamic attribute access via getattr()

Low
Category
Dangerous Code Execution
Confidence
50% confidence
Finding

Dynamic getattr() with a non-literal attribute name can access arbitrary object attributes, potentially bypassing access controls.

Content

Scanner excerpt · skills/smyx_common/scripts/dao.py (reported line 441)May include surrounding context.

python
if filters:
                for key, value in filters.items():
                    query = query.filter(getattr(self.__model__, key) == value)

            return query.scalar()
        finally:

Dynamic attribute access via getattr()

Low
Category
Dangerous Code Execution
Confidence
50% confidence
Finding

Dynamic getattr() with a non-literal attribute name can access arbitrary object attributes, potentially bypassing access controls.

Content

Scanner excerpt · skills/smyx_common/scripts/dao.py (reported line 353)May include surrounding context.

python
column_names = self.__model__.__table__.columns.keys()

            for key in column_names:
                value = getattr(model, key)
                setattr(instance, key, value)

            session.commit()

Dynamic attribute access via getattr()

Low
Category
Dangerous Code Execution
Confidence
50% confidence
Finding

Dynamic getattr() with a non-literal attribute name can access arbitrary object attributes, potentially bypassing access controls.

Content

Scanner excerpt · skills/smyx_common/scripts/util.py (reported line 30)May include surrounding context.

python
elif isinstance(cur, dict):
                        cur = cur.get(part, default)
                    else:
                        cur = getattr(cur, part)
                return cur
            except Exception:
                return default