diff options
-rw-r--r-- | libevmasm/PeepholeOptimiser.h | 1 | ||||
-rw-r--r-- | libsolidity/ast/ASTJsonConverter.cpp | 2 | ||||
-rw-r--r-- | libsolidity/ast/Types.cpp | 9 | ||||
-rw-r--r-- | libsolidity/ast/Types.h | 1 | ||||
-rw-r--r-- | libsolidity/codegen/CompilerUtils.cpp | 31 | ||||
-rw-r--r-- | libsolidity/codegen/CompilerUtils.h | 2 | ||||
-rw-r--r-- | libsolidity/interface/CompilerStack.cpp | 2 | ||||
-rw-r--r-- | test/libsolidity/SolidityEndToEndTest.cpp | 6 |
8 files changed, 33 insertions, 21 deletions
diff --git a/libevmasm/PeepholeOptimiser.h b/libevmasm/PeepholeOptimiser.h index dfc9a03b..372e49c5 100644 --- a/libevmasm/PeepholeOptimiser.h +++ b/libevmasm/PeepholeOptimiser.h @@ -22,6 +22,7 @@ #include <vector> #include <cstddef> +#include <iterator> namespace dev { diff --git a/libsolidity/ast/ASTJsonConverter.cpp b/libsolidity/ast/ASTJsonConverter.cpp index d6aca175..37dfd3c6 100644 --- a/libsolidity/ast/ASTJsonConverter.cpp +++ b/libsolidity/ast/ASTJsonConverter.cpp @@ -236,7 +236,7 @@ bool ASTJsonConverter::visit(FunctionTypeName const& _node) make_pair("payable", _node.isPayable()), make_pair("visibility", visibility), make_pair("constant", _node.isDeclaredConst()) - }); + }, true); return true; } diff --git a/libsolidity/ast/Types.cpp b/libsolidity/ast/Types.cpp index c1ae183e..3a8fc075 100644 --- a/libsolidity/ast/Types.cpp +++ b/libsolidity/ast/Types.cpp @@ -1930,6 +1930,12 @@ TypePointer FunctionType::unaryOperatorResult(Token::Value _operator) const return TypePointer(); } +string FunctionType::canonicalName(bool) const +{ + solAssert(m_location == Location::External, ""); + return "function"; +} + string FunctionType::toString(bool _short) const { string name = "function ("; @@ -2102,7 +2108,6 @@ TypePointer FunctionType::encodingType() const { // Only external functions can be encoded, internal functions cannot leave code boundaries. if (m_location == Location::External) - // This looks like bytes24, but bytes24 is stored differently on the stack. return shared_from_this(); else return TypePointer(); @@ -2111,7 +2116,7 @@ TypePointer FunctionType::encodingType() const TypePointer FunctionType::interfaceType(bool /*_inLibrary*/) const { if (m_location == Location::External) - return make_shared<FixedBytesType>(storageBytes()); + return shared_from_this(); else return TypePointer(); } diff --git a/libsolidity/ast/Types.h b/libsolidity/ast/Types.h index 84e56663..34fcfc82 100644 --- a/libsolidity/ast/Types.h +++ b/libsolidity/ast/Types.h @@ -897,6 +897,7 @@ public: virtual bool operator==(Type const& _other) const override; virtual TypePointer unaryOperatorResult(Token::Value _operator) const override; + virtual std::string canonicalName(bool /*_addDataLocation*/) const override; virtual std::string toString(bool _short) const override; virtual unsigned calldataEncodedSize(bool _padded) const override; virtual bool canBeStored() const override { return m_location == Location::Internal || m_location == Location::External; } diff --git a/libsolidity/codegen/CompilerUtils.cpp b/libsolidity/codegen/CompilerUtils.cpp index 1e21c020..1e819ed4 100644 --- a/libsolidity/codegen/CompilerUtils.cpp +++ b/libsolidity/codegen/CompilerUtils.cpp @@ -317,27 +317,32 @@ void CompilerUtils::memoryCopy() void CompilerUtils::splitExternalFunctionType(bool _leftAligned) { - // We have to split the left-aligned <function identifier><address> into two stack slots: + // We have to split the left-aligned <address><function identifier> into two stack slots: // address (right aligned), function identifier (right aligned) if (_leftAligned) - m_context << (u256(1) << 64) << Instruction::SWAP1 << Instruction::DIV; - m_context << Instruction::DUP1 << ((u256(1) << 160) - 1) << Instruction::AND << Instruction::SWAP1; - m_context << (u256(1) << 160) << Instruction::SWAP1 << Instruction::DIV; - if (!_leftAligned) - m_context << u256(0xffffffffUL) << Instruction::AND; + { + m_context << Instruction::DUP1 << (u256(1) << (64 + 32)) << Instruction::SWAP1 << Instruction::DIV; + // <input> <address> + m_context << Instruction::SWAP1 << (u256(1) << 64) << Instruction::SWAP1 << Instruction::DIV; + } + else + { + m_context << Instruction::DUP1 << (u256(1) << 32) << Instruction::SWAP1 << Instruction::DIV; + m_context << ((u256(1) << 160) - 1) << Instruction::AND << Instruction::SWAP1; + } + m_context << u256(0xffffffffUL) << Instruction::AND; } void CompilerUtils::combineExternalFunctionType(bool _leftAligned) { - if (_leftAligned) - m_context << (u256(1) << 224); - else - m_context << u256(0xffffffffUL) << Instruction::AND << (u256(1) << 160); - m_context << Instruction::MUL << Instruction::SWAP1; - m_context << ((u256(1) << 160) - 1) << Instruction::AND; + // <address> <function_id> + m_context << u256(0xffffffffUL) << Instruction::AND << Instruction::SWAP1; + if (!_leftAligned) + m_context << ((u256(1) << 160) - 1) << Instruction::AND; + m_context << (u256(1) << 32) << Instruction::MUL; + m_context << Instruction::OR; if (_leftAligned) m_context << (u256(1) << 64) << Instruction::MUL; - m_context << Instruction::OR; } void CompilerUtils::pushCombinedFunctionEntryLabel(Declaration const& _function) diff --git a/libsolidity/codegen/CompilerUtils.h b/libsolidity/codegen/CompilerUtils.h index 2ebec81a..8e4033d6 100644 --- a/libsolidity/codegen/CompilerUtils.h +++ b/libsolidity/codegen/CompilerUtils.h @@ -115,7 +115,7 @@ public: void memoryCopy(); /// Converts the combined and left-aligned (right-aligned if @a _rightAligned is true) - /// external function type <function identifier><address> into two stack slots: + /// external function type <address><function identifier> into two stack slots: /// address (right aligned), function identifier (right aligned) void splitExternalFunctionType(bool _rightAligned); /// Performs the opposite operation of splitExternalFunctionType(_rightAligned) diff --git a/libsolidity/interface/CompilerStack.cpp b/libsolidity/interface/CompilerStack.cpp index c86de43f..f1eb2614 100644 --- a/libsolidity/interface/CompilerStack.cpp +++ b/libsolidity/interface/CompilerStack.cpp @@ -597,7 +597,7 @@ void CompilerStack::compileContract( cloneCompiler.compileClone(_contract, _compiledContracts); compiledContract.cloneObject = cloneCompiler.assembledObject(); } - catch (eth::AssemblyException const& _e) + catch (eth::AssemblyException const&) { // In some cases (if the constructor requests a runtime function), it is not // possible to compile the clone. diff --git a/test/libsolidity/SolidityEndToEndTest.cpp b/test/libsolidity/SolidityEndToEndTest.cpp index c01d11d2..ed95d687 100644 --- a/test/libsolidity/SolidityEndToEndTest.cpp +++ b/test/libsolidity/SolidityEndToEndTest.cpp @@ -7703,8 +7703,8 @@ BOOST_AUTO_TEST_CASE(receive_external_function_type) compileAndRun(sourceCode, 0, "C"); BOOST_CHECK(callContractFunction( - "f(bytes24)", - FixedHash<4>(dev::keccak256("g()")).asBytes() + m_contractAddress.asBytes() + bytes(32 - 4 - 20, 0) + "f(function)", + m_contractAddress.asBytes() + FixedHash<4>(dev::keccak256("g()")).asBytes() + bytes(32 - 4 - 20, 0) ) == encodeArgs(u256(7))); } @@ -7722,7 +7722,7 @@ BOOST_AUTO_TEST_CASE(return_external_function_type) compileAndRun(sourceCode, 0, "C"); BOOST_CHECK( callContractFunction("f()") == - FixedHash<4>(dev::keccak256("g()")).asBytes() + m_contractAddress.asBytes() + bytes(32 - 4 - 20, 0) + m_contractAddress.asBytes() + FixedHash<4>(dev::keccak256("g()")).asBytes() + bytes(32 - 4 - 20, 0) ); } |