Skip to content

Commit 94c4e1e

Browse files
committed
Simplify yul conversion function even more.
1 parent 4480662 commit 94c4e1e

File tree

2 files changed

+38
-34
lines changed

2 files changed

+38
-34
lines changed

libsolidity/codegen/YulUtilFunctions.cpp

Lines changed: 34 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,16 @@ using namespace solidity;
3535
using namespace solidity::util;
3636
using namespace solidity::frontend;
3737

38+
string YulUtilFunctions::identityFunction()
39+
{
40+
string functionName = "identity";
41+
return m_functionCollector.createFunction("identity", [&](vector<string>& _args, vector<string>& _rets) {
42+
_args.push_back("value");
43+
_rets.push_back("ret");
44+
return "ret := value";
45+
});
46+
}
47+
3848
string YulUtilFunctions::combineExternalFunctionIdFunction()
3949
{
4050
string functionName = "combine_external_function_id";
@@ -3272,48 +3282,38 @@ string YulUtilFunctions::conversionFunction(Type const& _from, Type const& _to)
32723282
if (rational->isFractional())
32733283
solAssert(toCategory == Type::Category::FixedPoint, "");
32743284

3275-
if (toCategory == Type::Category::FixedBytes)
3276-
{
3277-
FixedBytesType const& toBytesType = dynamic_cast<FixedBytesType const&>(_to);
3278-
body =
3279-
Whiskers("converted := <shiftLeft>(<clean>(value))")
3280-
("shiftLeft", shiftLeftFunction(256 - toBytesType.numBytes() * 8))
3281-
("clean", cleanupFunction(_from))
3282-
.render();
3283-
}
3284-
else if (toCategory == Type::Category::Enum)
3285-
body =
3286-
Whiskers("converted := <cleanEnum>(<cleanInt>(value))")
3287-
("cleanEnum", cleanupFunction(_to))
3288-
("cleanInt", cleanupFunction(_from))
3289-
.render();
3290-
else if (toCategory == Type::Category::FixedPoint)
3291-
solUnimplemented("Not yet implemented - FixedPointType.");
3292-
else if (toCategory == Type::Category::Address || toCategory == Type::Category::Contract)
3285+
if (toCategory == Type::Category::Address || toCategory == Type::Category::Contract)
32933286
body =
32943287
Whiskers("converted := <convert>(value)")
32953288
("convert", conversionFunction(_from, IntegerType(160)))
32963289
.render();
3297-
else if (toCategory == Type::Category::Integer)
3290+
else
32983291
{
3299-
IntegerType const& to = dynamic_cast<IntegerType const&>(_to);
3300-
3301-
// Clean according to the "to" type, except if this is
3302-
// a widening conversion.
3303-
IntegerType const* cleanupType = &to;
3304-
if (fromCategory == Type::Category::Integer)
3292+
Whiskers bodyTemplate("converted := <cleanOutput>(<convert>(<cleanInput>(value)))");
3293+
bodyTemplate("cleanInput", cleanupFunction(_from));
3294+
bodyTemplate("cleanOutput", cleanupFunction(_to));
3295+
string convert;
3296+
3297+
if (auto const* toFixedBytes = dynamic_cast<FixedBytesType const*>(&_to))
3298+
convert = shiftLeftFunction(256 - toFixedBytes->numBytes() * 8);
3299+
else if (dynamic_cast<FixedPointType const*>(&_to))
3300+
solUnimplementedAssert(false, "");
3301+
else if (dynamic_cast<IntegerType const*>(&_to))
33053302
{
3306-
IntegerType const& from = dynamic_cast<IntegerType const&>(_from);
3307-
if (to.numBits() > from.numBits())
3308-
cleanupType = &from;
3303+
solUnimplementedAssert(fromCategory != Type::Category::FixedPoint, "");
3304+
convert = identityFunction();
33093305
}
3310-
body =
3311-
Whiskers("converted := <cleanInt>(value)")
3312-
("cleanInt", cleanupFunction(*cleanupType))
3313-
.render();
3306+
else if (toCategory == Type::Category::Enum)
3307+
{
3308+
solAssert(fromCategory != Type::Category::FixedPoint, "");
3309+
convert = identityFunction();
3310+
}
3311+
else
3312+
solAssert(false, "");
3313+
solAssert(!convert.empty(), "");
3314+
bodyTemplate("convert", convert);
3315+
body = bodyTemplate.render();
33143316
}
3315-
else
3316-
solAssert(false, "");
33173317
break;
33183318
}
33193319
case Type::Category::Bool:

libsolidity/codegen/YulUtilFunctions.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -59,6 +59,10 @@ class YulUtilFunctions
5959
m_functionCollector(_functionCollector)
6060
{}
6161

62+
/// @returns the name of a function that returns its argument.
63+
/// Sometimes needed to satisfy templates.
64+
std::string identityFunction();
65+
6266
/// @returns a function that combines the address and selector to a single value
6367
/// for use in the ABI.
6468
std::string combineExternalFunctionIdFunction();

0 commit comments

Comments
 (0)