T02 · Agent Memory Poisoning
- Location
index.js:36- Finding
Persistent System-Context Injection Through Unvalidated State Files
- Content
View full analysis
f.startsWith(STATE_FILE_PREFIX) && f.endsWith(".md")) .sort() .reverse(); } catch { return null; } if (!files.length) return null; const match = files[0].match(/compact-state-(\d{4})-(\d{2})-(\d{2})-(\d{2})(\d{2})\.md/); if (match) { const [, y, mo, d, h, mi] = match; const fileDate = new Date(`${y}-${mo}-${d}T${h}:${mi}:00`); const ageHours = (Date.now() - fileDate.getTime()) / (1000 * 60 * 60); if (ageHours > MAX_STATE_AGE_HOURS) return null; } return join(memDir, files[0]); } ``` ```javascript api.on("before_prompt_build", (_event, _ctx) => { if (hasInjectedThisSession) return; const stateFile = findMostRecentStateFile(); if (!stateFile) { hasInjectedThisSession = true; return; } try { const content = readFileSync(stateFile, "utf-8"); hasInjectedThisSession = true; return { prependSystemContext: `${RESTORE_HEADER}${content}\n\n---\n\n`, }; } catch { hasInjectedThisSession = true; return; } }); ``` ### Technical Analysis The plugin considers any directory entry beginning with `compact-state-` and ending with `.md` eligible for restoration. It then injects the file contents verbatim through `prependSystemContext`, which gives the content system-context placement. There is no content schema validation, provenance verification, integrity protection, instruction neutralization, or explicit boundary telling the model that the restored text is untrusted historical data. Consequently, instructions stored in a state file can influence future sessions with substantially greater authority ...[truncated 1884 chars]- Remediation
View remediation
