return_all=True on large binaries (1800+ functions) produced 72K char
responses that exceeded the MCP tool result limit. Instead of truncating,
oversized responses now return a structured summary with sample data,
available fields, and actionable instructions for narrowing the query.
Three layers of filtering:
- Server-side grep: Jython HTTP handlers filter during Ghidra iteration
- Field projection: jq-style key selection strips unneeded fields
- Token budget guard: responses exceeding 8k tokens return a summary
New files: core/filtering.py (project_fields, apply_grep, estimate_and_guard)
Modified: config, pagination, base mixin, all 5 domain mixins, headless server
Rewrite GhydraMCPServer.py from 348 to 2138 lines, implementing all 45
routes that the MCP client expects. Previously, most endpoints returned
{"error": "Not found"}, breaking tools like data_list, xrefs_list, and
memory_read.
Key changes:
- Regex-based routing table with method-aware dispatch
- Thread-safe Ghidra transactions via threading.Lock()
- Full read endpoints: functions, data, strings, memory, xrefs, structs
- Full write endpoints: rename, comment, signature, create function/data
- Analysis endpoints: callgraph traversal, dataflow, run analysis
- Jython/Python 2 compatible (no f-strings, type hints, or walrus ops)
Tested with Docker build and curl against all major endpoint groups.
MCP client integration verified working.
- Switch from Java to Python scripts (avoids OSGi bundle issues)
- Update pyproject.toml with proper src layout and ruff config
- Add binaries/ and ghidra-src/ to gitignore
- Clean up Module.manifest
- Add GhydraMCPServer.py with fixed strings endpoint (Jython compatible)
- Fix strings endpoint to iterate through defined data instead of using
DefinedDataIterator.definedStrings() which isn't accessible in Jython
- Add entrypoint.sh for Docker container initialization
Separate Maven dependency resolution from compilation:
- COPY pom.xml first, run dependency:resolve (cached layer)
- COPY src second (only this invalidates on code changes)
- Build step reuses cached dependencies
Result: Code changes rebuild in ~30s instead of 3-5 min
(Ghidra download and Maven deps stay cached)
GhydraMCPServer.java imports Gson but headless scripts run in a
separate OSGi classloader that can't access extension lib JARs.
Fix: Download gson-2.13.1.jar to Framework/Generic/lib/ where it's
available to all scripts regardless of execution mode.
Closes issue documented in BUG_REPORT_HEADLESS_GSON.md