Back to skill

Security audit

Cloud-Local Bridge

Security checks for vulnerabilities and agentic risk

Overview

This skill creates a powerful remote bridge to the local machine, but its command, file, network, and token handling are too broad and under-protected for routine installation.

Install only if you intentionally want to give a paired remote party broad control over the local machine. Use a private network or secure tunnel, do not expose the port publicly, rotate tokens, avoid running as root, and do not allow this bridge to read sensitive OpenClaw memory, configuration, SSH keys, or other private files.

Vulnerability Patterns
  • Unauthorized Access and Privilege EscalationObtains permissions beyond the task's legitimate needs
  • 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
Findings (9)

T05 · Unauthorized Access and Privilege Escalation

Error
Location
scripts/bridge_server.py:96
Finding
Unrestricted Remote Shell Command Execution<![CDATA[ ## Vulnerability Details **File Location**: `scripts/bridge_server.py:96-112` **Vulnerability Type**: Arbitrary command execution through an authenticated network endpoint **Risk Level**: Critical ### Vulnerable Code ```python def handle_execute(self, data): """执行命令""" command = data.get('command', '') timeout = data.get('timeout', 30) capture = data.get('capture_output', True) if not command: self.send_json_response(400, {"error": "Missing 'command' field"}) return logger.info(f"执行命令: {command}") try: result = subprocess.run( command, shell=True, capture_output=capture, text=True, timeout=timeout ) ``` ### Technical Analysis The `/execute` endpoint passes a remotely supplied string directly to `subprocess.run` with `shell=True`. Authentication consists only of possession of a single bearer token. There is no command allowlist, argument validation, user confirmation, sandbox, privilege separation, or operating-system policy limiting what the process can execute. Although remote command execution is part of the declared functionality, unrestricted shell access exceeds the minimum privilege needed for safe task delegation. The bearer token effectively becomes a reusable remote-administration credential. ### Attack Path 1. An attacker obtains the bearer token through network interception, logs, local configuration, pairing-state exposure, or accidental disclosure. 2. The attacker sends an authenticated POST request to `/execute`. 3. The JSON `command` field contains an arbitrary shell command. 4. `subprocess.run(..., shell=True)` invokes the system shell. 5. The command runs with all privileges available to the Bridge server process. 6. The attacker receives standard output and standard error in the HTTP response or through the callback feature. ### Impact Assessment A successful attacker can execute arbitrary programs, read ...[truncated 234 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Remove the generic shell endpoint and expose narrowly scoped, explicitly defined operations. - Use fixed executable paths and argument arrays with `shell=False`. - Validate every argument against an operation-specific allowlist. - Run the service under a dedicated unprivileged account with a minimal filesystem and network policy. - Isolate permitted operations in a container or sandbox with resource limits. - Require explicit user approval for security-sensitive actions. - Use short-lived, operation-scoped credentials instead of one reusable administrator token. - Record tamper-resistant audit events without logging commands that contain secrets. ]]>

T05 · Unauthorized Access and Privilege Escalation

Error
Location
scripts/bridge_server.py:147
Finding
Arbitrary Filesystem Read and Write Through Client-Controlled Paths<![CDATA[ ## Vulnerability Details **File Location**: `scripts/bridge_server.py:147-190` **Vulnerability Type**: Unrestricted file access and path traversal **Risk Level**: Critical ### Vulnerable Code ```python def handle_file(self, data): """处理文件传输""" action = data.get('action', '') file_path = data.get('path', '') if not action or not file_path: self.send_json_response(400, {"error": "Missing 'action' or 'path' field"}) return try: if action == 'upload': content = data.get('base64_content', '') if not content: self.send_json_response(400, {"error": "Missing 'base64_content' for upload"}) return file_content = base64.b64decode(content) os.makedirs(os.path.dirname(file_path), exist_ok=True) with open(file_path, 'wb') as f: f.write(file_content) response = {"status": "uploaded", "path": file_path} elif action == 'download': if not os.path.exists(file_path): self.send_json_response(404, {"error": "File not found"}) return with open(file_path, 'rb') as f: content = base64.b64encode(f.read()).decode('utf-8') response = { "status": "downloaded", "path": file_path, "base64_content": content } elif action == 'read': if not os.path.exists(file_path): self.send_json_response(404, {"error": "File not found"}) return with open(file_path, 'r', encoding='utf-8') as f: content = f.read() response = {"status": "read", "path": file_path, "content": content} ``` ### Technical Analysis The server accepts absolute paths and traversal paths directly from the client. It does not canonicalize paths, enforce an approved synchronization root, reject symbolic links, limi ...[truncated 1063 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Define separate, explicit synchronization roots for uploads and downloads. - Resolve requested paths with `Path.resolve()` and verify that the result remains beneath the configured root. - Reject absolute paths, traversal components, symbolic links, device files, and other special files. - Use separate scoped permissions for reading and writing. - Apply file-size, request-size, file-count, and storage quotas. - Avoid overwriting existing files unless specifically authorized. - Use atomic writes and restrictive file modes. - Explicitly deny access to Agent memory, credentials, configuration, SSH directories, and system paths. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
scripts/bridge_server.py:247
Finding
Remote Administration Service Exposed Over Cleartext HTTP<![CDATA[ ## Vulnerability Details **File Location**: `scripts/bridge_server.py:247-260`; `references/EXAMPLES.md:26-39` **Vulnerability Type**: Insecure network exposure and plaintext credential transport **Risk Level**: High ### Vulnerable Code ```python parser.add_argument('--port', type=int, default=8080, help='监听端口') parser.add_argument('--host', type=str, default='0.0.0.0', help='绑定地址') parser.add_argument('--token', type=str, required=True, help='认证 token') args = parser.parse_args() server = BridgeServer((args.host, args.port), BridgeHandler, token=args.token) logger.info(f"🚀 Cloud-Local Bridge Server 启动成功!") logger.info(f" 监听地址: http://{args.host}:{args.port}") logger.info(f" Token: {args.token}") ``` The documentation also directs users to transmit privileged requests over HTTP: ```bash curl -X POST http://192.168.1.100:8080/execute \ -H "Content-Type: application/json" \ -H "Authorization: Bearer YOUR_TOKEN" \ -d '{ "command": "openclaw cron add --name \\"喝水提醒\\" --at \\"30m\\" --message \\"该喝水啦!\\" --session isolated --delete-after-run", "timeout": 60 }' ``` ### Technical Analysis The default listener binds to every network interface, and both implementation messages and examples use plain HTTP. Bearer authentication does not protect credentials against passive interception or active modification. Because the same token authorizes command execution and arbitrary file access, interception has severe consequences. ### Attack Path 1. A user starts the server with the documented defaults. 2. Port 8080 becomes reachable through all host interfaces, subject only to external firewall rules. 3. A legitimate client sends the bearer token and privileged request over cleartext HTTP. 4. An attacker on the network path captures or modifies the request. 5. The attacker replays the token to access `/execute` and `/file`. ### Impact Assessment Token interception grants the attacker the Bridge account's full remote-command and filesy ...[truncated 153 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Bind to `127.0.0.1` by default. - Refuse non-loopback operation unless authenticated TLS or a secure mutually authenticated tunnel is configured. - Use TLS with certificate validation, preferably mutual TLS for device-to-device administration. - Add firewall guidance that denies public access. - Use short-lived, audience-bound credentials and rotate them after suspected exposure. - Update all examples to use HTTPS or a secure tunnel. - Do not display the full bearer token in server logs. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
scripts/bridge_server.py:224
Finding
Arbitrary Callback URL Enables SSRF and Command-Output Disclosure<![CDATA[ ## Vulnerability Details **File Location**: `scripts/bridge_server.py:119-121` and `scripts/bridge_server.py:224-230` **Vulnerability Type**: Server-side request forgery and sensitive data exfiltration **Risk Level**: High ### Vulnerable Code ```python response = { "success": True, "returncode": result.returncode, "stdout": result.stdout if capture else None, "stderr": result.stderr if capture else None } if data.get('reply_to'): self.send_callback(data['reply_to'], response) ``` ```python def send_callback(self, url, data): """发送回调通知""" try: import requests requests.post(url, json=data, timeout=10) except Exception as e: logger.warning(f"回调失败: {e}") ``` ### Technical Analysis The authenticated requester controls `reply_to`, and the server performs a POST request to that destination without validating the URL scheme, hostname, resolved address, port, redirects, or trust relationship. The callback body includes command output and error output. This creates an SSRF primitive and a direct channel for transmitting sensitive execution results to an attacker-selected destination. ### Attack Path 1. An attacker obtains the Bridge token. 2. The attacker invokes `/execute` with a command that reads sensitive data. 3. The attacker supplies a `reply_to` URL under attacker control, or an internal service URL. 4. The Bridge executes the command. 5. The Bridge sends the return code, standard output, and standard error to the selected URL. 6. For SSRF, the attacker observes timing or service effects to probe loopback, private, or link-local targets. ### Impact Assessment The attacker can exfiltrate command output and use the Bridge host's network position to access otherwise unreachable internal services. Depending on reachable endpoints, this may expose cloud metadata, internal APIs, or administrative services. ]]>
Remediation
<![CDATA[ ## Remediation Suggestions - Remove caller-controlled callbacks unless they are essential. - Configure callback destinations administratively rather than accepting them per request. - If callbacks remain, require HTTPS and enforce an exact hostname and port allowlist. - Resolve destinations and reject loopback, private, link-local, multicast, and reserved addresses. - Disable redirects or validate every redirect target. - Do not include command output in callbacks by default. - Apply egress firewall rules so the Bridge cannot contact sensitive internal networks or metadata services. ]]>

T05 · Unauthorized Access and Privilege Escalation

Error
Location
scripts/qq_handler.py:72
Finding
Bridge Administrator Token Exposed Through Pairing State, API Results, Logs, and Configuration<![CDATA[ ## Vulnerability Details **File Location**: `scripts/qq_handler.py:72-89`, `scripts/qq_handler.py:163-199`, `scripts/bridge_server.py:259-260`, `scripts/installer/install_and_run.py:76-77` **Vulnerability Type**: Sensitive credential exposure and over-privileged credential exchange **Risk Level**: Critical ### Vulnerable Code The pairing request stores the Bridge token in persistent state: ```python config = load_bridge_config() local_server = config.get('local', {}).get('server', '') if config else '' local_token = config.get('local', {}).get('token', '') if config else '' code = generate_pairing_code() expires = datetime.now() + timedelta(minutes=10) if 'pending' not in state: state['pending'] = {} state['pending'][user_id] = { 'code': code, 'user_id': user_id, 'user_name': user_name, 'server': local_server, 'token': local_token, 'created_at': datetime.now().isoformat(), 'expires_at': expires.isoformat() } save_state(state) ``` Confirmation persists and returns that token: ```python state['pairs'][user_id][pair_id] = { 'partner_id': initiator_id, 'partner_name': initiator_info['user_name'], 'code': code, 'server': initiator_info.get('server', ''), 'token': initiator_info.get('token', ''), 'paired_at': datetime.now().isoformat() } del state['pending'][initiator_id] save_state(state) return { 'action': 'success', 'pair_id': pair_id, 'partner_server': partner_server, 'partner_token': initiator_info.get('token', ''), 'message': ... } ``` The server logs the token in full: ```python logger.info(f" 监听地址: http://{args.host}:{args.port}") logger.info(f" Token: {args.token}") ``` The installer writes configuration without explicitly restrictive permissions: ```python with open(config_path, 'w') as f: json.dump(config, f, indent=2) ``` ### Technical Analysis The same bearer token authorizes unrestricted shell execution and file access. It is copied into pairing- ...[truncated 1083 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Never place the administrator bearer token in pairing messages, API results, or general pairing-state records. - Use a cryptographically authenticated pairing protocol with explicit approval on both devices. - Issue a new short-lived, device-specific, revocable credential after successful pairing. - Scope credentials by operation, path, device, and expiration time. - Redact all credentials from logs and terminal output. - Create secret files atomically with mode `0600` and ensure their parent directory is private. - Encrypt sensitive state where appropriate and define a credential rotation and revocation process. - Avoid using a six-digit code as the only protection for exchanging a high-privilege credential. ]]>

T05 · Unauthorized Access and Privilege Escalation

Error
Location
scripts/pairing_core.py:241
Finding
Unauthenticated and Brute-Forceable Pairing APIs Exposed on All Interfaces<![CDATA[ ## Vulnerability Details **File Location**: `scripts/pairing_core.py:44-46`, `scripts/pairing_core.py:241-292` **Vulnerability Type**: Weak pairing authentication and publicly exposed API **Risk Level**: High ### Vulnerable Code Pairing codes contain only six decimal digits: ```python def generate_pairing_code(): """生成6位数字配对码""" return ''.join([str(secrets.randbelow(10)) for _ in range(6)]) ``` The API accepts pairing requests and confirmations without authentication: ```python def do_POST(self): content_length = int(self.headers.get('Content-Length', 0)) body = self.rfile.read(content_length).decode('utf-8') try: data = json.loads(body) except: self.send_error(400, 'Invalid JSON') return path = self.path if path == '/api/pair/request': result = create_pairing_request( data.get('info', {}), data.get('channel', 'api') ) self.send_json(result) elif path == '/api/pair/confirm': result = confirm_pairing( data.get('code'), data.get('info', {}) ) self.send_json(result) elif path == '/api/pair/status': self.send_json(get_pairing_status()) ``` The server listens on every interface: ```python def run_api_server(port=8081): """运行 API 服务器""" load_state() server = HTTPServer(('0.0.0.0', port), create_api()) print(f'🔌 配对 API 服务已启动: http://0.0.0.0:{port}') server.serve_forever() ``` ### Technical Analysis The pairing API has no authentication, source throttling, account throttling, attempt limit, lockout, or mandatory local approval. A six-digit code provides at most one million possible values and is unsuitable as the sole control for a publicly reachable pairing operation. The API also exposes code-existence and initiator information through its GET behavior, making enumeration and privacy exposure easier. ### Attack Path 1. The pairing API is started and binds ...[truncated 683 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Bind pairing services to loopback or a trusted management interface by default. - Require an authenticated session before creating or confirming a pairing request. - Replace six-digit codes with high-entropy, single-use pairing tokens. - Require explicit local confirmation displaying the requesting device's identity. - Apply strict source and account rate limits, exponential backoff, attempt limits, and lockout. - Return indistinguishable responses for invalid and expired codes. - Expire codes promptly and invalidate them after any successful use. - Protect pairing traffic with TLS and mutually authenticate devices where possible. ]]>

T09 · Insecure Skill Coding Practices

Error
Location
scripts/sync_files.py:23
Finding
Unsafe Pickle Deserialization of a Predictable Synchronization Cache<![CDATA[ ## Vulnerability Details **File Location**: `scripts/sync_files.py:23-39` **Vulnerability Type**: Unsafe deserialization **Risk Level**: High ### Vulnerable Code ```python class FileSync: def __init__(self, server_url, token, sync_file='.sync_cache.pkl'): self.server_url = server_url.rstrip('/') self.token = token self.sync_cache_file = sync_file self.cache = self.load_cache() def load_cache(self): """加载同步缓存""" if os.path.exists(self.sync_cache_file): with open(self.sync_cache_file, 'rb') as f: return pickle.load(f) return {} def save_cache(self): """保存同步缓存""" with open(self.sync_cache_file, 'wb') as f: pickle.dump(self.cache, f) ``` ### Technical Analysis Python pickle is an executable serialization format. Loading a malicious pickle can invoke attacker-selected callables during deserialization. The default cache path is a predictable relative filename in the current working directory, increasing the chance that another user, process, extracted archive, or repository content can place or replace it. ### Attack Path 1. An attacker gains the ability to create or replace `.sync_cache.pkl` in a directory from which the user runs the synchronization script. 2. The attacker writes a crafted pickle containing a malicious reduction payload. 3. The user starts `sync_files.py`. 4. `FileSync.__init__` immediately calls `load_cache`. 5. `pickle.load` executes the payload with the user's privileges before synchronization begins. ### Impact Assessment Successful exploitation permits arbitrary local code execution with the privileges of the user running the synchronization tool. This can expose the Bridge token, local files, Agent data, and any other resources available to that account. ]]>
Remediation
<![CDATA[ ## Remediation Suggestions - Replace pickle with JSON or another non-executable serialization format. - Validate the loaded object schema and accept only expected string-to-string mappings. - Store cache data under a private application data directory rather than the current working directory. - Create the directory and cache file with restrictive permissions. - Use atomic replacement to prevent partial writes or races. - Do not attempt to make untrusted pickle data safe through superficial content checks; remove pickle deserialization entirely. ]]>

T08 · Insecure Dependencies

Warning
Location
scripts/installer/install_and_run.py:37
Finding
Unpinned Third-Party Packages Installed and Executed at Runtime<![CDATA[ ## Vulnerability Details **File Location**: `scripts/installer/install_and_run.py:37-49` **Vulnerability Type**: Insecure dependency installation and supply-chain exposure **Risk Level**: Medium ### Vulnerable Code ```python def check_dependencies(): """检查并安装依赖""" log("检查依赖...", Colors.BLUE) deps = ['requests', 'psutil'] for dep in deps: try: __import__(dep) log_success(f"{dep} 已安装") except ImportError: log_info(f"正在安装 {dep}...") subprocess.run( [sys.executable, '-m', 'pip', 'install', dep], check=True ) log_success(f"{dep} 安装完成") ``` ### Technical Analysis The installer invokes pip for unpinned package names. It does not use a lockfile, version constraints, package hashes, an isolated environment, or a fixed trusted package index. Installation executes package build and installation logic using the installer process's privileges. The package names shown are legitimate, and no malicious dependency was identified in the reviewed project. The vulnerability is the unsafe and non-reproducible acquisition process. ### Attack Path 1. A required dependency is absent. 2. The installer invokes pip using environment and user-controlled pip configuration. 3. Pip resolves the latest matching package from the configured index or mirror. 4. A compromised release, index, mirror, or configuration supplies hostile package content. 5. Package installation logic executes with the user's privileges. ### Impact Assessment A supply-chain compromise could execute arbitrary code during installation and gain access to all resources available to the installer account. If installation is performed with elevated privileges, impact may extend to the entire host. ]]>
Remediation
<![CDATA[ ## Remediation Suggestions - Declare dependencies in a reviewed lockfile with exact versions and cryptographic hashes. - Install dependencies in an isolated virtual environment during a separate, explicit setup step. - Use a trusted, explicitly configured package index. - Disable unnecessary build isolation or source builds where policy requires reviewed wheels. - Generate and review a software bill of materials. - Avoid silently installing packages at application runtime. - Document supported versions and update them through a controlled dependency-review process. ]]>

T05 · Unauthorized Access and Privilege Escalation

Error
Location
references/EXAMPLES.md:47
Finding
Documentation Encourages Remote Retrieval of Sensitive Agent Memory and Configuration<![CDATA[ ## Vulnerability Details **File Location**: `references/EXAMPLES.md:47-63`, `references/EXAMPLES.md:80-92`, `references/EXAMPLES.md:122-130` **Vulnerability Type**: Excessive data-access scope and sensitive information exposure **Risk Level**: High ### Vulnerable Code The examples explicitly retrieve Agent memory: ```python client = BridgeClient( server_url="http://192.168.1.100:8080", token="YOUR_TOKEN" ) status = client.get_status() print(status) result = client.execute("openclaw cron list") print(result) content = client.read_file("/root/.openclaw/memory/2026-02-20.md") print(content) ``` They also retrieve Agent configuration remotely: ```python response = requests.post( "http://LOCAL_IP:8080/file", json={ "action": "read", "path": "/root/.openclaw/config.json" }, headers={"Authorization": "Bearer TOKEN"} ) config = response.json() print(config) ``` The complete workflow repeats remote memory retrieval: ```python def get_local_memory(date): """读取本地某天的记忆文件""" response = requests.post( f"{LOCAL_SERVER}/file", json={"action": "read", "path": f"/root/.openclaw/memory/{date}.md"}, headers={"Authorization": f"Bearer {TOKEN}"} ) return response.json() ``` ### Technical Analysis The documentation does not merely demonstrate synchronization of a designated shared directory. It instructs users to expose and retrieve Agent memory and configuration through the unrestricted file API. These locations may contain private conversation data, behavioral context, identifiers, operational settings, or credentials. Because the examples use plain HTTP and a broad bearer token, they amplify the consequences of token or network compromise. ### Attack Path 1. A user deploys the Bridge according to the documentation. 2. Agent memory and configuration remain accessible through arbitrary file paths. 3. An attacker obtains the bearer token or unauthorized pairing access. 4. The atta ...[truncated 450 chars]
Remediation
<![CDATA[ ## Remediation Suggestions - Remove examples that access Agent memory, credentials, or global configuration. - Restrict file APIs to an explicit user-created sharing directory. - Deny Agent memory, configuration, key stores, SSH directories, and other sensitive paths regardless of supplied credentials. - Introduce per-file or per-directory user approval. - Apply data minimization and return only the information required for the requested operation. - Use encrypted transport and scoped, short-lived credentials. - Clearly document that Base64 is encoding rather than encryption. ]]>
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Excessive AgencyUnrestricted Tool Access, Autonomous Decision Making, Scope Creep
  • Tool MisuseTool Parameter Abuse, Chaining Abuse, Unsafe Defaults
  • Trigger AbuseOverly Broad Trigger, Shadow Command Trigger, Keyword Baiting Trigger
  • Taint TrackingDirect Taint Flow, Variable-Mediated Taint Flow, Credential Exfiltration Chain
Findings (76)

Tainted flow: 'port' from input (line 155, user input) → subprocess.Popen (code execution)

Critical
Category
Data Flow
Content
log(f"启动 Bridge 服务 (端口: {port})...", Colors.BLUE)
    
    # 启动进程
    process = subprocess.Popen(
        [sys.executable, server_script, '--port', str(port), '--token', token],
        stdout=subprocess.PIPE,
        stderr=subprocess.STDOUT,
Confidence
90% confidence
Finding
External input (network, user) flows to a code execution sink. This enables remote code execution or command injection.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
96% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
94% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding
Persisting server addresses and tokens locally and exchanging connection details between parties introduces secret-handling risk that is not plainly surfaced to the user. In a bridge scenario this is especially sensitive because compromise of those tokens or configs can grant remote access paths into the local environment.

Missing User Warnings

High
Confidence
97% confidence
Finding
The description emphasizes ease of use but omits prominent warnings about the consequences of remote command execution, file synchronization, and cloud-to-local bridging. In this context, lack of informed-consent messaging is highly dangerous because users may authorize a skill that can materially expose their local machine, data, and network boundary.

Vague Triggers

High
Confidence
95% confidence
Finding
The trigger phrases include very common terms such as '连接', '配对', and '添加设备', which can be invoked in ordinary conversation unrelated to security-sensitive actions. Because this skill concerns pairing and eventual remote/local bridging, accidental activation could initiate trust-establishment workflows or expose sensitive connection information without deliberate user intent.

Context-Inappropriate Capability

High
Confidence
99% confidence
Finding
The bridge exposes a general-purpose /execute endpoint that runs arbitrary shell commands, which goes far beyond simple message bridging. Because this service is intended to connect cloud control to a local host, the feature effectively grants remote administrators or attackers full execution capability on the local system.

Missing User Warnings

High
Confidence
98% confidence
Finding
Arbitrary shell commands are executed immediately with no local confirmation, safety interlock, or constrained permission model. In a local-bridge skill this makes compromise especially dangerous because cloud-originated requests can directly control the user's machine.

Tool Parameter Abuse

High
Category
Tool Misuse
Content
try:
            # 执行命令
            result = subprocess.run(
                command,
                shell=True,
                capture_output=capture,
Confidence
99% confidence
Finding
The command parameter is fully attacker-controlled and passed into subprocess.run with shell=True, making this a textbook tool-parameter-abuse path. In a bridge service this effectively turns the tool into a remote shell on the local host.

Missing User Warnings

High
Confidence
97% confidence
Finding
The upload handler writes attacker-supplied content to an attacker-specified filesystem path with no path restrictions. This permits arbitrary file overwrite or creation, enabling persistence, credential theft, configuration tampering, or code execution depending on where files are written.

Lp3

Medium
Category
MCP Least Privilege
Confidence
92% confidence
Finding
The skill advertises and operationalizes sensitive capabilities including network exposure, file access, and shell-related behavior, but the manifest does not declare any tool scope or permissions boundaries. This creates a dangerous transparency gap: users and host systems cannot accurately assess or constrain what the skill may do before installation or execution.

Natural-Language Policy Violations

Medium
Confidence
91% confidence
Finding
The skill description and all example trigger phrases are presented exclusively in Chinese, including prescriptive interaction text such as "像聊天一样说\"我想连接云端\"" and the supported natural-language command list. There is no indication that users may choose another language or that the Chinese-only constraint is required for a justified region-specific use case.

Missing User Warnings

Medium
Confidence
95% confidence
Finding
This documentation presents remote execution and file-access flows as routine usage without a prominent warning that these actions can alter the local system and expose private data. Users may deploy the bridge with insufficient understanding of the trust boundary, making insecure exposure more likely.

External Transmission

Medium
Category
Data Exfiltration
Content
```bash
# 示例:让本地添加一个定时提醒
curl -X POST http://192.168.1.100:8080/execute \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer YOUR_TOKEN" \
  -d '{
Confidence
60% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Context-Inappropriate Capability

Medium
Confidence
94% confidence
Finding
The example explicitly shows a cloud-side caller sending an arbitrary command string to a local bridge endpoint for execution. Even though the skill is intended as a bridge, documenting generic remote command execution materially expands the attack surface: compromise of the cloud side, token leakage, or misuse by a connected party would directly translate into code execution on the local machine.

Context-Inappropriate Capability

Medium
Confidence
93% confidence
Finding
The examples demonstrate remote reading of local files, including sensitive configuration and memory paths under /root/.openclaw. In a bridge context this is especially dangerous because any exposed or stolen token enables exfiltration of secrets, personal data, and operational state from the local system.

External Transmission

Medium
Category
Data Exfiltration
Content
# 在云端
import requests

response = requests.post(
    "http://LOCAL_IP:8080/file",
    json={
        "action": "read",
Confidence
60% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

External Transmission

Medium
Category
Data Exfiltration
Content
# 在云端
import requests

response = requests.post(
    "http://LOCAL_IP:8080/file",
    json={
        "action": "read",
Confidence
70% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

External Transmission

Medium
Category
Data Exfiltration
Content
def execute_on_local(command):
    """在本地执行命令"""
    response = requests.post(
        f"{LOCAL_SERVER}/execute",
        json={"command": command, "timeout": 60},
        headers={"Authorization": f"Bearer {TOKEN}"}
Confidence
70% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

External Transmission

Medium
Category
Data Exfiltration
Content
def get_local_memory(date):
    """读取本地某天的记忆文件"""
    response = requests.post(
        f"{LOCAL_SERVER}/file",
        json={"action": "read", "path": f"/root/.openclaw/memory/{date}.md"},
        headers={"Authorization": f"Bearer {TOKEN}"}
Confidence
70% confidence
Finding
Data is being sent to an external URL. This could be legitimate telemetry or data exfiltration. Manual review is recommended.

Static analysis

No suspicious patterns detected.