a representation using graph notation, of all paths that might be traversed through a program during its execution
The graph is not of a specific run, but rather a control-flow description of the static program.
The expectation is to generate a .dot file and the convert it to .png for visualisation.
What I tried so far
Using rustc unstable flags
The rustc debugging guide shows some interesting flags. I passed them to cargo with RUSTCFLAGS="-Zdump-mir=main -Zdump-mir-dataflow -Zdump-mir-graphviz"; cargo +nightly build.
No need for the mir-dataflow though, just the control-flow diagram. That command (or a very similar one) ran successfully once, producing the mir-dump/ but subsequent runs —even removing target/— did nothing. Same using cargo clean.
The expectation is that the MIR would be quite helpful, but HIR or just the source-code's CFG directly would be better.
Another try were cargo-callgraph and callgraph.rs cited in this reply to a post. But none of them succeeded installing with cargo install --git URL --locked. I think the docs are probably saying that one should clone the repo, and put the file to test under test/ to build the callgraph. I didn't try that yet.
So, can cargo +nightly currently do this without any package nor plugin ? Any maintained package that you recommend (or insist on the above)?
If you don't pass -Zdump-mir-dataflow it should dump the cfg without dataflow. And it should work more than once.
For HIR and AST building a CFG is non-trivial given that you can nest control flow within expressions. Borrowck used to run on the AST while attempting to produce a CFG. This was just too buggy as it turns out, hence why borrowck now runs on MIR.
cargo-callgraph produces a call graph, not a control-flow graph.
The first time, it added mir-dump/ which I originally deleted (to re-run a different variant of the command and not mix the results up). It did not generate it again (even after using clean or deleting target/)
For the rest, they were mostly alternatives that would at least give some visual information about the program, but indeed, not exactly what I try to get.
This does two things. First it sets the RUSTFLAGS shell variable (not env var!) and then it runs cargo. You need to either remove the ;\ and put both on the same line or use export before RUSTFLAGS to actually set the RUSTFLAGS env var for cargo.
echo $RUSTFLAGS
echo $RUSTFLAGS prints either a shell variable or env var. You can use env | grep RUSTFLAGS to see just the env var named RUSTFLAGS.
The .dot is printed to stdout using the command in the reply above, but it's still too large so I wonder whether it can be restricted to my local crate without dependencies (assume that's why it's so large).