Back to skill

Security audit

Smart Memory

Security checks for vulnerabilities and agentic risk

Overview

This is a local memory skill with no external exfiltration found, but it automatically persists sensitive conversation data, including API keys, in plaintext and has unclear deletion behavior.

Install only if you are comfortable with a local plaintext memory database that may store personal facts, project details, standing instructions, and credentials unless the agent avoids doing so. Do not store API keys, passwords, tokens, or private infrastructure details with this skill. Review and restrict ~/.openclaw/smart-memory permissions, treat exports and stats output as sensitive, and verify deletion behavior before relying on forget requests.

Vulnerability Patterns
  • Agent Memory PoisoningWrites attacker-controlled rules into memory that affect later sessions
  • 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
  • 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 (3)

T09 · Insecure Skill Coding Practices

Warning
Location
memory-manager.sh:21
Finding

Automatic Plaintext Retention of Sensitive Conversation Data

Content
View full analysis

Vulnerability Details

File Location: SKILL.md:27-39; memory-manager.sh:21-25, memory-manager.sh:77-109, and memory-manager.sh:207-225
Vulnerability Type: Plaintext sensitive-data storage with insufficient access-control hardening
Risk Level: Medium

The Skill explicitly instructs the Agent to collect personal information, infrastructure details, server addresses, and API keys:

markdown
Automatically extract and store memories whenever the user shares:

- **Preferences**: "I prefer dark mode", "I like Python over JavaScript"
- **Personal facts**: names, locations, roles, team members, project names
- **Decisions**: "We decided to use PostgreSQL", "Let's go with the microservice approach"
- **Instructions**: "Always run tests before committing", "Never deploy on Fridays"
- **Important dates**: deadlines, birthdays, recurring events
- **Technical context**: stack details, repo URLs, server addresses, API keys (stored locally only)
- **Corrections**: "Actually, my name is spelled with a K" (update existing memory)

The storage locations are ordinary local JSON files:

bash
MEMORY_DIR="${OPENCLAW_MEMORY_DIR:-$HOME/.openclaw/smart-memory}"
MEMORIES_FILE="$MEMORY_DIR/memories.json"
ARCHIVE_FILE="$MEMORY_DIR/archive.json"
STATS_FILE="$MEMORY_DIR/stats.json"
CONFIG_FILE="$MEMORY_DIR/config.json"

Initialization creates the directory and files without explicitly enforcing restrictive permission modes:

