diff options
Diffstat (limited to 'test')
9 files changed, 124 insertions, 95 deletions
diff --git a/test/libjulia/Inliner.cpp b/test/libjulia/Inliner.cpp index d0ecd42f..165e23ad 100644 --- a/test/libjulia/Inliner.cpp +++ b/test/libjulia/Inliner.cpp @@ -55,12 +55,6 @@ string inlinableFunctions(string const& _source) ); } -string inlineFunctions(string const& _source, bool _yul = true) -{ - auto ast = disambiguate(_source, _yul); - ExpressionInliner(ast).run(); - return assembly::AsmPrinter(_yul)(ast); -} string fullInline(string const& _source, bool _yul = true) { Block ast = disambiguate(_source, _yul); @@ -124,95 +118,6 @@ BOOST_AUTO_TEST_CASE(negative) BOOST_AUTO_TEST_SUITE_END() -BOOST_AUTO_TEST_SUITE(YulFunctionInliner) - -BOOST_AUTO_TEST_CASE(simple) -{ - BOOST_CHECK_EQUAL( - inlineFunctions("{ function f() -> x:u256 { x := 2:u256 } let y:u256 := f() }"), - format("{ function f() -> x:u256 { x := 2:u256 } let y:u256 := 2:u256 }") - ); -} - -BOOST_AUTO_TEST_CASE(with_args) -{ - BOOST_CHECK_EQUAL( - inlineFunctions("{ function f(a:u256) -> x:u256 { x := a } let y:u256 := f(7:u256) }"), - format("{ function f(a:u256) -> x:u256 { x := a } let y:u256 := 7:u256 }") - ); -} - -BOOST_AUTO_TEST_CASE(no_inline_with_mload) -{ - // Does not inline because mload could be moved out of sequence - BOOST_CHECK_EQUAL( - inlineFunctions("{ function f(a) -> x { x := a } let y := f(mload(2)) }", false), - format("{ function f(a) -> x { x := a } let y := f(mload(2)) }", false) - ); -} - -BOOST_AUTO_TEST_CASE(no_move_with_side_effects) -{ - // The calls to g and h cannot be moved because g and h are not movable. Therefore, the call - // to f is not inlined. - BOOST_CHECK_EQUAL( - inlineFunctions("{" - "function f(a, b) -> x { x := add(b, a) }" - "function g() -> y { y := mload(0) mstore(0, 4) }" - "function h() -> z { mstore(0, 4) z := mload(0) }" - "let r := f(g(), h())" - "}", false), - format("{" - "function f(a, b) -> x { x := add(b, a) }" - "function g() -> y { y := mload(0) mstore(0, 4) }" - "function h() -> z { mstore(0, 4) z := mload(0) }" - "let r := f(g(), h())" - "}", false) - ); -} - -BOOST_AUTO_TEST_CASE(complex_with_evm) -{ - BOOST_CHECK_EQUAL( - inlineFunctions("{ function f(a) -> x { x := add(a, a) } let y := f(calldatasize()) }", false), - format("{ function f(a) -> x { x := add(a, a) } let y := add(calldatasize(), calldatasize()) }", false) - ); -} - -BOOST_AUTO_TEST_CASE(double_calls) -{ - BOOST_CHECK_EQUAL( - inlineFunctions("{" - "function f(a) -> x { x := add(a, a) }" - "function g(b, c) -> y { y := mul(mload(c), f(b)) }" - "let y := g(calldatasize(), 7)" - "}", false), - format("{" - "function f(a) -> x { x := add(a, a) }" - "function g(b, c) -> y { y := mul(mload(c), add(b, b)) }" - "let y_1 := mul(mload(7), add(calldatasize(), calldatasize()))" - "}", false) - ); -} - -BOOST_AUTO_TEST_CASE(double_recursive_calls) -{ - BOOST_CHECK_EQUAL( - inlineFunctions("{" - "function f(a, r) -> x { x := g(a, g(r, r)) }" - "function g(b, s) -> y { y := f(b, f(s, s)) }" - "let y := g(calldatasize(), 7)" - "}", false), - format("{" - "function f(a, r) -> x { x := g(a, f(r, f(r, r))) }" - "function g(b, s) -> y { y := f(b, g(s, f(s, f(s, s))))}" - "let y_1 := f(calldatasize(), g(7, f(7, f(7, 7))))" - "}", false) - ); -} - -BOOST_AUTO_TEST_SUITE_END() - BOOST_AUTO_TEST_SUITE(YulFullInliner) BOOST_AUTO_TEST_CASE(simple) diff --git a/test/libjulia/YulOptimizerTest.cpp b/test/libjulia/YulOptimizerTest.cpp index 1ac2ddf5..878f1297 100644 --- a/test/libjulia/YulOptimizerTest.cpp +++ b/test/libjulia/YulOptimizerTest.cpp @@ -27,6 +27,7 @@ #include <libjulia/optimiser/ExpressionSplitter.h> #include <libjulia/optimiser/FunctionGrouper.h> #include <libjulia/optimiser/FunctionHoister.h> +#include <libjulia/optimiser/ExpressionInliner.h> #include <libsolidity/parsing/Scanner.h> #include <libsolidity/inlineasm/AsmPrinter.h> @@ -107,6 +108,11 @@ bool YulOptimizerTest::run(ostream& _stream, string const& _linePrefix, bool con disambiguate(); (FunctionHoister{})(*m_ast); } + else if (m_optimizerStep == "expressionInliner") + { + disambiguate(); + ExpressionInliner(*m_ast).run(); + } else { FormattedScope(_stream, _formatted, {formatting::BOLD, formatting::RED}) << _linePrefix << "Invalid optimizer step: " << m_optimizerStep << endl; diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/complex_with_evm.yul b/test/libjulia/yulOptimizerTests/expressionInliner/complex_with_evm.yul new file mode 100644 index 00000000..519a2af8 --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/complex_with_evm.yul @@ -0,0 +1,13 @@ +{ + function f(a) -> x { x := add(a, a) } + let y := f(calldatasize()) +} +// ---- +// expressionInliner +// { +// function f(a) -> x +// { +// x := add(a, a) +// } +// let y := add(calldatasize(), calldatasize()) +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/double_calls.yul b/test/libjulia/yulOptimizerTests/expressionInliner/double_calls.yul new file mode 100644 index 00000000..e1da8e07 --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/double_calls.yul @@ -0,0 +1,18 @@ +{ + function f(a) -> x { x := add(a, a) } + function g(b, c) -> y { y := mul(mload(c), f(b)) } + let y := g(calldatasize(), 7) +} +// ---- +// expressionInliner +// { +// function f(a) -> x +// { +// x := add(a, a) +// } +// function g(b, c) -> y +// { +// y := mul(mload(c), add(b, b)) +// } +// let y_1 := mul(mload(7), add(calldatasize(), calldatasize())) +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/double_recursive_calls.yul b/test/libjulia/yulOptimizerTests/expressionInliner/double_recursive_calls.yul new file mode 100644 index 00000000..082cb53f --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/double_recursive_calls.yul @@ -0,0 +1,18 @@ +{ + function f(a, r) -> x { x := g(a, g(r, r)) } + function g(b, s) -> y { y := f(b, f(s, s)) } + let y := g(calldatasize(), 7) +} +// ---- +// expressionInliner +// { +// function f(a, r) -> x +// { +// x := g(a, f(r, f(r, r))) +// } +// function g(b, s) -> y +// { +// y := f(b, g(s, f(s, f(s, s)))) +// } +// let y_1 := f(calldatasize(), g(7, f(7, f(7, 7)))) +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/no_inline_mload.yul b/test/libjulia/yulOptimizerTests/expressionInliner/no_inline_mload.yul new file mode 100644 index 00000000..0fb43a9d --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/no_inline_mload.yul @@ -0,0 +1,14 @@ +// Does not inline because mload could be moved out of sequence +{ + function f(a) -> x { x := a } + let y := f(mload(2)) +} +// ---- +// expressionInliner +// { +// function f(a) -> x +// { +// x := a +// } +// let y := f(mload(2)) +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/no_move_with_sideeffects.yul b/test/libjulia/yulOptimizerTests/expressionInliner/no_move_with_sideeffects.yul new file mode 100644 index 00000000..7fdad6c4 --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/no_move_with_sideeffects.yul @@ -0,0 +1,27 @@ +// The calls to g and h cannot be moved because g and h are not movable. Therefore, the call +// to f is not inlined. +{ + function f(a, b) -> x { x := add(b, a) } + function g() -> y { y := mload(0) mstore(0, 4) } + function h() -> z { mstore(0, 4) z := mload(0) } + let r := f(g(), h()) +} +// ---- +// expressionInliner +// { +// function f(a, b) -> x +// { +// x := add(b, a) +// } +// function g() -> y +// { +// y := mload(0) +// mstore(0, 4) +// } +// function h() -> z +// { +// mstore(0, 4) +// z := mload(0) +// } +// let r := f(g(), h()) +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/simple.yul b/test/libjulia/yulOptimizerTests/expressionInliner/simple.yul new file mode 100644 index 00000000..c186eafd --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/simple.yul @@ -0,0 +1,14 @@ +// yul +{ + function f() -> x:u256 { x := 2:u256 } + let y:u256 := f() +} +// ---- +// expressionInliner +// { +// function f() -> x:u256 +// { +// x := 2:u256 +// } +// let y:u256 := 2:u256 +// } diff --git a/test/libjulia/yulOptimizerTests/expressionInliner/with_args.yul b/test/libjulia/yulOptimizerTests/expressionInliner/with_args.yul new file mode 100644 index 00000000..b5f4d515 --- /dev/null +++ b/test/libjulia/yulOptimizerTests/expressionInliner/with_args.yul @@ -0,0 +1,14 @@ +// yul +{ + function f(a:u256) -> x:u256 { x := a } + let y:u256 := f(7:u256) +} +// ---- +// expressionInliner +// { +// function f(a:u256) -> x:u256 +// { +// x := a +// } +// let y:u256 := 7:u256 +// } |