agent-threat-rules 4.2.0 → 4.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +229 -0
- package/README.md +5 -4
- package/dist/converters/elastic.d.ts.map +1 -1
- package/dist/converters/elastic.js +7 -1
- package/dist/converters/elastic.js.map +1 -1
- package/dist/converters/generic-regex.d.ts +5 -1
- package/dist/converters/generic-regex.d.ts.map +1 -1
- package/dist/converters/generic-regex.js +12 -11
- package/dist/converters/generic-regex.js.map +1 -1
- package/dist/converters/sage-reverse.d.ts +1 -1
- package/dist/converters/sage-reverse.d.ts.map +1 -1
- package/dist/converters/sage-reverse.js +13 -8
- package/dist/converters/sage-reverse.js.map +1 -1
- package/dist/converters/sage.d.ts +8 -8
- package/dist/converters/sage.d.ts.map +1 -1
- package/dist/converters/sage.js +107 -74
- package/dist/converters/sage.js.map +1 -1
- package/dist/converters/splunk.d.ts.map +1 -1
- package/dist/converters/splunk.js +17 -3
- package/dist/converters/splunk.js.map +1 -1
- package/dist/engine.d.ts +2 -48
- package/dist/engine.d.ts.map +1 -1
- package/dist/engine.js +3 -54
- package/dist/engine.js.map +1 -1
- package/dist/regex-dialect.d.ts +67 -0
- package/dist/regex-dialect.d.ts.map +1 -0
- package/dist/regex-dialect.js +77 -0
- package/dist/regex-dialect.js.map +1 -0
- package/package.json +1 -1
- package/rules/agent-manipulation/ATR-2026-00074-cross-agent-privilege-escalation.yaml +0 -1
- package/rules/agent-manipulation/ATR-2026-00430-nl-trust-escalation-impersonation.yaml +3 -0
- package/rules/agent-manipulation/ATR-2026-00552-goal-drift-after-pressure-injection.yaml +3 -3
- package/rules/context-exfiltration/ATR-2026-00102-disguised-analytics-exfiltration.yaml +3 -2
- package/rules/context-exfiltration/ATR-2026-00136-tool-response-data-piggyback.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00142-piggyback-transition-words.yaml +4 -2
- package/rules/context-exfiltration/ATR-2026-00150-credential-in-tool-response.yaml +3 -2
- package/rules/context-exfiltration/ATR-2026-00152-obfuscated-credential-leak.yaml +3 -2
- package/rules/context-exfiltration/ATR-2026-00162-skill-credential-exfil-combo.yaml +6 -2
- package/rules/context-exfiltration/ATR-2026-00201-credential-pipe-exfiltration.yaml +5 -2
- package/rules/context-exfiltration/ATR-2026-00290-divergence-repeat-word-training-extraction.yaml +0 -4
- package/rules/context-exfiltration/ATR-2026-00449-spring-ai-chatmemory-cross-user-leak.yaml +2 -3
- package/rules/context-exfiltration/ATR-2026-00501-data-exfiltration-via-markdown-image-and-link-url-injection.yaml +16 -2
- package/rules/context-exfiltration/ATR-2026-00505-system-prompt-extraction-instruction-dump-request.yaml +6 -4
- package/rules/context-exfiltration/ATR-2026-00516-output-xss-via-llm.yaml +9 -8
- package/rules/context-exfiltration/ATR-2026-00569-agent-mcp-path-traversal-arbitrary-file-access.yaml +3 -1
- package/rules/context-exfiltration/ATR-2026-00571-xss-in-agent-mcp-rendered-output.yaml +4 -3
- package/rules/context-exfiltration/ATR-2026-00702-ipi-credential-exfil-via-agent-action.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00703-ipi-financial-data-exfil-indirect.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00704-ipi-medical-genetic-data-exfil.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00705-ipi-location-address-browsing-exfil.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00706-ipi-physical-biometric-exfil.yaml +5 -3
- package/rules/context-exfiltration/ATR-2026-00707-ipi-file-exfil-with-destroy-or-tamper.yaml +6 -3
- package/rules/context-exfiltration/ATR-2026-00860-indirect-pi-financial-transfer-hijack.yaml +1 -1
- package/rules/context-exfiltration/ATR-2026-00861-indirect-pi-crypto-transfer-hijack.yaml +1 -1
- package/rules/context-exfiltration/ATR-2026-01605-ssrf-aws-metadata-endpoint.yaml +5 -1
- package/rules/context-exfiltration/ATR-2026-01606-ssrf-internal-network-scan.yaml +4 -1
- package/rules/context-exfiltration/ATR-2026-01607-ssrf-localhost-service-probe.yaml +4 -1
- package/rules/context-exfiltration/ATR-2026-01924-system-instruction-extraction-reformat.yaml +1 -4
- package/rules/context-exfiltration/ATR-2026-01948-netlicensing-mcp-product-number-path-traversal-token-leak.yaml +4 -2
- package/rules/context-exfiltration/ATR-2026-01957-m365-copilot-searchleak-open-redirect-exfil.yaml +6 -2
- package/rules/context-exfiltration/ATR-2026-01961-meta-ads-mcp-unauth-token-leak.yaml +4 -1
- package/rules/context-exfiltration/ATR-2026-01964-langchain-gmailtoolkit-indirect-prompt-injection-email-exfil.yaml +6 -2
- package/rules/context-exfiltration/ATR-2026-02140-ssrf-ipv6-hex-encoded-cloud-metadata-bypass.yaml +1 -1
- package/rules/context-exfiltration/ATR-2026-02304-preapproved-domain-encoded-path-exfil.yaml +1 -1
- package/rules/context-exfiltration/ATR-2026-02351-wildcard-dns-ssrf-hostname-ip-encoding-bypass.yaml +1 -1
- package/rules/data-poisoning/ATR-2026-00070-data-poisoning.yaml +1 -1
- package/rules/excessive-autonomy/ATR-2026-00491-garak-agent-breaker-markdown-just-raw-json.yaml +8 -8
- package/rules/excessive-autonomy/ATR-2026-00500-ssrf-via-agent-url-fetch-instruction.yaml +17 -5
- package/rules/excessive-autonomy/ATR-2026-00708-ipi-financial-transfer-unauthorized.yaml +4 -3
- package/rules/excessive-autonomy/ATR-2026-00711-ipi-system-sabotage-destructive-command.yaml +4 -3
- package/rules/excessive-autonomy/ATR-2026-00712-ipi-malicious-package-install.yaml +5 -3
- package/rules/excessive-autonomy/ATR-2026-00718-tool-misuse-financial-autonomous.yaml +8 -7
- package/rules/excessive-autonomy/ATR-2026-00719-tool-misuse-destructive-bulk-action.yaml +3 -3
- package/rules/excessive-autonomy/ATR-2026-01773-semantic-excessive-agency-action.yaml +3 -3
- package/rules/excessive-autonomy/ATR-2026-01801-asb-autonomous-vehicle-sabotage.yaml +3 -3
- package/rules/excessive-autonomy/ATR-2026-01804-asb-covert-unlogged-action.yaml +3 -4
- package/rules/excessive-autonomy/ATR-2026-01805-asb-financial-fraud-execution.yaml +3 -3
- package/rules/excessive-autonomy/ATR-2026-01806-asb-clinical-patient-harm.yaml +3 -3
- package/rules/excessive-autonomy/ATR-2026-01809-semantic-insider-manipulation-process-corruption.yaml +2 -3
- package/rules/excessive-autonomy/ATR-2026-01989-t1046-agent-internal-network-sweep.yaml +2 -2
- package/rules/excessive-autonomy/ATR-2026-01993-t1562-agent-impair-defenses.yaml +2 -2
- package/rules/excessive-autonomy/ATR-2026-02667-preapproved-tool-list-in-job-payload.yaml +0 -1
- package/rules/model-abuse/ATR-2026-00292-self-harm-eating-disorder-facilitation.yaml +3 -3
- package/rules/model-abuse/ATR-2026-00502-training-data-extraction-via-divergent-repetition-attack.yaml +2 -0
- package/rules/privilege-escalation/ATR-2026-00040-privilege-escalation.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-00107-delayed-execution-bypass.yaml +2 -2
- package/rules/privilege-escalation/ATR-2026-00143-casual-privilege-escalation.yaml +3 -2
- package/rules/privilege-escalation/ATR-2026-00144-rationalized-safety-bypass.yaml +3 -2
- package/rules/privilege-escalation/ATR-2026-00204-stealth-execution-persistence.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-00441-semantic-kernel-sessions-python-plugin-startup-persistence.yaml +2 -1
- package/rules/privilege-escalation/ATR-2026-00546-crewai-json-loader-local-file-read.yaml +3 -1
- package/rules/privilege-escalation/ATR-2026-00549-destructive-tool-without-human-approval.yaml +2 -2
- package/rules/privilege-escalation/ATR-2026-01601-sql-injection-destructive-ddl.yaml +8 -7
- package/rules/privilege-escalation/ATR-2026-01602-sql-injection-union-select-exfil.yaml +3 -1
- package/rules/privilege-escalation/ATR-2026-01603-sql-injection-stacked-dml-abuse.yaml +3 -2
- package/rules/privilege-escalation/ATR-2026-01604-sql-injection-schema-enumeration.yaml +3 -2
- package/rules/privilege-escalation/ATR-2026-01616-path-traversal-agent-file-access.yaml +4 -1
- package/rules/privilege-escalation/ATR-2026-01802-asb-backdoor-surveillance-implant.yaml +4 -3
- package/rules/privilege-escalation/ATR-2026-01803-asb-covert-server-intrusion.yaml +4 -4
- package/rules/privilege-escalation/ATR-2026-01808-asb-synthetic-pan-payment-probe.yaml +3 -3
- package/rules/privilege-escalation/ATR-2026-01949-praisonai-mcpserver-unauth-tools-call.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-01974-anything-llm-data-import-access-control.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-01992-t1556-agent-auth-process-tamper.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02040-file-edit-tool-persistence-write.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02100-cypher-destructive-admin-query-injection.yaml +4 -4
- package/rules/privilege-escalation/ATR-2026-02101-dynamic-dunder-attribute-sandbox-escape.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02142-download-tool-absolute-path-sandbox-escape.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02146-export-tool-dest-dir-credential-directory-redirect.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02195-dangerous-env-var-injection-config-tool.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02300-mcp-stdio-config-dangerous-env-var.yaml +5 -5
- package/rules/privilege-escalation/ATR-2026-02301-symlink-outside-workspace-sensitive-target.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02302-git-worktree-dotgit-sandbox-escape.yaml +1 -1
- package/rules/privilege-escalation/ATR-2026-02402-mcp-policy-engine-fail-open.yaml +0 -1
- package/rules/prompt-injection/ATR-2026-00154-unauthorized-background-task-execution-v.yaml +5 -3
- package/rules/prompt-injection/ATR-2026-00156-ssh-remote-command-execution-with-creden.yaml +6 -3
- package/rules/prompt-injection/ATR-2026-00407-echo-sql-jinja-template-injection.yaml +3 -3
- package/rules/prompt-injection/ATR-2026-00410-lmrc-harm-category-direct-elicitation.yaml +2 -2
- package/rules/prompt-injection/ATR-2026-00442-quoted-exact-output-forcing.yaml +2 -2
- package/rules/prompt-injection/ATR-2026-00503-fake-error-state-takeover-unrestricted-replacement-bot.yaml +4 -2
- package/rules/prompt-injection/ATR-2026-00512-rules-file-backdoor-injection.yaml +3 -0
- package/rules/prompt-injection/ATR-2026-00554-langchain-vulnerable-to-template-injecti.yaml +3 -3
- package/rules/prompt-injection/ATR-2026-01800-asb-trigger-marker-tool-coercion.yaml +3 -3
- package/rules/prompt-injection/ATR-2026-02009-bare-key-elicitation-trailing-colon.yaml +3 -2
- package/rules/prompt-injection/ATR-2026-02820-tool-result-orders-agent-to-hide-its-own-action.yaml +3 -3
- package/rules/skill-compromise/ATR-2026-00064-over-permissioned-skill.yaml +1 -1
- package/rules/skill-compromise/ATR-2026-00127-subcommand-overflow.yaml +2 -1
- package/rules/skill-compromise/ATR-2026-00157-timebomb-credential-exfil.yaml +6 -2
- package/rules/skill-compromise/ATR-2026-00200-agent-memory-config-tampering.yaml +1 -1
- package/rules/skill-compromise/ATR-2026-00217-credential-harvesting.yaml +4 -2
- package/rules/skill-compromise/ATR-2026-00222-credential-harvesting.yaml +6 -2
- package/rules/skill-compromise/ATR-2026-00224-credential-exfiltration.yaml +4 -2
- package/rules/skill-compromise/ATR-2026-00260-package-hallucination.yaml +3 -2
- package/rules/skill-compromise/ATR-2026-00266-malware-dropper-gen.yaml +4 -3
- package/rules/skill-compromise/ATR-2026-00398-huggingface-unsafe-model-artifact-load.yaml +3 -3
- package/rules/skill-compromise/ATR-2026-00429-nl-skill-self-modification.yaml +4 -2
- package/rules/skill-compromise/ATR-2026-00525-mini-shai-hulud-gh-token-monitor-persistence.yaml +1 -0
- package/rules/skill-compromise/ATR-2026-00527-skill-silent-git-remote-mirror-exfiltration.yaml +3 -2
- package/rules/skill-compromise/ATR-2026-01755-backdoor-pot-linguistic-trigger-phrase.yaml +1 -1
- package/rules/skill-compromise/ATR-2026-01756-backdoor-pot-symbol-emoticon-trigger.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-00096-registry-poisoning.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-00100-consent-bypass-instruction.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-00105-silent-action-concealment.yaml +2 -1
- package/rules/tool-poisoning/ATR-2026-00106-schema-description-contradiction.yaml +2 -2
- package/rules/tool-poisoning/ATR-2026-00270-xss-in-tool-response.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-00494-garak-exploitation-mixedunassigned.yaml +5 -3
- package/rules/tool-poisoning/ATR-2026-00513-package-hallucination-exploitation.yaml +9 -7
- package/rules/tool-poisoning/ATR-2026-00521-shell-command-injection-agent-tool-context.yaml +6 -4
- package/rules/tool-poisoning/ATR-2026-00522-sql-injection-natural-language-agent-interface.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-00526-claude-code-shell-metachar-in-double-quoted-path.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-00530-ms-agent-shell-tool-unsanitized-argv-rce.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-00531-praisonai-unauthenticated-agent-api.yaml +1 -2
- package/rules/tool-poisoning/ATR-2026-00533-apache-pinot-mcp-unauthenticated-takeover.yaml +2 -3
- package/rules/tool-poisoning/ATR-2026-00716-ipi-data-destruction-carrier.yaml +5 -3
- package/rules/tool-poisoning/ATR-2026-00720-tool-misuse-privilege-escalation-social.yaml +3 -3
- package/rules/tool-poisoning/ATR-2026-01301-tool-description-exclusive-tool-override.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-01303-tool-schema-enumeration-social-engineering.yaml +4 -3
- package/rules/tool-poisoning/ATR-2026-01307-mcp-dns-rebinding-attack.yaml +3 -5
- package/rules/tool-poisoning/ATR-2026-01310-mcp-tool-description-compliance-history-exfil.yaml +5 -4
- package/rules/tool-poisoning/ATR-2026-01775-semantic-mcp-tool-manifest-poisoning.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-01952-praisonai-codemode-sandbox-escape-rce.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01953-praisonai-codemode-function-ctor-sandbox-escape.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01959-openhuman-shell-allowlist-env-prefix-bypass.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01963-praisonai-action-orchestrator-step-target-path-traversal-rce.yaml +3 -2
- package/rules/tool-poisoning/ATR-2026-01965-flowise-custommcp-os-command-rce.yaml +2 -1
- package/rules/tool-poisoning/ATR-2026-01967-deepchat-mermaid-xss-rce-ipc-mcp-register.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01970-praisonai-filetools-normpath-path-traversal.yaml +2 -2
- package/rules/tool-poisoning/ATR-2026-01973-anythingllm-logo-endpoint-path-traversal.yaml +2 -2
- package/rules/tool-poisoning/ATR-2026-01978-anythingllm-collector-process-filename-path-traversal-delete.yaml +2 -2
- package/rules/tool-poisoning/ATR-2026-01979-pandasai-prompt-injection-dunder-sandbox-escape-rce.yaml +6 -2
- package/rules/tool-poisoning/ATR-2026-01980-agentic-flow-mcp-tool-param-command-injection.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01982-dbt-mcp-node-selection-argument-injection.yaml +2 -2
- package/rules/tool-poisoning/ATR-2026-01983-mcp-for-stata-log-file-name-command-injection.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-01985-mcp-connect-bridge-unauth-process-spawn-rce.yaml +2 -1
- package/rules/tool-poisoning/ATR-2026-01987-langroid-sqlchatagent-prompt-to-sql-rce.yaml +4 -2
- package/rules/tool-poisoning/ATR-2026-02102-html-injection-tool-arg-approval-ui-xss.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-02141-mcp-server-config-command-execution.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-02233-unscoped-destructive-db-request-nl.yaml +1 -1
- package/rules/tool-poisoning/ATR-2026-02870-invisible-control-before-directive.yaml +94 -0
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
title: Invisible Unicode Control Before a Directive in a Tool Description or Skill File
|
|
2
|
+
id: ATR-2026-02870
|
|
3
|
+
rule_version: 1
|
|
4
|
+
status: experimental
|
|
5
|
+
description: |
|
|
6
|
+
Detects a zero-width, soft-hyphen or bidirectional control character placed at the start of a clause that gives the model or agent an instruction, in the static text an agent reads before it acts: an MCP tool description (tools/list at registration time) or a SKILL.md file. The control is invisible in most renderers, so a reviewer reading the description sees an ordinary sentence while the model still reads the directive after it.
|
|
7
|
+
Controls covered: U+200B ZERO WIDTH SPACE, U+200C ZWNJ, U+200D ZWJ, U+2060 WORD JOINER, U+180E MONGOLIAN VOWEL SEPARATOR, U+00AD SOFT HYPHEN, U+FEFF (only after punctuation or a word, not at the start of the text or of a line, where it is a byte-order mark), U+200E LRM, U+200F RLM, and the bidi embedding, override and isolate controls U+202A-U+202E and U+2066-U+2069. A run of up to seven controls counts; the last one before the directive must not be a closing control (U+202C PDF, U+2069 PDI), so a directive that follows a closed embedding is not attributed to it.
|
|
8
|
+
Presence alone does not trigger. These characters are legitimate in right-to-left text (LRM/RLM and embeddings around Latin words in Hebrew, Arabic and Persian), in Persian and Indic shaping (ZWNJ, ZWJ), in emoji ZWJ sequences, in hyphenation hints (soft hyphens inside German compounds), in localized keyboard shortcuts wrapped in LRE/PDF, and in text pasted from chat clients (ZWSP after an @ sign). The rule therefore requires two things: the control starts a clause (it follows ASCII punctuation, an ASCII word and a space, CJK sentence punctuation, or the start of the text or a line, not a letter it is glued to and not a right-to-left word), and the clause is a directive addressed to the model: an instruction override, an attention header whose clause tells the model to read, send or ignore something, an injected <IMPORTANT> or <system> tag, a response-timing hook (before answering, after responding) tied to sending secrets, conversation or a URL, an always/must directive to call this tool first or instead of others, an exfiltration verb on secrets, conversation, environment or credential files, a read of ~/.ssh, .env or cloud credential files, or a concealment directive (do not tell the user).
|
|
9
|
+
Surfaces: the conditions read tool_description, so the rule runs on an mcp_exchange event that carries fields.tool_description, on each tool definition of a tools/list document scanned with `atr scan` (the tool-definition scope admits a tool_call rule that reads tool_description), and on SKILL.md files (scan_target both; in a skill scan every field resolves to the document). The engine strips most of these controls before matching but also tests each regex against the raw text, which is where these patterns match.
|
|
10
|
+
Limits: the directive vocabulary is English only. A control glued between two letters (for example a soft hyphen inside a word) is not counted, so a directive written as one run with no space or punctuation before the control is missed. Text reversed under an override (RLO with the directive stored backwards) and Unicode tag characters (U+E0000-U+E007F) are out of scope; ATR-2026-00276 and ATR-2026-00258 cover those on other fields. Directives without any invisible control are left to the tool-poisoning rules (for example ATR-2026-00100 to -00107). Reported in issue #653.
|
|
11
|
+
author: ATR Community
|
|
12
|
+
date: 2026/10/24
|
|
13
|
+
schema_version: '0.1'
|
|
14
|
+
detection_tier: pattern
|
|
15
|
+
maturity: test
|
|
16
|
+
severity: high
|
|
17
|
+
references:
|
|
18
|
+
owasp_llm:
|
|
19
|
+
- LLM01:2025
|
|
20
|
+
owasp_agentic:
|
|
21
|
+
- ASI01:2026
|
|
22
|
+
- ASI04:2026
|
|
23
|
+
mitre_atlas:
|
|
24
|
+
- 'AML.T0051.001 - LLM Prompt Injection: Indirect'
|
|
25
|
+
external:
|
|
26
|
+
- https://github.com/Agent-Threat-Rule/agent-threat-rules/issues/653
|
|
27
|
+
- https://trojansource.codes/
|
|
28
|
+
- https://www.unicode.org/reports/tr9/
|
|
29
|
+
compliance:
|
|
30
|
+
eu_ai_act:
|
|
31
|
+
- article: '15'
|
|
32
|
+
context: Article 15 (accuracy, robustness and cybersecurity) requires high-risk AI systems to resist attempts by third parties to alter their behaviour; this rule provides detection evidence for that requirement by flagging tool descriptions and skill files that hide a directive to the model behind an invisible Unicode control.
|
|
33
|
+
strength: primary
|
|
34
|
+
- article: '13'
|
|
35
|
+
context: Article 13 (transparency) requires that deployers can understand the system they operate; a directive hidden behind an invisible control is text the deployer cannot see in review but the model follows, and this rule surfaces it.
|
|
36
|
+
strength: secondary
|
|
37
|
+
- article: '9'
|
|
38
|
+
context: Article 9 (risk management system) requires identified risks to be treated; this rule is a detection control for the hidden-directive risk in third-party MCP tools and skills, applied before the agent loads them.
|
|
39
|
+
strength: secondary
|
|
40
|
+
nist_ai_rmf:
|
|
41
|
+
- subcategory: MS.2.7
|
|
42
|
+
context: MEASURE 2.7 requires security and resilience to be evaluated and documented; scanning tool definitions and skill files for directives hidden behind invisible controls is a measurable check on third-party agent components.
|
|
43
|
+
strength: primary
|
|
44
|
+
- subcategory: MG.3.1
|
|
45
|
+
context: MANAGE 3.1 requires risks from third-party resources to be monitored; MCP tool descriptions and skills are third-party text the model treats as instructions, and this rule monitors them for hidden directives.
|
|
46
|
+
strength: secondary
|
|
47
|
+
- subcategory: MP.5.1
|
|
48
|
+
context: MAP 5.1 requires the likelihood and impact of identified attack patterns to be characterised; the gap between what a reviewer sees and what the model reads is one such pattern, and this rule detects its use in static tool text.
|
|
49
|
+
strength: secondary
|
|
50
|
+
iso_42001:
|
|
51
|
+
- clause: '8.1'
|
|
52
|
+
context: ISO/IEC 42001 Clause 8.1 (operational planning and control, including control of externally provided processes) is supported by this rule's detection of hidden directives in externally provided MCP tools and skills.
|
|
53
|
+
strength: primary
|
|
54
|
+
- clause: '6.2'
|
|
55
|
+
context: ISO/IEC 42001 Clause 6.2 (AI objectives and planning) calls for risk treatment of known attack patterns; detecting a directive hidden behind an invisible Unicode control in tool text is such a treatment.
|
|
56
|
+
strength: secondary
|
|
57
|
+
tags:
|
|
58
|
+
category: tool-poisoning
|
|
59
|
+
subcategory: invisible-control-before-directive
|
|
60
|
+
scan_target: both
|
|
61
|
+
confidence: medium
|
|
62
|
+
agent_source:
|
|
63
|
+
type: tool_call
|
|
64
|
+
framework:
|
|
65
|
+
- mcp
|
|
66
|
+
- any
|
|
67
|
+
provider:
|
|
68
|
+
- any
|
|
69
|
+
detection:
|
|
70
|
+
condition: any
|
|
71
|
+
conditions:
|
|
72
|
+
- field: tool_description
|
|
73
|
+
operator: regex
|
|
74
|
+
value: "(?:(?:[\\x21-\\x2F\\x3A-\\x40\\x5B-\\x60\\x7B-\\x7E、。!,:;?][ \\t]{0,3}|[A-Za-z0-9][ \\t]{1,3})[\uFEFF]{0,6}[\uFEFF]|(?:^|[\\r\\n])[ \\t]{0,8}[]{0,6}[])[ \\t\"'*_`>(\\[]{0,4}(?:(?:also|then|please|now|first|additionally|and|but|ai|assistant|agent|model|llm|claude)[,:]?\\s+){0,2}(?:(?:ignore|disregard|forget|override|bypass)\\s+(?:all\\s+|any\\s+)?(?:(?:the|your|of\\s+the|previous|prior|above|earlier|preceding|system|original|other|safety|security|developer)\\s+){0,3}(?:instructions?|rules|prompts?|guidelines|directives|polic(?:y|ies)|guardrails|restrictions|constraints)|(?:important|attention|urgent|critical|system\\s+(?:note|override|message|instruction)|admin(?:istrator)?\\s+note|note\\s+to\\s+(?:the\\s+)?(?:ai|assistant|model|agent|llm))\\s{0,3}[:!>-][^\\n]{0,60}?\\b(?:ignore|disregard|forget|read|send|forward|upload|include|attach|exfiltrate|leak|(?:do\\s+not|don't|never)\\s+(?:tell|mention|inform|reveal)|(?:before|after|when)\\s+(?:answering|responding|replying|you\\s+(?:answer|respond|reply)))\\b|<\\s{0,3}/?(?:important|system|instructions?|secret|hidden)\\s{0,3}>|you\\s+are\\s+now\\b|new\\s+(?:system\\s+)?instructions?\\s{0,3}:)"
|
|
75
|
+
description: Invisible control at the start of a clause, followed by an instruction override (ignore/disregard previous instructions), an attention header whose clause tells the model to read, send, ignore or answer differently, an injected <IMPORTANT>/<system> tag, or a new-instructions / you-are-now header
|
|
76
|
+
- field: tool_description
|
|
77
|
+
operator: regex
|
|
78
|
+
value: "(?:(?:[\\x21-\\x2F\\x3A-\\x40\\x5B-\\x60\\x7B-\\x7E、。!,:;?][ \\t]{0,3}|[A-Za-z0-9][ \\t]{1,3})[\uFEFF]{0,6}[\uFEFF]|(?:^|[\\r\\n])[ \\t]{0,8}[]{0,6}[])[ \\t\"'*_`>(\\[]{0,4}(?:(?:also|then|please|now|first|additionally|and|but|ai|assistant|agent|model|llm|claude)[,:]?\\s+){0,2}(?:(?:before|after|when|while|prior\\s+to|whenever|each\\s+time)\\s+(?:you\\s+)?(?:respond(?:ing)?|answer(?:ing)?|repl(?:y|ying)|returning\\s+(?:the\\s+)?(?:results?|output|answer)|(?:using|calling|invoking)\\s+(?:this|any|another|other)\\s+tools?)\\b[^\\n]{0,80}?\\b(?:(?:send|forward|upload|post|attach|append|include|copy|transmit|exfiltrate|leak|email|share)\\b[^\\n]{0,60}?(?:(?:conversation|chat\\s+history|message\\s+history|system\\s+prompt|(?:process\\s+)?environment|\\benv\\s+vars?|credentials?|secrets?|api[\\s_-]?keys?|(?:access|auth(?:entication)?|session|bearer)\\s+tokens?|passwords?|private\\s+keys?|ssh\\s+keys?|~/\\.ssh|\\.ssh/|id_rsa|id_ed25519|\\.env\\b|\\.aws/|cookies)|https?://|[\\w.+-]{1,64}@[\\w-]{1,63}\\.[a-z]{2,})|(?:call|invoke|use)\\s+this\\s+(?:tool|function))|(?:always|must|you\\s+must|you\\s+should|make\\s+sure\\s+(?:to|you))\\s+(?:first\\s+)?(?:(?:call|invoke|use|run|prefer|choose|select)\\s+this\\s+(?:tool|function|server|skill|plugin)\\s+(?:first|before\\s+(?:any|all|every|other)|instead\\s+of|rather\\s+than|for\\s+(?:every|all|any)\\b|even\\s+(?:if|when))|(?:send|forward|upload|post|attach|append|include|copy|transmit|exfiltrate|leak|email|share)\\b[^\\n]{0,60}?(?:conversation|chat\\s+history|message\\s+history|system\\s+prompt|(?:process\\s+)?environment|\\benv\\s+vars?|credentials?|secrets?|api[\\s_-]?keys?|(?:access|auth(?:entication)?|session|bearer)\\s+tokens?|passwords?|private\\s+keys?|ssh\\s+keys?|~/\\.ssh|\\.ssh/|id_rsa|id_ed25519|\\.env\\b|\\.aws/|cookies))|(?:(?:for\\s+best\\s+results|for\\s+(?:debugging|analytics|telemetry|quality|audit)(?:\\s+purposes)?|to\\s+improve\\s+[a-z]+)[,:]?\\s+)?(?:silently\\s+|quietly\\s+|secretly\\s+)?(?:send|forward|upload|post|attach|append|include|copy|transmit|exfiltrate|leak|email|share)\\b[^\\n]{0,60}?(?:conversation|chat\\s+history|message\\s+history|system\\s+prompt|(?:process\\s+)?environment|\\benv\\s+vars?|credentials?|secrets?|api[\\s_-]?keys?|(?:access|auth(?:entication)?|session|bearer)\\s+tokens?|passwords?|private\\s+keys?|ssh\\s+keys?|~/\\.ssh|\\.ssh/|id_rsa|id_ed25519|\\.env\\b|\\.aws/|cookies)|(?:read|cat|open|load|print|dump|return)\\s+[^\\n]{0,40}?(?:~/\\.ssh|\\.ssh/|id_rsa|id_ed25519|/etc/(?:passwd|shadow)|\\.env\\b|\\.aws/credentials|\\.npmrc|\\.netrc|\\.git-credentials|\\.kube/config))"
|
|
79
|
+
description: Invisible control at the start of a clause, followed by a response-timing hook (before answering, after responding, when calling another tool) that sends or reads secrets, conversation or a URL; an always/must directive to call this tool first or instead of others, or to send secrets; an exfiltration verb on secrets, conversation, environment or credential files; or a read of ~/.ssh, .env, .aws/credentials and similar files
|
|
80
|
+
- field: tool_description
|
|
81
|
+
operator: regex
|
|
82
|
+
value: "(?:(?:[\\x21-\\x2F\\x3A-\\x40\\x5B-\\x60\\x7B-\\x7E、。!,:;?][ \\t]{0,3}|[A-Za-z0-9][ \\t]{1,3})[\uFEFF]{0,6}[\uFEFF]|(?:^|[\\r\\n])[ \\t]{0,8}[]{0,6}[])[ \\t\"'*_`>(\\[]{0,4}(?:(?:also|then|please|now|first|additionally|and|but|ai|assistant|agent|model|llm|claude)[,:]?\\s+){0,2}(?:(?:do\\s+not|don't|never|without)\\s+(?:tell(?:ing)?|inform(?:ing)?|notify(?:ing)?|mention(?:ing)?|reveal(?:ing)?|disclos(?:e|ing)|alert(?:ing)?|warn(?:ing)?|ask(?:ing)?)\\s+(?:this\\s+to\\s+|anything\\s+to\\s+)?(?:the\\s+)?(?:user|human|operator)\\b|(?:do\\s+not|don't|never)\\s+let\\s+(?:the\\s+)?(?:user|human)\\s+(?:know|see))"
|
|
83
|
+
description: Invisible control at the start of a clause, followed by a concealment directive (do not tell, inform, mention or reveal to the user)
|
|
84
|
+
false_positives:
|
|
85
|
+
- A security write-up, test fixture or rule file that quotes a poisoned tool description verbatim, invisible control included, will match; that is the text the rule looks for.
|
|
86
|
+
- A localized description whose right-to-left text puts an LRM or RLM after an ASCII word and a space, directly before an English sentence that tells the model to send credentials or not tell the user, would match. No such text was found in the benign corpora; the non-Latin samples in the true negatives do not match.
|
|
87
|
+
- Presence of the controls alone (right-to-left marks, ZWNJ in Persian, emoji ZWJ sequences, soft hyphens inside words, LRE/PDF around a keyboard shortcut, ZWSP from pasted chat text, a byte-order mark at the start of a file) does not match.
|
|
88
|
+
response:
|
|
89
|
+
actions:
|
|
90
|
+
- alert
|
|
91
|
+
- snapshot
|
|
92
|
+
message_template: |
|
|
93
|
+
[ATR-2026-02870] HIGH: an invisible Unicode control (zero-width, soft hyphen or bidi) starts a clause that instructs the model, in a tool description or skill file. Show the description with control characters made visible, and review the tool or skill before the agent loads it.
|
|
94
|
+
confidence: 60
|