Skip to content

EA1 wildcard-tool-access pattern crosses blank lines and matches markdown bold syntax Affected rule: EA1 "Unrestricted Tool Access" Affected file: src/skillspector/nodes/analyzers/static_patterns_excessive_agency.py, line 45 #405

Description

@benedictkwok

Summary
python
(r"(?:tools?|permissions?)\s*:\s*[?\s*['"]?*['"]?\s*]?", 0.85)

Two independent problems, both confirmed on the official anthropics/skills repo, mcp-builder/SKILL.md:

  1. \s* is not bounded to a single line or a single paragraph. Python's \s matches newlines regardless of re.MULTILINE, so the gap between the colon and the expected wildcard value can span a blank line and bridge two unrelated pieces of markdown. SKILL.md:96:

markdown
For each tool:

Input Schema:

"For each tool:" is a heading intro; "Input Schema:" is a separate, unrelated heading two lines later. The pattern matches tool: + the intervening blank line + the first * of the next heading's bold marker, surfacing as matched text "tool:\n\n*".

  1. No check that the matched * is a standalone token. SKILL.md:25: API Coverage vs. Workflow Tools: — the pattern's only requirement after the colon is a literal , and the first * of the closing ** of a bold-markdown span satisfies it (matched text: "Tools:"). Nothing distinguishes this from an actual tools: * wildcard grant in a real permissions block. The same blind spot would also fire on, e.g., Tools: Read, Write — a bolded list of specific named tools, the opposite of an unrestricted grant.

Both findings fired as EA1/MEDIUM on mcp-builder and survived to the final report.

Proposed fix

Restrict the whitespace between the colon and the value to the same line, and require the matched * not be immediately followed by another * or a word character:

python
(r"(?:tools?|permissions?)\s*:[ \t][?[ \t]['"]?*(?!*|\w)['"]?[ \t]*]?", 0.85)
Verifying this doesn't weaken real detection

A genuine wildcard grant like tools: "", tools: [], or permissions: '*' on a single line still matches — none of those have a line break before the value, and the * in each case is followed by a quote/bracket/end-of-line, not another * or a letter. Only the cross-heading bridge and the bold-markdown collision stop matching.

Reported by

Benedict Kwok, ZTAI Security Advisors LLC (benedictkwok@ztai.ai) — found while independently evaluating SkillSpector against several official anthropics/skills skills.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions