From afde4ea4e33a65875557ed98b740ee7b3661210c Mon Sep 17 00:00:00 2001 From: Alex Crichton Date: Tue, 7 Mar 2023 17:58:03 -0600 Subject: [PATCH] Fix the original block for block params in egraphs (#5960) This fixes an issue where block params were always listed as being members of the current block in egraphs, even when the block param was actually defined in a separate block. This then enables instructions which depend on these parameters to get hoisted up out of inner loops at least to the block that defined the argument. Closes #5957 --- cranelift/codegen/src/egraph/elaborate.rs | 4 +- .../filetests/egraph/load-hoist.clif | 44 +++++++++++++++++++ 2 files changed, 46 insertions(+), 2 deletions(-) create mode 100644 cranelift/filetests/filetests/egraph/load-hoist.clif diff --git a/cranelift/codegen/src/egraph/elaborate.rs b/cranelift/codegen/src/egraph/elaborate.rs index dbb14505a7..6acf83cba9 100644 --- a/cranelift/codegen/src/egraph/elaborate.rs +++ b/cranelift/codegen/src/egraph/elaborate.rs @@ -330,14 +330,14 @@ impl<'a> Elaborator<'a> { ); (inst, result_idx) } - ValueDef::Param(_, _) => { + ValueDef::Param(in_block, _) => { // We don't need to do anything to compute // this value; just push its result on the // result stack (blockparams are already // available). trace!(" -> value {} is a blockparam", best_value); self.elab_result_stack.push(ElaboratedValue { - in_block: self.cur_block, + in_block, value: best_value, }); continue; diff --git a/cranelift/filetests/filetests/egraph/load-hoist.clif b/cranelift/filetests/filetests/egraph/load-hoist.clif new file mode 100644 index 0000000000..f52a1995c4 --- /dev/null +++ b/cranelift/filetests/filetests/egraph/load-hoist.clif @@ -0,0 +1,44 @@ +test optimize +set opt_level=speed_and_size +target x86_64 + +function %foo(i64 vmctx, i64, i32, i32) -> i32 fast { + gv0 = vmctx + gv1 = load.i64 notrap aligned readonly gv0+8 + gv2 = load.i64 notrap aligned gv1 + gv3 = vmctx + gv4 = load.i64 notrap aligned readonly gv3+80 + stack_limit = gv2 + + block0(v0: i64, v1: i64, v2: i32, v3: i32): + v5 = iconst.i32 0 + jump block2(v5, v2, v3) ; v5 = 0 + + block2(v6: i32, v7: i32, v15: i32): + v9 = load.i64 notrap aligned readonly v0+80 + v8 = uextend.i64 v7 + v10 = iadd v9, v8 + v11 = load.i32 little heap v10 + v16 = iconst.i32 1 + v17 = isub v15, v16 ; v16 = 1 + v12 = iadd v6, v11 + v4 -> v12 + v13 = iconst.i32 4 + v14 = iadd v7, v13 ; v13 = 4 + brif v17, block2(v12, v14, v17), block4 + + block4: + jump block3 + + block3: + jump block1 + + block1: + return v12 +} + +; check: v9 = load.i64 notrap aligned readonly v0+80 +; check: block2(v6: i32, v7: i32, v15: i32): +; check: v10 = iadd.i64 v9, v8 +; check: v11 = load.i32 little heap v10 +; check: brif v17, block2(v12, v14, v17), block4