The Most Expensive Command in Your Agent Is grep

Sonar just published a number that should stop every team running coding agents on a large repository: a single, ordinary pull request — about 800 lines of changes, the kind a senior engineer would describe as routine — consumed roughly 156 million tokens. About 700 model round-trips. A context window that peaked at 459k tokens. Across a broader batch of similar PRs, the average was around 234 million context tokens and roughly $65 per pull request, with a median near $52.

Read the final diff of that PR and you'd finish in five minutes. So where did 156 million tokens go?

Not into reasoning. Not into generation. They went into grep — or more precisely, into the file reads that follow every grep, and then into the conversation history that carries those reads forward, turn after turn after turn. Sonar calls this the context tax, and their measurement of it, published September 1 alongside their new Vortex product, is the most precise public accounting I've seen of where agent token budgets actually go.

The conclusion is uncomfortable for anyone who thinks model pricing is their cost problem. It isn't. The most expensive command in your agent's loop is a text search.

The Arithmetic of Residency

The core mechanic is simple once you see it, and almost nobody accounts for it. A coding agent doesn't read a file once. On every new step, the model is re-sent the entire conversation so far as input. Prompt caching makes those repeated tokens cheap per unit — roughly 10% of input price — but you pay that discounted rate on every single turn.

Which means the true cost of a token isn't its size. It's its size multiplied by the number of turns it survives.

Sonar's example: read a 600-line file on turn 40 of a 512-turn session and you haven't paid for 600 lines once. You've paid for 600 lines across roughly 470 more turns. One unnecessary file read in their measured trace carried about 2.7 million cache-read tokens that a precise lookup would have delivered in roughly 0.33 million — a 9x difference on a single navigation step, compounded across the rest of the run.

This is why agent bills feel irrational. The unit economics of autocomplete were proportional to human typing speed — the world's most natural rate limiter. Agents broke that proportionality twice over: they generate their own next step (more turns), and everything they touch stays resident in context for the rest of the run (more tokens per turn). Agent cost is approximately turns multiplied by resident context. Grep-and-read storms are the worst possible combination: they add turns and raise the resident-context floor at the same time.

Bigger Windows Made It Worse

Here's the part that runs against the industry's favorite fix. Most people think the path out of context pressure is bigger context windows. Actually, bigger windows made the tax worse.

Sonar's traces show context windows routinely peaking between 450k and 975k tokens on ordinary pull requests — brushing the 1M-token ceiling that frontier models now ship with. When the window fills, the agent is forced to compact, and compaction means losing earlier context: the task definition, the constraints, the file it read forty turns ago that turns out to matter. So the failure mode isn't just cost. It's the agent quietly forgetting what it was doing and re-deriving it — paying the tax again.

A bigger window doesn't eliminate the tax. It extends the runway over which every resident token keeps compounding before the reset. You go from paying 600 lines × 470 turns to paying 600 lines × 900 turns, and you call it an upgrade. The 1M-token window didn't fix navigation economics. It deferred the bill and made the final number larger.

The correct framing: a large context window is storage, not retrieval. Humans solved this decades ago — we don't keep entire libraries on our desks. We built indexes. Your agent is sitting in a library with a flashlight, and you're paying for every page it touches by the hour.

grep Finds Strings, Not Meaning

The tax has a second, quieter half that costs more than tokens. A regex finds the strings you thought to search for — not the call that reaches your function through an interface, an alias, or a different programming language.

Sonar's own pull request is the perfect example, and it's almost too on the nose: the change they were building added call-site resolution to their Python backend, mirroring logic that already existed in a C# backend. The C# function was named resolve_type_node. The Python function was named resolve_return_type. A grep for one name will never surface the other. Cross-language changes — the kind that are simultaneously the most expensive and the most error-prone thing you can ask an agent to do — are structurally invisible to text search.

What grep misses doesn't stay missed. It becomes a failed build, another round-trip to CI, another session of context re-accumulation — each retry paying the token tax again from a fresh start. And in the worst case it doesn't fail at all: a missed call site reached indirectly through an interface often still compiles, passes the tests that don't exercise that path, and ships as a silent bug. The navigation deficit converts directly into correctness debt.

The Graph Answer

Sonar's response is SemSitter, a semantic navigation engine that maintains what they call a Unified Dependency Graph of the repository: every function, method, class, field, and parameter is a node; the relationships between them — calls, references, returns, implements, extends — are typed edges. Instead of asking the filesystem "which files mention resolve_return_type?", the agent asks the graph: "give me the definition this call binds to, the type that owns it, its return type, and its callers." It gets back one method body plus the edges that answer the question. No surrounding file, no six-way grep spiral, nothing to widen.

The measured results, across six real refactoring scenarios in Java, Python, TypeScript, and C#: cost reductions from 6% to 36% per run. The best case — a BloomFilter self-typing refactor in Java — went from $14.29 to $9.38 per run with 31% fewer input tokens. A SQLAlchemy compiler change came in 29% cheaper. A C# return-type refactor, 20% cheaper.

