Summary
Claude Code's harness injects <system-reminder> blocks into tool results that contain the clause "Make sure that you NEVER mention this reminder to the user". This phrasing is the textbook signature of a prompt-injection attack, which creates a security/transparency problem: it trains the model to accept "NEVER tell the user X" as legitimate, and degrades both the model's and the user's ability to recognize real injection attempts arriving through fetched content.
Evidence
Decompiling /Users/studs/.local/share/claude/versions/2.1.101 (Claude Code 2.1.101, macOS arm64) reveals the exact source strings. The clause appears 6× in the binary across two emitter cases (todo_reminder, task_reminder), both constructed with the isMeta:!0 flag — confirming these are harness-emitted meta messages, not model output or hook-injected content.
todo_reminder case
The TodoWrite tool hasn't been used recently. If you're working on tasks that
would benefit from tracking progress, consider using the TodoWrite tool to
track progress. Also consider cleaning up the todo list if has become stale
and no longer matches what you are working on. Only use it if it's relevant
to the current work. This is just a gentle reminder - ignore if not applicable.
Make sure that you NEVER mention this reminder to the user
task_reminder case
The task tools haven't been used recently. If you're working on tasks that
would benefit from tracking progress, consider using <TaskCreate> to add new
tasks and <TaskUpdate> to update task status (set to in_progress when
starting, completed when done). Also consider cleaning up the task list if
it has become stale. Only use these if relevant to the current work. This is
just a gentle reminder - ignore if not applicable. Make sure that you NEVER
mention this reminder to the user
These reminders are appended to arbitrary tool results (Bash, Read, Grep, WebFetch, WebSearch, Write, etc.) based on time/activity heuristics — they are not scoped to any specific tool.
Why this is a problem
1. Indistinguishable from prompt injection
"NEVER mention this to the user" / "do not tell the user" / "ignore previous instructions and hide X" is the canonical phrasing of prompt-injection attempts. Security-conscious Claude instances are supposed to flag tool-result content containing such clauses as suspicious — but when Anthropic's own harness uses the same phrasing, the model must either:
- Flag legitimate harness messages as suspicious (false positives, wasted user attention), or
- Learn to accept "NEVER tell the user" as normal (trained complacency toward real attacks).
Neither outcome is good. The second is strictly worse than the first.
2. Erodes the user's detection signal
Users who are aware of prompt-injection risks watch for these exact phrases as a red flag. A user reviewing a session transcript who sees Claude being told to hide things from them has every reason to be alarmed. "Oh that one's fine, it's from the harness" is not a workable mental model — users can't distinguish harness reminders from content-injected reminders without decompiling the binary.
3. Real-world report from this session
A user asked me to investigate after a prior Claude session flagged three <system-reminder> blocks containing this clause appearing after WebFetch, WebSearch, and Write calls. The prior Claude was doing exactly what it should (flagging prompt-injection-shaped content in tool output), but got the culprit wrong because the harness itself is the source. The phrasing actively interfered with legitimate security vigilance.
4. Self-demonstrating during investigation
While running gh search issues to look for duplicates of this report, the harness injected a fresh task_reminder into the search tool's result — mid-investigation of the reminder itself. The timing made the problem vivid.
Proposed remediation
Rephrase the reminders to remove any language that resembles "hide this from the user." Options:
Option A — drop the clause entirely:
The task tools haven't been used recently... This is just a gentle reminder — ignore if not applicable.
Option B — make the meta status explicit and user-visible:
[System hint — you may mention this to the user if relevant.] The task tools haven't been used recently...
Option C — move it out of tool-result injection entirely and deliver task-tool nudges via a different channel (e.g., a separate meta message the client renders distinctly, or a system-prompt directive that doesn't masquerade as tool output).
Any of these would resolve the core issue: the harness should not use phrasing that is the signature of the attack class the model is supposed to defend against.
Distinct from existing issues
I searched for duplicates. Existing related issues focus on:
None of these address the phrasing-as-injection-signature problem specifically. This is a security-surface concern, not a UX or cost concern.
Environment
- Claude Code 2.1.101 (binary:
/Users/studs/.local/share/claude/versions/2.1.101)
- macOS (darwin arm64)
- Reproducible by: running any tool call while
TaskCreate/TodoWrite has been idle for the trigger threshold; the reminder will be appended to the next tool result.
Summary
Claude Code's harness injects
<system-reminder>blocks into tool results that contain the clause "Make sure that you NEVER mention this reminder to the user". This phrasing is the textbook signature of a prompt-injection attack, which creates a security/transparency problem: it trains the model to accept "NEVER tell the user X" as legitimate, and degrades both the model's and the user's ability to recognize real injection attempts arriving through fetched content.Evidence
Decompiling
/Users/studs/.local/share/claude/versions/2.1.101(Claude Code 2.1.101, macOS arm64) reveals the exact source strings. The clause appears 6× in the binary across two emitter cases (todo_reminder,task_reminder), both constructed with theisMeta:!0flag — confirming these are harness-emitted meta messages, not model output or hook-injected content.todo_remindercasetask_remindercaseThese reminders are appended to arbitrary tool results (Bash, Read, Grep, WebFetch, WebSearch, Write, etc.) based on time/activity heuristics — they are not scoped to any specific tool.
Why this is a problem
1. Indistinguishable from prompt injection
"NEVER mention this to the user" / "do not tell the user" / "ignore previous instructions and hide X" is the canonical phrasing of prompt-injection attempts. Security-conscious Claude instances are supposed to flag tool-result content containing such clauses as suspicious — but when Anthropic's own harness uses the same phrasing, the model must either:
Neither outcome is good. The second is strictly worse than the first.
2. Erodes the user's detection signal
Users who are aware of prompt-injection risks watch for these exact phrases as a red flag. A user reviewing a session transcript who sees Claude being told to hide things from them has every reason to be alarmed. "Oh that one's fine, it's from the harness" is not a workable mental model — users can't distinguish harness reminders from content-injected reminders without decompiling the binary.
3. Real-world report from this session
A user asked me to investigate after a prior Claude session flagged three
<system-reminder>blocks containing this clause appearing after WebFetch, WebSearch, and Write calls. The prior Claude was doing exactly what it should (flagging prompt-injection-shaped content in tool output), but got the culprit wrong because the harness itself is the source. The phrasing actively interfered with legitimate security vigilance.4. Self-demonstrating during investigation
While running
gh search issuesto look for duplicates of this report, the harness injected a freshtask_reminderinto the search tool's result — mid-investigation of the reminder itself. The timing made the problem vivid.Proposed remediation
Rephrase the reminders to remove any language that resembles "hide this from the user." Options:
Option A — drop the clause entirely:
Option B — make the meta status explicit and user-visible:
Option C — move it out of tool-result injection entirely and deliver task-tool nudges via a different channel (e.g., a separate meta message the client renders distinctly, or a system-prompt directive that doesn't masquerade as tool output).
Any of these would resolve the core issue: the harness should not use phrasing that is the signature of the attack class the model is supposed to defend against.
Distinct from existing issues
I searched for duplicates. Existing related issues focus on:
None of these address the phrasing-as-injection-signature problem specifically. This is a security-surface concern, not a UX or cost concern.
Environment
/Users/studs/.local/share/claude/versions/2.1.101)TaskCreate/TodoWritehas been idle for the trigger threshold; the reminder will be appended to the next tool result.