Security checks for vulnerabilities and agentic risk
Overview
The skill mostly does what it says, but its filesystem handling can let a crafted workspace cause reads or writes outside the selected workspace.
Review before installing. Use it only on workspaces you trust, avoid running it automatically on untrusted or shared workspaces, and do not use --fix until symlink containment, backup, and clearer dry-run behavior are added. There is no evidence here of hidden networking or intentional exfiltration, but the filesystem escape risk is material.
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
Error
Location
scripts/hygiene.py:191
Finding
Workspace Symlink Traversal Allows Reads and Writes Outside the Audited Workspace
Content
View full analysis
Vulnerability Details
File Location: scripts/hygiene.py, lines 191-211 and 440-450 Vulnerability Type: Unrestricted symlink following and insufficient filesystem boundary validation Risk Level: High
Vulnerable Code
python
def append_memory_content(target_path: Path, source_path: Path) -> bool:
source_text = load_text(source_path)
if not source_text.strip():
return False
target_text = load_text(target_path)
if source_text.strip() in target_text:
return False
if target_text and not target_text.endswith("\n"):
target_text += "\n"
if target_text.strip():
merged = target_text.rstrip() + "\n\n" + source_text.strip() + "\n"
else:
merged = source_text.rstrip() + "\n"
target_path.parent.mkdir(parents=True, exist_ok=True)
target_path.write_text(merged, encoding="utf-8")
return True
python
def write_report(result: AuditResult, report_date: dt.date, report_only: bool) -> Path:
report_dir = result.workspace / "projects" / "system"
if not report_dir.exists() and not report_only:
report_dir.mkdir(parents=True, exist_ok=True)
result.fixes.append("Created report directory: projects/system")
elif not report_dir.exists():
report_dir.mkdir(parents=True, exist_ok=True)
report_path = report_dir / "hygiene-{0}.md".format(report_date.isoformat())
report_path.write_text(render_report(result, report_date), encoding="utf-8")
result.report_path = report_path
return report_path
Technical Analysis
The skill treats the audited workspace as trusted and performs filesystem reads and writes without verifying whether path components or files are symbolic links. Python operations including Path.exists(), Path.is_file(), Path.read_text(), and Path.write_text() ordinarily follow symlinks.
Two exploitable paths result:
`write_report
...[truncated 2968 chars]
Remediation
View remediation
Remediation Suggestions
Treat every audited workspace and all of its contents as untrusted input.
Resolve each source, destination, and parent directory before access, then verify containment beneath the resolved workspace root:
python
Reject the operation if relative_to() raises ValueError.
Explicitly reject symlinks for memory source files, daily target files, projects, projects/system, and report files. Check every existing path component rather than only the final path.
For write operations, use descriptor-based APIs with no-follow semantics such as os.open() with O_NOFOLLOW where supported. Use safe create or replace behavior to reduce time-of-check/time-of-use races.
Open and validate trusted parent-directory descriptors, then perform relative operations through those descriptors where platform support permits.
Do not overwrite an existing report without an explicit option. Consider exclusive file creation or a securely generated filename.
Before --fix reads a memory file, require that it is a regular, non-symlinked file located directly inside the validated memory directory.
Before writing a daily memory file, reject an existing symlink or non-regular file and verify that the resolved parent remains inside the workspace.
Make --report-only genuinely non-mutating, or rename and document the option to clarify that it still writes a report.
Add regression tests using symlinked source files, target files, and parent directories to confirm that all attempted workspace escapes are rejected.
Data ExfiltrationExternal Transmission, Env Variable Harvesting, File System Enumeration
Findings (5)
Undeclared Tool Scope
Medium
Category
MCP Least Privilege
Confidence
91% confidence
Finding
The skill explicitly describes reading workspace files, scanning memory and project folders, and writing a hygiene report, yet it declares no tool or permission scope. That mismatch makes the skill harder to sandbox or review and can allow broader file access/modification than users or the platform may expect.
Content
No source excerpt is available for this finding.
Vague Triggers
Medium
Category
Not specified by scanner
Confidence
93% confidence
Finding
The trigger phrases are broad and generic to normal workspace assistance, which increases the chance the skill is invoked in situations where the user only wanted advice rather than an auditing/modifying workflow. Because the skill can scan and potentially alter files, overbroad activation raises the risk of unintended execution on sensitive or unrelated workspaces.
Content
No source excerpt is available for this finding.
Missing User Warnings
Medium
Category
Not specified by scanner
Confidence
94% confidence
Finding
The skill documents auto-consolidating memory files and writing reports, but it does not prominently warn that it will modify workspace files. Users may reasonably interpret a hygiene audit as read-only, so silent or insufficiently disclosed writes can lead to unexpected data changes, loss of provenance, or accidental alteration of important memory records.
Content
No source excerpt is available for this finding.
Intent-Code Divergence
Medium
Category
Not specified by scanner
Confidence
98% confidence
Finding
The help text promises 'Audit and report without applying fixes' and implies no workspace modification, but the program still creates directories and writes a report. This documentation/behavior mismatch is dangerous because operators and higher-level agents may select report-only mode expecting safe inspection, yet the tool still performs state-changing actions.
Content
No source excerpt is available for this finding.
Description-Behavior Mismatch
Medium
Category
Not specified by scanner
Confidence
97% confidence
Finding
The implementation writes a report file even when --report-only is set, so a mode advertised as non-modifying still changes the workspace. In an automation or auditing context, this can violate read-only expectations, alter evidence, trigger downstream workflows, or fail in environments where the workspace must not be mutated.