mirror of
https://github.com/ethereum/solidity
synced 2023-10-03 13:03:40 +00:00
Finish word size transform.
This commit is contained in:
parent
096e3fcd37
commit
ecab46c707
@ -18,6 +18,8 @@
|
|||||||
#include <libyul/AsmData.h>
|
#include <libyul/AsmData.h>
|
||||||
#include <libyul/backends/wasm/WordSizeTransform.h>
|
#include <libyul/backends/wasm/WordSizeTransform.h>
|
||||||
#include <libyul/Utilities.h>
|
#include <libyul/Utilities.h>
|
||||||
|
#include <libyul/Dialect.h>
|
||||||
|
#include <libyul/optimiser/NameDisplacer.h>
|
||||||
|
|
||||||
#include <libdevcore/CommonData.h>
|
#include <libdevcore/CommonData.h>
|
||||||
|
|
||||||
@ -41,6 +43,10 @@ void WordSizeTransform::operator()(FunctionalInstruction& _ins)
|
|||||||
|
|
||||||
void WordSizeTransform::operator()(FunctionCall& _fc)
|
void WordSizeTransform::operator()(FunctionCall& _fc)
|
||||||
{
|
{
|
||||||
|
if (BuiltinFunction const* fun = m_inputDialect.builtin(_fc.functionName.name))
|
||||||
|
if (fun->literalArguments)
|
||||||
|
return;
|
||||||
|
|
||||||
rewriteFunctionCallArguments(_fc.arguments);
|
rewriteFunctionCallArguments(_fc.arguments);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -48,7 +54,7 @@ void WordSizeTransform::operator()(If& _if)
|
|||||||
{
|
{
|
||||||
_if.condition = make_unique<Expression>(FunctionCall{
|
_if.condition = make_unique<Expression>(FunctionCall{
|
||||||
locationOf(*_if.condition),
|
locationOf(*_if.condition),
|
||||||
Identifier{locationOf(*_if.condition), "or_bool"_yulstring}, // TODO make sure this is not used
|
Identifier{locationOf(*_if.condition), "or_bool"_yulstring},
|
||||||
expandValueToVector(*_if.condition)
|
expandValueToVector(*_if.condition)
|
||||||
});
|
});
|
||||||
(*this)(_if.body);
|
(*this)(_if.body);
|
||||||
@ -59,6 +65,18 @@ void WordSizeTransform::operator()(Switch&)
|
|||||||
yulAssert(false, "Switch statement not implemented.");
|
yulAssert(false, "Switch statement not implemented.");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void WordSizeTransform::operator()(ForLoop& _for)
|
||||||
|
{
|
||||||
|
(*this)(_for.pre);
|
||||||
|
_for.condition = make_unique<Expression>(FunctionCall{
|
||||||
|
locationOf(*_for.condition),
|
||||||
|
Identifier{locationOf(*_for.condition), "or_bool"_yulstring},
|
||||||
|
expandValueToVector(*_for.condition)
|
||||||
|
});
|
||||||
|
(*this)(_for.post);
|
||||||
|
(*this)(_for.body);
|
||||||
|
}
|
||||||
|
|
||||||
void WordSizeTransform::operator()(Block& _block)
|
void WordSizeTransform::operator()(Block& _block)
|
||||||
{
|
{
|
||||||
iterateReplacing(
|
iterateReplacing(
|
||||||
@ -142,9 +160,11 @@ void WordSizeTransform::operator()(Block& _block)
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
void WordSizeTransform::run(Block& _ast, NameDispenser& _nameDispenser)
|
void WordSizeTransform::run(Dialect const& _inputDialect, Block& _ast, NameDispenser& _nameDispenser)
|
||||||
{
|
{
|
||||||
WordSizeTransform{_nameDispenser}(_ast);
|
// Free the name `or_bool`.
|
||||||
|
NameDisplacer{_nameDispenser, {"or_bool"_yulstring}}(_ast);
|
||||||
|
WordSizeTransform{_inputDialect, _nameDispenser}(_ast);
|
||||||
}
|
}
|
||||||
|
|
||||||
void WordSizeTransform::rewriteVarDeclList(TypedNameList& _nameList)
|
void WordSizeTransform::rewriteVarDeclList(TypedNameList& _nameList)
|
||||||
|
@ -51,7 +51,7 @@ namespace yul
|
|||||||
* take four times the parameters and each of type u64.
|
* take four times the parameters and each of type u64.
|
||||||
* In addition, it uses a single other builtin function called `or_bool` that
|
* In addition, it uses a single other builtin function called `or_bool` that
|
||||||
* takes four u64 parameters and is supposed to return the logical disjunction
|
* takes four u64 parameters and is supposed to return the logical disjunction
|
||||||
* of them es a u64 value.
|
* of them as a u64 value. If this name is already used somewhere, it is renamed.
|
||||||
*
|
*
|
||||||
* Prerequisite: Disambiguator, ExpressionSplitter
|
* Prerequisite: Disambiguator, ExpressionSplitter
|
||||||
*/
|
*/
|
||||||
@ -63,12 +63,14 @@ public:
|
|||||||
void operator()(FunctionCall&) override;
|
void operator()(FunctionCall&) override;
|
||||||
void operator()(If&) override;
|
void operator()(If&) override;
|
||||||
void operator()(Switch&) override;
|
void operator()(Switch&) override;
|
||||||
|
void operator()(ForLoop&) override;
|
||||||
void operator()(Block& _block) override;
|
void operator()(Block& _block) override;
|
||||||
|
|
||||||
static void run(Block& _ast, NameDispenser& _nameDispenser);
|
static void run(Dialect const& _inputDialect, Block& _ast, NameDispenser& _nameDispenser);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
explicit WordSizeTransform(NameDispenser& _nameDispenser):
|
explicit WordSizeTransform(Dialect const& _inputDialect, NameDispenser& _nameDispenser):
|
||||||
|
m_inputDialect(_inputDialect),
|
||||||
m_nameDispenser(_nameDispenser)
|
m_nameDispenser(_nameDispenser)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
@ -80,6 +82,7 @@ private:
|
|||||||
std::array<std::unique_ptr<Expression>, 4> expandValue(Expression const& _e);
|
std::array<std::unique_ptr<Expression>, 4> expandValue(Expression const& _e);
|
||||||
std::vector<Expression> expandValueToVector(Expression const& _e);
|
std::vector<Expression> expandValueToVector(Expression const& _e);
|
||||||
|
|
||||||
|
Dialect const& m_inputDialect;
|
||||||
NameDispenser& m_nameDispenser;
|
NameDispenser& m_nameDispenser;
|
||||||
/// maps original u256 variable's name to corresponding u64 variables' names
|
/// maps original u256 variable's name to corresponding u64 variables' names
|
||||||
std::map<YulString, std::array<YulString, 4>> m_variableMapping;
|
std::map<YulString, std::array<YulString, 4>> m_variableMapping;
|
||||||
|
@ -297,7 +297,7 @@ TestCase::TestResult YulOptimizerTest::run(ostream& _stream, string const& _line
|
|||||||
disambiguate();
|
disambiguate();
|
||||||
NameDispenser nameDispenser{*m_dialect, *m_ast};
|
NameDispenser nameDispenser{*m_dialect, *m_ast};
|
||||||
ExpressionSplitter{*m_dialect, nameDispenser}(*m_ast);
|
ExpressionSplitter{*m_dialect, nameDispenser}(*m_ast);
|
||||||
WordSizeTransform::run(*m_ast, nameDispenser);
|
WordSizeTransform::run(*m_dialect, *m_ast, nameDispenser);
|
||||||
}
|
}
|
||||||
else if (m_optimizerStep == "fullSuite")
|
else if (m_optimizerStep == "fullSuite")
|
||||||
{
|
{
|
||||||
|
@ -0,0 +1,25 @@
|
|||||||
|
{
|
||||||
|
let or_bool := 2
|
||||||
|
if or_bool { sstore(0, 1) }
|
||||||
|
}
|
||||||
|
// ====
|
||||||
|
// step: wordSizeTransform
|
||||||
|
// ----
|
||||||
|
// {
|
||||||
|
// let or_bool_3_0 := 0
|
||||||
|
// let or_bool_3_1 := 0
|
||||||
|
// let or_bool_3_2 := 0
|
||||||
|
// let or_bool_3_3 := 2
|
||||||
|
// if or_bool(or_bool_3_0, or_bool_3_1, or_bool_3_2, or_bool_3_3)
|
||||||
|
// {
|
||||||
|
// let _1_0 := 0
|
||||||
|
// let _1_1 := 0
|
||||||
|
// let _1_2 := 0
|
||||||
|
// let _1_3 := 1
|
||||||
|
// let _2_0 := 0
|
||||||
|
// let _2_1 := 0
|
||||||
|
// let _2_2 := 0
|
||||||
|
// let _2_3 := 0
|
||||||
|
// sstore(_2_0, _2_1, _2_2, _2_3, _1_0, _1_1, _1_2, _1_3)
|
||||||
|
// }
|
||||||
|
// }
|
Loading…
Reference in New Issue
Block a user