Merge pull request #9373 from ethereum/develop

Merge develop into breaking.
This commit is contained in:
chriseth
2020-07-09 16:15:43 +02:00
committed by GitHub
52 changed files with 674 additions and 100 deletions
+2
View File
@@ -2404,6 +2404,8 @@ bool TypeChecker::visit(FunctionCallOptions const& _functionCallOptions)
{
solAssert(_functionCallOptions.options().size() == _functionCallOptions.names().size(), "Lengths of name & value arrays differ!");
_functionCallOptions.expression().annotation().arguments = _functionCallOptions.annotation().arguments;
_functionCallOptions.expression().accept(*this);
auto expressionFunctionType = dynamic_cast<FunctionType const*>(type(_functionCallOptions.expression()));
+1 -9
View File
@@ -935,11 +935,6 @@ void ArrayUtils::clearStorageLoop(TypePointer _type) const
}
// stack: end_pos pos
// jump to and return from the loop to allow for duplicate code removal
evmasm::AssemblyItem returnTag = _context.pushNewTag();
_context << Instruction::SWAP2 << Instruction::SWAP1;
// stack: <return tag> end_pos pos
evmasm::AssemblyItem loopStart = _context.appendJumpToNew();
_context << loopStart;
// check for loop condition
@@ -959,11 +954,8 @@ void ArrayUtils::clearStorageLoop(TypePointer _type) const
_context.appendJumpTo(loopStart);
// cleanup
_context << zeroLoopEnd;
_context << Instruction::POP << Instruction::SWAP1;
// "return"
_context << Instruction::JUMP;
_context << Instruction::POP;
_context << returnTag;
solAssert(_context.stackHeight() == stackHeightStart - 1, "");
}
);
+8 -4
View File
@@ -792,20 +792,24 @@ bool ExpressionCompiler::visit(FunctionCall const& _functionCall)
TypePointer const& argType = arguments.front()->annotation().type;
solAssert(argType, "");
arguments.front()->accept(*this);
// Optimization: If type is bytes or string, then do not encode,
// but directly compute keccak256 on memory.
if (*argType == *TypeProvider::bytesMemory() || *argType == *TypeProvider::stringMemory())
if (auto const* stringLiteral = dynamic_cast<StringLiteralType const*>(argType))
// Optimization: Compute keccak256 on string literals at compile-time.
m_context << u256(keccak256(stringLiteral->value()));
else if (*argType == *TypeProvider::bytesMemory() || *argType == *TypeProvider::stringMemory())
{
// Optimization: If type is bytes or string, then do not encode,
// but directly compute keccak256 on memory.
ArrayUtils(m_context).retrieveLength(*TypeProvider::bytesMemory());
m_context << Instruction::SWAP1 << u256(0x20) << Instruction::ADD;
m_context << Instruction::KECCAK256;
}
else
{
utils().fetchFreeMemoryPointer();
utils().packedEncode({argType}, TypePointers());
utils().toSizeAfterFreeMemoryPointer();
m_context << Instruction::KECCAK256;
}
m_context << Instruction::KECCAK256;
break;
}
case FunctionType::Kind::Log0:
@@ -1020,18 +1020,28 @@ void IRGeneratorForStatements::endVisit(FunctionCall const& _functionCall)
ArrayType const* arrayType = TypeProvider::bytesMemory();
auto array = convert(*arguments[0], *arrayType);
if (auto const* stringLiteral = dynamic_cast<StringLiteralType const*>(arguments.front()->annotation().type))
{
// Optimization: Compute keccak256 on string literals at compile-time.
define(_functionCall) <<
("0x" + keccak256(stringLiteral->value()).hex()) <<
"\n";
}
else
{
auto array = convert(*arguments[0], *arrayType);
define(_functionCall) <<
"keccak256(" <<
m_utils.arrayDataAreaFunction(*arrayType) <<
"(" <<
array.commaSeparatedList() <<
"), " <<
m_utils.arrayLengthFunction(*arrayType) <<
"(" <<
array.commaSeparatedList() <<
"))\n";
define(_functionCall) <<
"keccak256(" <<
m_utils.arrayDataAreaFunction(*arrayType) <<
"(" <<
array.commaSeparatedList() <<
"), " <<
m_utils.arrayLengthFunction(*arrayType) <<
"(" <<
array.commaSeparatedList() <<
"))\n";
}
break;
}
case FunctionType::Kind::ArrayPop: