-
Notifications
You must be signed in to change notification settings - Fork 13.3k
MIR graphviz prettification #30602
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
MIR graphviz prettification #30602
Conversation
@tsion Very nice! I'd have to take a closer look if any vital information is missing now that was shown before, but from a first glance I like the new output a lot better. Much more readable |
Looks pretty good to me (both code and output). I have a minor concern that spelling out every branch (true/false/return/unwind) might introduce too much visual clutter, but I think it is fine to leave it as is for now and wait to see if it ends up being an issue. I’d argue it still would be better to name Lvalues |
Ah, also, I believe
and so on. EDIT: note that it doesn’t really matter whether it is a struct or enum variant, what matters is the kind of Adt, i.e. is it struct-like ( |
The |
👍 Nice! Looks great. |
@nagisa I think I agree about For aggregates, I was planning to drop the whole |
Sure, SGTM. |
Maybe there should be (choosable) levels of verbosity in the output, e.g. I imagine the spans are usually not needed at all (except for closures, maybe). |
Ah, @huonw, that's a great idea - would be useful for types, i.e. being able to see them everywhere, like in LLVM IR, when you need that. |
@huonw Yeah, that's a good idea. I was mainly aiming to remove irrelevant details, e.g. between constant-old and constant-new, but we could have flags for adding spans and/or types back in. |
Another thought: we could show all integer constants with their type suffixes (e.g. |
I made the change from |
Previously, all references to closure arguments went to the argument before the one they should (e.g. to `arg1` when it was supposed to go to `arg2`). This was because the MIR builder did not account for the implicit arguments that come before the explicit arguments, and closures have one implicit argument - the struct containing the captures. This is my test code and a diff of the MIR generated for the closure: ```rust let a = 2i32; let _f = |b: i32| -> i32 { a + b }: ``` ```diff --- old 2015-12-29 23:16:32.027926372 -0600 +++ new 2015-12-29 23:16:42.975400757 -0600 @@ -1,22 +1,22 @@ fn(arg0: &[[email protected]:8:14: 8:39 a:&i32], arg1: i32) -> i32 { let var0: i32; // b let tmp0: (); let tmp1: i32; let tmp2: i32; bb0: { - var0 = arg0; + var0 = arg1; tmp1 = (*(*arg0).0); tmp2 = var0; ReturnPointer = Add(tmp1, tmp2); goto -> bb1; } bb1: { return; } bb2: { diverge; } } ``` (If you're wondering where this text MIR output comes from, it's from another branch of mine waiting on rust-lang#30602 to get merged.)
@bors r+ |
📌 Commit 56343cd has been approved by |
pretty. :) |
r? @nikomatsakis cc @eddyb @nagisa This PR changes most of the MIR graphviz debug output, making it smaller and more consistent. Also, it changes all fonts to monospace and adds a graph label containing the type of the `fn` the MIR is for and all the values (arguments, named bindings, and compiler temporaries). I chose to re-write the graphviz output code instead of using the existing libgraphviz API because I found it much easier to prototype usage of various graphviz features when I had full control of the text output. It also makes the code simpler, I think. Below are a bunch of example functions and links to their output images on the current nightly vs. this PR. File names starting with numbers (e.g. `80-factorial_fold-new.png`) are for closures. There's still a bunch of low hanging fruit to make it even better, particularly around aggregates and references. I also imagine the textual output for MIR will be able to closely match the graphviz output. The list of statements should look identical and the terminators will be the same except that the text form will have a list of target blocks (potentially using the same edge labels as the graphviz does). I can PR a simple text output right after this PR. This is my first large change to the compiler, so if anything should be reorganized/renamed/etc, let me know! Also, feel free to bikeshed the details of the output, though any minor changes can come in future PRs. ```rust fn empty() {} ``` http://vps.solson.me/mir-graphviz/empty-new.png http://vps.solson.me/mir-graphviz/empty-old.png ```rust fn constant() -> i32 { 42 } ``` http://vps.solson.me/mir-graphviz/constant-new.png http://vps.solson.me/mir-graphviz/constant-old.png ```rust fn increment(x: i32) -> i32 { x + 1 } ``` http://vps.solson.me/mir-graphviz/increment-new.png http://vps.solson.me/mir-graphviz/increment-old.png ```rust fn factorial_recursive(n: usize) -> usize { if n == 0 { 1 } else { n * factorial_recursive(n - 1) } } ``` http://vps.solson.me/mir-graphviz/factorial_recursive-new.png http://vps.solson.me/mir-graphviz/factorial_recursive-old.png ```rust fn factorial_iterative(n: usize) -> usize { let mut prod = 1; for x in 1..n { prod *= x; } prod } ``` http://vps.solson.me/mir-graphviz/factorial_iterative-new.png http://vps.solson.me/mir-graphviz/factorial_iterative-old.png ```rust fn factorial_fold(n: usize) -> usize { (1..n).fold(1, |prod, x| prod * x) } ``` http://vps.solson.me/mir-graphviz/factorial_fold-new.png http://vps.solson.me/mir-graphviz/factorial_fold-old.png http://vps.solson.me/mir-graphviz/80-factorial_fold-new.png http://vps.solson.me/mir-graphviz/80-factorial_fold-old.png ```rust fn collatz(mut n: usize) { while n != 1 { if n % 2 == 0 { n /= 2; } else { n = 3 * n + 1; } } } ``` http://vps.solson.me/mir-graphviz/collatz-new.png http://vps.solson.me/mir-graphviz/collatz-old.png ```rust fn multi_switch(n: usize) -> usize { match n { 5 | 10 | 15 => 3, 20 | 30 => 2, _ => 1, } } ``` http://vps.solson.me/mir-graphviz/multi_switch-new.png http://vps.solson.me/mir-graphviz/multi_switch-old.png
r? @nikomatsakis
cc @eddyb @nagisa
This PR changes most of the MIR graphviz debug output, making it smaller and more consistent. Also, it changes all fonts to monospace and adds a graph label containing the type of the
fn
the MIR is for and all the values (arguments, named bindings, and compiler temporaries).I chose to re-write the graphviz output code instead of using the existing libgraphviz API because I found it much easier to prototype usage of various graphviz features when I had full control of the text output. It also makes the code simpler, I think.
Below are a bunch of example functions and links to their output images on the current nightly vs. this PR. File names starting with numbers (e.g.
80-factorial_fold-new.png
) are for closures. There's still a bunch of low hanging fruit to make it even better, particularly around aggregates and references.I also imagine the textual output for MIR will be able to closely match the graphviz output. The list of statements should look identical and the terminators will be the same except that the text form will have a list of target blocks (potentially using the same edge labels as the graphviz does). I can PR a simple text output right after this PR.
This is my first large change to the compiler, so if anything should be reorganized/renamed/etc, let me know! Also, feel free to bikeshed the details of the output, though any minor changes can come in future PRs.
http://vps.solson.me/mir-graphviz/empty-new.png
http://vps.solson.me/mir-graphviz/empty-old.png
http://vps.solson.me/mir-graphviz/constant-new.png
http://vps.solson.me/mir-graphviz/constant-old.png
http://vps.solson.me/mir-graphviz/increment-new.png
http://vps.solson.me/mir-graphviz/increment-old.png
http://vps.solson.me/mir-graphviz/factorial_recursive-new.png
http://vps.solson.me/mir-graphviz/factorial_recursive-old.png
http://vps.solson.me/mir-graphviz/factorial_iterative-new.png
http://vps.solson.me/mir-graphviz/factorial_iterative-old.png
http://vps.solson.me/mir-graphviz/factorial_fold-new.png
http://vps.solson.me/mir-graphviz/factorial_fold-old.png
http://vps.solson.me/mir-graphviz/80-factorial_fold-new.png
http://vps.solson.me/mir-graphviz/80-factorial_fold-old.png
http://vps.solson.me/mir-graphviz/collatz-new.png
http://vps.solson.me/mir-graphviz/collatz-old.png
http://vps.solson.me/mir-graphviz/multi_switch-new.png
http://vps.solson.me/mir-graphviz/multi_switch-old.png