From e2e4a9fe81656724111c444cbf253d39bbb2b67b Mon Sep 17 00:00:00 2001 From: chriseth Date: Tue, 2 Oct 2018 10:46:59 +0200 Subject: New full inliner. --- test/libyul/YulOptimizerTest.cpp | 4 ++ .../fullInliner/double_inline.yul | 30 +++++++++++++++ .../fullInliner/inside_condition.yul | 10 ++--- .../fullInliner/move_up_rightwards_argument.yul | 17 +++++---- .../yulOptimizerTests/fullInliner/multi_fun.yul | 34 +++++++---------- .../yulOptimizerTests/fullInliner/multi_return.yul | 13 +++++-- .../yulOptimizerTests/fullInliner/no_return.yul | 6 +-- .../fullInliner/not_inside_for.yul | 43 ++++++++++++++++++++++ .../yulOptimizerTests/fullInliner/pop_result.yul | 13 +++---- .../yulOptimizerTests/fullInliner/simple.yul | 10 ++--- 10 files changed, 124 insertions(+), 56 deletions(-) create mode 100644 test/libyul/yulOptimizerTests/fullInliner/double_inline.yul create mode 100644 test/libyul/yulOptimizerTests/fullInliner/not_inside_for.yul (limited to 'test/libyul') diff --git a/test/libyul/YulOptimizerTest.cpp b/test/libyul/YulOptimizerTest.cpp index d1990edb..8e4771c8 100644 --- a/test/libyul/YulOptimizerTest.cpp +++ b/test/libyul/YulOptimizerTest.cpp @@ -130,7 +130,11 @@ bool YulOptimizerTest::run(ostream& _stream, string const& _linePrefix, bool con disambiguate(); (FunctionHoister{})(*m_ast); (FunctionGrouper{})(*m_ast); + NameDispenser nameDispenser; + nameDispenser.m_usedNames = NameCollector(*m_ast).names(); + ExpressionSplitter{nameDispenser}(*m_ast); FullInliner(*m_ast).run(); + ExpressionJoiner::run(*m_ast); } else if (m_optimizerStep == "mainFunction") { diff --git a/test/libyul/yulOptimizerTests/fullInliner/double_inline.yul b/test/libyul/yulOptimizerTests/fullInliner/double_inline.yul new file mode 100644 index 00000000..dd1c1f8a --- /dev/null +++ b/test/libyul/yulOptimizerTests/fullInliner/double_inline.yul @@ -0,0 +1,30 @@ +{ + function f(a) -> b, c { let x := mload(a) b := sload(x) c := 3 } + let a1 := calldataload(0) + let b3, c3 := f(a1) + let b4, c4 := f(c3) +} +// ---- +// fullInliner +// { +// { +// let f_a := calldataload(0) +// let f_b +// let f_c +// f_b := sload(mload(f_a)) +// f_c := 3 +// let b3 := f_b +// let f_a_1 := f_c +// let f_b_1 +// let f_c_1 +// f_b_1 := sload(mload(f_a_1)) +// f_c_1 := 3 +// let b4 := f_b_1 +// let c4 := f_c_1 +// } +// function f(a) -> b, c +// { +// b := sload(mload(a)) +// c := 3 +// } +// } diff --git a/test/libyul/yulOptimizerTests/fullInliner/inside_condition.yul b/test/libyul/yulOptimizerTests/fullInliner/inside_condition.yul index 76b6054b..00bb6577 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/inside_condition.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/inside_condition.yul @@ -12,14 +12,12 @@ // fullInliner // { // { -// let _1 := mload(0) +// let _2 := mload(0) // let f_a := mload(1) // let f_r -// { -// f_a := mload(f_a) -// f_r := add(f_a, calldatasize()) -// } -// if gt(f_r, _1) +// f_a := mload(f_a) +// f_r := add(f_a, calldatasize()) +// if gt(f_r, _2) // { // sstore(0, 2) // } diff --git a/test/libyul/yulOptimizerTests/fullInliner/move_up_rightwards_argument.yul b/test/libyul/yulOptimizerTests/fullInliner/move_up_rightwards_argument.yul index e1def585..f3d0b286 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/move_up_rightwards_argument.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/move_up_rightwards_argument.yul @@ -9,16 +9,17 @@ // fullInliner // { // { -// let _1 := mload(5) -// let f_c := mload(4) -// let f_b := mload(3) +// let _2 := mload(5) +// let _4 := mload(4) +// let _6 := mload(3) // let f_a := mload(2) +// let f_b := _6 +// let f_c := _4 // let f_x -// { -// f_x := add(f_a, f_b) -// f_x := mul(f_x, f_c) -// } -// let y := add(mload(1), add(f_x, _1)) +// f_x := add(f_a, f_b) +// f_x := mul(f_x, f_c) +// let _10 := add(f_x, _2) +// let y := add(mload(1), _10) // } // function f(a, b, c) -> x // { diff --git a/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul b/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul index 94bbe5dc..40397a43 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul @@ -7,21 +7,17 @@ // fullInliner // { // { -// let g_c := 7 -// let f_a_1 := 3 -// let f_x_1 -// { -// f_x_1 := add(f_a_1, f_a_1) -// } +// let _1 := 7 +// let f_a := 3 +// let f_x +// f_x := add(f_a, f_a) +// let g_b := f_x +// let g_c := _1 // let g_y -// { -// let g_f_a := f_x_1 -// let g_f_x -// { -// g_f_x := add(g_f_a, g_f_a) -// } -// g_y := mul(mload(g_c), g_f_x) -// } +// let g_f_a_1 := g_b +// let g_f_x_1 +// g_f_x_1 := add(g_f_a_1, g_f_a_1) +// g_y := mul(mload(g_c), g_f_x_1) // let y_1 := g_y // } // function f(a) -> x @@ -30,11 +26,9 @@ // } // function g(b, c) -> y // { -// let f_a := b -// let f_x -// { -// f_x := add(f_a, f_a) -// } -// y := mul(mload(c), f_x) +// let f_a_1 := b +// let f_x_1 +// f_x_1 := add(f_a_1, f_a_1) +// y := mul(mload(c), f_x_1) // } // } diff --git a/test/libyul/yulOptimizerTests/fullInliner/multi_return.yul b/test/libyul/yulOptimizerTests/fullInliner/multi_return.yul index f3c5b0ee..eebdec38 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/multi_return.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/multi_return.yul @@ -1,17 +1,22 @@ -// The full inliner currently does not work with -// functions returning multiple values. { function f(a) -> x, y { x := mul(a, a) y := add(a, x) } - let a, b := f(mload(0)) + let r, s := f(mload(0)) + mstore(r, s) } // ---- // fullInliner // { // { -// let a_1, b := f(mload(0)) +// let f_a := mload(0) +// let f_x +// let f_y +// f_x := mul(f_a, f_a) +// f_y := add(f_a, f_x) +// let r := f_x +// mstore(r, f_y) // } // function f(a) -> x, y // { diff --git a/test/libyul/yulOptimizerTests/fullInliner/no_return.yul b/test/libyul/yulOptimizerTests/fullInliner/no_return.yul index 53fe3527..3708c557 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/no_return.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/no_return.yul @@ -9,11 +9,7 @@ // { // { // let f_a := mload(0) -// { -// sstore(f_a, f_a) -// } -// { -// } +// sstore(f_a, f_a) // } // function f(a) // { diff --git a/test/libyul/yulOptimizerTests/fullInliner/not_inside_for.yul b/test/libyul/yulOptimizerTests/fullInliner/not_inside_for.yul new file mode 100644 index 00000000..44fc7b21 --- /dev/null +++ b/test/libyul/yulOptimizerTests/fullInliner/not_inside_for.yul @@ -0,0 +1,43 @@ +{ + for { let x := f(0) } f(x) { x := f(x) } + { + let t := f(x) + } + function f(a) -> r { + sstore(a, 0) + r := a + } +} +// ---- +// fullInliner +// { +// { +// for { +// let f_a := 0 +// let f_r +// sstore(f_a, 0) +// f_r := f_a +// let x := f_r +// } +// f(x) +// { +// let f_a_1 := x +// let f_r_1 +// sstore(f_a_1, 0) +// f_r_1 := f_a_1 +// x := f_r_1 +// } +// { +// let f_a_2 := x +// let f_r_2 +// sstore(f_a_2, 0) +// f_r_2 := f_a_2 +// let t := f_r_2 +// } +// } +// function f(a) -> r +// { +// sstore(a, 0) +// r := a +// } +// } diff --git a/test/libyul/yulOptimizerTests/fullInliner/pop_result.yul b/test/libyul/yulOptimizerTests/fullInliner/pop_result.yul index 3883c67c..cd9e2746 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/pop_result.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/pop_result.yul @@ -1,4 +1,6 @@ -// This tests that `pop(r)` is removed. +// An earlier version of the inliner produced +// pop(...) statements and explicitly removed them. +// This used to test that they are removed. { function f(a) -> x { let r := mul(a, a) @@ -13,12 +15,9 @@ // let _1 := 2 // let f_a := 7 // let f_x -// { -// let f_r := mul(f_a, f_a) -// f_x := add(f_r, f_r) -// } -// { -// } +// let f_r := mul(f_a, f_a) +// f_x := add(f_r, f_r) +// pop(add(f_x, _1)) // } // function f(a) -> x // { diff --git a/test/libyul/yulOptimizerTests/fullInliner/simple.yul b/test/libyul/yulOptimizerTests/fullInliner/simple.yul index dd1a4e0a..fcdf453b 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/simple.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/simple.yul @@ -9,14 +9,12 @@ // fullInliner // { // { -// let _1 := mload(7) +// let _2 := mload(7) // let f_a := sload(mload(2)) // let f_x -// { -// let f_r := mul(f_a, f_a) -// f_x := add(f_r, f_r) -// } -// let y := add(f_x, _1) +// let f_r := mul(f_a, f_a) +// f_x := add(f_r, f_r) +// let y := add(f_x, _2) // } // function f(a) -> x // { -- cgit v1.2.3 From a435a14e135a4e31ce3cd2bacd32544b2b342074 Mon Sep 17 00:00:00 2001 From: chriseth Date: Tue, 16 Oct 2018 17:29:20 +0200 Subject: Test for crash via inlining. --- .../fullInliner/multi_fun_callback.yul | 84 ++++++++++++++++++++++ 1 file changed, 84 insertions(+) create mode 100644 test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul (limited to 'test/libyul') diff --git a/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul b/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul new file mode 100644 index 00000000..7588094f --- /dev/null +++ b/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul @@ -0,0 +1,84 @@ +{ + // This is a test for an older version where + // inlining was performed on a function + // just being called. This is a problem + // because the statemenst of the original + // function might be in an invalid state. + + function f(x) { + mstore(0, x) + mstore(7, h()) + g(10) + mstore(1, x) + } + function g(x) { + f(1) + } + function h() -> t { + t := 2 + + } + { + f(100) + } +} +// ---- +// fullInliner +// { +// { +// { +// let f_x_1 := 100 +// mstore(0, f_x_1) +// let f_h_t +// f_h_t := 2 +// mstore(7, f_h_t) +// let f__5 := 10 +// let f_g_x_1 := f__5 +// let f_g_f_x := 1 +// let +// mstore() +// let f_g_f_ := h() +// let +// mstore() +// let +// g(f__5) +// mstore(1, f_g_f_x) +// mstore(1, f_x_1) +// } +// } +// function f(x) +// { +// mstore(0, x) +// let h_t +// h_t := 2 +// mstore(7, h_t) +// let _5 := 10 +// let g_x_1 := _5 +// let g_f_x := 1 +// let +// mstore() +// let g_f_ := h() +// let +// mstore() +// let +// g(_5) +// mstore(1, g_f_x) +// mstore(1, x) +// } +// function g(x_1) +// { +// let f_x := 1 +// let +// mstore() +// let f_ := h() +// let +// mstore() +// let +// g(_5) +// mstore(1, f_x) +// } +// function h() -> t +// { +// t := 2 +// } +// } -- cgit v1.2.3 From 2ab6430303406b03191cb7e14ecd1384104b12fa Mon Sep 17 00:00:00 2001 From: chriseth Date: Tue, 16 Oct 2018 17:21:14 +0200 Subject: Inline each function separately. --- .../yulOptimizerTests/fullInliner/multi_fun.yul | 5 +-- .../fullInliner/multi_fun_callback.yul | 52 +++++++--------------- 2 files changed, 16 insertions(+), 41 deletions(-) (limited to 'test/libyul') diff --git a/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul b/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul index 40397a43..c704944d 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/multi_fun.yul @@ -14,10 +14,7 @@ // let g_b := f_x // let g_c := _1 // let g_y -// let g_f_a_1 := g_b -// let g_f_x_1 -// g_f_x_1 := add(g_f_a_1, g_f_a_1) -// g_y := mul(mload(g_c), g_f_x_1) +// g_y := mul(mload(g_c), f(g_b)) // let y_1 := g_y // } // function f(a) -> x diff --git a/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul b/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul index 7588094f..bcdba8e0 100644 --- a/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul +++ b/test/libyul/yulOptimizerTests/fullInliner/multi_fun_callback.yul @@ -27,23 +27,11 @@ // { // { // { -// let f_x_1 := 100 -// mstore(0, f_x_1) -// let f_h_t -// f_h_t := 2 -// mstore(7, f_h_t) -// let f__5 := 10 -// let f_g_x_1 := f__5 -// let f_g_f_x := 1 -// let -// mstore() -// let f_g_f_ := h() -// let -// mstore() -// let -// g(f__5) -// mstore(1, f_g_f_x) -// mstore(1, f_x_1) +// let f_x := 100 +// mstore(0, f_x) +// mstore(7, h()) +// g(10) +// mstore(1, f_x) // } // } // function f(x) @@ -52,30 +40,20 @@ // let h_t // h_t := 2 // mstore(7, h_t) -// let _5 := 10 -// let g_x_1 := _5 -// let g_f_x := 1 -// let -// mstore() -// let g_f_ := h() -// let -// mstore() -// let -// g(_5) -// mstore(1, g_f_x) +// let g_x_1 := 10 +// f(1) // mstore(1, x) // } // function g(x_1) // { -// let f_x := 1 -// let -// mstore() -// let f_ := h() -// let -// mstore() -// let -// g(_5) -// mstore(1, f_x) +// let f_x_1 := 1 +// mstore(0, f_x_1) +// let f_h_t +// f_h_t := 2 +// mstore(7, f_h_t) +// let f_g_x_1 := 10 +// f(1) +// mstore(1, f_x_1) // } // function h() -> t // { -- cgit v1.2.3