bash
cmd_init() {
    mkdir -p "$MEMORY_DIR"

    if [ ! -f "$MEMORIES_FILE" ]; then
        echo '{"memories":[],"version":"1.0.0","created":"'"$(now_iso)"'"}' | jq . > "$MEMORIES_FILE"
        info "Created memories store: $MEMORIES_FILE"
    fi

    if [ ! -f "$ARCHIVE_FILE" ]; then
        echo '{"archived":[],"version":"1.0.0"}' | jq . > "$ARCHIVE_FILE"
        info "Created archive: $ARCHIVE_FILE"
    fi

    if [ ! -f "$STATS_FILE" ]; then
        cat > "$
...[truncated 3306 chars]
Remediation
View remediation

Remediation Suggestions

  1. Prohibit storage of passwords, API keys, session tokens, private keys, recovery codes, and authentication headers.
  2. Add secret-detection rules before persistence and reject or redact values matching known credential formats and high-entropy token patterns.
  3. Require explicit user opt-in before retaining personal, technical, or otherwise sensitive information; do not infer consent from ordinary conversation.
  4. Create the storage directory with install -d -m 0700 or an equivalent operation and enforce 0600 on every JSON and lock file.
  5. Set a restrictive umask, such as umask 077, at script startup.
  6. Offer encryption at rest using an operating-system key store or another appropriately protected key source. Do not store the encryption key beside the data.
  7. Apply the same controls to archived values, update history, exports, and backups.
  8. Warn users that exports contain sensitive memory content and avoid sending exports to logs or shared output channels.

T02 · Agent Memory Poisoning

Warning
Location
SKILL.md:23
Finding

Persistent Instruction Poisoning Through Untrusted Conversation Memory

Content
View full analysis

Vulnerability Details

File Location: SKILL.md:23-39 and SKILL.md:63-73; memory-manager.sh:182-217
Vulnerability Type: Persistent storage and later reuse of attacker-controlled behavioral instructions
Risk Level: Medium

The Skill directs the Agent to automatically persist user-provided instructions:

markdown
## When to STORE a Memory

Automatically extract and store memories whenever the user shares:

- **Preferences**: "I prefer dark mode", "I like Python over JavaScript"
- **Personal facts**: names, locations, roles, team members, project names
- **Decisions**: "We decided to use PostgreSQL", "Let's go with the microservice approach"
- **Instructions**: "Always run tests before committing", "Never deploy on Fridays"
- **Important dates**: deadlines, birthdays, recurring events
- **Technical context**: stack details, repo URLs, server addresses, API keys (stored locally only)
- **Corrections**: "Actually, my name is spelled with a K" (update existing memory)

It then directs the Agent to retrieve and apply these memories before responding:

markdown
## When to RETRIEVE Memories

Before responding to any user message, check if relevant memories exist:

```bash
bash ~/.openclaw/smart-memory/memory-manager.sh search --query "<relevant keywords>"

Use retrieved memories to:

  • Personalize responses (use their name, reference their preferences)
  • Avoid asking questions you already know the answer to
  • Provide continuity across conversations
  • Reference past decisions and context
text

The implementation stores arbitrary values and metadata but does not enforce trust boundaries during insertion:

```bash
local new_memory
new_memory=$(jq -n \
    --arg key "$key" \
    --arg value "$value" \
    --arg category "$category" \
    --arg confidence "$confidence" \
    --arg source "$source" \
    --arg created "$timestamp" \
    --arg updated "$timestamp" 
...[truncated 2541 chars]
Remediation
View remediation

Remediation Suggestions

  1. Do not automatically persist behavioral instructions. Require explicit confirmation from an authenticated user before creating or modifying standing guidance.
  2. Separate factual memory from executable or behavioral policy. Retrieved memory should be treated as untrusted reference data, not as instructions.
  3. Bind every entry to a specific authenticated user, tenant, workspace, project, and session context as appropriate.
  4. Enforce authorization checks when storing, updating, retrieving, forgetting, exporting, and purging entries.
  5. Prevent memory content from overriding current user requests or higher-priority system and developer instructions.
  6. Display the proposed instruction, origin, scope, and expiration to the user before persistence.
  7. Add expiration dates and periodic reconfirmation for standing instructions.
  8. Preserve provenance and present it when retrieving entries, while ensuring provenance labels cannot be selected arbitrarily by an untrusted caller.
  9. Add an auditable interface through which users can inspect and revoke all persistent instructions.

other

Warning
Location
memory-manager.sh:409
Finding

Forget Operation Retains Complete Memory Values in the Archive

Content
View full analysis

Vulnerability Details

File Location: SKILL.md:87-93 and SKILL.md:124-129; memory-manager.sh:409-430 and memory-manager.sh:510-533
Vulnerability Type: Privacy retention mismatch and incomplete deletion
Risk Level: Medium

The documentation describes forget as a soft deletion:

markdown
## When to FORGET a Memory

If the user explicitly asks you to forget something:

```bash
bash ~/.openclaw/smart-memory/memory-manager.sh forget --key "<key_to_forget>"

This soft-deletes the memory (marks it as forgotten but retains it in the archive for 30 days before permanent deletion).

text

This conflicts with the stated privacy rule:

```markdown
## Privacy & Security Rules

1. **All data stays local** — Never transmit memory contents to external services
2. **Respect forget requests** — When the user says "forget X", delete it immediately
3. **No sensitive data in logs** — Memory contents never appear in system logs

The implementation marks the active entry as forgotten and copies the complete original entry into the archive:

bash
# Soft-delete: mark as forgotten and move to archive
local updated_file
updated_file=$(jq --arg k "$key" --arg ts "$timestamp" '
    .memories |= map(
        if .key == $k then
            .forgotten = true | .forgotten_at = $ts
        else . end
    )
' "$MEMORIES_FILE")
echo "$updated_file" > "$MEMORIES_FILE"

# Copy to archive
local archived_entry
archived_entry=$(echo "$existing" | jq --arg ts "$timestamp" '. + {forgotten: true, forgotten_at: $ts}')
local updated_archive
updated_archive=$(jq --argjson entry "$archived_entry" '.archived += [$entry]' "$ARCHIVE_FILE")
echo "$updated_archive" > "$ARCHIVE_FILE"

# Update stats
local updated_stats
updated_stats=$(jq '.total_deletes += 1' "$STATS_FILE")
echo "$updated_stats" > "$STATS_FILE"

release_lock
trap - EXIT

echo "Forgotten memory: $key (archived for $
...[truncated 2793 chars]
Remediation
View remediation

Remediation Suggestions

  1. Change forget to remove all matching records immediately from both memories.json and archive.json.
  2. Remove matching historical values and any other derived copies or indexes.
  3. Perform deletion under the existing write lock and use atomic file replacement to avoid partial updates.
  4. Clearly distinguish permanent deletion from optional soft deletion. If recovery is desired, expose it as a separate, explicitly named operation.
  5. Do not claim immediate deletion while retaining recoverable copies.
  6. If an archive is retained for a legitimate purpose, obtain explicit consent, encrypt it, restrict access, define a guaranteed deletion schedule, and document that limitation before data is stored.
  7. Run expiry automatically rather than relying only on optional maintenance, and report deletion failures.
  8. Add tests confirming that a forgotten key and its value cannot be found in active storage, archives, history, exports, or generated reports.
Vulnerability Patterns
  • Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
  • Privilege EscalationExcessive Permissions, Sudo/Root Execution, Credential Access
  • Rogue AgentSelf-Modification, Session Persistence
  • MCP Tool PoisoningHidden Instructions, Unicode Deception, Parameter Description Injection
  • Prompt InjectionInstruction Override, Hidden Instructions, Exfiltration Commands
Findings (12)

Tp4

High
Category
MCP Tool Poisoning
Confidence
89% confidence
Finding

The code mostly aligns with the declared local persistent memory/storage purpose: it stores, retrieves, updates, forgets, archives, and maintains memories in local JSON files without external APIs. However, there is a meaningful description/behavior mismatch because the description claims the skill 'automatically extracts' key facts from conversations and 'makes your bot smarter over time,' while the supplied code is only a command-line CRUD/maintenance tool and contains no conversation parsing or automatic extraction logic. Additionally, the code includes notable undeclared capabilities such as exporting all memories, purging all memories, and logging token-savings/statistics. These are related to memory management but are still extra capabilities not reflected in the declared description. Therefore this should be flagged as a mismatch, though the primary domain and resource usage are largely consistent.

Content

No source excerpt is available for this finding.

Tp4

High
Category
MCP Tool Poisoning
Confidence
95% confidence
Finding

The declared description presents the skill primarily as a persistent memory system that extracts, stores, and retrieves conversation facts using local JSON storage. The supplied code chunk does not implement those core memory operations. Instead, it is a reporting utility (memory-stats.sh) that analyzes existing local JSON files (memories.json, archive.json, stats.json) and prints a status report. While this is related to the broader memory skill and still uses local storage with no external APIs, the chunk’s actual purpose is analytics/monitoring rather than the declared primary functionality. That is a material description-behavior mismatch for this specific code chunk.

Content

No source excerpt is available for this finding.

Missing User Warnings

High
Category
Not specified by scanner
Confidence
98% confidence
Finding

The skill instructs automatic persistence of conversation data, including sensitive items like API keys, without requiring explicit opt-in or warning the user about retention risks. In the context of a persistent cross-session memory tool, this makes accidental collection of secrets and personal data significantly more dangerous.

Content

No source excerpt is available for this finding.

Ssd 3

High
Category
Not specified by scanner
Confidence
99% confidence
Finding

The instructions explicitly tell the agent to retain and store highly sensitive user data, including API keys, in persistent local memory. Even without network exfiltration, storing secrets in a broad-access local JSON repository creates serious exposure through local compromise, backups, logs, exports, archives, or accidental disclosure in later responses.

Content

No source excerpt is available for this finding.

Session Persistence

Medium
Category
Rogue Agent
Confidence
91% confidence
Finding

This skill establishes persistent cross-session storage and a daily heartbeat maintenance flow, which creates ongoing retention and processing of user data outside the immediate session. Session persistence is contextually central to the feature, but it still increases the blast radius of privacy mistakes and makes other findings more dangerous because stored data can survive and be reprocessed over time.

Content

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

md
tools:
  - shell
  - file_read
  - file_write
heartbeat:
  enabled: true
  interval: daily

Ssd 3

Medium
Category
Not specified by scanner
Confidence
93% confidence
Finding

The directive to 'Remember everything important. Forget nothing the user cares about.' promotes broad, effectively indefinite retention of user information across sessions. In a persistent assistant context, this increases privacy risk, over-collection, and the chance that stale or sensitive personal data is retained beyond necessity.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding

The skill encourages storing highly sensitive material such as API keys while also performing usage logging and stats collection. Even if the logs are intended not to contain secrets, retaining secrets in a general-purpose memory store materially increases the chance of accidental disclosure through debugging, export, archive, or future code changes.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
89% confidence
Finding

The skill directs the agent to perform write, update, forget, export, and purge operations on persistent user data, but the description does not prominently warn about these modifying and destructive capabilities. Users may enable or rely on the skill without understanding that it can materially alter or expose stored data.

Content

No source excerpt is available for this finding.

Intent-Code Divergence

Medium
Category
Not specified by scanner
Confidence
96% confidence
Finding

The skill says forget requests are deleted immediately, but elsewhere states forgotten items are soft-deleted and retained for 30 days. That inconsistency can cause unauthorized retention of data the user explicitly asked to erase, creating privacy, compliance, and trust risks.

Content

No source excerpt is available for this finding.

Sudo/Root Execution

Medium
Category
Privilege Escalation
Confidence
70% confidence
Finding

Commands invoke sudo or root privileges. Verify this elevated access is necessary and justified.

Content

Scanner excerpt · memory-manager.sh (reported line 81)May include surrounding context.

sh
# Ensure jq is available
require_jq() {
    command -v jq >/dev/null 2>&1 || die "jq is required but not installed. Install it: sudo apt install jq"
}

# ─── Init ────────────────────────────────────────────────────────────────────

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
89% confidence
Finding

The export command prints the full memory store, including all persisted conversation-derived facts and preferences, directly to stdout with no confirmation, redaction, or warning. In agent workflows, stdout is commonly logged, piped, or exposed to calling processes, so this can unintentionally disclose sensitive user data even though the feature appears intentionally designed for backup/export.

Content

No source excerpt is available for this finding.

Missing User Warnings

Medium
Category
Not specified by scanner
Confidence
92% confidence
Finding

This script prints raw memory values, top accessed memory entries, date ranges, and the absolute storage path directly to stdout. In the context of a persistent-memory skill, those fields can contain sensitive personal facts, inferred preferences, or internal filesystem details, so running the report can expose data to logs, screenshots, terminal history, or other local observers even though no explicit warning or redaction is applied.

Content

No source excerpt is available for this finding.

Static analysis

No suspicious patterns detected.