diff --git a/CMakeLists.txt b/CMakeLists.txt index 8d8430b5c..3336b4289 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -21,8 +21,7 @@ if(JSONRPC_LS) target_link_libraries(testeth web3jsonrpc) endif() if (EVMJIT) - target_link_libraries(testeth evm) - target_link_libraries(testeth evmjit) + target_link_libraries(testeth evmjit-cpp) endif() target_link_libraries(createRandomTest ethereum) @@ -30,8 +29,7 @@ target_link_libraries(createRandomTest ethcore) target_link_libraries(createRandomTest boost_chrono) target_link_libraries(createRandomTest boost_unit_test_framework) if (EVMJIT) - target_link_libraries(createRandomTest evm) - target_link_libraries(createRandomTest evmjit) + target_link_libraries(createRandomTest evmjit-cpp) endif() if ("${TARGET_PLATFORM}" STREQUAL "w64") diff --git a/TestHelper.cpp b/TestHelper.cpp index 1ece875ea..6f7bf31db 100644 --- a/TestHelper.cpp +++ b/TestHelper.cpp @@ -26,6 +26,7 @@ #include #include #include +#include using namespace std; using namespace dev::eth; @@ -72,7 +73,7 @@ ImportTest::ImportTest(json_spirit::mObject& _o, bool isFiller): m_TestObject(_o if (!isFiller) { importState(_o["post"].get_obj(), m_statePost); - m_environment.sub.logs = importLog(_o["logs"].get_obj()); + m_environment.sub.logs = importLog(_o["logs"].get_array()); } } @@ -259,16 +260,17 @@ bytes importCode(json_spirit::mObject& _o) return code; } -LogEntries importLog(json_spirit::mObject& _o) +LogEntries importLog(json_spirit::mArray& _a) { LogEntries logEntries; - for (auto const& l: _o) + for (auto const& l: _a) { - json_spirit::mObject o = l.second.get_obj(); + json_spirit::mObject o = l.get_obj(); // cant use BOOST_REQUIRE, because this function is used outside boost test (createRandomTest) assert(o.count("address") > 0); assert(o.count("topics") > 0); assert(o.count("data") > 0); + assert(o.count("bloom") > 0); LogEntry log; log.address = Address(o["address"].get_str()); for (auto const& t: o["topics"].get_array()) @@ -279,9 +281,9 @@ LogEntries importLog(json_spirit::mObject& _o) return logEntries; } -json_spirit::mObject exportLog(eth::LogEntries _logs) +json_spirit::mArray exportLog(eth::LogEntries _logs) { - json_spirit::mObject ret; + json_spirit::mArray ret; if (_logs.size() == 0) return ret; for (LogEntry const& l: _logs) { @@ -292,7 +294,8 @@ json_spirit::mObject exportLog(eth::LogEntries _logs) topics.push_back(toString(t)); o["topics"] = topics; o["data"] = "0x" + toHex(l.data); - ret[toString(l.bloom())] = o; + o["bloom"] = toString(l.bloom()); + ret.push_back(o); } return ret; } @@ -470,4 +473,20 @@ void executeTests(const string& _name, const string& _testPathAppendix, std::fun } } + +void processCommandLineOptions() +{ + auto argc = boost::unit_test::framework::master_test_suite().argc; + auto argv = boost::unit_test::framework::master_test_suite().argv; + + for (auto i = 0; i < argc; ++i) + { + if (std::string(argv[i]) == "--jit") + { + eth::VMFactory::setKind(eth::VMKind::JIT); + break; + } + } +} + } } // namespaces diff --git a/TestHelper.h b/TestHelper.h index c5c3a083d..20328c913 100644 --- a/TestHelper.h +++ b/TestHelper.h @@ -68,14 +68,15 @@ u256 toInt(json_spirit::mValue const& _v); byte toByte(json_spirit::mValue const& _v); bytes importCode(json_spirit::mObject& _o); bytes importData(json_spirit::mObject& _o); -eth::LogEntries importLog(json_spirit::mObject& _o); -json_spirit::mObject exportLog(eth::LogEntries _logs); +eth::LogEntries importLog(json_spirit::mArray& _o); +json_spirit::mArray exportLog(eth::LogEntries _logs); void checkOutput(bytes const& _output, json_spirit::mObject& _o); void checkStorage(std::map _expectedStore, std::map _resultStore, Address _expectedAddr); void checkLog(eth::LogEntries _resultLogs, eth::LogEntries _expectedLogs); void executeTests(const std::string& _name, const std::string& _testPathAppendix, std::function doTests); std::string getTestPath(); void userDefinedTest(std::string testTypeFlag, std::function doTests); +void processCommandLineOptions(); template void checkAddresses(mapType& _expectedAddrs, mapType& _resultAddrs) diff --git a/createRandomTest.cpp b/createRandomTest.cpp index 1647ce810..1af12f64d 100644 --- a/createRandomTest.cpp +++ b/createRandomTest.cpp @@ -1,18 +1,18 @@ /* - This file is part of cpp-ethereum. + This file is part of cpp-ethereum. - cpp-ethereum is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. - cpp-ethereum is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. + cpp-ethereum is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. - You should have received a copy of the GNU General Public License - along with cpp-ethereum. If not, see . + You should have received a copy of the GNU General Public License + along with cpp-ethereum. If not, see . */ /** @file createRandomTest.cpp * @author Christoph Jentzsch @@ -32,7 +32,7 @@ #include #include #include -#include +#include #include "vm.h" using namespace std; @@ -142,14 +142,14 @@ void doMyTests(json_spirit::mValue& v) } bytes output; - eth::VM vm(fev.gas); + auto vm = eth::VMFactory::create(fev.gas); u256 gas; bool vmExceptionOccured = false; try { - output = vm.go(fev, fev.simpleTrace()).toBytes(); - gas = vm.gas(); + output = vm->go(fev, fev.simpleTrace()).toBytes(); + gas = vm->gas(); } catch (eth::VMException const& _e) { @@ -189,7 +189,7 @@ void doMyTests(json_spirit::mValue& v) o["callcreates"] = fev.exportCallCreates(); o["out"] = "0x" + toHex(output); fev.push(o, "gas", gas); - o["logs"] = mValue(test::exportLog(fev.sub.logs)); + o["logs"] = test::exportLog(fev.sub.logs); } } } diff --git a/crypto.cpp b/crypto.cpp index 08236135a..466015ad7 100644 --- a/crypto.cpp +++ b/crypto.cpp @@ -44,6 +44,14 @@ static CryptoPP::OID s_curveOID(CryptoPP::ASN1::secp256k1()); static CryptoPP::DL_GroupParameters_EC s_params(s_curveOID); static CryptoPP::DL_GroupParameters_EC::EllipticCurve s_curve(s_params.GetCurve()); +BOOST_AUTO_TEST_CASE(cryptopp_patch) +{ + KeyPair k = KeyPair::create(); + bytes io_text; + s_secp256k1.decrypt(k.sec(), io_text); + BOOST_REQUIRE_EQUAL(io_text.size(), 0); +} + BOOST_AUTO_TEST_CASE(verify_secert) { h256 empty; diff --git a/genesis.cpp b/genesis.cpp index 6839d42e2..2cd9221a8 100644 --- a/genesis.cpp +++ b/genesis.cpp @@ -51,7 +51,7 @@ BOOST_AUTO_TEST_CASE(genesis_tests) BOOST_CHECK_EQUAL(BlockChain::genesis().stateRoot, h256(o["genesis_state_root"].get_str())); BOOST_CHECK_EQUAL(toHex(BlockChain::createGenesisBlock()), toHex(fromHex(o["genesis_rlp_hex"].get_str()))); - BOOST_CHECK_EQUAL(sha3(BlockChain::createGenesisBlock()), h256(o["genesis_hash"].get_str())); + BOOST_CHECK_EQUAL(BlockInfo::headerHash(BlockChain::createGenesisBlock()), h256(o["genesis_hash"].get_str())); } BOOST_AUTO_TEST_SUITE_END() diff --git a/jsonrpc.cpp b/jsonrpc.cpp index d17c5a594..20ffc6d54 100644 --- a/jsonrpc.cpp +++ b/jsonrpc.cpp @@ -19,7 +19,7 @@ * @date 2014 */ -#if ETH_JSONRPC +#if ETH_JSONRPC && 0 #include #include diff --git a/solidityCompiler.cpp b/solidityCompiler.cpp index 3e86919a6..004740b5e 100644 --- a/solidityCompiler.cpp +++ b/solidityCompiler.cpp @@ -46,16 +46,23 @@ namespace bytes compileContract(const string& _sourceCode) { Parser parser; - ASTPointer contract; - BOOST_REQUIRE_NO_THROW(contract = parser.parse(make_shared(CharStream(_sourceCode)))); + ASTPointer sourceUnit; + BOOST_REQUIRE_NO_THROW(sourceUnit = parser.parse(make_shared(CharStream(_sourceCode)))); NameAndTypeResolver resolver({}); - BOOST_REQUIRE_NO_THROW(resolver.resolveNamesAndTypes(*contract)); + resolver.registerDeclarations(*sourceUnit); + for (ASTPointer const& node: sourceUnit->getNodes()) + if (ContractDefinition* contract = dynamic_cast(node.get())) + { + BOOST_REQUIRE_NO_THROW(resolver.resolveNamesAndTypes(*contract)); - Compiler compiler; - compiler.compileContract(*contract, {}); - // debug - //compiler.streamAssembly(cout); - return compiler.getAssembledBytecode(); + Compiler compiler; + compiler.compileContract(*contract, {}); + // debug + //compiler.streamAssembly(cout); + return compiler.getAssembledBytecode(); + } + BOOST_FAIL("No contract found in source."); + return bytes(); } /// Checks that @a _compiledCode is present starting from offset @a _offset in @a _expectation. @@ -118,8 +125,8 @@ BOOST_AUTO_TEST_CASE(different_argument_numbers) byte(Instruction::JUMP), // end of f byte(Instruction::JUMPDEST), // beginning of g byte(Instruction::PUSH1), 0x0, - byte(Instruction::DUP1), // initialized e and h - byte(Instruction::PUSH1), byte(0x29 + shift), // ret address + byte(Instruction::PUSH1), 0x0, // initialized e and h + byte(Instruction::PUSH1), byte(0x2a + shift), // ret address byte(Instruction::PUSH1), 0x1, byte(Instruction::PUSH1), 0xff, byte(Instruction::AND), byte(Instruction::PUSH1), 0x2, byte(Instruction::PUSH1), 0xff, byte(Instruction::AND), byte(Instruction::PUSH1), 0x3, byte(Instruction::PUSH1), 0xff, byte(Instruction::AND), diff --git a/solidityEndToEndTest.cpp b/solidityEndToEndTest.cpp index 8b25d4031..3c77492a5 100644 --- a/solidityEndToEndTest.cpp +++ b/solidityEndToEndTest.cpp @@ -24,132 +24,18 @@ #include #include #include -#include -#include -#include #include +#include using namespace std; namespace dev { -/// Provides additional overloads for toBigEndian to encode arguments and return values. -inline bytes toBigEndian(byte _value) { return bytes({_value}); } -inline bytes toBigEndian(bool _value) { return bytes({byte(_value)}); } - namespace solidity { namespace test { -class ExecutionFramework -{ -public: - ExecutionFramework() { g_logVerbosity = 0; } - - bytes const& compileAndRun(string const& _sourceCode, u256 const& _value = 0) - { - bytes code = dev::solidity::CompilerStack::staticCompile(_sourceCode); - sendMessage(code, true, _value); - BOOST_REQUIRE(!m_output.empty()); - return m_output; - } - - bytes const& callContractFunction(byte _index, bytes const& _data = bytes(), u256 const& _value = 0) - { - sendMessage(bytes(1, _index) + _data, false, _value); - return m_output; - } - - template - bytes const& callContractFunction(byte _index, Args const&... _arguments) - { - return callContractFunction(_index, argsToBigEndian(_arguments...)); - } - - template - void testSolidityAgainstCpp(byte _index, CppFunction const& _cppFunction, Args const&... _arguments) - { - bytes solidityResult = callContractFunction(_index, _arguments...); - bytes cppResult = callCppAndEncodeResult(_cppFunction, _arguments...); - BOOST_CHECK_MESSAGE(solidityResult == cppResult, "Computed values do not match." - "\nSolidity: " + toHex(solidityResult) + "\nC++: " + toHex(cppResult)); - } - - template - void testSolidityAgainstCppOnRange(byte _index, CppFunction const& _cppFunction, - u256 const& _rangeStart, u256 const& _rangeEnd) - { - for (u256 argument = _rangeStart; argument < _rangeEnd; ++argument) - { - bytes solidityResult = callContractFunction(_index, argument); - bytes cppResult = callCppAndEncodeResult(_cppFunction, argument); - BOOST_CHECK_MESSAGE(solidityResult == cppResult, "Computed values do not match." - "\nSolidity: " + toHex(solidityResult) + "\nC++: " + toHex(cppResult) + - "\nArgument: " + toHex(toBigEndian(argument))); - } - } - -private: - template - bytes argsToBigEndian(FirstArg const& _firstArg, Args const&... _followingArgs) const - { - return toBigEndian(_firstArg) + argsToBigEndian(_followingArgs...); - } - - bytes argsToBigEndian() const { return bytes(); } - - template - auto callCppAndEncodeResult(CppFunction const& _cppFunction, Args const&... _arguments) - -> typename enable_if::value, bytes>::type - { - _cppFunction(_arguments...); - return bytes(); - } - template - auto callCppAndEncodeResult(CppFunction const& _cppFunction, Args const&... _arguments) - -> typename enable_if::value, bytes>::type - { - return toBigEndian(_cppFunction(_arguments...)); - } - - void sendMessage(bytes const& _data, bool _isCreation, u256 const& _value = 0) - { - eth::Executive executive(m_state); - eth::Transaction t = _isCreation ? eth::Transaction(_value, m_gasPrice, m_gas, _data, 0, KeyPair::create().sec()) - : eth::Transaction(_value, m_gasPrice, m_gas, m_contractAddress, _data, 0, KeyPair::create().sec()); - bytes transactionRLP = t.rlp(); - try - { - // this will throw since the transaction is invalid, but it should nevertheless store the transaction - executive.setup(&transactionRLP); - } - catch (...) {} - if (_isCreation) - { - BOOST_REQUIRE(!executive.create(Address(), _value, m_gasPrice, m_gas, &_data, Address())); - m_contractAddress = executive.newAddress(); - BOOST_REQUIRE(m_contractAddress); - BOOST_REQUIRE(m_state.addressHasCode(m_contractAddress)); - } - else - { - BOOST_REQUIRE(m_state.addressHasCode(m_contractAddress)); - BOOST_REQUIRE(!executive.call(m_contractAddress, Address(), _value, m_gasPrice, &_data, m_gas, Address())); - } - BOOST_REQUIRE(executive.go()); - executive.finalize(); - m_output = executive.out().toVector(); - } - -protected: - Address m_contractAddress; - eth::State m_state; - u256 const m_gasPrice = 100 * eth::szabo; - u256 const m_gas = 1000000; - bytes m_output; -}; - BOOST_FIXTURE_TEST_SUITE(SolidityCompilerEndToEndTest, ExecutionFramework) BOOST_AUTO_TEST_CASE(smoke_test) @@ -898,6 +784,163 @@ BOOST_AUTO_TEST_CASE(ecrecover) BOOST_CHECK(callContractFunction(0, h, v, r, s) == toBigEndian(addr)); } +BOOST_AUTO_TEST_CASE(inter_contract_calls) +{ + char const* sourceCode = R"( + contract Helper { + function multiply(uint a, uint b) returns (uint c) { + return a * b; + } + } + contract Main { + Helper h; + function callHelper(uint a, uint b) returns (uint c) { + return h.multiply(a, b); + } + function getHelper() returns (address haddress) { + return address(h); + } + function setHelper(address haddress) { + h = Helper(haddress); + } + })"; + compileAndRun(sourceCode, 0, "Helper"); + u160 const helperAddress = m_contractAddress; + compileAndRun(sourceCode, 0, "Main"); + BOOST_REQUIRE(callContractFunction(2, helperAddress) == bytes()); + BOOST_REQUIRE(callContractFunction(1, helperAddress) == toBigEndian(helperAddress)); + u256 a(3456789); + u256 b("0x282837623374623234aa74"); + BOOST_REQUIRE(callContractFunction(0, a, b) == toBigEndian(a * b)); +} + +BOOST_AUTO_TEST_CASE(inter_contract_calls_with_complex_parameters) +{ + char const* sourceCode = R"( + contract Helper { + function sel(uint a, bool select, uint b) returns (uint c) { + if (select) return a; else return b; + } + } + contract Main { + Helper h; + function callHelper(uint a, bool select, uint b) returns (uint c) { + return h.sel(a, select, b) * 3; + } + function getHelper() returns (address haddress) { + return address(h); + } + function setHelper(address haddress) { + h = Helper(haddress); + } + })"; + compileAndRun(sourceCode, 0, "Helper"); + u160 const helperAddress = m_contractAddress; + compileAndRun(sourceCode, 0, "Main"); + BOOST_REQUIRE(callContractFunction(2, helperAddress) == bytes()); + BOOST_REQUIRE(callContractFunction(1, helperAddress) == toBigEndian(helperAddress)); + u256 a(3456789); + u256 b("0x282837623374623234aa74"); + BOOST_REQUIRE(callContractFunction(0, a, true, b) == toBigEndian(a * 3)); + BOOST_REQUIRE(callContractFunction(0, a, false, b) == toBigEndian(b * 3)); +} + +BOOST_AUTO_TEST_CASE(inter_contract_calls_accessing_this) +{ + char const* sourceCode = R"( + contract Helper { + function getAddress() returns (address addr) { + return address(this); + } + } + contract Main { + Helper h; + function callHelper() returns (address addr) { + return h.getAddress(); + } + function getHelper() returns (address addr) { + return address(h); + } + function setHelper(address addr) { + h = Helper(addr); + } + })"; + compileAndRun(sourceCode, 0, "Helper"); + u160 const helperAddress = m_contractAddress; + compileAndRun(sourceCode, 0, "Main"); + BOOST_REQUIRE(callContractFunction(2, helperAddress) == bytes()); + BOOST_REQUIRE(callContractFunction(1, helperAddress) == toBigEndian(helperAddress)); + BOOST_REQUIRE(callContractFunction(0) == toBigEndian(helperAddress)); +} + +BOOST_AUTO_TEST_CASE(calls_to_this) +{ + char const* sourceCode = R"( + contract Helper { + function invoke(uint a, uint b) returns (uint c) { + return this.multiply(a, b, 10); + } + function multiply(uint a, uint b, uint8 c) returns (uint ret) { + return a * b + c; + } + } + contract Main { + Helper h; + function callHelper(uint a, uint b) returns (uint ret) { + return h.invoke(a, b); + } + function getHelper() returns (address addr) { + return address(h); + } + function setHelper(address addr) { + h = Helper(addr); + } + })"; + compileAndRun(sourceCode, 0, "Helper"); + u160 const helperAddress = m_contractAddress; + compileAndRun(sourceCode, 0, "Main"); + BOOST_REQUIRE(callContractFunction(2, helperAddress) == bytes()); + BOOST_REQUIRE(callContractFunction(1, helperAddress) == toBigEndian(helperAddress)); + u256 a(3456789); + u256 b("0x282837623374623234aa74"); + BOOST_REQUIRE(callContractFunction(0, a, b) == toBigEndian(a * b + 10)); +} + +BOOST_AUTO_TEST_CASE(inter_contract_calls_with_local_vars) +{ + // note that a reference to another contract's function occupies two stack slots, + // so this tests correct stack slot allocation + char const* sourceCode = R"( + contract Helper { + function multiply(uint a, uint b) returns (uint c) { + return a * b; + } + } + contract Main { + Helper h; + function callHelper(uint a, uint b) returns (uint c) { + var fu = h.multiply; + var y = 9; + var ret = fu(a, b); + return ret + y; + } + function getHelper() returns (address haddress) { + return address(h); + } + function setHelper(address haddress) { + h = Helper(haddress); + } + })"; + compileAndRun(sourceCode, 0, "Helper"); + u160 const helperAddress = m_contractAddress; + compileAndRun(sourceCode, 0, "Main"); + BOOST_REQUIRE(callContractFunction(2, helperAddress) == bytes()); + BOOST_REQUIRE(callContractFunction(1, helperAddress) == toBigEndian(helperAddress)); + u256 a(3456789); + u256 b("0x282837623374623234aa74"); + BOOST_REQUIRE(callContractFunction(0, a, b) == toBigEndian(a * b + 9)); +} + BOOST_AUTO_TEST_SUITE_END() } diff --git a/solidityExecutionFramework.h b/solidityExecutionFramework.h new file mode 100644 index 000000000..9d40e8a46 --- /dev/null +++ b/solidityExecutionFramework.h @@ -0,0 +1,161 @@ + +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + cpp-ethereum is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with cpp-ethereum. If not, see . +*/ +/** + * @author Christian + * @date 2014 + * Framework for executing Solidity contracts and testing them against C++ implementation. + */ + +#pragma once + +#include +#include +#include +#include +#include +#include + +namespace dev +{ +/// Provides additional overloads for toBigEndian to encode arguments and return values. +inline bytes toBigEndian(byte _value) { return bytes({_value}); } +inline bytes toBigEndian(bool _value) { return bytes({byte(_value)}); } + +namespace solidity +{ +namespace test +{ + +class ExecutionFramework +{ +public: + ExecutionFramework() { g_logVerbosity = 0; } + + bytes const& compileAndRun(std::string const& _sourceCode, u256 const& _value = 0, std::string const& _contractName = "") + { + dev::solidity::CompilerStack compiler; + compiler.compile(_sourceCode, m_optimize); + bytes code = compiler.getBytecode(_contractName); + sendMessage(code, true, _value); + BOOST_REQUIRE(!m_output.empty()); + return m_output; + } + + bytes const& callContractFunction(byte _index, bytes const& _data = bytes(), u256 const& _value = 0) + { + sendMessage(bytes(1, _index) + _data, false, _value); + return m_output; + } + + template + bytes const& callContractFunction(byte _index, Args const&... _arguments) + { + return callContractFunction(_index, argsToBigEndian(_arguments...)); + } + + template + void testSolidityAgainstCpp(byte _index, CppFunction const& _cppFunction, Args const&... _arguments) + { + bytes solidityResult = callContractFunction(_index, _arguments...); + bytes cppResult = callCppAndEncodeResult(_cppFunction, _arguments...); + BOOST_CHECK_MESSAGE(solidityResult == cppResult, "Computed values do not match." + "\nSolidity: " + toHex(solidityResult) + "\nC++: " + toHex(cppResult)); + } + + template + void testSolidityAgainstCppOnRange(byte _index, CppFunction const& _cppFunction, + u256 const& _rangeStart, u256 const& _rangeEnd) + { + for (u256 argument = _rangeStart; argument < _rangeEnd; ++argument) + { + bytes solidityResult = callContractFunction(_index, argument); + bytes cppResult = callCppAndEncodeResult(_cppFunction, argument); + BOOST_CHECK_MESSAGE(solidityResult == cppResult, "Computed values do not match." + "\nSolidity: " + toHex(solidityResult) + "\nC++: " + toHex(cppResult) + + "\nArgument: " + toHex(toBigEndian(argument))); + } + } + +private: + template + bytes argsToBigEndian(FirstArg const& _firstArg, Args const&... _followingArgs) const + { + return toBigEndian(_firstArg) + argsToBigEndian(_followingArgs...); + } + + bytes argsToBigEndian() const { return bytes(); } + + template + auto callCppAndEncodeResult(CppFunction const& _cppFunction, Args const&... _arguments) + -> typename std::enable_if::value, bytes>::type + { + _cppFunction(_arguments...); + return bytes(); + } + template + auto callCppAndEncodeResult(CppFunction const& _cppFunction, Args const&... _arguments) + -> typename std::enable_if::value, bytes>::type + { + return toBigEndian(_cppFunction(_arguments...)); + } + + void sendMessage(bytes const& _data, bool _isCreation, u256 const& _value = 0) + { + m_state.addBalance(m_sender, _value); // just in case + eth::Executive executive(m_state); + eth::Transaction t = _isCreation ? eth::Transaction(_value, m_gasPrice, m_gas, _data, 0, KeyPair::create().sec()) + : eth::Transaction(_value, m_gasPrice, m_gas, m_contractAddress, _data, 0, KeyPair::create().sec()); + bytes transactionRLP = t.rlp(); + try + { + // this will throw since the transaction is invalid, but it should nevertheless store the transaction + executive.setup(&transactionRLP); + } + catch (...) {} + if (_isCreation) + { + BOOST_REQUIRE(!executive.create(m_sender, _value, m_gasPrice, m_gas, &_data, m_sender)); + m_contractAddress = executive.newAddress(); + BOOST_REQUIRE(m_contractAddress); + BOOST_REQUIRE(m_state.addressHasCode(m_contractAddress)); + } + else + { + BOOST_REQUIRE(m_state.addressHasCode(m_contractAddress)); + BOOST_REQUIRE(!executive.call(m_contractAddress, m_sender, _value, m_gasPrice, &_data, m_gas, m_sender)); + } + BOOST_REQUIRE(executive.go()); + m_state.noteSending(m_sender); + executive.finalize(); + m_output = executive.out().toVector(); + } + +protected: + bool m_optimize = false; + Address m_sender; + Address m_contractAddress; + eth::State m_state; + u256 const m_gasPrice = 100 * eth::szabo; + u256 const m_gas = 1000000; + bytes m_output; +}; + +} +} +} // end namespaces + diff --git a/solidityExpressionCompiler.cpp b/solidityExpressionCompiler.cpp index 6ea66badb..486b46ebb 100644 --- a/solidityExpressionCompiler.cpp +++ b/solidityExpressionCompiler.cpp @@ -86,27 +86,34 @@ bytes compileFirstExpression(const string& _sourceCode, vector> _ vector> _localVariables = {}) { Parser parser; - ASTPointer contract; - BOOST_REQUIRE_NO_THROW(contract = parser.parse(make_shared(CharStream(_sourceCode)))); + ASTPointer sourceUnit; + BOOST_REQUIRE_NO_THROW(sourceUnit = parser.parse(make_shared(CharStream(_sourceCode)))); NameAndTypeResolver resolver({}); - BOOST_REQUIRE_NO_THROW(resolver.resolveNamesAndTypes(*contract)); - FirstExpressionExtractor extractor(*contract); - BOOST_REQUIRE(extractor.getExpression() != nullptr); + resolver.registerDeclarations(*sourceUnit); + for (ASTPointer const& node: sourceUnit->getNodes()) + if (ContractDefinition* contract = dynamic_cast(node.get())) + { + BOOST_REQUIRE_NO_THROW(resolver.resolveNamesAndTypes(*contract)); + FirstExpressionExtractor extractor(*contract); + BOOST_REQUIRE(extractor.getExpression() != nullptr); - CompilerContext context; - for (vector const& function: _functions) - context.addFunction(dynamic_cast(resolveDeclaration(function, resolver))); - for (vector const& variable: _localVariables) - context.addVariable(dynamic_cast(resolveDeclaration(variable, resolver))); + CompilerContext context; + for (vector const& function: _functions) + context.addFunction(dynamic_cast(resolveDeclaration(function, resolver))); + for (vector const& variable: _localVariables) + context.addVariable(dynamic_cast(resolveDeclaration(variable, resolver))); - ExpressionCompiler::compileExpression(context, *extractor.getExpression()); + ExpressionCompiler::compileExpression(context, *extractor.getExpression()); - for (vector const& function: _functions) - context << context.getFunctionEntryLabel(dynamic_cast(resolveDeclaration(function, resolver))); - bytes instructions = context.getAssembledBytecode(); - // debug - // cout << eth::disassemble(instructions) << endl; - return instructions; + for (vector const& function: _functions) + context << context.getFunctionEntryLabel(dynamic_cast(resolveDeclaration(function, resolver))); + bytes instructions = context.getAssembledBytecode(); + // debug + // cout << eth::disassemble(instructions) << endl; + return instructions; + } + BOOST_FAIL("No contract found in source."); + return bytes(); } } // end anonymous namespace diff --git a/solidityJSONInterfaceTest.cpp b/solidityJSONInterfaceTest.cpp index 1a443087f..487508bb9 100644 --- a/solidityJSONInterfaceTest.cpp +++ b/solidityJSONInterfaceTest.cpp @@ -23,6 +23,7 @@ #include #include #include +#include namespace dev { @@ -34,23 +35,37 @@ namespace test class InterfaceChecker { public: - bool checkInterface(std::string const& _code, std::string const& _expectedInterfaceString) + void checkInterface(std::string const& _code, std::string const& _expectedInterfaceString) { - m_compilerStack.parse(_code); - std::string generatedInterfaceString = m_compilerStack.getInterface(); + try + { + m_compilerStack.parse(_code); + } + catch (const std::exception& e) + { + std::string const* extra = boost::get_error_info(e); + std::string msg = std::string("Parsing contract failed with: ") + + e.what() + std::string("\n"); + if (extra) + msg += *extra; + BOOST_FAIL(msg); + } + std::string generatedInterfaceString = m_compilerStack.getJsonDocumentation("", DocumentationType::ABI_INTERFACE); Json::Value generatedInterface; m_reader.parse(generatedInterfaceString, generatedInterface); Json::Value expectedInterface; m_reader.parse(_expectedInterfaceString, expectedInterface); - return expectedInterface == generatedInterface; + BOOST_CHECK_MESSAGE(expectedInterface == generatedInterface, + "Expected " << _expectedInterfaceString << + "\n but got:\n" << generatedInterfaceString); } - + private: CompilerStack m_compilerStack; Json::Reader m_reader; }; -BOOST_FIXTURE_TEST_SUITE(SolidityCompilerJSONInterfaceOutput, InterfaceChecker) +BOOST_FIXTURE_TEST_SUITE(SolidityABIJSON, InterfaceChecker) BOOST_AUTO_TEST_CASE(basic_test) { @@ -76,7 +91,7 @@ BOOST_AUTO_TEST_CASE(basic_test) } ])"; - BOOST_CHECK(checkInterface(sourceCode, interface)); + checkInterface(sourceCode, interface); } BOOST_AUTO_TEST_CASE(empty_contract) @@ -86,7 +101,7 @@ BOOST_AUTO_TEST_CASE(empty_contract) char const* interface = "[]"; - BOOST_CHECK(checkInterface(sourceCode, interface)); + checkInterface(sourceCode, interface); } BOOST_AUTO_TEST_CASE(multiple_methods) @@ -95,7 +110,7 @@ BOOST_AUTO_TEST_CASE(multiple_methods) " function f(uint a) returns(uint d) { return a * 7; }\n" " function g(uint b) returns(uint e) { return b * 8; }\n" "}\n"; - + char const* interface = R"([ { "name": "f", @@ -129,7 +144,7 @@ BOOST_AUTO_TEST_CASE(multiple_methods) } ])"; - BOOST_CHECK(checkInterface(sourceCode, interface)); + checkInterface(sourceCode, interface); } BOOST_AUTO_TEST_CASE(multiple_params) @@ -160,7 +175,7 @@ BOOST_AUTO_TEST_CASE(multiple_params) } ])"; - BOOST_CHECK(checkInterface(sourceCode, interface)); + checkInterface(sourceCode, interface); } BOOST_AUTO_TEST_CASE(multiple_methods_order) @@ -170,7 +185,7 @@ BOOST_AUTO_TEST_CASE(multiple_methods_order) " function f(uint a) returns(uint d) { return a * 7; }\n" " function c(uint b) returns(uint e) { return b * 8; }\n" "}\n"; - + char const* interface = R"([ { "name": "c", @@ -203,8 +218,8 @@ BOOST_AUTO_TEST_CASE(multiple_methods_order) ] } ])"; - - BOOST_CHECK(checkInterface(sourceCode, interface)); + + checkInterface(sourceCode, interface); } BOOST_AUTO_TEST_SUITE_END() diff --git a/solidityNameAndTypeResolution.cpp b/solidityNameAndTypeResolution.cpp index 8804c519c..783972296 100644 --- a/solidityNameAndTypeResolution.cpp +++ b/solidityNameAndTypeResolution.cpp @@ -41,10 +41,12 @@ namespace void parseTextAndResolveNames(std::string const& _source) { Parser parser; - ASTPointer contract = parser.parse( - std::make_shared(CharStream(_source))); + ASTPointer sourceUnit = parser.parse(std::make_shared(CharStream(_source))); NameAndTypeResolver resolver({}); - resolver.resolveNamesAndTypes(*contract); + resolver.registerDeclarations(*sourceUnit); + for (ASTPointer const& node: sourceUnit->getNodes()) + if (ContractDefinition* contract = dynamic_cast(node.get())) + resolver.resolveNamesAndTypes(*contract); } } diff --git a/solidityNatspecJSON.cpp b/solidityNatspecJSON.cpp new file mode 100644 index 000000000..641bb82ab --- /dev/null +++ b/solidityNatspecJSON.cpp @@ -0,0 +1,488 @@ +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + cpp-ethereum is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with cpp-ethereum. If not, see . + */ +/** + * @author Lefteris Karapetsas + * @date 2014 + * Unit tests for the solidity compiler JSON Interface output. + */ + +#include +#include +#include +#include +#include + +namespace dev +{ +namespace solidity +{ +namespace test +{ + +class DocumentationChecker +{ +public: + void checkNatspec(std::string const& _code, + std::string const& _expectedDocumentationString, + bool _userDocumentation) + { + std::string generatedDocumentationString; + try + { + m_compilerStack.parse(_code); + } + catch (const std::exception& e) + { + std::string const* extra = boost::get_error_info(e); + std::string msg = std::string("Parsing contract failed with: ") + + e.what() + std::string("\n"); + if (extra) + msg += *extra; + BOOST_FAIL(msg); + } + + if (_userDocumentation) + generatedDocumentationString = m_compilerStack.getJsonDocumentation("", DocumentationType::NATSPEC_USER); + else + generatedDocumentationString = m_compilerStack.getJsonDocumentation("", DocumentationType::NATSPEC_DEV); + Json::Value generatedDocumentation; + m_reader.parse(generatedDocumentationString, generatedDocumentation); + Json::Value expectedDocumentation; + m_reader.parse(_expectedDocumentationString, expectedDocumentation); + BOOST_CHECK_MESSAGE(expectedDocumentation == generatedDocumentation, + "Expected " << _expectedDocumentationString << + "\n but got:\n" << generatedDocumentationString); + } + +private: + CompilerStack m_compilerStack; + Json::Reader m_reader; +}; + +BOOST_FIXTURE_TEST_SUITE(SolidityNatspecJSON, DocumentationChecker) + +BOOST_AUTO_TEST_CASE(user_basic_test) +{ + char const* sourceCode = "contract test {\n" + " /// @notice Multiplies `a` by 7\n" + " function mul(uint a) returns(uint d) { return a * 7; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \"notice\": \"Multiplies `a` by 7\"}" + "}}"; + + checkNatspec(sourceCode, natspec, true); +} + +BOOST_AUTO_TEST_CASE(dev_and_user_basic_test) +{ + char const* sourceCode = "contract test {\n" + " /// @notice Multiplies `a` by 7\n" + " /// @dev Multiplies a number by 7\n" + " function mul(uint a) returns(uint d) { return a * 7; }\n" + "}\n"; + + char const* devNatspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7\"\n" + " }\n" + " }\n" + "}}"; + + char const* userNatspec = "{" + "\"methods\":{" + " \"mul\":{ \"notice\": \"Multiplies `a` by 7\"}" + "}}"; + + checkNatspec(sourceCode, devNatspec, false); + checkNatspec(sourceCode, userNatspec, true); +} + +BOOST_AUTO_TEST_CASE(user_multiline_comment) +{ + char const* sourceCode = "contract test {\n" + " /// @notice Multiplies `a` by 7\n" + " /// and then adds `b`\n" + " function mul_and_add(uint a, uint256 b) returns(uint256 d)\n" + " {\n" + " return (a * 7) + b;\n" + " }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul_and_add\":{ \"notice\": \"Multiplies `a` by 7 and then adds `b`\"}" + "}}"; + + checkNatspec(sourceCode, natspec, true); +} + +BOOST_AUTO_TEST_CASE(user_multiple_functions) +{ + char const* sourceCode = "contract test {\n" + " /// @notice Multiplies `a` by 7 and then adds `b`\n" + " function mul_and_add(uint a, uint256 b) returns(uint256 d)\n" + " {\n" + " return (a * 7) + b;\n" + " }\n" + "\n" + " /// @notice Divides `input` by `div`\n" + " function divide(uint input, uint div) returns(uint d)\n" + " {\n" + " return input / div;\n" + " }\n" + " /// @notice Subtracts 3 from `input`\n" + " function sub(int input) returns(int d)\n" + " {\n" + " return input - 3;\n" + " }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul_and_add\":{ \"notice\": \"Multiplies `a` by 7 and then adds `b`\"}," + " \"divide\":{ \"notice\": \"Divides `input` by `div`\"}," + " \"sub\":{ \"notice\": \"Subtracts 3 from `input`\"}" + "}}"; + + checkNatspec(sourceCode, natspec, true); +} + +BOOST_AUTO_TEST_CASE(user_empty_contract) +{ + char const* sourceCode = "contract test {\n" + "}\n"; + + char const* natspec = "{\"methods\":{} }"; + + checkNatspec(sourceCode, natspec, true); +} + +BOOST_AUTO_TEST_CASE(dev_and_user_no_doc) +{ + char const* sourceCode = "contract test {\n" + " function mul(uint a) returns(uint d) { return a * 7; }\n" + " function sub(int input) returns(int d)\n" + " {\n" + " return input - 3;\n" + " }\n" + "}\n"; + + char const* devNatspec = "{\"methods\":{}}"; + + char const* userNatspec = "{\"methods\":{}}"; + + checkNatspec(sourceCode, devNatspec, false); + checkNatspec(sourceCode, userNatspec, true); +} + +BOOST_AUTO_TEST_CASE(dev_desc_after_nl) +{ + char const* sourceCode = "contract test {\n" + " /// @dev\n" + " /// Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter\n" + " /// @param second Documentation for the second parameter\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \" Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " }\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_multiple_params) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter\n" + " /// @param second Documentation for the second parameter\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " }\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_mutiline_param_description) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter starts here.\n" + " /// Since it's a really complicated parameter we need 2 lines\n" + " /// @param second Documentation for the second parameter\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter starts here. Since it's a really complicated parameter we need 2 lines\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " }\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_multiple_functions) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter\n" + " /// @param second Documentation for the second parameter\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + " \n" + " /// @dev Divides 2 numbers\n" + " /// @param input Documentation for the input parameter\n" + " /// @param div Documentation for the div parameter\n" + " function divide(uint input, uint div) returns(uint d)\n" + " {\n" + " return input / div;\n" + " }\n" + " /// @dev Subtracts 3 from `input`\n" + " /// @param input Documentation for the input parameter\n" + " function sub(int input) returns(int d)\n" + " {\n" + " return input - 3;\n" + " }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " }\n" + " },\n" + " \"divide\":{ \n" + " \"details\": \"Divides 2 numbers\",\n" + " \"params\": {\n" + " \"input\": \"Documentation for the input parameter\",\n" + " \"div\": \"Documentation for the div parameter\"\n" + " }\n" + " },\n" + " \"sub\":{ \n" + " \"details\": \"Subtracts 3 from `input`\",\n" + " \"params\": {\n" + " \"input\": \"Documentation for the input parameter\"\n" + " }\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_return) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter starts here.\n" + " /// Since it's a really complicated parameter we need 2 lines\n" + " /// @param second Documentation for the second parameter\n" + " /// @return The result of the multiplication\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter starts here. Since it's a really complicated parameter we need 2 lines\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " },\n" + " \"return\": \"The result of the multiplication\"\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} +BOOST_AUTO_TEST_CASE(dev_return_desc_after_nl) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter starts here.\n" + " /// Since it's a really complicated parameter we need 2 lines\n" + " /// @param second Documentation for the second parameter\n" + " /// @return\n" + " /// The result of the multiplication\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter starts here. Since it's a really complicated parameter we need 2 lines\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " },\n" + " \"return\": \" The result of the multiplication\"\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + + +BOOST_AUTO_TEST_CASE(dev_multiline_return) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Multiplies a number by 7 and adds second parameter\n" + " /// @param a Documentation for the first parameter starts here.\n" + " /// Since it's a really complicated parameter we need 2 lines\n" + " /// @param second Documentation for the second parameter\n" + " /// @return The result of the multiplication\n" + " /// and cookies with nutella\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + "\"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Multiplies a number by 7 and adds second parameter\",\n" + " \"params\": {\n" + " \"a\": \"Documentation for the first parameter starts here. Since it's a really complicated parameter we need 2 lines\",\n" + " \"second\": \"Documentation for the second parameter\"\n" + " },\n" + " \"return\": \"The result of the multiplication and cookies with nutella\"\n" + " }\n" + "}}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_contract_no_doc) +{ + char const* sourceCode = "contract test {\n" + " /// @dev Mul function\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + " \"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Mul function\"\n" + " }\n" + " }\n" + "}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_contract_doc) +{ + char const* sourceCode = " /// @author Lefteris\n" + " /// @title Just a test contract\n" + "contract test {\n" + " /// @dev Mul function\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + " \"author\": \"Lefteris\"," + " \"title\": \"Just a test contract\"," + " \"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Mul function\"\n" + " }\n" + " }\n" + "}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_author_at_function) +{ + char const* sourceCode = " /// @author Lefteris\n" + " /// @title Just a test contract\n" + "contract test {\n" + " /// @dev Mul function\n" + " /// @author John Doe\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + " \"author\": \"Lefteris\"," + " \"title\": \"Just a test contract\"," + " \"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Mul function\",\n" + " \"author\": \"John Doe\",\n" + " }\n" + " }\n" + "}"; + + checkNatspec(sourceCode, natspec, false); +} + +BOOST_AUTO_TEST_CASE(dev_title_at_function_error) +{ + char const* sourceCode = " /// @author Lefteris\n" + " /// @title Just a test contract\n" + "contract test {\n" + " /// @dev Mul function\n" + " /// @title I really should not be here\n" + " function mul(uint a, uint second) returns(uint d) { return a * 7 + second; }\n" + "}\n"; + + char const* natspec = "{" + " \"author\": \"Lefteris\"," + " \"title\": \"Just a test contract\"," + " \"methods\":{" + " \"mul\":{ \n" + " \"details\": \"Mul function\"\n" + " }\n" + " }\n" + "}"; + + BOOST_CHECK_THROW(checkNatspec(sourceCode, natspec, false), DocstringParsingError); +} + +BOOST_AUTO_TEST_SUITE_END() + +} +} +} diff --git a/solidityOptimizerTest.cpp b/solidityOptimizerTest.cpp new file mode 100644 index 000000000..b689fe54e --- /dev/null +++ b/solidityOptimizerTest.cpp @@ -0,0 +1,131 @@ + +/* + This file is part of cpp-ethereum. + + cpp-ethereum is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + cpp-ethereum is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with cpp-ethereum. If not, see . +*/ +/** + * @author Christian + * @date 2014 + * Tests for the Solidity optimizer. + */ + +#include +#include +#include +#include +#include + +using namespace std; + +namespace dev +{ +namespace solidity +{ +namespace test +{ + +class OptimizerTestFramework: public ExecutionFramework +{ +public: + OptimizerTestFramework() { } + /// Compiles the source code with and without optimizing. + void compileBothVersions(unsigned _expectedSizeDecrease, std::string const& _sourceCode, u256 const& _value = 0, std::string const& _contractName = "") { + m_optimize = false; + bytes nonOptimizedBytecode = compileAndRun(_sourceCode, _value, _contractName); + m_nonOptimizedContract = m_contractAddress; + m_optimize = true; + bytes optimizedBytecode = compileAndRun(_sourceCode, _value, _contractName); + int sizeDiff = nonOptimizedBytecode.size() - optimizedBytecode.size(); + BOOST_CHECK_MESSAGE(sizeDiff >= (int)_expectedSizeDecrease, "Bytecode did only shrink by " + + boost::lexical_cast(sizeDiff) + " bytes, expected: " + + boost::lexical_cast(_expectedSizeDecrease)); + m_optimizedContract = m_contractAddress; + } + + template + void compareVersions(byte _index, Args const&... _arguments) + { + m_contractAddress = m_nonOptimizedContract; + bytes nonOptimizedOutput = callContractFunction(_index, _arguments...); + m_contractAddress = m_optimizedContract; + bytes optimizedOutput = callContractFunction(_index, _arguments...); + BOOST_CHECK_MESSAGE(nonOptimizedOutput == optimizedOutput, "Computed values do not match." + "\nNon-Optimized: " + toHex(nonOptimizedOutput) + + "\nOptimized: " + toHex(optimizedOutput)); + } + +protected: + Address m_optimizedContract; + Address m_nonOptimizedContract; +}; + +BOOST_FIXTURE_TEST_SUITE(SolidityOptimizerTest, OptimizerTestFramework) + +BOOST_AUTO_TEST_CASE(smoke_test) +{ + char const* sourceCode = R"( + contract test { + function f(uint a) returns (uint b) { + return a; + } + })"; + compileBothVersions(4, sourceCode); + compareVersions(0, u256(7)); +} + +BOOST_AUTO_TEST_CASE(large_integers) +{ + char const* sourceCode = R"( + contract test { + function f() returns (uint a, uint b) { + a = 0x234234872642837426347000000; + b = 0x110000000000000000000000002; + } + })"; + compileBothVersions(28, sourceCode); + compareVersions(0); +} + +BOOST_AUTO_TEST_CASE(invariants) +{ + char const* sourceCode = R"( + contract test { + function f(uint a) returns (uint b) { + return (((a + (1 - 1)) ^ 0) | 0) & (uint(0) - 1); + } + })"; + compileBothVersions(19, sourceCode); + compareVersions(0, u256(0x12334664)); +} + +BOOST_AUTO_TEST_CASE(unused_expressions) +{ + char const* sourceCode = R"( + contract test { + uint data; + function f() returns (uint a, uint b) { + 10 + 20; + data; + } + })"; + compileBothVersions(11, sourceCode); + compareVersions(0); +} + +BOOST_AUTO_TEST_SUITE_END() + +} +} +} // end namespaces diff --git a/solidityParser.cpp b/solidityParser.cpp index 6a97a5d99..a9e2d531f 100644 --- a/solidityParser.cpp +++ b/solidityParser.cpp @@ -21,13 +21,15 @@ */ #include - +#include #include #include #include #include #include +using namespace std; + namespace dev { namespace solidity @@ -40,7 +42,12 @@ namespace ASTPointer parseText(std::string const& _source) { Parser parser; - return parser.parse(std::make_shared(CharStream(_source))); + ASTPointer sourceUnit = parser.parse(std::make_shared(CharStream(_source))); + for (ASTPointer const& node: sourceUnit->getNodes()) + if (ASTPointer contract = dynamic_pointer_cast(node)) + return contract; + BOOST_FAIL("No contract found in source."); + return ASTPointer(); } } @@ -380,6 +387,50 @@ BOOST_AUTO_TEST_CASE(statement_starting_with_type_conversion) BOOST_CHECK_NO_THROW(parseText(text)); } +BOOST_AUTO_TEST_CASE(import_directive) +{ + char const* text = "import \"abc\";\n" + "contract test {\n" + " function fun() {\n" + " uint64(2);\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(multiple_contracts) +{ + char const* text = "contract test {\n" + " function fun() {\n" + " uint64(2);\n" + " }\n" + "}\n" + "contract test2 {\n" + " function fun() {\n" + " uint64(2);\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + +BOOST_AUTO_TEST_CASE(multiple_contracts_and_imports) +{ + char const* text = "import \"abc\";\n" + "contract test {\n" + " function fun() {\n" + " uint64(2);\n" + " }\n" + "}\n" + "import \"def\";\n" + "contract test2 {\n" + " function fun() {\n" + " uint64(2);\n" + " }\n" + "}\n" + "import \"ghi\";\n"; + BOOST_CHECK_NO_THROW(parseText(text)); +} + BOOST_AUTO_TEST_SUITE_END() } diff --git a/stLogTestsFiller.json b/stLogTestsFiller.json new file mode 100644 index 000000000..34758ff83 --- /dev/null +++ b/stLogTestsFiller.json @@ -0,0 +1,1851 @@ +{ + "log0_emptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (LOG0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log0_nonEmptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG0 0 32) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log0_nonEmptyMem_logMemSize1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG0 0 1) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "log0_nonEmptyMem_logMemSize1_logMemStart31": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG0 31 1) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log0_logMemStartTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 1) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log0_logMemsizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG0 1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log0_logMemsizeZero": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG0 1 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_emptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (LOG1 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_nonEmptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG1 0 32 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_nonEmptyMem_logMemSize1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 0 1 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "log1_nonEmptyMem_logMemSize1_logMemStart31": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 31 1 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_logMemStartTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 1 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_logMemsizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_logMemsizeZero": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 1 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_MaxTopic": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG1 0 32 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log1_Caller": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG1 0 32 (CALLER)) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_emptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (LOG2 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_nonEmptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG2 0 32 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_nonEmptyMem_logMemSize1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 0 1 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "log2_nonEmptyMem_logMemSize1_logMemStart31": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 31 1 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_logMemStartTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 1 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_logMemsizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_logMemsizeZero": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 1 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_MaxTopic": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG2 0 32 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log2_Caller": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG2 0 32 0 (CALLER) ) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_emptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (LOG3 0 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_nonEmptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG3 0 32 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_nonEmptyMem_logMemSize1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 0 1 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "log3_nonEmptyMem_logMemSize1_logMemStart31": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 31 1 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_logMemStartTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 1 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_logMemsizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_logMemsizeZero": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 1 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_MaxTopic": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG3 0 32 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_Caller": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG3 0 32 0 0 (CALLER) ) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log3_PC": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG3 0 32 (PC) (PC) (PC) ) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_emptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (LOG4 0 0 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_nonEmptyMem": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG4 0 32 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_nonEmptyMem_logMemSize1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 0 1 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "log4_nonEmptyMem_logMemSize1_logMemStart31": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 31 1 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_logMemStartTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 1 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_logMemsizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 1 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_logMemsizeZero": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 1 0 0 0 0 0) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_MaxTopic": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xaabbffffffffffffffffffffffffffffffffffffffffffffffffffffffffccdd) (LOG4 0 32 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_Caller": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG3 0 32 0 0 0 (CALLER) ) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "log4_PC": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALL 1000 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6 23 0 0 0 0) }", + "storage": {} + }, + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE8 0 0xff) (LOG3 0 32 (PC) (PC) (PC) (PC) ) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + } +} diff --git a/stPreCompiledContractsFiller.json b/stPreCompiledContractsFiller.json index 9c65ad37b..62a3a1623 100644 --- a/stPreCompiledContractsFiller.json +++ b/stPreCompiledContractsFiller.json @@ -33,6 +33,41 @@ } }, + "CallEcrecover0_overlappingInputOutput": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code": "{ (MSTORE 0 0x18c547e4f7b0f325ad1e56f57e26c745b09a3e503d86e00e5255ff7f715d3d1c) (MSTORE 32 28) (MSTORE 64 0x73b1693892219d736caba55bdb67216e485557ea6b6af75f37096c9aa6a5a75f) (MSTORE 96 0xeeb940b1d03b21e36b0e47e79769f095fe2ab855bd91e3a38756b7d75a9c4549) [[ 2 ]] (CALL 1000 1 0 0 128 64 32) [[ 0 ]] (MOD (MLOAD 64) (EXP 2 160)) [[ 1 ]] (EQ (ORIGIN) (SLOAD 0)) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallEcrecover0_completeReturnValue": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", diff --git a/stSystemOperationsTestFiller.json b/stSystemOperationsTestFiller.json index edd803641..9fc8db773 100644 --- a/stSystemOperationsTestFiller.json +++ b/stSystemOperationsTestFiller.json @@ -634,6 +634,86 @@ } }, + "CallRecursiveBombLog": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (CALL 100000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG0 0 32) [[ 0 ]] (+ (SLOAD 0) 1) [[ 1 ]] (CALL (- (GAS) 224) (ADDRESS) 0 0 0 0 0) } ", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRecursiveBombLog2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (CALL 100000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 (GAS)) (LOG0 0 32) [[ 0 ]] (+ (SLOAD 0) 1) [[ 1 ]] (CALL (- (GAS) 224) (ADDRESS) 0 0 0 0 0) } ", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + "CallRecursiveBomb1": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", diff --git a/state.cpp b/state.cpp index 5fc23f149..961f0f13b 100644 --- a/state.cpp +++ b/state.cpp @@ -43,6 +43,8 @@ namespace dev { namespace test { void doStateTests(json_spirit::mValue& v, bool _fillin) { + processCommandLineOptions(); + for (auto& i: v.get_obj()) { cnote << i.first; @@ -125,6 +127,11 @@ BOOST_AUTO_TEST_CASE(stPreCompiledContracts) dev::test::executeTests("stPreCompiledContracts", "/StateTests", dev::test::doStateTests); } +BOOST_AUTO_TEST_CASE(stLogTests) +{ + dev::test::executeTests("stLogTests", "/StateTests", dev::test::doStateTests); +} + BOOST_AUTO_TEST_CASE(stSpecialTest) { dev::test::executeTests("stSpecialTest", "/StateTests", dev::test::doStateTests); diff --git a/trie.cpp b/trie.cpp index 67f706917..3f072a6d1 100644 --- a/trie.cpp +++ b/trie.cpp @@ -59,8 +59,8 @@ BOOST_AUTO_TEST_CASE(trie_tests) cnote << "Testing Trie..."; js::mValue v; - string s = asString(contents(testPath + "/trietest.json")); - BOOST_REQUIRE_MESSAGE(s.length() > 0, "Contents of 'trietest.json' is empty. Have you cloned the 'tests' repo branch develop?"); + string s = asString(contents(testPath + "/trieanyorder.json")); + BOOST_REQUIRE_MESSAGE(s.length() > 0, "Contents of 'trieanyorder.json' is empty. Have you cloned the 'tests' repo branch develop?"); js::read_string(s, v); for (auto& i: v.get_obj()) { @@ -88,12 +88,11 @@ BOOST_AUTO_TEST_CASE(trie_tests) BOOST_REQUIRE(t.check(true)); } BOOST_REQUIRE(!o["root"].is_null()); - BOOST_CHECK_EQUAL(o["root"].get_str(), toHex(t.root().asArray())); + BOOST_CHECK_EQUAL(o["root"].get_str(), "0x" + toHex(t.root().asArray())); } } } - inline h256 stringMapHash256(StringMap const& _s) { return hash256(_s); diff --git a/vm.cpp b/vm.cpp index 354defe44..075b3f2a0 100644 --- a/vm.cpp +++ b/vm.cpp @@ -22,8 +22,10 @@ #include #include -#include +#include +#include #include "vm.h" + using namespace std; using namespace json_spirit; using namespace dev; @@ -121,41 +123,6 @@ void FakeExtVM::importEnv(mObject& _o) currentBlock.coinbaseAddress = Address(_o["currentCoinbase"].get_str()); } -mObject FakeExtVM::exportLog() -{ - mObject ret; - for (LogEntry const& l: sub.logs) - { - mObject o; - o["address"] = toString(l.address); - mArray topics; - for (auto const& t: l.topics) - topics.push_back(toString(t)); - o["topics"] = topics; - o["data"] = "0x" + toHex(l.data); - ret[toString(l.bloom())] = o; - } - return ret; -} - -void FakeExtVM::importLog(mObject& _o) -{ - for (auto const& l: _o) - { - mObject o = l.second.get_obj(); - // cant use BOOST_REQUIRE, because this function is used outside boost test (createRandomTest) - assert(o.count("address") > 0); - assert(o.count("topics") > 0); - assert(o.count("data") > 0); - LogEntry log; - log.address = Address(o["address"].get_str()); - for (auto const& t: o["topics"].get_array()) - log.topics.push_back(h256(t.get_str())); - log.data = importData(o); - sub.logs.push_back(log); - } -} - mObject FakeExtVM::exportState() { mObject ret; @@ -277,10 +244,11 @@ void FakeExtVM::importCallCreates(mArray& _callcreates) eth::OnOpFunc FakeExtVM::simpleTrace() { - return [](uint64_t steps, eth::Instruction inst, bigint newMemSize, bigint gasCost, void* voidVM, void const* voidExt) + + return [](uint64_t steps, eth::Instruction inst, bigint newMemSize, bigint gasCost, dev::eth::VM* voidVM, dev::eth::ExtVMFace const* voidExt) { - FakeExtVM const& ext = *(FakeExtVM const*)voidExt; - eth::VM& vm = *(eth::VM*)voidVM; + FakeExtVM const& ext = *static_cast(voidExt); + eth::VM& vm = *voidVM; std::ostringstream o; o << std::endl << " STACK" << std::endl; @@ -309,6 +277,8 @@ namespace dev { namespace test { void doVMTests(json_spirit::mValue& v, bool _fillin) { + processCommandLineOptions(); + for (auto& i: v.get_obj()) { cnote << i.first; @@ -318,18 +288,7 @@ void doVMTests(json_spirit::mValue& v, bool _fillin) BOOST_REQUIRE(o.count("pre") > 0); BOOST_REQUIRE(o.count("exec") > 0); - auto argc = boost::unit_test::framework::master_test_suite().argc; - auto argv = boost::unit_test::framework::master_test_suite().argv; - auto useJit = false; - for (auto i = 0; i < argc && !useJit; ++i) - useJit |= std::string(argv[i]) == "--jit"; -#if ETH_EVMJIT - auto vmKind = useJit ? VMFactory::JIT : VMFactory::Interpreter; -#else - auto vmKind == VMFactory::Interpreter; -#endif - dev::test::FakeExtVM fev; - + FakeExtVM fev; fev.importEnv(o["env"].get_obj()); fev.importState(o["pre"].get_obj()); @@ -343,14 +302,13 @@ void doVMTests(json_spirit::mValue& v, bool _fillin) fev.code = fev.thisTxCode; } - auto vm = VMFactory::create(vmKind, fev.gas); bytes output; - - auto startTime = std::chrono::high_resolution_clock::now(); u256 gas; bool vmExceptionOccured = false; + auto startTime = std::chrono::high_resolution_clock::now(); try { + auto vm = eth::VMFactory::create(fev.gas); output = vm->go(fev, fev.simpleTrace()).toBytes(); gas = vm->gas(); } @@ -371,6 +329,8 @@ void doVMTests(json_spirit::mValue& v, bool _fillin) } auto endTime = std::chrono::high_resolution_clock::now(); + auto argc = boost::unit_test::framework::master_test_suite().argc; + auto argv = boost::unit_test::framework::master_test_suite().argv; for (auto i = 0; i < argc; ++i) { if (std::string(argv[i]) == "--show-times") @@ -410,7 +370,7 @@ void doVMTests(json_spirit::mValue& v, bool _fillin) o["callcreates"] = fev.exportCallCreates(); o["out"] = "0x" + toHex(output); fev.push(o, "gas", gas); - o["logs"] = mValue(exportLog(fev.sub.logs)); + o["logs"] = exportLog(fev.sub.logs); } } else @@ -428,7 +388,7 @@ void doVMTests(json_spirit::mValue& v, bool _fillin) dev::test::FakeExtVM test; test.importState(o["post"].get_obj()); test.importCallCreates(o["callcreates"].get_array()); - test.sub.logs = importLog(o["logs"].get_obj()); + test.sub.logs = importLog(o["logs"].get_array()); checkOutput(output, o); @@ -514,6 +474,26 @@ BOOST_AUTO_TEST_CASE(vmLogTest) dev::test::executeTests("vmLogTest", "/VMTests", dev::test::doVMTests); } +BOOST_AUTO_TEST_CASE(vmPerformanceTest) +{ + for (int i = 1; i < boost::unit_test::framework::master_test_suite().argc; ++i) + { + string arg = boost::unit_test::framework::master_test_suite().argv[i]; + if (arg == "--performance") + dev::test::executeTests("vmPerformanceTest", "/VMTests", dev::test::doVMTests); + } +} + +BOOST_AUTO_TEST_CASE(vmArithPerformanceTest) +{ + for (int i = 1; i < boost::unit_test::framework::master_test_suite().argc; ++i) + { + string arg = boost::unit_test::framework::master_test_suite().argv[i]; + if (arg == "--performance") + dev::test::executeTests("vmArithPerformanceTest", "/VMTests", dev::test::doVMTests); + } +} + BOOST_AUTO_TEST_CASE(vmRandom) { string testPath = getTestPath(); diff --git a/vm.h b/vm.h index fb0346d51..3d4b88d54 100644 --- a/vm.h +++ b/vm.h @@ -72,8 +72,6 @@ public: void importExec(json_spirit::mObject& _o); json_spirit::mArray exportCallCreates(); void importCallCreates(json_spirit::mArray& _callcreates); - json_spirit::mObject exportLog(); - void importLog(json_spirit::mObject& _o); eth::OnOpFunc simpleTrace(); @@ -82,9 +80,6 @@ public: bytes thisTxData; bytes thisTxCode; u256 gas; - -private: - eth::Manifest m_ms; }; diff --git a/vmEnvironmentalInfoTestFiller.json b/vmEnvironmentalInfoTestFiller.json index 95e7936aa..abeed9945 100644 --- a/vmEnvironmentalInfoTestFiller.json +++ b/vmEnvironmentalInfoTestFiller.json @@ -338,6 +338,33 @@ } }, + "calldataloadSizeTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (CALLDATALOAD 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa)}", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "0x123456789abcdef0000000000000000000000000000000000000000000000000024", + "gasPrice" : "1000000000", + "gas" : "100000000000" + } + }, "calldatasize0": { "env" : { @@ -451,6 +478,62 @@ } }, + "calldatacopy_DataIndexTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (CALLDATACOPY 0 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa 0xff ) [[ 0 ]] @0}", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "0x1234567890abcdef01234567890abcdef", + "gasPrice" : "1000000000", + "gas" : "100000000000" + } + }, + + "calldatacopy_DataIndexTooHigh2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (CALLDATACOPY 0 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa 9 ) [[ 0 ]] @0}", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "0x1234567890abcdef01234567890abcdef", + "gasPrice" : "1000000000", + "gas" : "100000000000" + } + }, + "calldatacopy1": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", @@ -535,6 +618,34 @@ } }, + "codecopy_DataIndexTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (CODECOPY 0 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa 8 ) [[ 0 ]] @0}", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "0x1234567890abcdef01234567890abcdef", + "gasPrice" : "1000000000", + "gas" : "100000000000" + } + }, + "codecopy0": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", @@ -686,6 +797,35 @@ } }, + "extcodecopy_DataIndexTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (EXTCODECOPY (ADDRESS) 0 0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa 8 ) [[ 0 ]] @0}", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "0x1234567890abcdef01234567890abcdef", + "gasPrice" : "1000000000", + "gas" : "100000000000" + } + }, + + "extcodecopy0": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", diff --git a/vmLogTestFiller.json b/vmLogTestFiller.json index f4fb48b52..4f3d26f52 100644 --- a/vmLogTestFiller.json +++ b/vmLogTestFiller.json @@ -55,6 +55,34 @@ } }, + "log_2logs": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (LOG0 0 32) (LOG0 2 16) }", + "storage": {} + } + }, + "exec" : { + "address" : "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6", + "origin" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "caller" : "cd1722f3947def4cf144679da39c4c32bdc35681", + "value" : "1000000000000000000", + "data" : "", + "gasPrice" : "100000000000000", + "gas" : "10000" + } + }, + "log0_nonEmptyMem_logMemSize1": { "env" : { "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", diff --git a/whisperTopic.cpp b/whisperTopic.cpp index 493b37bc2..c5e59332d 100644 --- a/whisperTopic.cpp +++ b/whisperTopic.cpp @@ -32,7 +32,8 @@ BOOST_AUTO_TEST_SUITE(whisper) BOOST_AUTO_TEST_CASE(topic) { - g_logVerbosity = 0; + cnote << "Testing Whisper..."; +// g_logVerbosity = 0; bool started = false; unsigned result = 0; @@ -40,16 +41,16 @@ BOOST_AUTO_TEST_CASE(topic) { setThreadName("other"); - Host ph("Test", NetworkPreferences(30303, "", false, true)); + Host ph("Test", NetworkPreferences(50303, "", false, true)); auto wh = ph.registerCapability(new WhisperHost()); ph.start(); started = true; /// Only interested in odd packets - auto w = wh->installWatch(BuildTopicMask()("odd")); + auto w = wh->installWatch(BuildTopicMask("odd")); - for (int i = 0, last = 0; i < 100 && last < 81; ++i) + for (int i = 0, last = 0; i < 200 && last < 81; ++i) { for (auto i: wh->checkWatch(w)) { @@ -65,10 +66,12 @@ BOOST_AUTO_TEST_CASE(topic) while (!started) this_thread::sleep_for(chrono::milliseconds(50)); - Host ph("Test", NetworkPreferences(30300, "", false, true)); + Host ph("Test", NetworkPreferences(50300, "", false, true)); auto wh = ph.registerCapability(new WhisperHost()); + this_thread::sleep_for(chrono::milliseconds(500)); ph.start(); - ph.connect("127.0.0.1", 30303); + this_thread::sleep_for(chrono::milliseconds(500)); + ph.connect("127.0.0.1", 50303); KeyPair us = KeyPair::create(); for (int i = 0; i < 10; ++i) @@ -78,6 +81,8 @@ BOOST_AUTO_TEST_CASE(topic) } listener.join(); +// g_logVerbosity = 0; + BOOST_REQUIRE_EQUAL(result, 1 + 9 + 25 + 49 + 81); }