But the number I respect most in their entire publication is the one that didn't move: a TanStack refactoring task where savings were around 5%, and other task shapes where cost stayed within a few percent of baseline. Sonar states plainly that the engine "will not help on tasks where navigation is not the constraint." This is the honest boundary, and it maps exactly onto when you should care: if your agent's cost is dominated by build loops, long test suites, or tasks where sufficient context fits in a single pass, semantic navigation has nothing to accelerate. If your agent is grepping its way through a codebase bigger than its window — and on any real production repository, it is — the tax is already on your bill.

Substitutive Beats Additive

Buried in Sonar's engineering detail is a design principle that generalizes far past this one product, and it's the reason I'd take this launch seriously even if you never buy a SonarQube license.

A navigation tool can be additive — it returns the right symbols but not their locations, so the agent still has to grep to find the edit points, stacking the query on top of the search. Or it can be substitutive — it hands back a deduplicated list of {file_path, line} rows, one per affected source line, and the search step disappears entirely. Sonar's engine returns exact line anchors, which is precisely what makes it a cost win instead of a cost add-on. The difference between the two is not implementation detail. It's the difference between a tool that shrinks your agent's loop and a tool that grows it while feeling helpful.

This is the sharpest version of a test I'd apply to anything that wants to sit inside an agent's loop: does it replace turns, or add them? Tools that inject context but don't remove work are additive — they make the agent smarter and more expensive simultaneously. Tools that answer a question the agent would otherwise spend five tool calls approximating are substitutive. This distinction between additive and substitutive tooling is one of the core ideas in harness engineering — I devote a full chapter to it in Harness Engineering: The Complete Guide to Agent-First Software Development — because it's the difference between a harness that compounds savings and one that compounds cost.

The Industry Is Converging From Both Ends

Sonar isn't alone in discovering that navigation, not reasoning, is the bottleneck. The same week, Meta shipped Muse Spark 1.3, and the headline claims weren't benchmark scores — they were 20% fewer tool calls and 25% fewer tokens per comparable engineering task. Meta is training the model itself to grep less: fewer turns where unnecessary, less verbosity, cleaner navigation behavior. It's the same diagnosis arriving through the parametric route instead of the infrastructure route.

Both will matter, but they're not equal. A model trained to navigate more carefully is still guessing at structure it cannot see — it's a better blindfolded searcher. A graph the agent can query is sight. And the model-side gains get captured once per model generation, while infrastructure-side gains compound with codebase size: the bigger the repository relative to the window, the more every structural lookup saves. For the codebases where agents cost the most — the ones that don't fit in any window — the graph wins by construction.

Expect this layer to become standard harness furniture. The MCP ecosystem already made servers the integration point: Sonar's engine ships as a SonarQube MCP Server or CLI-installed skill, meaning Claude Code, Codex, Cursor, and anything else MCP-capable can query the same graph. Once one vendor proved the context tax is measurable and cuttable, every serious harness will grow an index. The terminal ate the IDE this year. Next year, the index eats the grep.

What to Do This Week

You don't need to buy anything to act on this. Three moves, in order of effort.

Measure your residency multiplier. Pull the traces from a few representative agent sessions and compute two numbers: total round-trips, and resident context at the final turn. Multiply them and compare against your invoice. If your sessions run hundreds of turns on tasks whose diffs are a few hundred lines, navigation is your cost center, and no model downgrade will fix it — a cheaper model just greps more inefficiently for fewer dollars per turn.

Kill the biggest over-reads. Before adding anything, subtract. Most harnesses re-read entire files after every edit when a diff would do. Most agents open files far wider than the symbol they need. Compacting tool output, truncating file reads to relevant ranges, and summarizing stale exploration are pure subtraction — they cut resident context on every remaining turn. Sonar's own data says a single avoided over-read is worth millions of cache-read tokens.

Give the agent an index, not a flashlight. Try structural navigation on one codebase where agents burn the most money. Sonar's version requires their cloud Enterprise or Teams Annual tiers, but the pattern isn't proprietary: language servers already expose references, definitions, and type hierarchies, and wiring an LSP-backed tool into an agent's toolset gets you the substitutive queries — exact locations, no grep aftermath — without waiting for procurement. Measure cost per completed task before and after. That delta, on your repository, is the only benchmark that matters.

The Bigger Picture

Two years of agent economics have been argued as if the bill were a function of model pricing, and every pricing announcement has been covered accordingly. The context tax shows the premise is wrong. The bill is a function of how the harness moves information into the loop — and text search in a conversation that never forgets is close to the worst possible design.

The teams that internalize this will stop shopping for cheaper tokens and start engineering smaller loops: fewer turns, less residency, structural retrieval instead of textual scanning. That work is unglamorous and yields no leaderboard scores. It just shows up, month after month, as the difference between an agent infrastructure that scales and one that doesn't.

grep built the modern software world. It should not be allowed to unbuild your token budget.