dillon1000/react
Commit
Browse files [rust] Initial port of EnterSSA
This is a first pass at porting EnterSSA to Rust. First pass in the sense that it's hard to fully test it, and also in the sense that we'll likely figure out even better ways to work w the HIR as we iterate. Oh and i didn't do recusing into function expressions yet, since we can't even represent function expressions yet, and that may require modifying the design a bit (though i have an idea that i think will work, which is for the Builder to have an optional parent. When we encounter a block with no predecessors, we check the parent. I _think_ this will make all the borrowing "just work"). A few notes: Rust's compilation model parallelizes and incrementally computes at the crate granularity, so builds are faster if we split up our code into more but smaller crates. Setting up a clean dependency graph can dramatically improve build performance too. For example, to run the `fixtures` tests we can build `estree` and `hir` in parallel, then once those build _all_ of our other crates can be built in parallel until we get to `fixtures` which depends on the everything else. The various passes don't have any build dependencies on each other so they can build in parallel. Hence the new code for SSA stuff is in a separate `hir-ssa` crate. We should similarly group other passes (approximately one crate per folder in the babel-plugin-react-forget/src/ directory, eg SSA, Inference, Optimization, etc). Second, shared mutable ownership can be modeled in Rust but requires wrappers such as `Rc<RefCell<>>`. It's generally more efficient and more idiomatic to rethink the data model and algorithm. For EnterSSA, the Builder object holds a reference into the HIR that it only ever reads, and the pass (which drives the builder) also holds a reference into the HIR, which it mutates. The previous PR split up Blocks and Instructions, and the value of that is more apparent in `enter_ssa()`. The Rust equivalent of the builder holds a _shared_ (immutable) reference to just the HIR's blocks, while the pass (driving the builder) holds a _unique_ (mutable) reference to just the HIR's instructions. This lets us keep the overall feel of the algorithm while keeping Rust happy. Also note that the other change — to making operands be InstrIx indices into the instructions array — means that the SSA logic is simpler. Most instructions don't have to be visited at all, since they don't deal with loads/stores. Terminals also don't need to be visited, since they reference instructions, not identifiers. The Phi concept seems to just work too. I also updated the printer to print predecessors and phis.
Changed paths17 files
First-parent comparisoncompiler/forget/crates/build-hir/src/build.rs ModifiedM compiler/forget/crates/build-hir/src/builder.rs ModifiedM compiler/forget/crates/fixtures/Cargo.toml ModifiedA compiler/forget/crates/fixtures/tests/fixtures/ssa-reassign-if.js AddedM compiler/forget/crates/fixtures/tests/fixtures_test.rs ModifiedM compiler/forget/crates/fixtures/tests/snapshots/[email protected] ModifiedM compiler/forget/crates/fixtures/tests/snapshots/[email protected] ModifiedM compiler/forget/crates/fixtures/tests/snapshots/[email protected] ModifiedM compiler/forget/crates/fixtures/tests/snapshots/[email protected] ModifiedA compiler/forget/crates/fixtures/tests/snapshots/[email protected] AddedM compiler/forget/crates/hir-ssa/Cargo.toml ModifiedM compiler/forget/crates/hir-ssa/src/enter.rs ModifiedM compiler/forget/crates/hir/src/basic_block.rs ModifiedM compiler/forget/crates/hir/src/function.rs ModifiedM compiler/forget/crates/hir/src/instruction.rs ModifiedM compiler/forget/crates/hir/src/print.rs ModifiedM compiler/forget/crates/hir/src/types.rs ModifiedPatch
Files changed
Rendering syntax-highlighted changes…