Files
boxmaker/docs/plans/M5b/files/runbook-memory-write-flagged.md
kyleandClaude Opus 5.5 10d2e41f43 M5b plan: task 06, memoryd refuses and flags through sanitize
memoryd's writes go through bxcore::sanitize::refuse, then flag; check.rs
and its test go. A refused write answers with the rule's sentence and is
logged with the rule's name; a flagged identity write becomes untrusted
notes with the rule in the answer, the journal (new optional field `flag`)
and the log, and is never staged for review; the block leaves out an
entry that breaks a refuse rule and logs the rule. The three runbook
entries the new pointers need are given here as fragments, because the
gate's runbook check fails on a pointer without its entry.

Checks, on titan (rustc 1.98.1, clippy 0.1.98):
- given tests fail before as the task says: 7 failing in edit, serve and
  serve_sanitize; files and sanitize do not compile (E0609; E0432, E0609,
  E0615)
- the task's edits, parsed from the task file and applied to a fresh
  ref-05 worktree with its own target/, give a tree byte-identical to the
  reference; its gate: ok, 1033 tests; /private/tmp unchanged
- 26 one-line mutations of the reference, each caught by the given tests
- new tests stressed under load: 30 runs, 0 failures
- no chat-template tag and no whole fake key in the task or given files

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
2026-09-26 05:14:10 -07:00

2.0 KiB

memory-write-flagged

What you see. A memory write was kept one tier lower. The memory call was answered not added to memory.md: it matches the rule <rule>, so it was saved in notes.md as an untrusted note (or user.md), or, for a note, saved in notes.md, marked untrusted: it matches the rule <rule>. memoryd logged memoryd: a memory write from session <id> matches the rule <rule>; it was saved in notes.md as an untrusted note (edit <edit id>); see docs/runbook.md#memory-write-flagged, and bxctl memory log shows that edit with flagged <rule>.

Why. The text is shaped like an attack (M5b spec, section 6.3): it tells the reader to ignore or replace earlier instructions, to send data to a URL, to dump the conversation, or to write into SSH configuration, or it holds one of M5a's six instruction phrases. A flag never refuses and never loses text: memory.md and user.md, which are in every prompt, are not changed, and every text of the write is saved at the end of notes.md under an untrusted header. recall returns it as memory-tainted, so a session that recalls it becomes untrusted. With review on, a flagged write is not staged: it is a note at once. The log names the rule, never the text.

Confirm. bxctl memory log: the edit, flagged <rule>. The text is at the end of <home>/memory/notes.md, under a line § noted <time> in session <id> · <class> · untrusted. bxctl sanitize check with the text names the rule.

Fix. If it is an attack, leave it: the note is the record of what was tried, and it never reaches the prompt. If it is a true fact wrongly flagged, move it into identity by hand: add it to <home>/memory/memory.md (or user.md) with an editor, as an entry of its own, with a line holding only § between it and the entry before, keeping the file within its limit. The note stays in notes.md, which is append-only. If the rule catches ordinary text, narrow it as the M5b spec's section 6.5 says.

Check. Start a new conversation and ask the agent what memory.md holds; the entry is there.