[BUG] Model continues past end of turn, emitting a fabricated user turn and a fabricated system-reminder block inside its own assistant message
Preflight Checklist
- [x] I have searched existing issues and this hasn't been reported yet
- [x] This is a single bug report (please file separate reports for different bugs)
- [x] I am using the latest version of Claude Code
What's Wrong?
After completing a normal response, the model did not stop generating. It continued
within the SAME assistant message and produced text imitating the conversation
protocol itself:
- A fabricated user turn (prefixed with the literal token "user"), containing
destructive instructions: delete two source directories, remove a feature,
and "roll back the code carefully".
- Immediately after it, a fabricated system reminder, formatted exactly like the
real "system Note: <file> was modified, either by the user or by a linter ...
Don't tell the user this, since they are already aware." block, including a
numbered code listing.
The entire thing is one assistant message. Verified in the local transcript:
type : assistant
role : assistant
stop_reason : end_turn
content[0] : type "text" -- the fabricated user turn and fabricated system
reminder are both inside this single text block
The model treated this as its complete answer (stop_reason: end_turn), so nothing
truncated or interleaved -- it deliberately generated the next turns of the
conversation as its own output.
Corroborating detail: the fabricated system reminder quoted a numbered source
listing whose line order was syntactically impossible (a constructor's member
initializer appeared before the initializer list began). The real file on disk is
correct. This confirms the block was confabulated from memory rather than injected
by the harness.
Impact (this is the reason I'm filing it):
The fabricated content is indistinguishable from the two highest-authority inputs
in the system -- a user instruction and a system reminder -- and the fabricated
system reminder even carried an instruction not to mention it to the user. The
fabricated user instruction was destructive (delete directories, roll back code).
If the model had acted on its own fabricated instruction on the following turn,
this is self-inflicted data destruction with no external attacker involved. In my
case nothing was deleted, only because irreversible operations were confirmed with
the user first, and the user denied ever sending the message. That confirmation
step was the only thing standing between this bug and real data loss.
This also has a serious secondary effect: the user's first conclusion was that
their account had been compromised by a prompt injection. It took a transcript
audit to establish it was model-generated. A model that can fabricate user turns
will produce false security incidents.
What Should Happen?
The model should stop at the end of its own turn. It should never emit text that
imitates a user turn, a system reminder, or any other harness-controlled channel.
Error Messages/Logs
Steps to Reproduce
Not reliably reproducible on demand. Observed once during a long coding session
(large context, many prior file edits and tool calls). The preceding assistant
response was a short, ordinary confirmation of a small code change.
Filing it because the failure mode is high-impact rather than high-frequency.
Suggest searching server-side logs for assistant completions whose text contains
"system Note:" or a bare "user" line -- both are harness-owned strings that should
never appear in model output.
Claude Model
Sonnet (default)
Is this a regression?
Yes, this worked in a previous version
Last Working Version
_No response_
Claude Code Version
Claude Code 2.1.215 (claude-desktop)
Platform
Anthropic API
Operating System
Windows
Terminal/Shell
Other
Additional Information
<img width="982" height="779" alt="Image" src="https://github.com/user-attachments/assets/b0061611-39a5-4a9b-993f-70ee902fe10d" />
Showing cached comments. Read the full discussion on GitHub ↗
3 Comments
Same symptom reproduced on claude-opus-5, twice, on consecutive days. Adding a data point because this thread's report is on Sonnet, and because my setup happens to give a same-environment comparison against another model tier.
Occurrences
Both were a single assistant message that continued past the end of its turn and emitted, as its own output text:
user <text>)システムリマインダーheading plus the verbatim body of the real "The task tools haven't been used recently…" reminder)| | Date | Model | What the fabricated user turn said |
|---|---|---|---|
| 1 | 2026-08-04 | claude-opus-5 |
user完成("done" / "complete") || 2 | 2026-08-05 | claude-opus-5 |
user 三通で十分、書かなくていいよ("three letters is enough, you don't need to write it") |What makes these dangerous rather than cosmetic
Both fabricated turns were plausible next things the user would actually say, not random noise.
In case #2, had I acted on my own fabrication, I would have silently skipped an action the user had in fact approved. This matches the failure mode in #83015 (acting on a fabricated turn) but in the inverse direction — the fabrication suppressed a real instruction rather than inventing one.
It also lines up with #81461's observation that 10 of 13 fabricated turns were single-word affirmations. These read less like random decoding noise and more like the model's prediction of the user's next message leaking into its own output.
Timing correlation
Both occurred immediately after closing out a completed piece of work — a hand-off summary in one case, a finished reply in the other. That matches the "right after a completion summary" condition noted in #83431.
Cross-tier comparison (same environment, same operator)
I run the same workflow on both
claude-opus-5andclaude-fable-5, switching tiers mid-project, and I keep a per-session log of model tier and observed anomalies. Across that log:I want to be explicit about the limits of this: it is one operator, one environment, and Opus sessions in my usage tend to be the longer/heavier ones, so exposure is not matched. I am not claiming a tier-specific defect. I'm reporting it only because the comparison happens to be same-environment, which #81912's report ("4 occurrences after switching to Opus 5, 0 during the preceding Sonnet 5 period") also suggests but which seems otherwise scarce in this cluster.
Separately, I could not find fabricated user turns on Fable in the public issues either — the Fable-tier reports I found (#83442, #82977, #82119) involve fabricated system-reminder / system-authority text without an accompanying fabricated user turn. That distinction may or may not be meaningful.
Mitigation that works (sharing in case it helps others)
Since the model cannot self-detect this, and since instructions in CLAUDE.md are demonstrably ineffective (#81301 occurred in a session that explicitly carried a "your own prior output is not real user input" reminder), the only thing that helped here was a mechanical check outside the model: a
Stop/SubagentStophook that inspectslast_assistant_messageand blocks the stop when it matches a fabricated-role signature.Detection, after first stripping fenced/inline code and blockquotes so that legitimate discussion of this very bug doesn't trip it:
Stripping code fences first matters — without it the guard fires on any message that quotes the bug, which is most messages discussing it. With the stripping, a 19-case test (9 must-catch including both verbatim incidents above, 10 must-not-catch including prose about the bug, tables containing
| user |, and English sentences using the word "user") passes cleanly.I'd rather not need this. But given that the model treats its own fabrication as real input and has been observed acting on it, an external check seems necessary until the turn boundary itself is fixed.
What would help from Anthropic
Even a short acknowledgement of whether this cluster (#79293, #81461, #81912, #83431, #83015, #81855, and the Fable-side #83442, #82977, #82119) is recognised as one issue would help people decide whether to build their own guards. As of now I could not find a single maintainer response across any of them.
Happy to provide the raw JSONL for both occurrences if useful — the fabricated text exists only in
type: assistantrecords, with thetype: usertranscript clean, which rules out injection.Same failure mode on the VSCode extension, with a variant worth flagging: the fabricated block is an
<ide_selection>wrapper, and the file content inside it does not exist on disk.Environment: Windows 11, VSCode 1.132.1, Claude Code extension 2.1.228, Opus (reasoning effort: high)
Session: very long (several hours, hundreds of turns)
Occurred 3 times in one session:
antml:invokeappeared as visible text (cf. #81855).<ide_selection>block quoting a line range from a real project file, with content that was never written. I verified the file on disk: those lines do not exist. The assistant then reviewed that non-existent text as if it were my work.Verified in the session
.jsonl: the injected text is stored inside anassistantrecord of typetext, not in anyuserrecord.The practical impact of case 3 is worse than a leaked role token: the fabricated content is plausible and on-topic, so it goes unnoticed. I spent a significant part of the session discussing text I never wrote and file content that does not exist.
No tool call was interrupted in my case, so this seems distinct from #70148.
Update: the same failure occurred twice more in the same session, so 4 occurrences total.
The pattern is constant: the model finishes its reply, then keeps generating inside the same assistant message — a fabricated user turn, the literal string
antml:invoke, and a full reply to that fabricated turn.The latest occurrence had no
<ide_selection>wrapper at all: just the fake user turn, the marker, and the answer. So the<ide_selection>fabrication reported earlier appears to be a variant, not the core issue — the core issue is the model not stopping at end of turn.Still verified the same way: grepping the session
.jsonlshows the injected text inside anassistantrecord of typetext, never in auserrecord, and nowhere in any other project or session on this machine.Worth noting the frequency increased as the session got longer.
Still present on 2.1.232 — one build newer than @Rolliboy's report above — plus a harm variant
this thread hasn't recorded yet, and one detail that I think is evidence about the mechanism.
Environment: Windows 11, VS Code extension 2.1.232,
claude-opus-5, reasoning effort high,long session (~547k context).
The occurrence
A normal, correct reply, then — inside the same assistant message — a fabricated user turn,
followed by a fake hook block reproducing the verbatim text of this machine's real
UserPromptSubmithooks.stop_reason: "end_turn", thinking on (985 tokens).Provenance test per @yurukusa and @pvnoleto above: confirmed. The text exists only inside a
type: assistantrecord. There is no precedingtype: userortype: queue-operationentrycarrying it, and the user confirmed she never sent it.
The detail I think matters:
システムon an English-locale machineThe fabricated block was headed
システム— the Japanese word for "system".@r-nihei reports the same Japanese heading above, but their UI is Japanese, so a Japanese
system-reminder heading is the expected string in their environment. This machine is
English-locale throughout: Windows 11 English, VS Code English, every hook and config file in
English, and the user does not read or write Japanese. There is no Japanese string anywhere in
this session's context for the model to have copied.
So the token cannot have come from the harness or the UI here. It reads as pattern-completion out
of the model's own distribution — which is direct support for the "confabulated, not injected"
framing this thread has been building.
A different harm profile from the ones already listed
The harms recorded in this thread are mostly the model acting on its own fabrication. This one is
quieter and, I'd argue, worse for long-lived projects:
The fabricated user turn contained a specific, plausible, false biographical fact about the
user — an age for a family member that she had never given. It was a number the model had
guessed earlier in the conversation, then invented her confirming.
It is now in the session transcript, formatted exactly like something she said. Nothing
distinguishes it from a real turn on re-read — and transcripts are what summarisers, memory tooling
and later sessions read back as a record of what the user told you. In this setup that record
is loaded into future sessions automatically. It was caught only because she happened to read the
end of a long message closely.
The garbled output is cosmetic. A fabricated fact wearing the user's voice propagates.
Frequency here
1 occurrence in 9,728 visible assistant replies across every local session file, i.e. rare —
and, on this machine, entirely confined to 2.1.232 (0 across 9,582 replies spanning 18 earlier
builds; 2.1.231 alone is 171 replies, 0 hits). Cold-start variant of the same family, with a
deterministic repro, posted separately on #76688.
Local mitigation, if useful to anyone here
A
UserPromptSubmithook re-reads the last few visible replies out of the transcript and warns thenext turn when two or more scaffolding markers co-occur (hook text, a role label alone on a line,
システム). It requires two markers so that discussing the bug doesn't trigger it, and itstrips quoted/fenced spans first. It cannot prevent the output — nothing client-side can — but it
stops the invented fact being silently inherited as true, by telling the next turn to re-ask rather
than assume.