How trace_path with data_flow Mode Follows Value Propagation Through Argument Expressions
In data_flow mode, the trace_path tool traverses DATA_FLOWS edges to track how values move from argument expressions through parameters and field-level sub-expressions, using a breadth-first search that begins at the target function and follows hybrid LSP-resolved symbols to their ultimate source.
The codebase-memory-mcp project provides a trace_path MCP tool that can operate in a specialized data_flow mode. This mode moves beyond simple call-graph traversal to answer where a specific argument's value originates, following the chain of data dependencies through the codebase.
The Anatomy of DATA_FLOWS Edges
Value propagation relies on explicit DATA_FLOWS edges stored in the code graph. These edges are generated during the indexing phase and encode how data moves between AST nodes.
Mapping Arguments to Parameters in semantic.c
During semantic analysis, the indexer inspects function calls to create direct mappings between argument expressions and their corresponding formal parameters. In src/semantic/semantic.c, the analysis uses the w_dataflow weight to emit DATA_FLOWS edges that link the argument's AST node to the parameter name.
- Each argument expression at a call site generates a
DATA_FLOWSedge pointing to the callee's parameter. - The edge captures the exact source range of the argument expression for precise traceability.
Chaining Sub-Expressions in dataflow.c
Argument expressions often contain nested structures such as field accesses (obj.field), array indexing, or dereferences. The pipeline in src/pipeline/dataflow.c decomposes these expressions into leaf identifiers. For every sub-expression that contributes to the final value, an additional DATA_FLOWS edge is created, chaining the argument node to the underlying symbols that actually hold the data.
Hybrid LSP Resolution for Accurate Propagation
Before DATA_FLOWS edges are finalized, the system must resolve symbols across file boundaries, imports, generics, and inheritance hierarchies. The Hybrid LSP layer, implemented in src/hybrid_lsp/resolution.c, performs this resolution. It ensures that an argument expression is linked to the exact declaration the runtime would use, preventing false positives from name collisions or incomplete type information.
The trace_path Traversal Algorithm
The implementation in src/mcp/tools/trace_path.c handles the mode parameter and executes the appropriate traversal strategy.
BFS with Edge Type Filtering
When invoked with mode: "dataflow", the tool performs a breadth-first search starting from the target function node:
- It first follows standard
CALLSedges to reach caller nodes. - At each caller, it queries the graph for
DATA_FLOWSedges associated with the specificarg_index. - It traverses these edges backward (or forward, depending on
direction) to the originating symbols. - The search recurses through additional
DATA_FLOWSedges until it reaches source leafs such as variables, constants, or static fields.
The traversal respects the max_depth parameter (defaulting to 5) to prevent combinatorial explosion in complex expression trees.
Handling Argument Expressions
The tool specifically tracks the argument expression node rather than just the call site. This allows it to distinguish between different arguments passed to the same parameter across multiple call sites. The graph walk aggregates all unique source symbols discovered along the propagation chain, de-duplicating paths to provide a concise provenance list.
Practical Usage and Code Examples
You can invoke trace_path in data_flow mode via the CLI or MCP client to analyze value provenance.
Basic call-graph trace (excludes data flow):
codebase-memory-mcp cli trace_path '{"project":"my-proj","function_name":"processOrder","direction":"inbound"}'
Data-flow mode targeting the first argument (index 0):
codebase-memory-mcp cli trace_path '{
"project": "my-proj",
"function_name": "processOrder",
"direction": "inbound",
"mode": "dataflow",
"arg_index": 0,
"max_depth": 5
}'
The response provides structured provenance paths showing which variables or fields ultimately supply the value:
{
"paths": [
{
"caller": "OrderService.validate",
"arg_expression": "checkout.cart",
"source": "checkout.cart.items"
},
{
"caller": "ApiController.postCheckout",
"arg_expression": "body.cart",
"source": "request.body.cart"
}
]
}
Summary
DATA_FLOWSedges are created insrc/semantic/semantic.cusing thew_dataflowweight to link arguments to parameters.src/pipeline/dataflow.cextends these edges to cover nested sub-expressions like field accesses and array indices.src/hybrid_lsp/resolution.cresolves symbols across files before edge creation, ensuring accurate type information.src/mcp/tools/trace_path.cimplements BFS traversal that filters forDATA_FLOWSedges whenmodeis set to"dataflow".- The tool tracks specific argument expressions by index, following chains of value propagation to their source leafs while respecting depth limits.
Frequently Asked Questions
How does trace_path identify which argument to track in data_flow mode?
The tool uses the arg_index parameter (0-based) provided in the request to filter DATA_FLOWS edges, examining only the edges that correspond to the specified argument position at each call site.
What happens if the argument contains multiple nested field accesses?
The traversal follows the chain of DATA_FLOWS edges created by src/pipeline/dataflow.c for each sub-expression, recursively walking from the root argument node down through field accessors, array indices, or pointer dereferences until it reaches terminal identifier nodes.
Does data_flow mode work across language boundaries?
Yes, provided the Hybrid LSP layer in src/hybrid_lsp/resolution.c can resolve the symbols. The system uses cross-file type resolution to link arguments in one language to parameters in another (e.g., TypeScript to C++ bindings) before creating the DATA_FLOWS edges that trace_path traverses.
Is there a limit to how deep the propagation analysis goes?
By default, trace_path limits traversal to a depth of 5 edges, configurable via the max_depth parameter. This prevents excessive computation when analyzing highly interconnected data flow graphs.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →