nsight-graphics-mcp
An MCP (Model Context Protocol) server for NVIDIA Nsight Graphics on
Windows. It wraps the entire Nsight Graphics command-line surface
(ngfx.exe, ngfx-capture.exe, ngfx-replay.exe, ngfx-rpc.exe, the
nv-aftermath-* tools, nv-nsight-remote-monitor.exe, the layer-install
batch scripts, the NGFX in-app SDK headers, glslang.exe, and the bundled
DXC) so an LLM agent can drive Graphics Capture, GPU Trace Profiler,
Generate C++ Capture, OpenGL Frame Debugger, Aftermath crash analysis, and
in-app integration end-to-end — without the Nsight UI.
Why a wrapper? The Nsight Graphics CLIs are scriptable, but their outputs are coarse:
ngfx-replay --metadata-functionsdumps the entire recorded API stream to stdout,--metadata-objectsdumps every API object as JSON,.nsight-gputracereports are zip-like archives, and the NGFX in-app SDK is a tree of headers.nsight-graphics-mcpindexes those coarse outputs into per-capture SQLite databases, peeks inside the archives, parses the SDK headers, and exposes precise queries the LLM can call instantly without re-running the CLI.
What it can do
Drive the four documented activities (ngfx.exe --activity)
Each one accepts the full set of activity-specific flags from ngfx --help-all — start triggers (--start-after-frames / --start-after-ms
/ --start-after-hotkey / --start-with-ngfx-sdk / …), stop triggers
(--limit-to-frames / --max-duration-ms / --stop-with-ngfx-sdk / …),
per-arch metric-set selection, GPU clock locking, shader-pipeline
collection toggles, and so on.
Pass background=True to keep ngfx.exe running so you can hit the
capture / trace hotkey in-app — the call returns a launch-session handle
you can poll with ngfx_launch_status and terminate with
ngfx_launch_stop.
Headless capture (ngfx-capture.exe) — no Nsight UI required
Deep Nsight-only capture capability report
Object index (Pipelines / Shaders / Resources — GUI 'Resources' pane parity)
Protobuf schema reference (RE-derived)
The internal capture format is protobuf-encoded in the NV.* namespace.
The MCP extracts the schema directly from the Nsight binaries so the LLM
can navigate the format conceptually without re-running protoc.
Two layers are exposed:
- Inventory only (fast) — string-scan for proto filenames and message names. No protobuf decoder required.
- Full FileDescriptorProto extraction — walks the embedded descriptor
blobs in
ngfx-replay.exe, decodes them withgoogle.protobuf.descriptor_pb2, and builds aDescriptorPoolso any message can be looked up by FQN and dynamically instantiated. Recovers all 22 .proto files + 648 messages including the criticalNV.EventParameters.Messages.PbFunctionCallDesc(which has the per-callfunctionName+ repeatedPbArgument argumentsthat--metadata-functionshides).
Low-level capture-format probing (experimental, RE-derived)
Direct .ngfx-gfxcap decoder (RE-derived, no UI required)
Decodes the capture wrapper format end-to-end — no ngfx-replay /
ngfx-ui roundtrip needed for the metadata layer. The wrapper is fully
reverse-engineered: nlyp file-magic, then a sequence of chunks each
prefixed by a 48-byte mini-header (elif magic + version + compression
flag + compressed/uncompressed sizes + chunk-id + self-offset), payload
either LZ4-block compressed or stored, 16-byte aligned. The file ends
with a TOC region of elif-magic records pointing back to chunk
offsets. One chunk holds a serialised NV.PbTableOfContents with the
UUID, frame counts, GPU info, primary API, and lists of
FunctionInfoChunkIds + ResourceInfoChunkIds.
Caveat (work in progress). The chunks listed by
FunctionInfoChunkIds hold a binary fixed-stride table, not
PbFunctionCallDesc protobuf messages — Nsight stores the per-event
arg stream as packed C-style records, not protobuf. The wrapper +
TOC are fully decoded so the metadata layer works headless today; the
per-record layout of FunctionInfo is the remaining RE work for direct
arg extraction. Until that's done, use the C++-Capture roundtrip path
above for arg-level queries.
ngfx-rpc custom transport client (RE-derived, partial)
ngfx-rpc.exe is the "Replayer UI Server" — a long-running process the
Nsight UI connects to over TCP / named-pipe / domain-socket. It speaks
a custom length-prefixed protobuf protocol (not standard gRPC, even
though its 30 .proto files contain ~50 Request/Reply message pairs
that look gRPC-shaped). The transport layer is fully decoded; the
per-message header encoding is decoded statically but not yet verified
over a live round-trip (see caveat below).
Wire format (verified):
byte 0 = 0x54 ('T') magic
byte 1 = 0x08 magic
byte 2 = channel_id u8
byte 3 = 0x00 flag/padding
byte 4-7 = body_size u32 BIG-ENDIAN
byte 8+ = body (length = body_size)
Dispatch model: (category u32, method u32) keyed 2-D handler table.
Method enums (already in the proto pool) include BinaryReplayMethod
with 110 entries — MethodApiInspectorStateRequest=33,
MethodRootParametersRequest=67, etc. System category ids are pinned from
ngfx-rpc.exe::SystemCategories.proto; Pylon replay uses its own category
namespace where CategoryBinaryReplay=1. The remaining live blocker is the
private namespace/session/slot binding the UI performs before BinaryReplay
requests are accepted.
Caveat (live-round-trip work in progress). ngfx-rpc's TCP server is
one-shot: it exits the moment the first client session ends. That makes
iterative "guess header → observe reply" probing impractical (the first
attempt at the most-likely MessageHeader layout crashes the server,
and relaunching takes ~30s). The structural header layout was recovered
statically from IDA (is_valid u8@+2, category u32@+32, method u32@+36, ticket_id u64@+48, sertype u32@+56, 60 bytes total) but isn't yet
confirmed on-wire. The two remaining angles are:
pktmoncapture of a real ngfx-ui ↔ ngfx-rpc exchange — the schema pool decodes every observed message; recovers handshake + real method calls by observation.- IDA on
NV::TPS::ProtoBufMessage::Serialize— read the exact serialiser bytes the C++ side emits.
Both are documented in docs/RPC_PROTOCOL.md.
RPC probing, transcripts, and live-event mapping
Helpers that sit one layer above the raw wire protocol — for resolving
endpoints, recording real ngfx-ui ↔ ngfx-rpc exchanges, replaying
those transcripts offline, and mapping a hook-side ordinal back to a
saved-capture event_index.
ETW kernel-file capture of ngfx-ui ↔ ngfx-rpc
A short-lived ETW session that watches kernel file / pipe I/O so the MCP
can observe the real bytes exchanged between the Nsight UI and
ngfx-rpc.exe for offline decoding. Wraps logman + tracerpt.
PE-patch planner for ngfx-rpc.exe
One of the three documented workarounds for the private-bridge wall: a
non-destructive patch plan that adds logger trampolines into
ngfx-rpc.exe so its private serializers emit byte-level evidence at
runtime. Plans are emitted, not applied — apply with an external patcher
or via the IDA script tool below.
Pylon private-bridge RE — saved-capture → C++ export
PylonPlugin.dll runs the UI activity bridge that maps activity id 3 to
Generate C++ Capture. The full headless replacement still depends on
either re-entering Pylon's private activity manager or wiring the direct
FrameDebugger Core RPC. These tools preserve the current RE evidence and
let an LLM iterate on each path safely.
Saved-capture → C++ Capture autonomy + route picker
Pickers and one-shot orchestrators that turn the saved-capture export
into a chain you can drive end-to-end without the UI. Use
ngfx_deep_capture_capability_report (above) first to decide whether
this route is worth attempting on the current install.
Fine-grained event queries (built on a SQLite index of the function stream)
Replay (ngfx-replay.exe)
GPU Trace report inspection
Binary WRPV .ngfx-gputrace inspection (RE-derived)
Some Nsight builds emit GPU Trace as a binary WRPV container rather than the documented zip. These tools probe that format directly without needing to extract it first.
Generate C++ Capture → build → run
Nsight 2026's durable replacement path for D3D12/Vulkan persistence is
Graphics Capture (ngfx-capture / ngfx-replay) plus Graphics Debugger live
replay. C++ Capture is still useful when it emits a project because the MCP
can index generated source for per-call arguments, but the saved-capture
exporter is private UI/plugin code and some Nsight builds can refuse D3D11/D3D12
C++ serialization with guidance to migrate to Graphics Capture. Use
ngfx_deep_capture_capability_report first when deciding whether C++ export,
live replay RPC, GPU Trace-on-replay, or raw .ngfx-capture decoding is the
right next step.
The CLI activity (ngfx --activity 'Generate C++ Capture') requires the
original application to launch — it can't run against a saved capture.
The MCP also exposes the UI-driven path for that case (see next section).
The saved-capture → C++ path is still private NVIDIA plugin code. The RE
tools above preserve the current evidence: BattlePlugin sends
PbSerializeRequestMessage through the FrameDebugger service and handles file
transfer notifications, while PylonPlugin exposes the UI activity bridge
that maps activity id 3 to Generate C++ Capture. The Pylon argv/config
handoff is pinned now: the bridge uses ngfx-replay.exe, passes the saved
capture as the first quoted argument, appends flattened replay-option args,
passes a semicolon-joined environment string, and persists the platform map
under JsonProject['launcher']. The remaining fully-headless gap is invoking
Pylon's private activity manager outside the UI process, or completing the
direct FrameDebugger Core RPC namespace/session binding.
Per-call argument extraction (C++ Capture → SQLite index)
Nsight's CLI (ngfx-replay --metadata-functions) returns function NAMES
per event but no argument values — it's a deliberate design choice.
To answer "what's bound at root parameter N of event G?" or "which CBV
did this draw use?" you need argument values.
The workflow these tools enable:
- Open a saved capture in the Nsight UI (which CAN run Generate C++ Capture on saved captures, unlike the CLI activity).
- Click File → Activity → Generate C++ Capture, pick an output dir.
- The MCP parses the emitted
.cppfiles and indexes every command-list / command-buffer call into SQLite, keyed by a syntheticevent_indexthat matches--metadata-functionsorder. - Per-event queries — full structured args for ~25 common D3D12/Vulkan/OpenGL descriptor / draw / dispatch calls.
ngfx_cpp_capture_descriptor_bindingswalks backwards from any draw/dispatch to reconstruct the full root-param + descriptor heap + CBV/SRV/UAV + VBV/IBV + RT state in effect at that event — the missing-piece answer for "what's bound here?"
The same parser is used by ngfx_find_calls_by_arg and by
ngfx_resolve_handle when a sibling C++-Capture index is present.
Capture-stream diff (event-level)
PSO → DXBC / SPIR-V hash mapping
Nsight's CLI does not expose the link between a PSO (D3D12 pipeline /
Vulkan VkPipeline) and the shader bytecode hashes it uses. The protobuf
schema does have it (NV.Pylon.Replay.PbPipelineShaderStageInfo —
fields pipeline, driverAppHash, stage) but extracting it from a
saved .ngfx-gfxcap is part of the in-progress capture decoder.
The path that works today: parse the Generate C++ Capture emitted
source. Shader bytecode is emitted as flat static const unsigned char
arrays — DXBC blobs have the Microsoft compiler's 128-bit MD5 hash baked
in at bytes 4..20 of the container (the exact bytes Nsight / PIX /
RenderDoc display as the shader identity). For SPIR-V we compute SHA-1
of the blob so Vulkan shaders still get a stable identity. We also compute
ShaderToggler's hash for every blob: CRC32 over the full raw shader
bytecode, reported as both 8 hex digits and unsigned decimal.
PSO creation calls (CreateGraphicsPipelineState /
CreateComputePipelineState / vkCreateGraphicsPipelines /
vkCreateComputePipelines / vkCreateRayTracingPipelinesKHR) reference
those byte-array symbols (D3D12) or vkCreateShaderModule handles
(Vulkan). The indexer matches them up.
Shader visual-bug triage
These tools compose C++-Capture event args, PSO identity, descriptor state, and IDA-derived Nsight RE facts into reports an LLM can use to localise a visual bug before patching shaders.
Autonomous shader-fix loop helpers
Resource write history & producer lineage
Static, event-order analyses built on the C++-Capture index, useful for "who wrote to this render target before the bad draw?" and for diffing left/right eye resource histories.
Subnautica 2 fog & CopyRectPS automation (worked-example shader-fix harness)
A concrete, end-to-end shader-fix harness for the SN2 right-eye fog and CopyRectPS bugs. These tools double as a reference template for wiring a fix loop against any specific game.
SN2 fog (VoxelizePS / VoxelizeGS)
SN2 CopyRectPS (right-eye texture copy)
Object handle / UID resolver
"What wrote to this buffer?" without the GUI. Given a uid or canonical
name (e.g. Buffer_91), cross-references the objects index, the events
index, and (when present) the C++-Capture index.
Frame cost analysis (top-N expensive actions)
Aftermath / Remote / RPC
Layer (un)install for Vulkan / VulkanSC / OpenXR
NGFX in-app SDK (header-only C/C++ runtime)
IDA Pro headless RE bridge
The shipped headers cover in-app capture/trace control, but saved-capture frame-debugger state, pixel history, resource history, and several replay/RPC paths live behind Nsight's internal binaries. The MCP can drive IDA Pro headless to cache compact JSON facts for those gaps.
Project files + UI hand-off
Shader compilation + reflection + disassembly
Discovery + escape hatch
How big is the surface?
252 MCP tools (+ 4 prompts) as of this writing, grouped by the sections below.
Run nsight-graphics-mcp --list-tools (or import the package and inspect
server) for an up-to-date enumeration.
Install
git clone https://github.com/elliotttate/nsight-graphics-mcp
cd nsight-graphics-mcp
python -m venv .venv
.venv\Scripts\activate
pip install -e ".[dev]"
Runtime dependencies (auto-installed):
mcp>=1.2— MCP server SDKpydantic>=2.0— schema validation for MCP tool paramspsutil>=5.9— process / handle introspection for launch sessionsprotobuf>=4.21— decoding the embeddedFileDescriptorProtoblobs used byproto_descriptors/ngfx_proto_describe
Requires Windows and NVIDIA Nsight Graphics installed (default
location C:\Program Files\NVIDIA Corporation\Nsight Graphics <version>).
The MCP auto-discovers the newest installed version; override with
NSIGHT_GRAPHICS_MCP_INSTALL_ROOT=<path> or per-tool overrides
(NSIGHT_GRAPHICS_MCP_NGFX, NSIGHT_GRAPHICS_MCP_NGFX_CAPTURE,
NSIGHT_GRAPHICS_MCP_NGFX_REPLAY, …).
Quick smoke test:
nsight-graphics-mcp --help
.venv\Scripts\python.exe -c "from nsight_graphics_mcp.config import get_settings; import json; print(json.dumps(get_settings().installation_info(), indent=2, default=str))"
Wiring it into Claude Code / Claude Desktop
Add to your MCP config (claude_desktop_config.json or the CLI equivalent):
{
"mcpServers": {
"nsight-graphics": {
"command": "E:/github/nsight-graphics-mcp/.venv/Scripts/nsight-graphics-mcp.exe",
"args": [],
"env": {
"NSIGHT_GRAPHICS_MCP_INSTALL_ROOT": "C:/Program Files/NVIDIA Corporation/Nsight Graphics 2026.1.0"
}
}
}
}
(Set NSIGHT_GRAPHICS_MCP_INSTALL_ROOT only if auto-discovery isn't
finding the right install — pass the directory that contains
host/windows-desktop-nomad-x64/.)
Typical workflows
1. Capture, then analyze
ngfx_capture_launched(
exe="C:/games/MyGame.exe",
args=["-windowed"],
output_file="mygame.ngfx-gfxcap",
output_dir="C:/captures",
capture_frame=120,
bundle_replayer=True,
)
ngfx_open_capture("C:/captures/mygame.ngfx-gfxcap")
ngfx_capture_summary(capture="<handle>")
ngfx_index_events(capture="<handle>")
ngfx_event_histogram(capture="<handle>", by="kind")
2. Interactive: launch, press F11 in-game, find the capture
ngfx_capture_launched(
exe="C:/games/MyGame.exe",
output_dir="C:/captures",
capture_hotkey=True,
background=True,
)
# ...play, hit F11...
ngfx_find_recent_captures(limit=5)
ngfx_open_capture("<newest path>")
3. "What draw inside marker X is most expensive?" (no UI)
ngfx_gputrace_launched(
exe="C:/games/MyGame.exe",
architecture="Blackwell GB20x",
metric_set_name="Top-Level Triage",
multi_pass_metrics=True,
real_time_shader_profiler=True,
limit_to_frames=1,
auto_export=True,
)
# Find newest .nsight-gputrace
ngfx_find_recent_captures(kinds=["gpu_trace"], limit=1)
ngfx_open_gputrace("<path>")
ngfx_gputrace_archive(gputrace="<handle>")
ngfx_gputrace_read_member(gputrace="<handle>", member="metrics.json")
4. In-app SDK integration
ngfx_sdk_reference() # discover all entry points
ngfx_sdk_snippet(activity="GraphicsCapture", api="D3D12")
ngfx_sdk_grep(pattern="NGFX_GPUTrace_StartEvent_") # find struct fields / enums
ngfx_sdk_header_text(header="NGFX_GraphicsCapture_D3D12_Types.h")
5. Find every call that touches a specific resource
ngfx_index_events(capture="<h>")
ngfx_find_calls_by_arg(capture="<h>", substring="0x000001E1ABCD0000", limit=200)
ngfx_find_events(capture="<h>", kind="barrier", start=2000, end=3000)
6. Generate a C++ repro and verify it builds
ngfx_cpp_capture_launched(
exe="C:/games/MyGame.exe",
wait_frames=120,
output_dir="C:/repros/mygame_frame120",
)
ngfx_cpp_capture_find_solution(dir_or_sln="C:/repros/mygame_frame120")
ngfx_cpp_capture_build(dir_or_sln="C:/repros/mygame_frame120")
ngfx_cpp_capture_run(exe="<produced .exe>")
7. Enable Vulkan capture layer for the current user
ngfx_layer_list()
ngfx_layer_install(layer="vk_ngfx_capture")
# ... run your Vulkan app, capture via F11, then:
ngfx_layer_install(layer="vk_ngfx_capture", uninstall=True)
8. Hand off to the UI when needed
ngfx_open_in_ui(path="C:/captures/mygame.ngfx-gfxcap")
9. Escape hatch — anything not exposed by a typed tool
ngfx_raw(tool="ngfx_replay", argv=[
"--metadata-objects", "--quiet", "C:/captures/mygame.ngfx-gfxcap",
])
10. Per-call argument extraction (UI roundtrip → SQLite index)
When --metadata-functions only gives you function names but you need
"what's bound at root parameter 3 of event 18742?":
ngfx_cpp_capture_open_in_ui(capture="C:/captures/mygame.ngfx-gfxcap")
# (human clicks File → Activity → Generate C++ Capture, picks output dir)
ngfx_cpp_capture_wait_for_project(
watch_dir="C:/captures/mygame.ngfx-gfxcap.ngfxmcp/cpp_capture")
# → returns {project_dir: "...", solution: "...sln"}
ngfx_cpp_capture_index_calls(project_dir="<project_dir>")
# → builds <project_dir>/.ngfxmcp_cpp_calls.db
ngfx_cpp_capture_descriptor_bindings(
db_path="<project_dir>/.ngfxmcp_cpp_calls.db",
event_index=18742,
)
# → {d3d12: {root_signature, descriptor_heaps, pipeline_state,
# root_params: {0: {call, ...}, 1: {...}}, vertex_buffers,
# index_buffer, render_targets}, ...}
11. "What wrote to this buffer?"
ngfx_index_objects(capture="C:/captures/mygame.ngfx-gfxcap")
ngfx_index_events(capture="C:/captures/mygame.ngfx-gfxcap")
# (optional but recommended: run the C++ Capture flow first)
ngfx_resolve_handle(
capture="C:/captures/mygame.ngfx-gfxcap",
object_name="Buffer_91",
)
# → {uid, type_name, category, create_call: {event_index, function_name},
# mention_count, mentions_by_role: {bind: 14, write: 2, draw: 0, ...},
# mentions: [...]}
12. Frame perf triage — top-N expensive draws
ngfx_gputrace_launched(
exe="C:/games/MyGame.exe", architecture="Blackwell GB20x",
limit_to_frames=1, auto_export=True,
)
# ngfx writes a .nsight-gputrace; or use --perf-report-dir to get CSVs:
ngfx_replay_run_advanced(
capture="C:/captures/mygame.ngfx-gfxcap",
extra_args=["--perf-report-dir", "C:/perf/mygame"],
)
ngfx_top_n_costs(report_or_trace="C:/perf/mygame", n=20, kind_filter="draw")
13. Capture diff — what changed between good and bad?
ngfx_index_events(capture="C:/captures/good.ngfx-gfxcap")
ngfx_index_events(capture="C:/captures/bad.ngfx-gfxcap")
ngfx_event_stream_diff(
capture_a="C:/captures/good.ngfx-gfxcap",
capture_b="C:/captures/bad.ngfx-gfxcap",
cluster_min_size=2,
)
# → function/kind histogram deltas + LCS-aligned insert/delete clusters,
# + arg-level diff if both have a C++-Capture index.
14. PSO → DXBC hash lookup
Nsight's CLI hides the link between a PSO and the shader bytecode hashes it uses; this recovers it from the C++-Capture emitted source:
# After ngfx_cpp_capture_index_calls has written the .db,
ngfx_pso_index(project_dir="C:/.../GeneratedCpp")
# → {shader_blob_count, pso_count, shader_format_histogram: {dxbc: N, spirv: M}, ...}
ngfx_pso_get(
db_path="C:/.../GeneratedCpp/.ngfxmcp_cpp_calls.db",
pso_symbol="g_PSO_42",
)
# → {pso_symbol, api: 'd3d12', creator: 'CreateGraphicsPipelineState',
# stages: {VS: {shader_symbol, hash_hex (DXBC MD5), format: 'dxbc', ...},
# PS: {...}}}
# Reverse: given a hash from a perf tool / shader debugger,
ngfx_pso_find_by_shader(db_path="...", hash_hex="aabbccdd...")
# → [{pso_symbol, stage, shader_symbol, api}, ...]
# ShaderToggler hash path: hex notes and decimal ShaderToggler.ini values both work.
ngfx_shader_blobs_find_crc32(db_path="...", crc32_hex="1cf439e7")
ngfx_shader_blob_dump(db_path="...", crc32_hex="1cf439e7", output_path="C:/tmp/1cf439e7.dxil")
15. Browse the protobuf schema (RE-derived)
ngfx_proto_search(pattern="RootParam")
# → ["PbRootParameter", "PbRootDescriptor", ...]
ngfx_proto_describe(message_fqn="NV.EventParameters.Messages.PbFunctionCallDesc")
# → {full_name, fields: [{name: 'functionName', ...},
# {name: 'arguments', is_repeated: True,
# type_name: 'NV.EventParameters.Messages.PbArgument'},
# ...]}
How the function index works
The first time you call ngfx_index_events, the MCP runs
ngfx-replay --metadata-functions --quiet <capture> > <cache>/functions.txt
and writes both the dump and a SQLite DB (<capture>.ngfxmcp/functions.db)
next to the capture. Schema:
calls(
idx INTEGER PRIMARY KEY,
name TEXT,
args TEXT,
ret TEXT,
kind TEXT, -- draw|dispatch|copy|barrier|present|ray_tracing|sync|set_state|other
line INTEGER,
raw TEXT
);
The index is keyed by the capture's mtime, so subsequent re-captures auto-invalidate it.
Caveats
- Windows only. The Nsight Graphics CLIs are Win32-native (Windows 10 / 11 x64).
- Nsight Graphics must be installed. Set
NSIGHT_GRAPHICS_MCP_INSTALL_ROOTif auto-discovery doesn't pick the right version. - The function-stream parser is regex-based against
ngfx-replay's human-readable output. Lines that don't match theName(args)shape are bucketed underunrecognised_linesand remain accessible viangfx_capture_functions(raw passthrough). - Some interactive UI features — the per-shader source profiler scroll,
PSO browser, screenshot scrubber, frame-debugger pixel history — are
not fully replicable headless. Use
ngfx_open_in_uifor those. - System-wide layer install (
global_install=True) requires running the MCP host elevated. - The DirectX Shader Compiler (
dxc.exe) is not always shipped with Nsight Graphics; install it separately ifngfx_dxc_compilereports it missing.
Layout
src/nsight_graphics_mcp/
config.py # install / SDK / per-tool discovery + cache paths
cli.py # generic subprocess wrappers (sync + async + background)
session.py # capture / gputrace / launch session registries
capture_info.py # ngfx-replay --metadata* parsers
captures.py # capture-dir discovery + diff (Recent Captures parity)
capture_diff.py # event-stream LCS diff between two captures
capture_format.py # low-level .ngfx-gfxcap inspection (RE-derived)
capture_decoder.py # direct .ngfx-gfxcap header/chunk/TOC decoder
deep_capture.py # capability report for deep Nsight-only capture analysis
events.py # function-stream indexer (Event List parity)
gputrace.py # .nsight-gputrace zip + WRPV binary inspection
cpp_capture.py # MSBuild + run for Generate-C++-Capture output
cpp_capture_parser.py # walk emitted .cpp, index per-call args into SQLite
cpp_bridge_re.py # saved-capture → C++ export private-bridge RE helpers
proto_schemas.py # name-only protobuf schema inventory
proto_descriptors.py # full FileDescriptorProto extraction → DescriptorPool
rpc_client.py # ngfx-rpc.exe custom transport client (RE-derived)
rpc_trace.py # offline ngfx-rpc frame transcript decoder
frame_debugger_rpc.py # persistent private frame-debugger RPC sessions
etw_capture.py # logman/tracerpt ETW kernel-file capture wrappers
pe_patch_planner.py # PE-patch planner for ngfx-rpc.exe logger trampolines
ida_re.py # IDA Pro headless RE helpers
handle_resolver.py # object handle → create call + role-bucketed mentions
pso_resolver.py # PSO → DXBC/SPIR-V hash mapping (Nsight CLI gap)
frame_costs.py # Top-N by GPU time from perf-report dirs / gputrace zips
objects.py # object index (Resources / Pipelines pane parity)
project.py # .nsight-gfxproj XML authoring
shaders.py # glslang + DXC + shaderdebugger configurator wrappers
shader_debug.py # shader-debug orchestration (RE-cache gating + plans)
shader_triage.py # shader visual-bug triage composition layer
eye_issue.py # saved-capture stereo eye-issue triage
autonomous_shader_fix.py # deterministic helpers for an LLM-driven fix loop
layers.py # Vulkan/VKSC/XR layer (un)install scripts
sdk.py # NGFX in-app SDK header reference + codegen
ui.py # ngfx-ui.exe hand-off
watch.py # capture-dir watcher (for hotkey-driven flows)
redist.py # bundled D3D12 Agility SDK / DXC / DLSS / etc. inventory
doctor.py # one-shot health check
server.py # FastMCP server registering every tool
__main__.py # console entry point
tests/ # pytest suite — synthetic data for the parsers,
# real-binary tests for proto_descriptors when
# Nsight Graphics is installed locally.
docs/
CAPTURE_FORMAT.md # RE notes on the .ngfx-gfxcap wrapper
RPC_PROTOCOL.md # RE notes on ngfx-rpc.exe transport
NSIGHT_SHADER_DEBUG_AUTONOMY.md # current shader-debugging status/plan
License
MIT.
Full tool reference
Auto-generated from server.py docstrings. 252 tools organised by
the section comments in server.py — the order matches what you'd
discover scrolling the file.
environment + discovery
ngfx_environment— Report the resolved Nsight Graphics install + per-tool paths + cache dirs.ngfx_list_installs— List every Nsight Graphics install detected on this machine.ngfx_deep_capture_capability_report— Rank Graphics Capture, live replay RPC, GPU Trace-on-replay, C++ Capture, and raw capture decoding for deep shader/render debugging from a saved dump.ngfx_version— Return the version reported byngfx.exe --version.ngfx_list_activities— List the activity names thatngfx.exeaccepts (parsed from --help).
Graphics Capture activity (via ngfx.exe)
ngfx_graphics_capture_launched— Runngfx --activity 'Graphics Capture' --exe <exe> ....ngfx_graphics_capture_attached— Same asngfx_graphics_capture_launchedbut attaches to a running PID.
Headless Graphics Capture via ngfx-capture.exe
ngfx_capture_launched— Runngfx-capture.exedirectly (no Nsight UI required).ngfx_capture_recapture— Recapture / recompress an existing.ngfx-capture/.ngfx-gfxcapwith the current format.ngfx_capture_recompress— Recompress an existing capture without re-running the application.
Capture session management + metadata
ngfx_open_capture— Register a capture file path as a session handle.ngfx_list_captures— List all opened capture sessions.ngfx_close_capture— (no docstring)ngfx_capture_summary— High-level summary of a capture (runsngfx-replay --metadata).ngfx_capture_objects— Runngfx-replay --metadata-objects: full JSON list of every API object recorded in the capture (devices, queues, pipelines, resources...).ngfx_capture_functions— Dump the recorded function stream (ngfx-replay --metadata-functions).ngfx_capture_logs— Dump captured application/driver log messages embedded in the capture.ngfx_capture_screenshot— Write the embedded final-present screenshot to a file.
Replay (ngfx-replay.exe)
ngfx_replay_run— Replay a capture withngfx-replay.exeand return its output.ngfx_replay_bundle_extract— Extract a bundled-replayer capture's contents to a directory without running the replay.ngfx_replay_metadata— Direct passthrough tongfx-replay --metadata(parsed key/value).
GPU Trace Profiler
ngfx_gputrace_archs— Return the list of GPU architectures accepted by--architecture.ngfx_gputrace_launched— Runngfx --activity 'GPU Trace Profiler' --exe <exe> ....ngfx_gputrace_attached— Attach GPU Trace to a running process by PID. Defaults to hotkey-driven.ngfx_gputrace_capture_replay— Run GPU Trace Profiler againstngfx-replay.exefor a saved Graphics Capture, using replay-begin/replay-end triggers.
GPU Trace report session management
ngfx_open_gputrace— Register a .nsight-gputrace path as a session handle.ngfx_list_gputraces— (no docstring)ngfx_close_gputrace— (no docstring)ngfx_gputrace_inspect— Best-effort inspection of a.nsight-gputracefile.ngfx_gputrace_shader_pipeline_search— Search shader/pipeline GPU Trace data for a shader hash, name, or entry point.
Generate C++ Capture activity
ngfx_cpp_capture_launched— Runngfx --activity 'Generate C++ Capture' ....ngfx_cpp_capture_saved_bridge_re_analyze— Run the targeted IDA passes for the private saved-capture -> C++ bridge.ngfx_cpp_capture_saved_bridge_re_report— Summarize current RE evidence for fully headless saved C++ export.ngfx_cpp_capture_saved_pylon_handoff_preview— Preview the pinned Pylon launcher settings for saved-capture Generate C++ Capture.ngfx_cpp_capture_saved_direct_rpc_plan— Preview the direct FrameDebugger serialize-RPC request/callback plan.ngfx_cpp_capture_saved_file_transfer_apply— Apply one FrameDebugger serialize file-transfer notification to disk.ngfx_cpp_capture_saved_output_dir_setting— Preview or write the candidate QSettings output-dir value for C++ export.ngfx_cpp_capture_saved_export_validate— Validate and index a saved-capture Generate-C++-Capture export.ngfx_cpp_capture_saved_ui_automation_attempt— Best-effort pywinauto UI fallback for saved-capture C++ export.ngfx_cpp_capture_saved_headless_attempt— Try all known saved-capture -> C++ export routes, then validate output.ngfx_cpp_capture_saved_artifact_bundle— Bundle capture/export validation artifacts into one zip.
OpenGL Frame Debugger
ngfx_framedebugger_launched— Runngfx --activity 'OpenGL Frame Debugger' ....
Launch / background process management
ngfx_launch_status— Status + recent stdout/stderr of a background launch.ngfx_list_launches— (no docstring)ngfx_launch_stop— (no docstring)
Remote monitor / RPC
ngfx_remote_monitor_start— Startnv-nsight-remote-monitor.exeheadless on this machine so a remote Nsight UI can connect. Returns a launch handle — callngfx_launch_stopto terminate it.ngfx_rpc_start— Startngfx-rpc.exe(the replayer UI server) headless.ngfx_rpc_protocol_info— Return everything we know about thengfx-rpc.execustom wire protocol — handy as a self-describing reference for callers writing their own clients. The full derivation lives indocs/RPC_PROTOCOL.md(in this repo).ngfx_rpc_transport_connect— Open one TCP transport connection to a runningngfx-rpc.exeand immediately close it. Useful as a smoke test: it verifies the server is reachable and that the 8-byte frame magic checks out.ngfx_rpc_send_raw_frame— Low-level escape hatch: send one transport frame and (optionally) await one reply frame. Useful for protocol RE work.ngfx_frame_debugger_rpc_schema— Describe the private BinaryReplay RPC methods used for pixel/resource history.ngfx_pixel_history— Call Nsight's private BinaryReplay pixel-history method or preview the exact protobuf request.ngfx_resource_access_history— Call Nsight's private resource-access-history method for one API handle.ngfx_resource_revision_at_event— Derive a resource revision at an event from private resource history, with optional persistent-session reuse.ngfx_rpc_open_capture_session— Open a persistent frame-debugger RPC session and optionally launch a capture.ngfx_rpc_capture_session_status— List persistent frame-debugger RPC sessions, or summarize one handle.ngfx_rpc_close_capture_session— Close a persistent frame-debugger RPC session.ngfx_rpc_call_binary_replay— Call an arbitrary BinaryReplay method on an open frame-debugger RPC session.
Aftermath (crash-dump tools)
ngfx_aftermath_control— Runnv-aftermath-control.exewith the provided args.ngfx_aftermath_monitor_start— Startnv-aftermath-monitor.exein the background to watch for GPU crashes / hangs and write dump files.ngfx_aftermath_format— Runnv-aftermath-format.exeagainst an existing crash dump.
Layer install helpers
ngfx_layer_list— List the Vulkan / VulkanSC / OpenXR layer install scripts shipped with the Nsight Graphics install, and whether each one is present.ngfx_layer_install— Run a Nsight Graphics layer install script.
NGFX SDK helpers (in-app integration)
ngfx_sdk_reference— Enumerate every header in the NGFX in-app SDK, with parsed function declarations (name, params, brief) for each.ngfx_sdk_grep— Regex-search across the NGFX header tree (returns matched filename, line number, and matched line text).ngfx_sdk_snippet— Generate a C++ integration snippet for an (activity, API) pair.ngfx_sdk_header_text— Return the raw text of an NGFX SDK header.
Escape hatch
ngfx_raw— Escape hatch — invoke any supported Nsight tool with arbitrary argv.
Capture-directory discovery + diff (parity with GUI 'Recent Captures')
ngfx_find_recent_captures— Look in the standard Nsight output directories (and optionally extra dirs) for recent capture / GPU-trace files. Newest first.ngfx_list_captures_in_dir— Enumerate every capture / gputrace file under a directory.ngfx_capture_diff— Diff the parsed--metadatasummaries of two captures.
Function-stream indexer (Event List parity)
ngfx_index_events— Index a capture's function stream into a SQLite DB next to it.ngfx_find_events— Filtered search over the indexed function stream.ngfx_get_event— Look up a single call by index in the indexed function stream.ngfx_event_histogram— Histogram of recorded calls grouped bynameorkind.ngfx_find_calls_by_arg— Search recorded calls by argument substring.
Object index (PSO / shader / resource inventory — GUI 'Resources' parity)
ngfx_index_objects— Index every API object recorded in a capture into a SQLite DB.ngfx_query_objects— Filtered listing of recorded objects.ngfx_get_object— Look up a single recorded object by uid.ngfx_object_histogram— Histogram of recorded objects grouped bytype_name,category, orapi.ngfx_object_query— Read-only SQL (SELECT / WITH) against the object index.ngfx_list_pipelines— List every Pipeline / PipelineLayout / DescriptorSetLayout / PipelineCache / RootSignature / StateObject in a capture.ngfx_list_shaders— List every ShaderModule / ShaderProgram / Shader recorded in a capture.ngfx_list_resources— List every recorded resource (Buffer / Image / Sampler / DeviceMemory / Heap).ngfx_event_query— Read-only SQL query (SELECT / WITH) against the function index.
Deep GPU Trace inspection (Trace Analysis parity)
ngfx_gputrace_archive— Open a .nsight-gputrace as a zip archive and list its members + decode any small JSON manifests inline.ngfx_gputrace_read_member— Read a member of the .nsight-gputrace archive as UTF-8 text (no disk extraction). Auto-decodes JSON / CSV payloads.ngfx_gputrace_extract— Extract a specific member of the .nsight-gputrace archive toout_dir.ngfx_gputrace_shader_pipeline_search— Search shader/pipeline-looking archive members for CopyRectPS-style shader evidence.ngfx_list_perf_report— List the artifacts written byngfx-replay --perf-report-dir.ngfx_gputrace_export_summary— Summarize Nsight GPU Trace auto-export folders.ngfx_gputrace_export_search— Search exported GPU Trace text/XLS files for shader names, hashes, or event text.
Nsight project file authoring
ngfx_project_create— Write a minimal Nsight project XML atpath.ngfx_project_read— Read an existing Nsight project XML.ngfx_project_update— Mutate fields of an existing Nsight project file in-place.
C++ Capture build + run
ngfx_cpp_capture_find_solution— Locate the .sln produced by a Generate-C++-Capture run.ngfx_cpp_capture_build— Invoke MSBuild on a Generate-C++-Capture output directory or .sln.ngfx_cpp_capture_run— Run a Generate-C++-Capture exe to verify the repro still works.ngfx_cpp_capture_dump— One-stop helper for producing a C++ Capture dump and indexing it. Uses the headless CLI for live app launches and the UI-assisted path for saved captures.ngfx_cpp_capture_open_in_ui— Open a saved capture inngfx-ui.exeso the human can run the UI's Generate C++ Capture activity against it (the CLI activity can't, it requires the original application to re-launch).ngfx_cpp_capture_wait_for_project— Pollwatch_diruntil a Generate-C++-Capture project lands and its .sln stops growing. Returns the project root + the solution path.ngfx_cpp_capture_index_calls— Walk a Generate-C++-Capture project, parse every command-list / command-buffer call, and index them into SQLite for per-event queries.ngfx_cpp_capture_event_args— Look up one C++-capture event by its syntheticevent_index.ngfx_cpp_capture_query_calls— Filtered query against the indexed C++ call stream.ngfx_cpp_capture_descriptor_bindings— Reconstruct the descriptor / root-parameter / vertex+index buffer / render-target binding state in effect atevent_indexby scanning backwards through the indexed C++ call stream.ngfx_cpp_capture_sql— Read-only SELECT/WITH query against the C++ call index DB.
Shader compilation + Shader Debugger
ngfx_glslang_compile— Compile a GLSL / SPIR-V shader usingglslang.exe(bundled).ngfx_dxc_compile— Compile an HLSL shader via DXC.ngfx_shaderdebugger_configure— Runnv-shaderdebugger-configurator.exe(useextra_args=['--help']to discover flags).
UI hand-off
ngfx_open_in_ui— Spawnngfx-ui.exeto open a capture / gputrace / project file in the full Nsight Graphics UI.
Capture watcher / wait-for-new-capture
ngfx_wait_for_new_capture— Poll one or more directories until a new capture (or GPU trace) lands, its size stabilises, then return its path.
Doctor / health check + tool-help introspection
ngfx_doctor— One-shot health check: install discovery, every tool path, layer scripts, output-dir writability,nvidia-smidriver/GPU info, and the Vulkan implicit/explicit-layer registry. Reports a list ofissuesyou should fix before running captures.ngfx_tool_help— Run<tool> --help(or--help-allfor ngfx) to discover the exact flags supported by your installed version of any Nsight binary.
Function-stream raw sample + cross-capture diff
ngfx_function_stream_sample— Return the firsthead(and optionally lasttail) raw lines of the recorded function stream.ngfx_function_stream_diff— Diff the indexed function streams of two captures.
Triage macro
ngfx_capture_quick_triage— Run the full 'first look' pipeline on a capture in one call:
Redistributables + registry
ngfx_list_d3d12_redist— List the bundled D3D12 Agility SDK redistributable shipped with Nsight Graphics. Passpreview=Truefor the preview SDK.ngfx_list_runtime_dlls— List the runtime DLLs (DXC, DXIL, Aftermath, WinPixEventRuntime, DirectStorage, NGX/DLSS) bundled in the Nsight Graphics host bin dir.ngfx_registry_restore— Run the bundledRegistryRestore.ps1to restore Nsight Graphics' registry keys to defaults.
Proto schema reference (extracted from ngfx-replay binary)
ngfx_proto_schemas— Return the protobuf schema inventory extracted from the Nsight binaries.ngfx_proto_search— Regex-search the extracted protobuf schema for a name or FQN.ngfx_proto_describe— Return the full field-level schema for a protobuf message extracted from Nsight's binaries.ngfx_proto_list_messages— List every fully-qualified message name in the decoded schema pool.ngfx_proto_extract_descriptors— Re-extract FileDescriptorProto blobs from a Nsight binary and rebuild the in-process schema registry.
Capture diff — "git diff for captures"
ngfx_event_stream_diff— Diff the per-event function streams of two captures (deeper thanngfx_capture_diffwhich only diffs the metadata summaries).
Object handle / UID resolver
ngfx_resolve_handle— Look up an API object by uid or name, find its create call, and enumerate every C++-capture event that mentions it — bucketed by role (create / write / bind / draw / dispatch / barrier / destroy / other).
PSO → DXBC / SPIR-V hash mapping
ngfx_pso_index— Walk a Generate-C++-Capture project and index PSO → shader-hash mappings into SQLite.ngfx_pso_get— Look up one PSO's shader stages: each entry is{shader_symbol, format (dxbc/dxil/spirv), hash_hex, hash_source, shader_toggler_crc32, declared_byte_count, head_hex}.ngfx_pso_list— List every indexed PSO with a one-line stage summary (VS:g_VS_xxx, PS:g_PS_yyy). Filter byapi(d3d12/vulkan).ngfx_pso_find_by_shader— Reverse lookup: which PSOs use a given shader? Supply the C-level shader symbol (e.g.g_VS_0x1234), a DXBC/SPIR-V hash, or a ShaderToggler CRC32.ngfx_shader_blobs_list— List indexed shader bytecode blobs from a C++-Capture project. Filter byformat(dxbc/dxil/spirv/unknown),hash_hex(exact match), and/orshader_toggler_crc32.ngfx_shader_blobs_find_crc32— Find shader bytecode blobs by ShaderToggler CRC32, accepting either hex or decimal.ngfx_shader_blob_dump— Dump one indexed shader bytecode blob to disk by shader symbol or ShaderToggler CRC32.
Shader visual-bug triage orchestration
ngfx_shader_triage_plan— Return the concrete MCP workflow for localising and fixing a shader visual bug.ngfx_eye_issue_dump_report— Summarize saved-capture evidence, dump-only blockers, and the next Nsight-only actions for the right-eye issue.ngfx_eye_issue_event_signatures— Build candidate left/right event pairs from name-only saved function metadata.ngfx_eye_event_index— Classify C++-Capture events as left/right/both/unknown using stereo regexes, viewport/scissor half hints, and inherited state.ngfx_compare_eye_passes— Compare left/right draw/dispatch/copy counts from a C++-Capture index.ngfx_find_missing_eye_dispatches— Find dispatch/ray-tracing asymmetries between classified eyes.ngfx_event_state— Return a draw/dispatch event, nearby calls, bound descriptors, and PSO info.ngfx_trace_resource_lineage— Find C++-Capture calls that mention a resource/symbol and bucket by role.ngfx_pso_bind_trace— Trace SetPipelineState/vkCmdBindPipeline and following draw/dispatch work.ngfx_pso_swap_harness_plan— Generate a D3D12 draw-time PSO swap harness plan and optional C++ files.ngfx_shader_probe_plan— Generate a targeted shader-probe plan for suspect terms such as t5/t8/t9.ngfx_shader_bug_triage— Produce one LLM-ready shader-bug report from capture/index/handoff evidence.ngfx_sn2_repro_plan— Build the exact Subnautica 2 launch-script repro command and expected artifacts.ngfx_sn2_repro_run— Dry-run or execute the Subnautica 2 repro launch script with capture-friendly environment.ngfx_cpp_capture_from_saved_capture— Export Generate-C++-Capture output from a saved capture via the available Nsight path.ngfx_pair_eye_events— Pair left/right draw, dispatch, copy, and ray-tracing events and report missing counterparts.ngfx_resolve_shader_slots— Resolve shader resource slots such ast5,t8, andt9to root/descriptor evidence where available.ngfx_descriptor_resource_candidates— Score likely resource handles for shader slots from a private descriptor-state RPC reply.ngfx_trace_roi_history— Generate or execute private pixel-history requests for a grid over a suspect ROI.ngfx_resource_producer_graph— Build a best-effort graph of resource producers/readers from a C++-Capture index.ngfx_import_uevr_trace— Import UEVR hook traces from JSON, NDJSON, CSV, or key/value logs into summaries or SQLite.ngfx_pso_rehydration_plan— Generate a C++ clone/recreate plan for testing patched shader bytecode in a graphics PSO.ngfx_shader_probe_execution_plan— Emit the closed-loop steps for a concrete shader probe trial.ngfx_diff_hdr_roi— Compare raw/PFM float image ROI data without 8-bit clamping.ngfx_autofix_loop_plan— Return the autonomous patch/test/score loop used to drive repeated fix trials.ngfx_validate_fix_claim— Reject or accept fix claims using improvement, repeatability, left-eye drift, and causality gates.ngfx_shader_fix_regression_score— Score whether a shader-fix run is acceptable or regressed.
Frame cost analysis — top-N expensive draws/dispatches/regions
ngfx_top_n_costs— Return the top-N most expensive actions by GPU time across all CSVs in angfx-replay --perf-report-diroutput, or a.nsight-gputracearchive.
Low-level capture-file inspection (RE-derived)
ngfx_capture_format_info— Structural inspection of a .ngfx-gfxcap file.ngfx_capture_lz4_decompress— Experimental: attempt LZ4-block decompression of a byte range from a capture file. Useful for probing the chunk layout. Returns a hex preview of the decompressed bytes plus sizes; for unknown blocks, pass a generousuncompressed_size_hint(defaults tolen(data) * 8).ngfx_decode_protobuf_wire— Experimental: decode a byte range as generic protobuf wire format.
Direct capture-file decoder (header / chunks / TOC / events)
ngfx_capture_decode_header— Decode the wrapper header of a.ngfx-capture/.ngfx-gfxcap.ngfx_capture_decode_chunks— List the firstmax_chunkschunks of a capture file.ngfx_capture_decode_toc— Decode theNV.PbTableOfContentschunk of a capture file.ngfx_capture_decompress_chunk_by_id— Locate the chunk whosekind(chunk-id) equalschunk_idand decompress it.ngfx_capture_search_payloads— Search decompressed capture chunks for shader names, hashes, or raw hex bytes.ngfx_capture_shader_chunks— Find embedded DXBC/DXIL shader blobs in a saved capture and return chunk IDs, strings, and hash candidates.ngfx_capture_chunk_references— Search decompressed capture chunks for references to a chunk id or arbitrary byte/string needles.ngfx_capture_decode_events— Best-effort scan for serialisedPbFunctionCallDescrecords.ngfx_capture_event_args— Look up the per-event arguments atevent_indexvia direct capture decoding.