Skip to content

Cost tracker keeps an unbounded partial JSONL event and repeatedly recopies it #138

Description

@GautamSharma99

Summary

The incremental cost-session reader has no maximum JSONL event size:

readSessionUsage lines 186-226

After each 64 KiB read, it concatenates session.remainder with the new buffer. Everything after the last newline is retained as the next remainder.

If a session file contains a very large unterminated line, or is corrupted so that no newline arrives, the remainder grows to the size of the file. Each iteration recopies the entire previous remainder through Buffer.concat, producing unbounded memory growth and roughly quadratic copying.

Why this matters

A malformed or unexpectedly large Codex session event can consume substantial memory during cost polling. Because maxCostUsd enforcement depends on this reader completing and reporting usage, the same condition can delay the budget abort and scan shutdown.

Normal partial writes make a remainder necessary, but they do not require retaining an unlimited event.

Expected behavior

The tracker should accept ordinary partial writes while rejecting or ignoring a session once one event exceeds a documented maximum size.

Suggested direction

Track pending-line bytes and stop reading/quarantine the session after a fixed maximum. Avoid repeatedly concatenating the entire remainder; accumulate bounded chunks or scan new buffers incrementally. Surface the failure through the existing tracker error path without including raw session content.

Add tests for a line exceeding the limit across multiple reads, a normal event split across reads, and recovery when a newline arrives below the limit.

This is related to cost tracking but distinct from #31, which concerns queued full session-tree rescans rather than the JSONL parser's line buffer.

Found by static audit of upstream main at 9c7634b.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions