Follow-up to the salvaged str(tools) fix. The id()-keyed _TOOLS_TOKENS_CACHE had no eviction, so a long-lived gateway/desktop backend could accumulate an unbounded number of stale entries as it builds transient tool lists. Cap it at 256 with oldest-first eviction (insertion-ordered dict) and add a regression test asserting the cache never exceeds the cap.