From 3d70090fe43bb1693129bd7d6ca03ccfea059091 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 3 Nov 2014 16:54:03 +0100 Subject: [PATCH 01/38] jsonrpc 0.3.0 working, needs cleanup --- cmake/EthDependenciesDeprecated.cmake | 38 +- eth/main.cpp | 2 +- libqethereum/QEthereum.h | 3 +- libweb3jsonrpc/CMakeLists.txt | 2 + libweb3jsonrpc/CorsHttpServer.h | 3 +- libweb3jsonrpc/WebThreeStubServer.cpp | 2 +- libweb3jsonrpc/WebThreeStubServer.h | 3 +- libweb3jsonrpc/abstractwebthreestubserver.h | 368 +++++----- libweb3jsonrpc/spec.json | 100 +-- neth/main.cpp | 2 +- test/CMakeLists.txt | 1 + test/jsonrpc.cpp | 11 +- test/webthreestubclient.h | 713 ++++++++------------ 13 files changed, 560 insertions(+), 688 deletions(-) diff --git a/cmake/EthDependenciesDeprecated.cmake b/cmake/EthDependenciesDeprecated.cmake index d1c51f6c4..d815bef3e 100644 --- a/cmake/EthDependenciesDeprecated.cmake +++ b/cmake/EthDependenciesDeprecated.cmake @@ -125,21 +125,47 @@ else() message(STATUS "Failed to find the miniupnpc headers!") endif () - find_path( JSONRPC_ID jsonrpc/rpc.h - /usr/include - /usr/local/include - ) + find_path( JSONRPC_ID jsonrpccpp/server.h + /usr/include + /usr/local/include + ) + if ( JSONRPC_ID ) message(STATUS "Found jsonrpc headers") - find_library( JSONRPC_LS NAMES jsonrpc + find_library( JSONRPC_LS NAMES jsonrpccpp-server PATHS /usr/lib /usr/local/lib /opt/local/lib /usr/lib/*/ ) - if ( JSONRPC_LS ) + + find_library( JSONRPC_COMMON_LS NAMES jsonrpccpp-common + PATHS + /usr/lib + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + find_library( JSONCPP_LS NAMES jsoncpp + /usr/lib + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + find_library( JSONRPC_CLIENT_LS NAMES jsonrpccpp-client + PATHS + /usr/lib/ + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + if ( JSONRPC_LS AND JSONRPC_COMMON_LS ) message(STATUS "Found jsonrpc library: ${JSONRPC_LS}") + message(STATUS "Found jsonrpc-common library: ${JSONRPC_COMMON_LS}") add_definitions(-DETH_JSONRPC) else () message(STATUS "Failed to find the jsonrpc library!") diff --git a/eth/main.cpp b/eth/main.cpp index 759dd40d0..447729c1a 100644 --- a/eth/main.cpp +++ b/eth/main.cpp @@ -28,7 +28,7 @@ #include #include #if ETH_JSONRPC -#include +//#include #include #endif #include diff --git a/libqethereum/QEthereum.h b/libqethereum/QEthereum.h index 4f276b7e1..b4c17fdab 100644 --- a/libqethereum/QEthereum.h +++ b/libqethereum/QEthereum.h @@ -25,7 +25,8 @@ #include #include -#include +#include +//#include class QWebThree: public QObject { diff --git a/libweb3jsonrpc/CMakeLists.txt b/libweb3jsonrpc/CMakeLists.txt index b24a11196..6966cd10a 100644 --- a/libweb3jsonrpc/CMakeLists.txt +++ b/libweb3jsonrpc/CMakeLists.txt @@ -23,7 +23,9 @@ if(MINIUPNPC_LS) endif() target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) target_link_libraries(${EXECUTABLE} ${CRYPTOPP_LS}) +target_link_libraries(${EXECUTABLE} ${JSONCPP_LS}) target_link_libraries(${EXECUTABLE} ${JSONRPC_LS}) +target_link_libraries(${EXECUTABLE} ${JSONRPC_COMMON_LS}) target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) if(READLINE_LS) target_link_libraries(${EXECUTABLE} ${READLINE_LS}) diff --git a/libweb3jsonrpc/CorsHttpServer.h b/libweb3jsonrpc/CorsHttpServer.h index d3bd8a6e9..5dd3130a4 100644 --- a/libweb3jsonrpc/CorsHttpServer.h +++ b/libweb3jsonrpc/CorsHttpServer.h @@ -19,7 +19,8 @@ * @date 2014 */ -#include +#include +//#include namespace jsonrpc { diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index e7eb62e04..ed5907f53 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -217,7 +217,7 @@ static Json::Value toJson(h256 const& _h, shh::Envelope const& _e, shh::Message WebThreeStubServer::WebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, WebThreeDirect& _web3, std::vector const& _accounts): - AbstractWebThreeStubServer(_conn), + AbstractWebThreeStubServer(*_conn), m_web3(_web3) { setAccounts(_accounts); diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index b18faf95a..193f1f6ff 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -29,7 +29,8 @@ #pragma warning(pop) #include -#include +//#include +#include #include #pragma GCC diagnostic push #pragma GCC diagnostic ignored "-Wunused-parameter" diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index ac6893933..90ee422a0 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -1,323 +1,287 @@ /** - * THIS FILE IS GENERATED BY jsonrpcstub, DO NOT CHANGE IT!!!!! + * This file is generated by jsonrpcstub, DO NOT CHANGE IT MANUALLY! */ -#ifndef _ABSTRACTWEBTHREESTUBSERVER_H_ -#define _ABSTRACTWEBTHREESTUBSERVER_H_ +#ifndef JSONRPC_CPP_STUB_ABSTRACTWEBTHREESTUBSERVER_H_ +#define JSONRPC_CPP_STUB_ABSTRACTWEBTHREESTUBSERVER_H_ -#include +#include class AbstractWebThreeStubServer : public jsonrpc::AbstractServer { public: - AbstractWebThreeStubServer(jsonrpc::AbstractServerConnector* conn) : - jsonrpc::AbstractServer(conn) + AbstractWebThreeStubServer(jsonrpc::AbstractServerConnector &conn) : jsonrpc::AbstractServer(conn) { - this->bindAndAddMethod(new jsonrpc::Procedure("account", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::accountI); - this->bindAndAddMethod(new jsonrpc::Procedure("accounts", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::accountsI); - this->bindAndAddMethod(new jsonrpc::Procedure("addToGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::addToGroupI); - this->bindAndAddMethod(new jsonrpc::Procedure("balanceAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::balanceAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("blockByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::blockByHashI); - this->bindAndAddMethod(new jsonrpc::Procedure("blockByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::blockByNumberI); - this->bindAndAddMethod(new jsonrpc::Procedure("call", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::callI); - this->bindAndAddMethod(new jsonrpc::Procedure("changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::changedI); - this->bindAndAddMethod(new jsonrpc::Procedure("codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::coinbaseI); - this->bindAndAddMethod(new jsonrpc::Procedure("compile", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::compileI); - this->bindAndAddMethod(new jsonrpc::Procedure("countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::countAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::defaultBlockI); - this->bindAndAddMethod(new jsonrpc::Procedure("gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::gasPriceI); - this->bindAndAddMethod(new jsonrpc::Procedure("get", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getI); - this->bindAndAddMethod(new jsonrpc::Procedure("getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::getMessagesI); - this->bindAndAddMethod(new jsonrpc::Procedure("getString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("haveIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::haveIdentityI); + this->bindAndAddMethod(new jsonrpc::Procedure("setCoinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::setCoinbaseI); this->bindAndAddMethod(new jsonrpc::Procedure("listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::listeningI); + this->bindAndAddMethod(new jsonrpc::Procedure("setListening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setListeningI); this->bindAndAddMethod(new jsonrpc::Procedure("mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::miningI); - this->bindAndAddMethod(new jsonrpc::Procedure("newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::newFilterI); - this->bindAndAddMethod(new jsonrpc::Procedure("newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newFilterStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("newGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newGroupI); - this->bindAndAddMethod(new jsonrpc::Procedure("newIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newIdentityI); - this->bindAndAddMethod(new jsonrpc::Procedure("number", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::numberI); + this->bindAndAddMethod(new jsonrpc::Procedure("setMining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setMiningI); + this->bindAndAddMethod(new jsonrpc::Procedure("gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::gasPriceI); + this->bindAndAddMethod(new jsonrpc::Procedure("account", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::accountI); + this->bindAndAddMethod(new jsonrpc::Procedure("accounts", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::accountsI); this->bindAndAddMethod(new jsonrpc::Procedure("peerCount", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::peerCountI); - this->bindAndAddMethod(new jsonrpc::Procedure("post", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::postI); - this->bindAndAddMethod(new jsonrpc::Procedure("put", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putI); - this->bindAndAddMethod(new jsonrpc::Procedure("putString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("setCoinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::setCoinbaseI); + this->bindAndAddMethod(new jsonrpc::Procedure("defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::defaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("setDefaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::setDefaultBlockI); - this->bindAndAddMethod(new jsonrpc::Procedure("setListening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setListeningI); - this->bindAndAddMethod(new jsonrpc::Procedure("setMining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setMiningI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhChanged", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhChangedI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhNewFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shhNewFilterI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhUninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhUninstallFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("number", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::numberI); + this->bindAndAddMethod(new jsonrpc::Procedure("balanceAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::balanceAtI); this->bindAndAddMethod(new jsonrpc::Procedure("stateAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::stateAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::countAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("transact", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::transactI); + this->bindAndAddMethod(new jsonrpc::Procedure("call", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::callI); + this->bindAndAddMethod(new jsonrpc::Procedure("blockByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::blockByHashI); + this->bindAndAddMethod(new jsonrpc::Procedure("blockByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::blockByNumberI); this->bindAndAddMethod(new jsonrpc::Procedure("transactionByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::transactionByHashI); this->bindAndAddMethod(new jsonrpc::Procedure("transactionByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::transactionByNumberI); this->bindAndAddMethod(new jsonrpc::Procedure("uncleByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uncleByHashI); this->bindAndAddMethod(new jsonrpc::Procedure("uncleByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uncleByNumberI); + this->bindAndAddMethod(new jsonrpc::Procedure("compile", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::compileI); + this->bindAndAddMethod(new jsonrpc::Procedure("newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::newFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newFilterStringI); this->bindAndAddMethod(new jsonrpc::Procedure("uninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uninstallFilterI); - + this->bindAndAddMethod(new jsonrpc::Procedure("changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::changedI); + this->bindAndAddMethod(new jsonrpc::Procedure("getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::getMessagesI); + this->bindAndAddMethod(new jsonrpc::Procedure("put", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putI); + this->bindAndAddMethod(new jsonrpc::Procedure("get", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getI); + this->bindAndAddMethod(new jsonrpc::Procedure("putString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putStringI); + this->bindAndAddMethod(new jsonrpc::Procedure("getString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getStringI); + this->bindAndAddMethod(new jsonrpc::Procedure("post", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::postI); + this->bindAndAddMethod(new jsonrpc::Procedure("newIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newIdentityI); + this->bindAndAddMethod(new jsonrpc::Procedure("haveIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::haveIdentityI); + this->bindAndAddMethod(new jsonrpc::Procedure("newGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newGroupI); + this->bindAndAddMethod(new jsonrpc::Procedure("addToGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::addToGroupI); + this->bindAndAddMethod(new jsonrpc::Procedure("shhNewFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shhNewFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("shhUninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhUninstallFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("shhChanged", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhChangedI); } - - inline virtual void accountI(const Json::Value& request, Json::Value& response) + + inline virtual void coinbaseI(const Json::Value &request, Json::Value &response) { - response = this->account(); + (void)request; + response = this->coinbase(); } - - inline virtual void accountsI(const Json::Value& request, Json::Value& response) + inline virtual void setCoinbaseI(const Json::Value &request, Json::Value &response) { - response = this->accounts(); + response = this->setCoinbase(request[0u].asString()); } - - inline virtual void addToGroupI(const Json::Value& request, Json::Value& response) + inline virtual void listeningI(const Json::Value &request, Json::Value &response) { - response = this->addToGroup(request[0u].asString(), request[1u].asString()); + (void)request; + response = this->listening(); } - - inline virtual void balanceAtI(const Json::Value& request, Json::Value& response) + inline virtual void setListeningI(const Json::Value &request, Json::Value &response) { - response = this->balanceAt(request[0u].asString()); + response = this->setListening(request[0u].asBool()); } - - inline virtual void blockByHashI(const Json::Value& request, Json::Value& response) + inline virtual void miningI(const Json::Value &request, Json::Value &response) { - response = this->blockByHash(request[0u].asString()); + (void)request; + response = this->mining(); } - - inline virtual void blockByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void setMiningI(const Json::Value &request, Json::Value &response) { - response = this->blockByNumber(request[0u].asInt()); + response = this->setMining(request[0u].asBool()); } - - inline virtual void callI(const Json::Value& request, Json::Value& response) + inline virtual void gasPriceI(const Json::Value &request, Json::Value &response) { - response = this->call(request[0u]); + (void)request; + response = this->gasPrice(); } - - inline virtual void changedI(const Json::Value& request, Json::Value& response) + inline virtual void accountI(const Json::Value &request, Json::Value &response) { - response = this->changed(request[0u].asInt()); + (void)request; + response = this->account(); } - - inline virtual void codeAtI(const Json::Value& request, Json::Value& response) + inline virtual void accountsI(const Json::Value &request, Json::Value &response) { - response = this->codeAt(request[0u].asString()); + (void)request; + response = this->accounts(); } - - inline virtual void coinbaseI(const Json::Value& request, Json::Value& response) + inline virtual void peerCountI(const Json::Value &request, Json::Value &response) { - response = this->coinbase(); + (void)request; + response = this->peerCount(); } - - inline virtual void compileI(const Json::Value& request, Json::Value& response) + inline virtual void defaultBlockI(const Json::Value &request, Json::Value &response) { - response = this->compile(request[0u].asString()); + (void)request; + response = this->defaultBlock(); } - - inline virtual void countAtI(const Json::Value& request, Json::Value& response) + inline virtual void setDefaultBlockI(const Json::Value &request, Json::Value &response) { - response = this->countAt(request[0u].asString()); + response = this->setDefaultBlock(request[0u].asInt()); } - - inline virtual void defaultBlockI(const Json::Value& request, Json::Value& response) + inline virtual void numberI(const Json::Value &request, Json::Value &response) { - response = this->defaultBlock(); + (void)request; + response = this->number(); } - - inline virtual void gasPriceI(const Json::Value& request, Json::Value& response) + inline virtual void balanceAtI(const Json::Value &request, Json::Value &response) { - response = this->gasPrice(); + response = this->balanceAt(request[0u].asString()); } - - inline virtual void getI(const Json::Value& request, Json::Value& response) + inline virtual void stateAtI(const Json::Value &request, Json::Value &response) { - response = this->get(request[0u].asString(), request[1u].asString()); + response = this->stateAt(request[0u].asString(), request[1u].asString()); } - - inline virtual void getMessagesI(const Json::Value& request, Json::Value& response) + inline virtual void countAtI(const Json::Value &request, Json::Value &response) { - response = this->getMessages(request[0u].asInt()); + response = this->countAt(request[0u].asString()); } - - inline virtual void getStringI(const Json::Value& request, Json::Value& response) + inline virtual void codeAtI(const Json::Value &request, Json::Value &response) { - response = this->getString(request[0u].asString(), request[1u].asString()); + response = this->codeAt(request[0u].asString()); } - - inline virtual void haveIdentityI(const Json::Value& request, Json::Value& response) + inline virtual void transactI(const Json::Value &request, Json::Value &response) { - response = this->haveIdentity(request[0u].asString()); + response = this->transact(request[0u]); } - - inline virtual void listeningI(const Json::Value& request, Json::Value& response) + inline virtual void callI(const Json::Value &request, Json::Value &response) { - response = this->listening(); + response = this->call(request[0u]); } - - inline virtual void miningI(const Json::Value& request, Json::Value& response) + inline virtual void blockByHashI(const Json::Value &request, Json::Value &response) { - response = this->mining(); + response = this->blockByHash(request[0u].asString()); } - - inline virtual void newFilterI(const Json::Value& request, Json::Value& response) + inline virtual void blockByNumberI(const Json::Value &request, Json::Value &response) { - response = this->newFilter(request[0u]); + response = this->blockByNumber(request[0u].asInt()); } - - inline virtual void newFilterStringI(const Json::Value& request, Json::Value& response) + inline virtual void transactionByHashI(const Json::Value &request, Json::Value &response) { - response = this->newFilterString(request[0u].asString()); + response = this->transactionByHash(request[0u].asString(), request[1u].asInt()); } - - inline virtual void newGroupI(const Json::Value& request, Json::Value& response) + inline virtual void transactionByNumberI(const Json::Value &request, Json::Value &response) { - response = this->newGroup(request[0u].asString(), request[1u].asString()); + response = this->transactionByNumber(request[0u].asInt(), request[1u].asInt()); } - - inline virtual void newIdentityI(const Json::Value& request, Json::Value& response) + inline virtual void uncleByHashI(const Json::Value &request, Json::Value &response) { - response = this->newIdentity(); + response = this->uncleByHash(request[0u].asString(), request[1u].asInt()); } - - inline virtual void numberI(const Json::Value& request, Json::Value& response) + inline virtual void uncleByNumberI(const Json::Value &request, Json::Value &response) { - response = this->number(); + response = this->uncleByNumber(request[0u].asInt(), request[1u].asInt()); } - - inline virtual void peerCountI(const Json::Value& request, Json::Value& response) + inline virtual void compileI(const Json::Value &request, Json::Value &response) { - response = this->peerCount(); + response = this->compile(request[0u].asString()); } - - inline virtual void postI(const Json::Value& request, Json::Value& response) + inline virtual void newFilterI(const Json::Value &request, Json::Value &response) { - response = this->post(request[0u]); + response = this->newFilter(request[0u]); } - - inline virtual void putI(const Json::Value& request, Json::Value& response) + inline virtual void newFilterStringI(const Json::Value &request, Json::Value &response) { - response = this->put(request[0u].asString(), request[1u].asString(), request[2u].asString()); + response = this->newFilterString(request[0u].asString()); } - - inline virtual void putStringI(const Json::Value& request, Json::Value& response) + inline virtual void uninstallFilterI(const Json::Value &request, Json::Value &response) { - response = this->putString(request[0u].asString(), request[1u].asString(), request[2u].asString()); + response = this->uninstallFilter(request[0u].asInt()); } - - inline virtual void setCoinbaseI(const Json::Value& request, Json::Value& response) + inline virtual void changedI(const Json::Value &request, Json::Value &response) { - response = this->setCoinbase(request[0u].asString()); + response = this->changed(request[0u].asInt()); } - - inline virtual void setDefaultBlockI(const Json::Value& request, Json::Value& response) + inline virtual void getMessagesI(const Json::Value &request, Json::Value &response) { - response = this->setDefaultBlock(request[0u].asInt()); + response = this->getMessages(request[0u].asInt()); } - - inline virtual void setListeningI(const Json::Value& request, Json::Value& response) + inline virtual void putI(const Json::Value &request, Json::Value &response) { - response = this->setListening(request[0u].asBool()); + response = this->put(request[0u].asString(), request[1u].asString(), request[2u].asString()); } - - inline virtual void setMiningI(const Json::Value& request, Json::Value& response) + inline virtual void getI(const Json::Value &request, Json::Value &response) { - response = this->setMining(request[0u].asBool()); + response = this->get(request[0u].asString(), request[1u].asString()); } - - inline virtual void shhChangedI(const Json::Value& request, Json::Value& response) + inline virtual void putStringI(const Json::Value &request, Json::Value &response) { - response = this->shhChanged(request[0u].asInt()); + response = this->putString(request[0u].asString(), request[1u].asString(), request[2u].asString()); } - - inline virtual void shhNewFilterI(const Json::Value& request, Json::Value& response) + inline virtual void getStringI(const Json::Value &request, Json::Value &response) { - response = this->shhNewFilter(request[0u]); + response = this->getString(request[0u].asString(), request[1u].asString()); } - - inline virtual void shhUninstallFilterI(const Json::Value& request, Json::Value& response) + inline virtual void postI(const Json::Value &request, Json::Value &response) { - response = this->shhUninstallFilter(request[0u].asInt()); + response = this->post(request[0u]); } - - inline virtual void stateAtI(const Json::Value& request, Json::Value& response) + inline virtual void newIdentityI(const Json::Value &request, Json::Value &response) { - response = this->stateAt(request[0u].asString(), request[1u].asString()); + (void)request; + response = this->newIdentity(); } - - inline virtual void transactI(const Json::Value& request, Json::Value& response) + inline virtual void haveIdentityI(const Json::Value &request, Json::Value &response) { - response = this->transact(request[0u]); + response = this->haveIdentity(request[0u].asString()); } - - inline virtual void transactionByHashI(const Json::Value& request, Json::Value& response) + inline virtual void newGroupI(const Json::Value &request, Json::Value &response) { - response = this->transactionByHash(request[0u].asString(), request[1u].asInt()); + response = this->newGroup(request[0u].asString(), request[1u].asString()); } - - inline virtual void transactionByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void addToGroupI(const Json::Value &request, Json::Value &response) { - response = this->transactionByNumber(request[0u].asInt(), request[1u].asInt()); + response = this->addToGroup(request[0u].asString(), request[1u].asString()); } - - inline virtual void uncleByHashI(const Json::Value& request, Json::Value& response) + inline virtual void shhNewFilterI(const Json::Value &request, Json::Value &response) { - response = this->uncleByHash(request[0u].asString(), request[1u].asInt()); + response = this->shhNewFilter(request[0u]); } - - inline virtual void uncleByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void shhUninstallFilterI(const Json::Value &request, Json::Value &response) { - response = this->uncleByNumber(request[0u].asInt(), request[1u].asInt()); + response = this->shhUninstallFilter(request[0u].asInt()); } - - inline virtual void uninstallFilterI(const Json::Value& request, Json::Value& response) + inline virtual void shhChangedI(const Json::Value &request, Json::Value &response) { - response = this->uninstallFilter(request[0u].asInt()); + response = this->shhChanged(request[0u].asInt()); } - - - virtual std::string account() = 0; - virtual Json::Value accounts() = 0; - virtual std::string addToGroup(const std::string& param1, const std::string& param2) = 0; - virtual std::string balanceAt(const std::string& param1) = 0; - virtual Json::Value blockByHash(const std::string& param1) = 0; - virtual Json::Value blockByNumber(const int& param1) = 0; - virtual std::string call(const Json::Value& param1) = 0; - virtual bool changed(const int& param1) = 0; - virtual std::string codeAt(const std::string& param1) = 0; virtual std::string coinbase() = 0; - virtual std::string compile(const std::string& param1) = 0; - virtual double countAt(const std::string& param1) = 0; - virtual int defaultBlock() = 0; - virtual std::string gasPrice() = 0; - virtual std::string get(const std::string& param1, const std::string& param2) = 0; - virtual Json::Value getMessages(const int& param1) = 0; - virtual std::string getString(const std::string& param1, const std::string& param2) = 0; - virtual bool haveIdentity(const std::string& param1) = 0; + virtual bool setCoinbase(const std::string& param1) = 0; virtual bool listening() = 0; + virtual bool setListening(const bool& param1) = 0; virtual bool mining() = 0; - virtual int newFilter(const Json::Value& param1) = 0; - virtual int newFilterString(const std::string& param1) = 0; - virtual std::string newGroup(const std::string& param1, const std::string& param2) = 0; - virtual std::string newIdentity() = 0; - virtual int number() = 0; + virtual bool setMining(const bool& param1) = 0; + virtual std::string gasPrice() = 0; + virtual std::string account() = 0; + virtual Json::Value accounts() = 0; virtual int peerCount() = 0; - virtual bool post(const Json::Value& param1) = 0; - virtual bool put(const std::string& param1, const std::string& param2, const std::string& param3) = 0; - virtual bool putString(const std::string& param1, const std::string& param2, const std::string& param3) = 0; - virtual bool setCoinbase(const std::string& param1) = 0; + virtual int defaultBlock() = 0; virtual bool setDefaultBlock(const int& param1) = 0; - virtual bool setListening(const bool& param1) = 0; - virtual bool setMining(const bool& param1) = 0; - virtual Json::Value shhChanged(const int& param1) = 0; - virtual int shhNewFilter(const Json::Value& param1) = 0; - virtual bool shhUninstallFilter(const int& param1) = 0; + virtual int number() = 0; + virtual std::string balanceAt(const std::string& param1) = 0; virtual std::string stateAt(const std::string& param1, const std::string& param2) = 0; + virtual double countAt(const std::string& param1) = 0; + virtual std::string codeAt(const std::string& param1) = 0; virtual std::string transact(const Json::Value& param1) = 0; + virtual std::string call(const Json::Value& param1) = 0; + virtual Json::Value blockByHash(const std::string& param1) = 0; + virtual Json::Value blockByNumber(const int& param1) = 0; virtual Json::Value transactionByHash(const std::string& param1, const int& param2) = 0; virtual Json::Value transactionByNumber(const int& param1, const int& param2) = 0; virtual Json::Value uncleByHash(const std::string& param1, const int& param2) = 0; virtual Json::Value uncleByNumber(const int& param1, const int& param2) = 0; + virtual std::string compile(const std::string& param1) = 0; + virtual int newFilter(const Json::Value& param1) = 0; + virtual int newFilterString(const std::string& param1) = 0; virtual bool uninstallFilter(const int& param1) = 0; - + virtual bool changed(const int& param1) = 0; + virtual Json::Value getMessages(const int& param1) = 0; + virtual bool put(const std::string& param1, const std::string& param2, const std::string& param3) = 0; + virtual std::string get(const std::string& param1, const std::string& param2) = 0; + virtual bool putString(const std::string& param1, const std::string& param2, const std::string& param3) = 0; + virtual std::string getString(const std::string& param1, const std::string& param2) = 0; + virtual bool post(const Json::Value& param1) = 0; + virtual std::string newIdentity() = 0; + virtual bool haveIdentity(const std::string& param1) = 0; + virtual std::string newGroup(const std::string& param1, const std::string& param2) = 0; + virtual std::string addToGroup(const std::string& param1, const std::string& param2) = 0; + virtual int shhNewFilter(const Json::Value& param1) = 0; + virtual bool shhUninstallFilter(const int& param1) = 0; + virtual Json::Value shhChanged(const int& param1) = 0; }; -#endif //_ABSTRACTWEBTHREESTUBSERVER_H_ + +#endif //JSONRPC_CPP_ABSTRACTWEBTHREESTUBSERVER_H_ diff --git a/libweb3jsonrpc/spec.json b/libweb3jsonrpc/spec.json index 1e7065970..aea50adf9 100644 --- a/libweb3jsonrpc/spec.json +++ b/libweb3jsonrpc/spec.json @@ -1,55 +1,55 @@ [ - { "method": "coinbase", "params": [], "order": [], "returns" : "" }, - { "method": "setCoinbase", "params": [""], "order": [], "returns" : true }, - { "method": "listening", "params": [], "order": [], "returns" : false }, - { "method": "setListening", "params": [false], "order" : [], "returns" : true }, - { "method": "mining", "params": [], "order": [], "returns" : false }, - { "method": "setMining", "params": [false], "order" : [], "returns" : true }, - { "method": "gasPrice", "params": [], "order": [], "returns" : "" }, - { "method": "account", "params": [], "order": [], "returns" : "" }, - { "method": "accounts", "params": [], "order": [], "returns" : [] }, - { "method": "peerCount", "params": [], "order": [], "returns" : 0 }, - { "method": "defaultBlock", "params": [], "order": [], "returns" : 0}, - { "method": "setDefaultBlock", "params": [0], "order": [], "returns" : true}, - { "method": "number", "params": [], "order": [], "returns" : 0}, - - { "method": "balanceAt", "params": [""], "order": [], "returns" : ""}, - { "method": "stateAt", "params": ["", ""], "order": [], "returns": ""}, - { "method": "countAt", "params": [""], "order": [], "returns" : 0.0}, - { "method": "codeAt", "params": [""], "order": [], "returns": ""}, - - { "method": "transact", "params": [{}], "order": [], "returns": ""}, - { "method": "call", "params": [{}], "order": [], "returns": ""}, - - { "method": "blockByHash", "params": [""],"order": [], "returns": {}}, - { "method": "blockByNumber", "params": [0],"order": [], "returns": {}}, - { "method": "transactionByHash", "params": ["", 0], "order": [], "returns": {}}, - { "method": "transactionByNumber", "params": [0, 0], "order": [], "returns": {}}, - { "method": "uncleByHash", "params": ["", 0], "order": [], "returns": {}}, - { "method": "uncleByNumber", "params": [0, 0], "order": [], "returns": {}}, - - { "method": "compile", "params": [""], "order": [], "returns": ""}, - - { "method": "newFilter", "params": [{}], "order": [], "returns": 0}, - { "method": "newFilterString", "params": [""], "order": [], "returns": 0}, - { "method": "uninstallFilter", "params": [0], "order": [], "returns": true}, - { "method": "changed", "params": [0], "order": [], "returns": false}, - { "method": "getMessages", "params": [0], "order": [], "returns": []}, - - { "method": "put", "params": ["", "", ""], "order": [], "returns": true}, - { "method": "get", "params": ["", ""], "order": [], "returns": ""}, - { "method": "putString", "params": ["", "", ""], "order": [], "returns": true}, - { "method": "getString", "params": ["", ""], "order": [], "returns": ""}, - - { "method": "post", "params": [{}], "order": [], "returns": true}, - { "method": "newIdentity", "params": [], "order": [], "returns": ""}, - { "method": "haveIdentity", "params": [""], "order": [], "returns": false}, - { "method": "newGroup", "params": ["", ""], "order": [], "returns": ""}, - { "method": "addToGroup", "params": ["", ""], "order": [], "returns": ""}, + { "name": "coinbase", "params": [], "order": [], "returns" : "" }, + { "name": "setCoinbase", "params": [""], "order": [], "returns" : true }, + { "name": "listening", "params": [], "order": [], "returns" : false }, + { "name": "setListening", "params": [false], "order" : [], "returns" : true }, + { "name": "mining", "params": [], "order": [], "returns" : false }, + { "name": "setMining", "params": [false], "order" : [], "returns" : true }, + { "name": "gasPrice", "params": [], "order": [], "returns" : "" }, + { "name": "account", "params": [], "order": [], "returns" : "" }, + { "name": "accounts", "params": [], "order": [], "returns" : [] }, + { "name": "peerCount", "params": [], "order": [], "returns" : 0 }, + { "name": "defaultBlock", "params": [], "order": [], "returns" : 0}, + { "name": "setDefaultBlock", "params": [0], "order": [], "returns" : true}, + { "name": "number", "params": [], "order": [], "returns" : 0}, + + { "name": "balanceAt", "params": [""], "order": [], "returns" : ""}, + { "name": "stateAt", "params": ["", ""], "order": [], "returns": ""}, + { "name": "countAt", "params": [""], "order": [], "returns" : 0.0}, + { "name": "codeAt", "params": [""], "order": [], "returns": ""}, + + { "name": "transact", "params": [{}], "order": [], "returns": ""}, + { "name": "call", "params": [{}], "order": [], "returns": ""}, + + { "name": "blockByHash", "params": [""],"order": [], "returns": {}}, + { "name": "blockByNumber", "params": [0],"order": [], "returns": {}}, + { "name": "transactionByHash", "params": ["", 0], "order": [], "returns": {}}, + { "name": "transactionByNumber", "params": [0, 0], "order": [], "returns": {}}, + { "name": "uncleByHash", "params": ["", 0], "order": [], "returns": {}}, + { "name": "uncleByNumber", "params": [0, 0], "order": [], "returns": {}}, + + { "name": "compile", "params": [""], "order": [], "returns": ""}, + + { "name": "newFilter", "params": [{}], "order": [], "returns": 0}, + { "name": "newFilterString", "params": [""], "order": [], "returns": 0}, + { "name": "uninstallFilter", "params": [0], "order": [], "returns": true}, + { "name": "changed", "params": [0], "order": [], "returns": false}, + { "name": "getMessages", "params": [0], "order": [], "returns": []}, + + { "name": "put", "params": ["", "", ""], "order": [], "returns": true}, + { "name": "get", "params": ["", ""], "order": [], "returns": ""}, + { "name": "putString", "params": ["", "", ""], "order": [], "returns": true}, + { "name": "getString", "params": ["", ""], "order": [], "returns": ""}, + + { "name": "post", "params": [{}], "order": [], "returns": true}, + { "name": "newIdentity", "params": [], "order": [], "returns": ""}, + { "name": "haveIdentity", "params": [""], "order": [], "returns": false}, + { "name": "newGroup", "params": ["", ""], "order": [], "returns": ""}, + { "name": "addToGroup", "params": ["", ""], "order": [], "returns": ""}, - { "method": "shhNewFilter", "params": [{}], "order": [], "returns": 0}, - { "method": "shhUninstallFilter", "params": [0], "order": [], "returns": true}, - { "method": "shhChanged", "params": [0], "order": [], "returns": []} + { "name": "shhNewFilter", "params": [{}], "order": [], "returns": 0}, + { "name": "shhUninstallFilter", "params": [0], "order": [], "returns": true}, + { "name": "shhChanged", "params": [0], "order": [], "returns": []} ] diff --git a/neth/main.cpp b/neth/main.cpp index 4e3a0f40a..8512cf77b 100644 --- a/neth/main.cpp +++ b/neth/main.cpp @@ -27,7 +27,7 @@ #include #include #if ETH_JSONRPC -#include +#include #endif #include #include diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index a11c9fa16..63094fa23 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -18,6 +18,7 @@ target_link_libraries(testeth ${CRYPTOPP_LS}) target_link_libraries(testeth webthree) if(JSONRPC_LS) target_link_libraries(testeth web3jsonrpc) +target_link_libraries(testeth ${JSONRPC_CLIENT_LS}) endif() target_link_libraries(createRandomTest ethereum) diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 033339ec2..f261a5164 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -29,8 +29,10 @@ #include #include #include -#include -#include +#include +#include +//#include +//#include #include #include "JsonSpiritHeaders.h" #include "TestHelper.h" @@ -54,7 +56,8 @@ dev::WebThreeDirect web3(name, dbPath, true, s, np); unique_ptr jsonrpcServer; unique_ptr jsonrpcClient; - +jsonrpc::HttpClient httpClient("http://localhost:8080"); + struct JsonrpcFixture { JsonrpcFixture() { @@ -66,7 +69,7 @@ struct JsonrpcFixture { jsonrpcServer->setIdentities({}); jsonrpcServer->StartListening(); - jsonrpcClient = unique_ptr(new WebThreeStubClient(new jsonrpc::HttpClient("http://localhost:8080"))); + jsonrpcClient = unique_ptr(new WebThreeStubClient(httpClient)); } ~JsonrpcFixture() { diff --git a/test/webthreestubclient.h b/test/webthreestubclient.h index 6beee5bb6..abe146efc 100644 --- a/test/webthreestubclient.h +++ b/test/webthreestubclient.h @@ -1,587 +1,460 @@ /** - * THIS FILE IS GENERATED BY jsonrpcstub, DO NOT CHANGE IT!!!!! + * This file is generated by jsonrpcstub, DO NOT CHANGE IT MANUALLY! */ -#ifndef _WEBTHREESTUBCLIENT_H_ -#define _WEBTHREESTUBCLIENT_H_ +#ifndef JSONRPC_CPP_STUB_WEBTHREESTUBCLIENT_H_ +#define JSONRPC_CPP_STUB_WEBTHREESTUBCLIENT_H_ -#include +#include -class WebThreeStubClient +class WebThreeStubClient : public jsonrpc::Client { public: - WebThreeStubClient(jsonrpc::AbstractClientConnector* conn) - { - this->client = new jsonrpc::Client(conn); - } - ~WebThreeStubClient() - { - delete this->client; - } + WebThreeStubClient(jsonrpc::IClientConnector &conn) : jsonrpc::Client(conn) {} - std::string account() throw (jsonrpc::JsonRpcException) + std::string coinbase() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("account",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("coinbase",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value accounts() throw (jsonrpc::JsonRpcException) + bool setCoinbase(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("accounts",p); - if (result.isArray()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + Json::Value result = this->CallMethod("setCoinbase",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string addToGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + bool listening() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("addToGroup",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("listening",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string balanceAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + bool setListening(const bool& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("balanceAt",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("setListening",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value blockByHash(const std::string& param1) throw (jsonrpc::JsonRpcException) + bool mining() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("blockByHash",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("mining",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value blockByNumber(const int& param1) throw (jsonrpc::JsonRpcException) + bool setMining(const bool& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("blockByNumber",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("setMining",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string call(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + std::string gasPrice() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("call",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("gasPrice",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool changed(const int& param1) throw (jsonrpc::JsonRpcException) + std::string account() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("changed",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("account",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string codeAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + Json::Value accounts() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("codeAt",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("accounts",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string coinbase() throw (jsonrpc::JsonRpcException) + int peerCount() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("coinbase",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("peerCount",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string compile(const std::string& param1) throw (jsonrpc::JsonRpcException) + int defaultBlock() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("compile",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("defaultBlock",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - double countAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + bool setDefaultBlock(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("countAt",p); - if (result.isDouble()) - return result.asDouble(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("setDefaultBlock",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int defaultBlock() throw (jsonrpc::JsonRpcException) + int number() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("defaultBlock",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("number",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string gasPrice() throw (jsonrpc::JsonRpcException) + std::string balanceAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("gasPrice",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + Json::Value result = this->CallMethod("balanceAt",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string get(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + std::string stateAt(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("get",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("stateAt",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value getMessages(const int& param1) throw (jsonrpc::JsonRpcException) + double countAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("getMessages",p); - if (result.isArray()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("countAt",p); + if (result.isDouble()) + return result.asDouble(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string getString(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + std::string codeAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("getString",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("codeAt",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool haveIdentity(const std::string& param1) throw (jsonrpc::JsonRpcException) + std::string transact(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("haveIdentity",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("transact",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool listening() throw (jsonrpc::JsonRpcException) + std::string call(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("listening",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + Json::Value result = this->CallMethod("call",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool mining() throw (jsonrpc::JsonRpcException) + Json::Value blockByHash(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("mining",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + Json::Value result = this->CallMethod("blockByHash",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int newFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + Json::Value blockByNumber(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("newFilter",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("blockByNumber",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int newFilterString(const std::string& param1) throw (jsonrpc::JsonRpcException) + Json::Value transactionByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("newFilterString",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("transactionByHash",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string newGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + Json::Value transactionByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("newGroup",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("transactionByNumber",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string newIdentity() throw (jsonrpc::JsonRpcException) + Json::Value uncleByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("newIdentity",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + p.append(param2); + Json::Value result = this->CallMethod("uncleByHash",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int number() throw (jsonrpc::JsonRpcException) + Json::Value uncleByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("number",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + p.append(param2); + Json::Value result = this->CallMethod("uncleByNumber",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int peerCount() throw (jsonrpc::JsonRpcException) + std::string compile(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("peerCount",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param1); + Json::Value result = this->CallMethod("compile",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool post(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + int newFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("post",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("newFilter",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool put(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + int newFilterString(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); -p.append(param3); - - Json::Value result = this->client->CallMethod("put",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("newFilterString",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool putString(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + bool uninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); -p.append(param3); - - Json::Value result = this->client->CallMethod("putString",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("uninstallFilter",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool setCoinbase(const std::string& param1) throw (jsonrpc::JsonRpcException) + bool changed(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("setCoinbase",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("changed",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool setDefaultBlock(const int& param1) throw (jsonrpc::JsonRpcException) + Json::Value getMessages(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("setDefaultBlock",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("getMessages",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool setListening(const bool& param1) throw (jsonrpc::JsonRpcException) + bool put(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("setListening",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + p.append(param3); + Json::Value result = this->CallMethod("put",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool setMining(const bool& param1) throw (jsonrpc::JsonRpcException) + std::string get(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("setMining",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("get",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value shhChanged(const int& param1) throw (jsonrpc::JsonRpcException) + bool putString(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("shhChanged",p); - if (result.isArray()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + p.append(param3); + Json::Value result = this->CallMethod("putString",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - int shhNewFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + std::string getString(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("shhNewFilter",p); - if (result.isInt()) - return result.asInt(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("getString",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool shhUninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) + bool post(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("shhUninstallFilter",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("post",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string stateAt(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + std::string newIdentity() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("stateAt",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p = Json::nullValue; + Json::Value result = this->CallMethod("newIdentity",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - std::string transact(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + bool haveIdentity(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("transact",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("haveIdentity",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value transactionByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) + std::string newGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("transactionByHash",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("newGroup",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value transactionByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) + std::string addToGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("transactionByNumber",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + p.append(param2); + Json::Value result = this->CallMethod("addToGroup",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value uncleByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) + int shhNewFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("uncleByHash",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("shhNewFilter",p); + if (result.isInt()) + return result.asInt(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - Json::Value uncleByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) + bool shhUninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("uncleByNumber",p); - if (result.isObject()) - return result; - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("shhUninstallFilter",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - bool uninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) + Json::Value shhChanged(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - - Json::Value result = this->client->CallMethod("uninstallFilter",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - + Json::Value result = this->CallMethod("shhChanged",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - - private: - jsonrpc::Client* client; }; -#endif //_WEBTHREESTUBCLIENT_H_ + +#endif //JSONRPC_CPP_WEBTHREESTUBCLIENT_H_ From 7c81eca7e0fbe8c53e4abf93a4c40e3eaacb45f4 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 3 Nov 2014 17:00:39 +0100 Subject: [PATCH 02/38] updated README.md --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 23a202510..8b5ff903d 100644 --- a/README.md +++ b/README.md @@ -36,5 +36,5 @@ Please read [CodingStandards.txt](CodingStandards.txt) thoroughly before making libweb3jsonrpc/abstractwebthreestubserver.h is autogenerated from the jsonrpcstub executable that comes with the libjsonrpc library (json-rpc-cpp project). It shouldn't be maually altered. ```bash -jsonrpcstub -s -c spec.json WebThreeStub +jsonrpcstub spec.json --cpp-server=AbstractWebThreeStubServer ``` From 23c39172f8dc3072cd908724f92a1f4e6ef44187 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 4 Nov 2014 11:15:16 +0100 Subject: [PATCH 03/38] little cleanup after upgrading jsonrpc --- CMakeLists.txt | 4 +- cmake/EthDependenciesDeprecated.cmake | 68 ++++++++++++++------------- eth/CMakeLists.txt | 2 +- eth/main.cpp | 1 - libqethereum/CMakeLists.txt | 2 +- libqethereum/QEthereum.h | 1 - libweb3jsonrpc/CMakeLists.txt | 2 +- libweb3jsonrpc/CorsHttpServer.h | 1 - libweb3jsonrpc/WebThreeStubServer.h | 1 - neth/CMakeLists.txt | 2 +- test/CMakeLists.txt | 2 +- test/jsonrpc.cpp | 2 - 12 files changed, 42 insertions(+), 46 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index b4aa2352f..5e99e1c41 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -119,7 +119,7 @@ endif() add_subdirectory(lllc) add_subdirectory(solc) add_subdirectory(sc) -if (JSONRPC_LS) +if (JSONRPC_SERVER_LS) add_subdirectory(libweb3jsonrpc) endif() if (NOT LANGUAGES) @@ -150,7 +150,7 @@ if (NOT LANGUAGES) if ("${TARGET_PLATFORM}" STREQUAL "w64") cmake_policy(SET CMP0020 NEW) endif () - if (NOT JSONRPC_LS) + if (NOT JSONRPC_SERVER_LS) message(FATAL_ERROR "Alethzero requires jsonrpc.") endif() diff --git a/cmake/EthDependenciesDeprecated.cmake b/cmake/EthDependenciesDeprecated.cmake index d815bef3e..8c6d07e48 100644 --- a/cmake/EthDependenciesDeprecated.cmake +++ b/cmake/EthDependenciesDeprecated.cmake @@ -125,48 +125,50 @@ else() message(STATUS "Failed to find the miniupnpc headers!") endif () - find_path( JSONRPC_ID jsonrpccpp/server.h - /usr/include - /usr/local/include - ) + find_path( JSONRPC_ID jsonrpccpp/server.h + /usr/include + /usr/local/include + ) if ( JSONRPC_ID ) message(STATUS "Found jsonrpc headers") - find_library( JSONRPC_LS NAMES jsonrpccpp-server + + find_library( JSONCPP_LS NAMES jsoncpp + /usr/lib + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + find_library( JSONRPC_SERVER_LS NAMES jsonrpccpp-server PATHS /usr/lib /usr/local/lib /opt/local/lib /usr/lib/*/ ) - - find_library( JSONRPC_COMMON_LS NAMES jsonrpccpp-common - PATHS - /usr/lib - /usr/local/lib - /opt/local/lib - /usr/lib/*/ - ) - - find_library( JSONCPP_LS NAMES jsoncpp - /usr/lib - /usr/local/lib - /opt/local/lib - /usr/lib/*/ - ) - - find_library( JSONRPC_CLIENT_LS NAMES jsonrpccpp-client - PATHS - /usr/lib/ - /usr/local/lib - /opt/local/lib - /usr/lib/*/ - ) - - if ( JSONRPC_LS AND JSONRPC_COMMON_LS ) - message(STATUS "Found jsonrpc library: ${JSONRPC_LS}") - message(STATUS "Found jsonrpc-common library: ${JSONRPC_COMMON_LS}") - add_definitions(-DETH_JSONRPC) + + find_library( JSONRPC_COMMON_LS NAMES jsonrpccpp-common + PATHS + /usr/lib + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + find_library( JSONRPC_CLIENT_LS NAMES jsonrpccpp-client + PATHS + /usr/lib/ + /usr/local/lib + /opt/local/lib + /usr/lib/*/ + ) + + if ( JSONRPC_SERVER_LS AND JSONRPC_COMMON_LS ) + message(STATUS "Found jsonrpc-server library: ${JSONRPC_SERVER_LS}") + message(STATUS "Found jsonrpc-client library: ${JSONRPC_CLIENT_LS}") + message(STATUS "Found jsonrpc-common library: ${JSONRPC_COMMON_LS}") + add_definitions(-DETH_JSONRPC) else () message(STATUS "Failed to find the jsonrpc library!") endif () diff --git a/eth/CMakeLists.txt b/eth/CMakeLists.txt index 7c997b256..1d6325ecc 100644 --- a/eth/CMakeLists.txt +++ b/eth/CMakeLists.txt @@ -17,7 +17,7 @@ if(MINIUPNPC_LS) endif() target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) target_link_libraries(${EXECUTABLE} ${CRYPTOPP_LS}) -if(JSONRPC_LS) +if(JSONRPC_SERVER_LS) target_link_libraries(${EXECUTABLE} web3jsonrpc) endif() if(READLINE_LS) diff --git a/eth/main.cpp b/eth/main.cpp index 447729c1a..25ebe5cdc 100644 --- a/eth/main.cpp +++ b/eth/main.cpp @@ -28,7 +28,6 @@ #include #include #if ETH_JSONRPC -//#include #include #endif #include diff --git a/libqethereum/CMakeLists.txt b/libqethereum/CMakeLists.txt index ba7cd3b67..709f7f066 100644 --- a/libqethereum/CMakeLists.txt +++ b/libqethereum/CMakeLists.txt @@ -59,7 +59,7 @@ endif() include_directories(/) qt5_use_modules(${EXECUTABLE} Core Gui WebKit WebKitWidgets Widgets Network Quick Qml) -target_link_libraries(${EXECUTABLE} ethereum secp256k1 ${CRYPTOPP_LS} ${JSONRPC_LS}) +target_link_libraries(${EXECUTABLE} ethereum secp256k1 ${CRYPTOPP_LS} ${JSONRPC_SERVER_LS}) if (APPLE) if (${ADDFRAMEWORKS}) diff --git a/libqethereum/QEthereum.h b/libqethereum/QEthereum.h index b4c17fdab..eeb5a493b 100644 --- a/libqethereum/QEthereum.h +++ b/libqethereum/QEthereum.h @@ -26,7 +26,6 @@ #include #include #include -//#include class QWebThree: public QObject { diff --git a/libweb3jsonrpc/CMakeLists.txt b/libweb3jsonrpc/CMakeLists.txt index 6966cd10a..ec8adbffb 100644 --- a/libweb3jsonrpc/CMakeLists.txt +++ b/libweb3jsonrpc/CMakeLists.txt @@ -24,8 +24,8 @@ endif() target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) target_link_libraries(${EXECUTABLE} ${CRYPTOPP_LS}) target_link_libraries(${EXECUTABLE} ${JSONCPP_LS}) -target_link_libraries(${EXECUTABLE} ${JSONRPC_LS}) target_link_libraries(${EXECUTABLE} ${JSONRPC_COMMON_LS}) +target_link_libraries(${EXECUTABLE} ${JSONRPC_SERVER_LS}) target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) if(READLINE_LS) target_link_libraries(${EXECUTABLE} ${READLINE_LS}) diff --git a/libweb3jsonrpc/CorsHttpServer.h b/libweb3jsonrpc/CorsHttpServer.h index 5dd3130a4..e697ecaa1 100644 --- a/libweb3jsonrpc/CorsHttpServer.h +++ b/libweb3jsonrpc/CorsHttpServer.h @@ -20,7 +20,6 @@ */ #include -//#include namespace jsonrpc { diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 193f1f6ff..5a1f04d8e 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -29,7 +29,6 @@ #pragma warning(pop) #include -//#include #include #include #pragma GCC diagnostic push diff --git a/neth/CMakeLists.txt b/neth/CMakeLists.txt index ac275f663..d8b3d8f75 100644 --- a/neth/CMakeLists.txt +++ b/neth/CMakeLists.txt @@ -18,7 +18,7 @@ target_link_libraries(${EXECUTABLE} ${MINIUPNPC_LS}) endif() target_link_libraries(${EXECUTABLE} ${LEVELDB_LS}) target_link_libraries(${EXECUTABLE} ${CRYPTOPP_LS}) -if(JSONRPC_LS) +if(JSONRPC_SERVER_LS) target_link_libraries(${EXECUTABLE} web3jsonrpc) endif() diff --git a/test/CMakeLists.txt b/test/CMakeLists.txt index 63094fa23..52a73f84a 100644 --- a/test/CMakeLists.txt +++ b/test/CMakeLists.txt @@ -16,7 +16,7 @@ target_link_libraries(testeth gmp) target_link_libraries(testeth solidity) target_link_libraries(testeth ${CRYPTOPP_LS}) target_link_libraries(testeth webthree) -if(JSONRPC_LS) +if(JSONRPC_SERVER_LS) target_link_libraries(testeth web3jsonrpc) target_link_libraries(testeth ${JSONRPC_CLIENT_LS}) endif() diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index f261a5164..1eee21357 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -31,8 +31,6 @@ #include #include #include -//#include -//#include #include #include "JsonSpiritHeaders.h" #include "TestHelper.h" From 874abf6e0b16f892f11d93b4ea2f595ced11623f Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 4 Nov 2014 12:03:24 +0100 Subject: [PATCH 04/38] fixed WebThreeStubServer constructor --- alethzero/MainWin.cpp | 2 +- eth/main.cpp | 9 ++++++--- libweb3jsonrpc/WebThreeStubServer.cpp | 4 ++-- libweb3jsonrpc/WebThreeStubServer.h | 2 +- neth/main.cpp | 7 +++++-- test/jsonrpc.cpp | 4 +++- third/MainWin.cpp | 2 +- 7 files changed, 19 insertions(+), 11 deletions(-) diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index f413532b7..46d09f8c1 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -149,7 +149,7 @@ Main::Main(QWidget *parent) : m_webThree.reset(new WebThreeDirect(string("AlethZero/v") + dev::Version + "/" DEV_QUOTED(ETH_BUILD_TYPE) "/" DEV_QUOTED(ETH_BUILD_PLATFORM), getDataDir() + "/AlethZero", false, {"eth", "shh"})); - m_server = unique_ptr(new WebThreeStubServer(&m_qwebConnector, *web3(), keysAsVector(m_myKeys))); + m_server = unique_ptr(new WebThreeStubServer(m_qwebConnector, *web3(), keysAsVector(m_myKeys))); m_server->setIdentities(keysAsVector(owned())); m_server->StartListening(); diff --git a/eth/main.cpp b/eth/main.cpp index 25ebe5cdc..fb9e7e4a0 100644 --- a/eth/main.cpp +++ b/eth/main.cpp @@ -336,10 +336,12 @@ int main(int argc, char** argv) web3.connect(remoteHost, remotePort); #if ETH_JSONRPC - auto_ptr jsonrpcServer; + unique_ptr jsonrpcServer; + unique_ptr jsonrpcConnector; if (jsonrpc > -1) { - jsonrpcServer = auto_ptr(new WebThreeStubServer(new jsonrpc::CorsHttpServer(jsonrpc), web3, {us})); + jsonrpcConnector = unique_ptr(new jsonrpc::CorsHttpServer(jsonrpc)); + jsonrpcServer = unique_ptr(new WebThreeStubServer(*jsonrpcConnector.get(), web3, {us})); jsonrpcServer->setIdentities({us}); jsonrpcServer->StartListening(); } @@ -427,7 +429,8 @@ int main(int argc, char** argv) { if (jsonrpc < 0) jsonrpc = 8080; - jsonrpcServer = auto_ptr(new WebThreeStubServer(new jsonrpc::CorsHttpServer(jsonrpc), web3, {us})); + jsonrpcConnector = unique_ptr(new jsonrpc::CorsHttpServer(jsonrpc)); + jsonrpcServer = auto_ptr(new WebThreeStubServer(*jsonrpcConnector.get(), web3, {us})); jsonrpcServer->setIdentities({us}); jsonrpcServer->StartListening(); } diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index ed5907f53..aacc64a4e 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -216,8 +216,8 @@ static Json::Value toJson(h256 const& _h, shh::Envelope const& _e, shh::Message } -WebThreeStubServer::WebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, WebThreeDirect& _web3, std::vector const& _accounts): - AbstractWebThreeStubServer(*_conn), +WebThreeStubServer::WebThreeStubServer(jsonrpc::AbstractServerConnector& _conn, WebThreeDirect& _web3, std::vector const& _accounts): + AbstractWebThreeStubServer(_conn), m_web3(_web3) { setAccounts(_accounts); diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 5a1f04d8e..f6b5cb224 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -60,7 +60,7 @@ class Interface; class WebThreeStubServer: public AbstractWebThreeStubServer { public: - WebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); + WebThreeStubServer(jsonrpc::AbstractServerConnector& _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); virtual std::string account(); virtual Json::Value accounts(); diff --git a/neth/main.cpp b/neth/main.cpp index 8512cf77b..b2b9a155f 100644 --- a/neth/main.cpp +++ b/neth/main.cpp @@ -476,9 +476,11 @@ int main(int argc, char** argv) #if ETH_JSONRPC auto_ptr jsonrpcServer; + unique_ptr jsonrpcConnector; if (jsonrpc > -1) { - jsonrpcServer = auto_ptr(new WebThreeStubServer(new jsonrpc::HttpServer(jsonrpc), web3, {us})); + jsonrpcConnector = unique_ptr(new jsonrpc::HttpServer(jsonrpc)); + jsonrpcServer = auto_ptr(new WebThreeStubServer(*jsonrpcConnector.get(), web3, {us})); jsonrpcServer->setIdentities({us}); jsonrpcServer->StartListening(); } @@ -552,7 +554,8 @@ int main(int argc, char** argv) { if (jsonrpc < 0) jsonrpc = 8080; - jsonrpcServer = auto_ptr(new WebThreeStubServer(new jsonrpc::HttpServer(jsonrpc), web3, {us})); + jsonrpcConnector = unique_ptr(new jsonrpc::HttpServer(jsonrpc)); + jsonrpcServer = auto_ptr(new WebThreeStubServer(*jsonrpcConnector.get(), web3, {us})); jsonrpcServer->setIdentities({us}); jsonrpcServer->StartListening(); } diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 1eee21357..80c4f5018 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -54,6 +54,7 @@ dev::WebThreeDirect web3(name, dbPath, true, s, np); unique_ptr jsonrpcServer; unique_ptr jsonrpcClient; +unique_ptr jsonrpcConnector; jsonrpc::HttpClient httpClient("http://localhost:8080"); struct JsonrpcFixture { @@ -63,7 +64,8 @@ struct JsonrpcFixture { web3.setIdealPeerCount(5); web3.ethereum()->setForceMining(true); - jsonrpcServer = unique_ptr(new WebThreeStubServer(new jsonrpc::CorsHttpServer(8080), web3, {})); + jsonrpcConnector = unique_ptr(new jsonrpc::CorsHttpServer(8080)); + jsonrpcServer = unique_ptr(new WebThreeStubServer(*jsonrpcConnector.get(), web3, {})); jsonrpcServer->setIdentities({}); jsonrpcServer->StartListening(); diff --git a/third/MainWin.cpp b/third/MainWin.cpp index c2dcb7ce2..7be9d8db3 100644 --- a/third/MainWin.cpp +++ b/third/MainWin.cpp @@ -117,7 +117,7 @@ Main::Main(QWidget *parent) : m_web3.reset(new WebThreeDirect("Third", getDataDir() + "/Third", false, {"eth", "shh"})); m_web3->connect(Host::pocHost()); - m_server = unique_ptr(new WebThreeStubServer(&m_qwebConnector, *web3(), keysAsVector(m_myKeys))); + m_server = unique_ptr(new WebThreeStubServer(m_qwebConnector, *web3(), keysAsVector(m_myKeys))); m_server->setIdentities(keysAsVector(owned())); m_server->StartListening(); From 79267006ce3072390ebab78114004a4eab32e4a5 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 10 Nov 2014 21:32:13 +0100 Subject: [PATCH 05/38] js abi connection --- libethereum/Client.cpp | 2 +- libjsqrc/main.js | 14 +++-- libweb3jsonrpc/CMakeLists.txt | 1 + libweb3jsonrpc/WebThreeStubServer.cpp | 67 ++++++++++++++++++-- libweb3jsonrpc/WebThreeStubServer.h | 6 +- libweb3jsonrpc/abstractwebthreestubserver.h | 36 +++++++++-- libweb3jsonrpc/spec.json | 6 +- test/webthreestubclient.h | 70 ++++++++++++++++----- 8 files changed, 170 insertions(+), 32 deletions(-) diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index d87e9c33e..0be499541 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -341,7 +341,7 @@ bytes Client::call(Secret _secret, u256 _value, Address _dest, bytes const& _dat n = temp.transactionsFrom(toAddress(_secret)); } Transaction t(_value, _gasPrice, _gas, _dest, _data, n, _secret); - u256 gasUsed = temp.execute(t.data(), &out, false); + u256 gasUsed = temp.execute(t.rlp(), &out, false); (void)gasUsed; // TODO: do something with gasused which it returns. } catch (...) diff --git a/libjsqrc/main.js b/libjsqrc/main.js index eb1dd25b9..c07a938e4 100644 --- a/libjsqrc/main.js +++ b/libjsqrc/main.js @@ -87,7 +87,11 @@ { name: 'block', call: blockCall }, { name: 'transaction', call: transactionCall }, { name: 'uncle', call: uncleCall }, - { name: 'compile', call: 'compile' } + { name: 'compilers', call: 'compilers' }, + { name: 'lll', call: 'lll' }, + { name: 'solidity', call: 'solidity' }, + { name: 'contractCreate', call: 'contractCreate' }, + { name: 'contractCall', call: 'contractCall' } ]; return methods; }; @@ -414,10 +418,8 @@ }; Filter.prototype.trigger = function(messages) { - if (!(messages instanceof Array) || messages.length) { - for(var i = 0; i < this.callbacks.length; i++) { - this.callbacks[i].call(this, messages); - } + for(var i = 0; i < this.callbacks.length; i++) { + this.callbacks[i].call(this, messages); } }; @@ -446,7 +448,7 @@ if(data._id) { var cb = web3._callbacks[data._id]; if (cb) { - cb.call(this, data.error, data.data); + cb.call(this, data.error, data.data) delete web3._callbacks[data._id]; } } diff --git a/libweb3jsonrpc/CMakeLists.txt b/libweb3jsonrpc/CMakeLists.txt index b24a11196..2f2219461 100644 --- a/libweb3jsonrpc/CMakeLists.txt +++ b/libweb3jsonrpc/CMakeLists.txt @@ -18,6 +18,7 @@ endif() target_link_libraries(${EXECUTABLE} webthree) target_link_libraries(${EXECUTABLE} secp256k1) target_link_libraries(${EXECUTABLE} gmp) +target_link_libraries(${EXECUTABLE} solidity) if(MINIUPNPC_LS) target_link_libraries(${EXECUTABLE} ${MINIUPNPC_LS}) endif() diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 40ec744bd..6b1ab6d68 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -31,6 +31,8 @@ #include #include #include +#include +#include using namespace std; using namespace dev; @@ -373,13 +375,13 @@ static TransactionSkeleton toTransaction(Json::Value const& _json) ret.data = jsToBytes(_json["code"].asString()); else if (_json["data"].isArray()) for (auto i: _json["data"]) - dev::operator +=(ret.data, jsToBytes(jsPadded(i.asString(), 32))); + dev::operator +=(ret.data, asBytes(jsPadded(i.asString(), 32))); else if (_json["code"].isArray()) for (auto i: _json["code"]) - dev::operator +=(ret.data, jsToBytes(jsPadded(i.asString(), 32))); + dev::operator +=(ret.data, asBytes(jsPadded(i.asString(), 32))); else if (_json["dataclose"].isArray()) for (auto i: _json["dataclose"]) - dev::operator +=(ret.data, jsToBytes(i.asString())); + dev::operator +=(ret.data, asBytes(i.asString())); } return ret; } @@ -516,9 +518,64 @@ std::string WebThreeStubServer::newIdentity() return toJS(kp.pub()); } -std::string WebThreeStubServer::compile(string const& _s) +Json::Value WebThreeStubServer::compilers() { - return toJS(dev::eth::compileLLL(_s)); + Json::Value ret(Json::arrayValue); + ret.append("lll"); + ret.append("solidity"); + return ret; +} + +static bytes paramsToBytes(Json::Value const& _params) +{ + bytes data; + if (_params.isArray()) + for (auto i: _params) +// data += asBytes(i.asString()); +// data += toBigEndian(jsToU256(i.asString())); + data += asBytes(jsPadded(i.asString(), 33)); + cwarn << data; + return data; +} + +std::string WebThreeStubServer::contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params) +{ + auto from = m_accounts.begin()->first; + for (auto a: m_accounts) + if (client()->balanceAt(a.first) > client()->balanceAt(from)) + from = a.first; + + cwarn << "Silently signing transaction from address" << from.abridged() << ": User validation hook goes here."; + + auto gasPrice = 10 * dev::eth::szabo; + auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); + auto bytes = paramsToBytes(_params); + return toJS(client()->call(m_accounts[from].secret(), jsToU256(_value), jsToAddress(_address), paramsToBytes(_params), gas, gasPrice)); +} + +std::string WebThreeStubServer::contractCreate(std::string const& _bytecode, std::string const& _value) +{ + auto from = m_accounts.begin()->first; + for (auto a: m_accounts) + if (client()->balanceAt(a.first) > client()->balanceAt(from)) + from = a.first; + + cwarn << "Silently signing transaction from address" << from.abridged() << ": User validation hook goes here."; + + auto gasPrice = 10 * dev::eth::szabo; + auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); + return toJS(client()->transact(m_accounts[from].secret(), jsToU256(_value), jsToBytes(_bytecode), gas, gasPrice)); +} + +std::string WebThreeStubServer::lll(std::string const& _code) +{ + return toJS(dev::eth::compileLLL(_code)); +} + +std::string WebThreeStubServer::solidity(std::string const& _code) +{ + shared_ptr scanner = make_shared(); + return toJS(dev::solidity::CompilerStack::compile(_code, scanner)); } int WebThreeStubServer::number() diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 33163b75e..1ca77b497 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -73,7 +73,9 @@ public: virtual bool changed(int const& _id); virtual std::string codeAt(std::string const& _address); virtual std::string coinbase(); - virtual std::string compile(std::string const& _s); + virtual Json::Value compilers(); + virtual std::string contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params); + virtual std::string contractCreate(std::string const& _bytecode, std::string const& _value); virtual double countAt(std::string const& _address); virtual int defaultBlock(); virtual std::string gasPrice(); @@ -82,6 +84,7 @@ public: virtual std::string getString(std::string const& _name, std::string const& _key); virtual bool haveIdentity(std::string const& _id); virtual bool listening(); + virtual std::string lll(std::string const& _code); virtual bool mining(); virtual int newFilter(Json::Value const& _json); virtual int newFilterString(std::string const& _filter); @@ -99,6 +102,7 @@ public: virtual Json::Value shhChanged(int const& _id); virtual int shhNewFilter(Json::Value const& _json); virtual bool shhUninstallFilter(int const& _id); + virtual std::string solidity(std::string const& _code); virtual std::string stateAt(std::string const& _address, std::string const& _storage); virtual std::string transact(Json::Value const& _json); virtual Json::Value transactionByHash(std::string const& _hash, int const& _i); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index 66b9ff77d..97b7a219f 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -22,7 +22,9 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::changedI); this->bindAndAddMethod(new jsonrpc::Procedure("codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::coinbaseI); - this->bindAndAddMethod(new jsonrpc::Procedure("compile", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::compileI); + this->bindAndAddMethod(new jsonrpc::Procedure("compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::compilersI); + this->bindAndAddMethod(new jsonrpc::Procedure("contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::contractCallI); + this->bindAndAddMethod(new jsonrpc::Procedure("contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::contractCreateI); this->bindAndAddMethod(new jsonrpc::Procedure("countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::defaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::gasPriceI); @@ -31,6 +33,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("getString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getStringI); this->bindAndAddMethod(new jsonrpc::Procedure("haveIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::haveIdentityI); this->bindAndAddMethod(new jsonrpc::Procedure("listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::listeningI); + this->bindAndAddMethod(new jsonrpc::Procedure("lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::lllI); this->bindAndAddMethod(new jsonrpc::Procedure("mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::miningI); this->bindAndAddMethod(new jsonrpc::Procedure("newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::newFilterI); this->bindAndAddMethod(new jsonrpc::Procedure("newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newFilterStringI); @@ -48,6 +51,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("shhChanged", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhChangedI); this->bindAndAddMethod(new jsonrpc::Procedure("shhNewFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shhNewFilterI); this->bindAndAddMethod(new jsonrpc::Procedure("shhUninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhUninstallFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("solidity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::solidityI); this->bindAndAddMethod(new jsonrpc::Procedure("stateAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::stateAtI); this->bindAndAddMethod(new jsonrpc::Procedure("transact", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::transactI); this->bindAndAddMethod(new jsonrpc::Procedure("transactionByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::transactionByHashI); @@ -103,9 +107,19 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServercoinbase(); } - inline virtual void compileI(const Json::Value& request, Json::Value& response) + inline virtual void compilersI(const Json::Value& request, Json::Value& response) { - response = this->compile(request[0u].asString()); + response = this->compilers(); + } + + inline virtual void contractCallI(const Json::Value& request, Json::Value& response) + { + response = this->contractCall(request[0u].asString(), request[1u].asString(), request[2u]); + } + + inline virtual void contractCreateI(const Json::Value& request, Json::Value& response) + { + response = this->contractCreate(request[0u].asString(), request[1u].asString()); } inline virtual void countAtI(const Json::Value& request, Json::Value& response) @@ -148,6 +162,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerlistening(); } + inline virtual void lllI(const Json::Value& request, Json::Value& response) + { + response = this->lll(request[0u].asString()); + } + inline virtual void miningI(const Json::Value& request, Json::Value& response) { response = this->mining(); @@ -233,6 +252,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServershhUninstallFilter(request[0u].asInt()); } + inline virtual void solidityI(const Json::Value& request, Json::Value& response) + { + response = this->solidity(request[0u].asString()); + } + inline virtual void stateAtI(const Json::Value& request, Json::Value& response) { response = this->stateAt(request[0u].asString(), request[1u].asString()); @@ -278,7 +302,9 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient; } - std::string account() throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("account",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - Json::Value accounts() throw (jsonrpc::JsonRpcException) { Json::Value p; @@ -147,12 +135,40 @@ p.append(param2); } - std::string compile(const std::string& param1) throw (jsonrpc::JsonRpcException) + Json::Value compilers() throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p = Json::nullValue; + Json::Value result = this->client->CallMethod("compilers",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + + std::string contractCall(const std::string& param1, const std::string& param2, const Json::Value& param3) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); +p.append(param2); +p.append(param3); + + Json::Value result = this->client->CallMethod("contractCall",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + + std::string contractCreate(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("compile",p); + Json::Value result = this->client->CallMethod("contractCreate",p); if (result.isString()) return result.asString(); else @@ -263,6 +279,19 @@ p.append(param2); } + std::string lll(const std::string& param1) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); + + Json::Value result = this->client->CallMethod("lll",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + bool mining() throw (jsonrpc::JsonRpcException) { Json::Value p; @@ -485,6 +514,19 @@ p.append(param3); } + std::string solidity(const std::string& param1) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); + + Json::Value result = this->client->CallMethod("solidity",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + std::string stateAt(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; From 6cc9e6952e5bf14b014e0da4d96868bac6806fc8 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 10 Nov 2014 22:51:10 +0100 Subject: [PATCH 06/38] merge --- alethzero/MainWin.cpp | 2 +- alethzero/OurWebThreeStubServer.cpp | 2 +- alethzero/OurWebThreeStubServer.h | 2 +- libethereum/Executive.cpp | 4 +- libevmcore/Assembly.cpp | 81 +- libevmcore/Assembly.h | 2 +- libevmcore/Instruction.cpp | 260 ++-- libevmcore/Instruction.h | 1 + libjsqrc/main.js | 80 +- libjsqrc/setup.js | 2 +- libqethereum/QEthereum.cpp | 29 +- libsolidity/Compiler.cpp | 9 +- libsolidity/Compiler.h | 4 +- libsolidity/CompilerContext.h | 2 +- libsolidity/CompilerStack.cpp | 5 +- libsolidity/CompilerStack.h | 2 +- libweb3jsonrpc/WebThreeStubServer.cpp | 94 +- libweb3jsonrpc/WebThreeStubServer.h | 96 +- libweb3jsonrpc/abstractwebthreestubserver.h | 368 ++--- libweb3jsonrpc/spec.json | 106 +- solc/main.cpp | 10 +- test/TestHelper.cpp | 43 +- test/TestHelper.h | 1 + test/jsonrpc.cpp | 46 +- test/stPreCompiledContractsFiller.json | 717 ++++++++++ test/stSystemOperationsTestFiller.json | 1334 +++++++++++++++++++ test/state.cpp | 11 +- test/vm.cpp | 35 +- test/vmArithmeticTestFiller.json | 14 +- test/webthreestubclient.h | 356 ++--- 30 files changed, 2956 insertions(+), 762 deletions(-) create mode 100644 test/stPreCompiledContractsFiller.json create mode 100644 test/stSystemOperationsTestFiller.json diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index e43a61d37..8fe76e24b 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -1605,7 +1605,7 @@ void Main::on_data_textChanged() shared_ptr scanner = make_shared(); try { - m_data = dev::solidity::CompilerStack::compile(src, scanner); + m_data = dev::solidity::CompilerStack::compile(src, scanner, m_enableOptimizer); } catch (dev::Exception const& exception) { diff --git a/alethzero/OurWebThreeStubServer.cpp b/alethzero/OurWebThreeStubServer.cpp index ca1b77649..a40727e1e 100644 --- a/alethzero/OurWebThreeStubServer.cpp +++ b/alethzero/OurWebThreeStubServer.cpp @@ -28,7 +28,7 @@ OurWebThreeStubServer::OurWebThreeStubServer(jsonrpc::AbstractServerConnector* _ WebThreeStubServer(_conn, _web3, _accounts) {} -std::string OurWebThreeStubServer::newIdentity() +std::string OurWebThreeStubServer::shh_newIdentity() { dev::KeyPair kp = dev::KeyPair::create(); emit onNewId(QString::fromStdString(toJS(kp.sec()))); diff --git a/alethzero/OurWebThreeStubServer.h b/alethzero/OurWebThreeStubServer.h index be06da62d..b3492df5e 100644 --- a/alethzero/OurWebThreeStubServer.h +++ b/alethzero/OurWebThreeStubServer.h @@ -31,7 +31,7 @@ class OurWebThreeStubServer: public QObject, public WebThreeStubServer public: OurWebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); - virtual std::string newIdentity() override; + virtual std::string shh_newIdentity() override; signals: void onNewId(QString _s); diff --git a/libethereum/Executive.cpp b/libethereum/Executive.cpp index 71fc12a8c..fb89eb21e 100644 --- a/libethereum/Executive.cpp +++ b/libethereum/Executive.cpp @@ -80,14 +80,14 @@ bool Executive::setup(bytesConstRef _rlp) if (m_s.balance(m_sender) < cost) { clog(StateDetail) << "Not enough cash: Require >" << cost << " Got" << m_s.balance(m_sender); - BOOST_THROW_EXCEPTION(NotEnoughCash()); + BOOST_THROW_EXCEPTION(NotEnoughCash() << RequirementError((int)cost, (int)m_s.balance(m_sender))); } u256 startGasUsed = m_s.gasUsed(); if (startGasUsed + m_t.gas() > m_s.m_currentBlock.gasLimit) { clog(StateDetail) << "Too much gas used in this block: Require <" << (m_s.m_currentBlock.gasLimit - startGasUsed) << " Got" << m_t.gas(); - BOOST_THROW_EXCEPTION(BlockGasLimitReached()); + BOOST_THROW_EXCEPTION(BlockGasLimitReached() << RequirementError((int)(m_s.m_currentBlock.gasLimit - startGasUsed), (int)m_t.gas())); } // Increment associated nonce for sender. diff --git a/libevmcore/Assembly.cpp b/libevmcore/Assembly.cpp index d4f6c0a73..4725c8c1a 100644 --- a/libevmcore/Assembly.cpp +++ b/libevmcore/Assembly.cpp @@ -70,7 +70,12 @@ unsigned Assembly::bytesRequired() const case PushData: case PushSub: ret += 1 + br; - default:; + break; + case NoOptimizeBegin: + case NoOptimizeEnd: + break; + default: + BOOST_THROW_EXCEPTION(InvalidOpcode()); } if (dev::bytesRequired(ret) <= br) return ret; @@ -140,9 +145,17 @@ ostream& dev::eth::operator<<(ostream& _out, AssemblyItemsConstRef _i) case PushSubSize: _out << " PUSHss[" << hex << h256(i.data()).abridged() << "]"; break; + case NoOptimizeBegin: + _out << " DoNotOptimze{{"; + break; + case NoOptimizeEnd: + _out << " DoNotOptimze}}"; + break; case UndefinedItem: _out << " ???"; - default:; + break; + default: + BOOST_THROW_EXCEPTION(InvalidOpcode()); } return _out; } @@ -177,7 +190,14 @@ ostream& Assembly::streamRLP(ostream& _out, string const& _prefix) const case PushData: _out << _prefix << " PUSH [" << hex << (unsigned)i.m_data << "]" << endl; break; - default:; + case NoOptimizeBegin: + _out << _prefix << "DoNotOptimze{{" << endl; + break; + case NoOptimizeEnd: + _out << _prefix << "DoNotOptimze}}" << endl; + break; + default: + BOOST_THROW_EXCEPTION(InvalidOpcode()); } if (m_data.size() || m_subs.size()) @@ -217,6 +237,12 @@ inline bool matches(AssemblyItemsConstRef _a, AssemblyItemsConstRef _b) return true; } +inline bool popCountIncreased(AssemblyItemsConstRef _pre, AssemblyItems const& _post) +{ + auto isPop = [](AssemblyItem const& _item) -> bool { return _item.match(AssemblyItem(Instruction::POP)); }; + return count_if(begin(_post), end(_post), isPop) > count_if(begin(_pre), end(_pre), isPop); +} + struct OptimiserChannel: public LogChannel { static const char* name() { return "OPT"; } static const int verbosity = 12; }; #define copt dev::LogOutputStream() @@ -224,6 +250,14 @@ Assembly& Assembly::optimise(bool _enable) { if (!_enable) return *this; + auto signextend = [](u256 a, u256 b) -> u256 + { + if (a >= 31) + return b; + unsigned testBit = unsigned(a) * 8 + 7; + u256 mask = (u256(1) << testBit) - 1; + return boost::multiprecision::bit_test(b, testBit) ? b | ~mask : b & mask; + }; map> c_simple = { { Instruction::SUB, [](u256 a, u256 b)->u256{return a - b;} }, @@ -232,6 +266,7 @@ Assembly& Assembly::optimise(bool _enable) { Instruction::MOD, [](u256 a, u256 b)->u256{return a % b;} }, { Instruction::SMOD, [](u256 a, u256 b)->u256{return s2u(u2s(a) % u2s(b));} }, { Instruction::EXP, [](u256 a, u256 b)->u256{return (u256)boost::multiprecision::powm((bigint)a, (bigint)b, bigint(2) << 256);} }, + { Instruction::SIGNEXTEND, signextend }, { Instruction::LT, [](u256 a, u256 b)->u256{return a < b ? 1 : 0;} }, { Instruction::GT, [](u256 a, u256 b)->u256{return a > b ? 1 : 0;} }, { Instruction::SLT, [](u256 a, u256 b)->u256{return u2s(a) < u2s(b) ? 1 : 0;} }, @@ -242,6 +277,9 @@ Assembly& Assembly::optimise(bool _enable) { { Instruction::ADD, [](u256 a, u256 b)->u256{return a + b;} }, { Instruction::MUL, [](u256 a, u256 b)->u256{return a * b;} }, + { Instruction::AND, [](u256 a, u256 b)->u256{return a & b;} }, + { Instruction::OR, [](u256 a, u256 b)->u256{return a | b;} }, + { Instruction::XOR, [](u256 a, u256 b)->u256{return a ^ b;} }, }; std::vector>> rules = { @@ -260,8 +298,23 @@ Assembly& Assembly::optimise(bool _enable) { rules.push_back({ { Push, Push, i.first }, [&](AssemblyItemsConstRef m) -> AssemblyItems { return { i.second(m[1].data(), m[0].data()) }; } }); rules.push_back({ { Push, i.first, Push, i.first }, [&](AssemblyItemsConstRef m) -> AssemblyItems { return { i.second(m[2].data(), m[0].data()), i.first }; } }); - rules.push_back({ { PushTag, Instruction::JUMP, Tag }, [&](AssemblyItemsConstRef m) -> AssemblyItems { if (m[0].m_data == m[2].m_data) return {}; else return m.toVector(); }}); } + // jump to next instruction + rules.push_back({ { PushTag, Instruction::JUMP, Tag }, [&](AssemblyItemsConstRef m) -> AssemblyItems { if (m[0].m_data == m[2].m_data) return {m[2]}; else return m.toVector(); }}); + + // pop optimization, do not compute values that are popped again anyway + rules.push_back({ { AssemblyItem(UndefinedItem), Instruction::POP }, [](AssemblyItemsConstRef m) -> AssemblyItems + { + if (m[0].type() != Operation) + return m.toVector(); + Instruction instr = Instruction(byte(m[0].data())); + if (Instruction::DUP1 <= instr && instr <= Instruction::DUP16) + return {}; + InstructionInfo info = instructionInfo(instr); + if (info.sideEffects || info.additional != 0 || info.ret != 1) + return m.toVector(); + return AssemblyItems(info.args, Instruction::POP); + } }); copt << *this; @@ -269,16 +322,21 @@ Assembly& Assembly::optimise(bool _enable) for (unsigned count = 1; count > 0; total += count) { count = 0; - map tags; for (unsigned i = 0; i < m_items.size(); ++i) { + if (m_items[i].type() == NoOptimizeBegin) + { + while (i < m_items.size() && m_items[i].type() != NoOptimizeEnd) + ++i; + continue; + } for (auto const& r: rules) { auto vr = AssemblyItemsConstRef(&m_items).cropped(i, r.first.size()); - if (matches(&r.first, vr)) + if (matches(vr, &r.first)) { auto rw = r.second(vr); - if (rw.size() < vr.size()) + if (rw.size() < vr.size() || (rw.size() == vr.size() && popCountIncreased(vr, rw))) { copt << vr << "matches" << AssemblyItemsConstRef(&r.first) << "becomes..."; for (unsigned j = 0; j < vr.size(); ++j) @@ -297,6 +355,8 @@ Assembly& Assembly::optimise(bool _enable) bool o = false; while (m_items.size() > i + 1 && m_items[i + 1].type() != Tag) { + if (m_items[i + 1].type() == NoOptimizeBegin) + break; m_items.erase(m_items.begin() + i + 1); o = true; } @@ -308,6 +368,7 @@ Assembly& Assembly::optimise(bool _enable) } } + map tags; for (unsigned i = 0; i < m_items.size(); ++i) if (m_items[i].type() == Tag) tags.insert(make_pair(m_items[i].data(), i)); @@ -416,7 +477,11 @@ bytes Assembly::assemble() const tagPos[(unsigned)i.m_data] = ret.size(); ret.push_back((byte)Instruction::JUMPDEST); break; - default:; + case NoOptimizeBegin: + case NoOptimizeEnd: + break; + default: + BOOST_THROW_EXCEPTION(InvalidOpcode()); } for (auto const& i: tagRef) diff --git a/libevmcore/Assembly.h b/libevmcore/Assembly.h index ef5294a54..b8e59a474 100644 --- a/libevmcore/Assembly.h +++ b/libevmcore/Assembly.h @@ -32,7 +32,7 @@ namespace dev namespace eth { -enum AssemblyItemType { UndefinedItem, Operation, Push, PushString, PushTag, PushSub, PushSubSize, Tag, PushData }; +enum AssemblyItemType { UndefinedItem, Operation, Push, PushString, PushTag, PushSub, PushSubSize, Tag, PushData, NoOptimizeBegin, NoOptimizeEnd }; class Assembly; diff --git a/libevmcore/Instruction.cpp b/libevmcore/Instruction.cpp index ad27b28ef..2df77a3c5 100644 --- a/libevmcore/Instruction.cpp +++ b/libevmcore/Instruction.cpp @@ -162,136 +162,136 @@ const std::map dev::eth::c_instructions = }; static const std::map c_instructionInfo = -{ // Add, Args, Ret - { Instruction::STOP, { "STOP", 0, 0, 0 } }, - { Instruction::ADD, { "ADD", 0, 2, 1 } }, - { Instruction::SUB, { "SUB", 0, 2, 1 } }, - { Instruction::MUL, { "MUL", 0, 2, 1 } }, - { Instruction::DIV, { "DIV", 0, 2, 1 } }, - { Instruction::SDIV, { "SDIV", 0, 2, 1 } }, - { Instruction::MOD, { "MOD", 0, 2, 1 } }, - { Instruction::SMOD, { "SMOD", 0, 2, 1 } }, - { Instruction::EXP, { "EXP", 0, 2, 1 } }, - { Instruction::NOT, { "NOT", 0, 1, 1 } }, - { Instruction::LT, { "LT", 0, 2, 1 } }, - { Instruction::GT, { "GT", 0, 2, 1 } }, - { Instruction::SLT, { "SLT", 0, 2, 1 } }, - { Instruction::SGT, { "SGT", 0, 2, 1 } }, - { Instruction::EQ, { "EQ", 0, 2, 1 } }, - { Instruction::ISZERO, { "ISZERO", 0, 1, 1 } }, - { Instruction::AND, { "AND", 0, 2, 1 } }, - { Instruction::OR, { "OR", 0, 2, 1 } }, - { Instruction::XOR, { "XOR", 0, 2, 1 } }, - { Instruction::BYTE, { "BYTE", 0, 2, 1 } }, - { Instruction::ADDMOD, { "ADDMOD", 0, 3, 1 } }, - { Instruction::MULMOD, { "MULMOD", 0, 3, 1 } }, - { Instruction::SIGNEXTEND, { "SIGNEXTEND", 0, 2, 1 } }, - { Instruction::SHA3, { "SHA3", 0, 2, 1 } }, - { Instruction::ADDRESS, { "ADDRESS", 0, 0, 1 } }, - { Instruction::BALANCE, { "BALANCE", 0, 1, 1 } }, - { Instruction::ORIGIN, { "ORIGIN", 0, 0, 1 } }, - { Instruction::CALLER, { "CALLER", 0, 0, 1 } }, - { Instruction::CALLVALUE, { "CALLVALUE", 0, 0, 1 } }, - { Instruction::CALLDATALOAD,{ "CALLDATALOAD", 0, 1, 1 } }, - { Instruction::CALLDATASIZE,{ "CALLDATASIZE", 0, 0, 1 } }, - { Instruction::CALLDATACOPY,{ "CALLDATACOPY", 0, 3, 0 } }, - { Instruction::CODESIZE, { "CODESIZE", 0, 0, 1 } }, - { Instruction::CODECOPY, { "CODECOPY", 0, 3, 0 } }, - { Instruction::GASPRICE, { "GASPRICE", 0, 0, 1 } }, - { Instruction::EXTCODESIZE, { "EXTCODESIZE", 0, 1, 1 } }, - { Instruction::EXTCODECOPY, { "EXTCODECOPY", 0, 4, 0 } }, - { Instruction::PREVHASH, { "PREVHASH", 0, 0, 1 } }, - { Instruction::COINBASE, { "COINBASE", 0, 0, 1 } }, - { Instruction::TIMESTAMP, { "TIMESTAMP", 0, 0, 1 } }, - { Instruction::NUMBER, { "NUMBER", 0, 0, 1 } }, - { Instruction::DIFFICULTY, { "DIFFICULTY", 0, 0, 1 } }, - { Instruction::GASLIMIT, { "GASLIMIT", 0, 0, 1 } }, - { Instruction::POP, { "POP", 0, 1, 0 } }, - { Instruction::MLOAD, { "MLOAD", 0, 1, 1 } }, - { Instruction::MSTORE, { "MSTORE", 0, 2, 0 } }, - { Instruction::MSTORE8, { "MSTORE8", 0, 2, 0 } }, - { Instruction::SLOAD, { "SLOAD", 0, 1, 1 } }, - { Instruction::SSTORE, { "SSTORE", 0, 2, 0 } }, - { Instruction::JUMP, { "JUMP", 0, 1, 0 } }, - { Instruction::JUMPI, { "JUMPI", 0, 2, 0 } }, - { Instruction::PC, { "PC", 0, 0, 1 } }, - { Instruction::MSIZE, { "MSIZE", 0, 0, 1 } }, - { Instruction::GAS, { "GAS", 0, 0, 1 } }, - { Instruction::JUMPDEST, { "JUMPDEST", 0, 1, 0 } }, - { Instruction::PUSH1, { "PUSH1", 1, 0, 1 } }, - { Instruction::PUSH2, { "PUSH2", 2, 0, 1 } }, - { Instruction::PUSH3, { "PUSH3", 3, 0, 1 } }, - { Instruction::PUSH4, { "PUSH4", 4, 0, 1 } }, - { Instruction::PUSH5, { "PUSH5", 5, 0, 1 } }, - { Instruction::PUSH6, { "PUSH6", 6, 0, 1 } }, - { Instruction::PUSH7, { "PUSH7", 7, 0, 1 } }, - { Instruction::PUSH8, { "PUSH8", 8, 0, 1 } }, - { Instruction::PUSH9, { "PUSH9", 9, 0, 1 } }, - { Instruction::PUSH10, { "PUSH10", 10, 0, 1 } }, - { Instruction::PUSH11, { "PUSH11", 11, 0, 1 } }, - { Instruction::PUSH12, { "PUSH12", 12, 0, 1 } }, - { Instruction::PUSH13, { "PUSH13", 13, 0, 1 } }, - { Instruction::PUSH14, { "PUSH14", 14, 0, 1 } }, - { Instruction::PUSH15, { "PUSH15", 15, 0, 1 } }, - { Instruction::PUSH16, { "PUSH16", 16, 0, 1 } }, - { Instruction::PUSH17, { "PUSH17", 17, 0, 1 } }, - { Instruction::PUSH18, { "PUSH18", 18, 0, 1 } }, - { Instruction::PUSH19, { "PUSH19", 19, 0, 1 } }, - { Instruction::PUSH20, { "PUSH20", 20, 0, 1 } }, - { Instruction::PUSH21, { "PUSH21", 21, 0, 1 } }, - { Instruction::PUSH22, { "PUSH22", 22, 0, 1 } }, - { Instruction::PUSH23, { "PUSH23", 23, 0, 1 } }, - { Instruction::PUSH24, { "PUSH24", 24, 0, 1 } }, - { Instruction::PUSH25, { "PUSH25", 25, 0, 1 } }, - { Instruction::PUSH26, { "PUSH26", 26, 0, 1 } }, - { Instruction::PUSH27, { "PUSH27", 27, 0, 1 } }, - { Instruction::PUSH28, { "PUSH28", 28, 0, 1 } }, - { Instruction::PUSH29, { "PUSH29", 29, 0, 1 } }, - { Instruction::PUSH30, { "PUSH30", 30, 0, 1 } }, - { Instruction::PUSH31, { "PUSH31", 31, 0, 1 } }, - { Instruction::PUSH32, { "PUSH32", 32, 0, 1 } }, - { Instruction::DUP1, { "DUP1", 0, 1, 2 } }, - { Instruction::DUP2, { "DUP2", 0, 2, 3 } }, - { Instruction::DUP3, { "DUP3", 0, 3, 4 } }, - { Instruction::DUP4, { "DUP4", 0, 4, 5 } }, - { Instruction::DUP5, { "DUP5", 0, 5, 6 } }, - { Instruction::DUP6, { "DUP6", 0, 6, 7 } }, - { Instruction::DUP7, { "DUP7", 0, 7, 8 } }, - { Instruction::DUP8, { "DUP8", 0, 8, 9 } }, - { Instruction::DUP9, { "DUP9", 0, 9, 10 } }, - { Instruction::DUP10, { "DUP10", 0, 10, 11 } }, - { Instruction::DUP11, { "DUP11", 0, 11, 12 } }, - { Instruction::DUP12, { "DUP12", 0, 12, 13 } }, - { Instruction::DUP13, { "DUP13", 0, 13, 14 } }, - { Instruction::DUP14, { "DUP14", 0, 14, 15 } }, - { Instruction::DUP15, { "DUP15", 0, 15, 16 } }, - { Instruction::DUP16, { "DUP16", 0, 16, 17 } }, - { Instruction::SWAP1, { "SWAP1", 0, 2, 2 } }, - { Instruction::SWAP2, { "SWAP2", 0, 3, 3 } }, - { Instruction::SWAP3, { "SWAP3", 0, 4, 4 } }, - { Instruction::SWAP4, { "SWAP4", 0, 5, 5 } }, - { Instruction::SWAP5, { "SWAP5", 0, 6, 6 } }, - { Instruction::SWAP6, { "SWAP6", 0, 7, 7 } }, - { Instruction::SWAP7, { "SWAP7", 0, 8, 8 } }, - { Instruction::SWAP8, { "SWAP8", 0, 9, 9 } }, - { Instruction::SWAP9, { "SWAP9", 0, 10, 10 } }, - { Instruction::SWAP10, { "SWAP10", 0, 11, 11 } }, - { Instruction::SWAP11, { "SWAP11", 0, 12, 12 } }, - { Instruction::SWAP12, { "SWAP12", 0, 13, 13 } }, - { Instruction::SWAP13, { "SWAP13", 0, 14, 14 } }, - { Instruction::SWAP14, { "SWAP14", 0, 15, 15 } }, - { Instruction::SWAP15, { "SWAP15", 0, 16, 16 } }, - { Instruction::SWAP16, { "SWAP16", 0, 17, 17 } }, - { Instruction::LOG0, { "LOG0", 0, 1, 0 } }, - { Instruction::LOG1, { "LOG1", 0, 2, 0 } }, - { Instruction::LOG2, { "LOG2", 0, 3, 0 } }, - { Instruction::LOG3, { "LOG3", 0, 4, 0 } }, - { Instruction::LOG4, { "LOG4", 0, 5, 0 } }, - { Instruction::CREATE, { "CREATE", 0, 3, 1 } }, - { Instruction::CALL, { "CALL", 0, 7, 1 } }, - { Instruction::CALLCODE, { "CALLCODE", 0, 7, 1 } }, - { Instruction::RETURN, { "RETURN", 0, 2, 0 } }, - { Instruction::SUICIDE, { "SUICIDE", 0, 1, 0} } +{ // Add, Args, Ret, SideEffects + { Instruction::STOP, { "STOP", 0, 0, 0, true } }, + { Instruction::ADD, { "ADD", 0, 2, 1, false } }, + { Instruction::SUB, { "SUB", 0, 2, 1, false } }, + { Instruction::MUL, { "MUL", 0, 2, 1, false } }, + { Instruction::DIV, { "DIV", 0, 2, 1, false } }, + { Instruction::SDIV, { "SDIV", 0, 2, 1, false } }, + { Instruction::MOD, { "MOD", 0, 2, 1, false } }, + { Instruction::SMOD, { "SMOD", 0, 2, 1, false } }, + { Instruction::EXP, { "EXP", 0, 2, 1, false } }, + { Instruction::NOT, { "NOT", 0, 1, 1, false } }, + { Instruction::LT, { "LT", 0, 2, 1, false } }, + { Instruction::GT, { "GT", 0, 2, 1, false } }, + { Instruction::SLT, { "SLT", 0, 2, 1, false } }, + { Instruction::SGT, { "SGT", 0, 2, 1, false } }, + { Instruction::EQ, { "EQ", 0, 2, 1, false } }, + { Instruction::ISZERO, { "ISZERO", 0, 1, 1, false } }, + { Instruction::AND, { "AND", 0, 2, 1, false } }, + { Instruction::OR, { "OR", 0, 2, 1, false } }, + { Instruction::XOR, { "XOR", 0, 2, 1, false } }, + { Instruction::BYTE, { "BYTE", 0, 2, 1, false } }, + { Instruction::ADDMOD, { "ADDMOD", 0, 3, 1, false } }, + { Instruction::MULMOD, { "MULMOD", 0, 3, 1, false } }, + { Instruction::SIGNEXTEND, { "SIGNEXTEND", 0, 2, 1, false } }, + { Instruction::SHA3, { "SHA3", 0, 2, 1, false } }, + { Instruction::ADDRESS, { "ADDRESS", 0, 0, 1, false } }, + { Instruction::BALANCE, { "BALANCE", 0, 1, 1, false } }, + { Instruction::ORIGIN, { "ORIGIN", 0, 0, 1, false } }, + { Instruction::CALLER, { "CALLER", 0, 0, 1, false } }, + { Instruction::CALLVALUE, { "CALLVALUE", 0, 0, 1, false } }, + { Instruction::CALLDATALOAD,{ "CALLDATALOAD", 0, 1, 1, false } }, + { Instruction::CALLDATASIZE,{ "CALLDATASIZE", 0, 0, 1, false } }, + { Instruction::CALLDATACOPY,{ "CALLDATACOPY", 0, 3, 0, true } }, + { Instruction::CODESIZE, { "CODESIZE", 0, 0, 1, false } }, + { Instruction::CODECOPY, { "CODECOPY", 0, 3, 0, true } }, + { Instruction::GASPRICE, { "GASPRICE", 0, 0, 1, false } }, + { Instruction::EXTCODESIZE, { "EXTCODESIZE", 0, 1, 1, false } }, + { Instruction::EXTCODECOPY, { "EXTCODECOPY", 0, 4, 0, true } }, + { Instruction::PREVHASH, { "PREVHASH", 0, 0, 1, false } }, + { Instruction::COINBASE, { "COINBASE", 0, 0, 1, false } }, + { Instruction::TIMESTAMP, { "TIMESTAMP", 0, 0, 1, false } }, + { Instruction::NUMBER, { "NUMBER", 0, 0, 1, false } }, + { Instruction::DIFFICULTY, { "DIFFICULTY", 0, 0, 1, false } }, + { Instruction::GASLIMIT, { "GASLIMIT", 0, 0, 1, false } }, + { Instruction::POP, { "POP", 0, 1, 0, false } }, + { Instruction::MLOAD, { "MLOAD", 0, 1, 1, false } }, + { Instruction::MSTORE, { "MSTORE", 0, 2, 0, true } }, + { Instruction::MSTORE8, { "MSTORE8", 0, 2, 0, true } }, + { Instruction::SLOAD, { "SLOAD", 0, 1, 1, false } }, + { Instruction::SSTORE, { "SSTORE", 0, 2, 0, true } }, + { Instruction::JUMP, { "JUMP", 0, 1, 0, true } }, + { Instruction::JUMPI, { "JUMPI", 0, 2, 0, true } }, + { Instruction::PC, { "PC", 0, 0, 1, false } }, + { Instruction::MSIZE, { "MSIZE", 0, 0, 1, false } }, + { Instruction::GAS, { "GAS", 0, 0, 1, false } }, + { Instruction::JUMPDEST, { "JUMPDEST", 0, 1, 0, true } }, + { Instruction::PUSH1, { "PUSH1", 1, 0, 1, false } }, + { Instruction::PUSH2, { "PUSH2", 2, 0, 1, false } }, + { Instruction::PUSH3, { "PUSH3", 3, 0, 1, false } }, + { Instruction::PUSH4, { "PUSH4", 4, 0, 1, false } }, + { Instruction::PUSH5, { "PUSH5", 5, 0, 1, false } }, + { Instruction::PUSH6, { "PUSH6", 6, 0, 1, false } }, + { Instruction::PUSH7, { "PUSH7", 7, 0, 1, false } }, + { Instruction::PUSH8, { "PUSH8", 8, 0, 1, false } }, + { Instruction::PUSH9, { "PUSH9", 9, 0, 1, false } }, + { Instruction::PUSH10, { "PUSH10", 10, 0, 1, false } }, + { Instruction::PUSH11, { "PUSH11", 11, 0, 1, false } }, + { Instruction::PUSH12, { "PUSH12", 12, 0, 1, false } }, + { Instruction::PUSH13, { "PUSH13", 13, 0, 1, false } }, + { Instruction::PUSH14, { "PUSH14", 14, 0, 1, false } }, + { Instruction::PUSH15, { "PUSH15", 15, 0, 1, false } }, + { Instruction::PUSH16, { "PUSH16", 16, 0, 1, false } }, + { Instruction::PUSH17, { "PUSH17", 17, 0, 1, false } }, + { Instruction::PUSH18, { "PUSH18", 18, 0, 1, false } }, + { Instruction::PUSH19, { "PUSH19", 19, 0, 1, false } }, + { Instruction::PUSH20, { "PUSH20", 20, 0, 1, false } }, + { Instruction::PUSH21, { "PUSH21", 21, 0, 1, false } }, + { Instruction::PUSH22, { "PUSH22", 22, 0, 1, false } }, + { Instruction::PUSH23, { "PUSH23", 23, 0, 1, false } }, + { Instruction::PUSH24, { "PUSH24", 24, 0, 1, false } }, + { Instruction::PUSH25, { "PUSH25", 25, 0, 1, false } }, + { Instruction::PUSH26, { "PUSH26", 26, 0, 1, false } }, + { Instruction::PUSH27, { "PUSH27", 27, 0, 1, false } }, + { Instruction::PUSH28, { "PUSH28", 28, 0, 1, false } }, + { Instruction::PUSH29, { "PUSH29", 29, 0, 1, false } }, + { Instruction::PUSH30, { "PUSH30", 30, 0, 1, false } }, + { Instruction::PUSH31, { "PUSH31", 31, 0, 1, false } }, + { Instruction::PUSH32, { "PUSH32", 32, 0, 1, false } }, + { Instruction::DUP1, { "DUP1", 0, 1, 2, false } }, + { Instruction::DUP2, { "DUP2", 0, 2, 3, false } }, + { Instruction::DUP3, { "DUP3", 0, 3, 4, false } }, + { Instruction::DUP4, { "DUP4", 0, 4, 5, false } }, + { Instruction::DUP5, { "DUP5", 0, 5, 6, false } }, + { Instruction::DUP6, { "DUP6", 0, 6, 7, false } }, + { Instruction::DUP7, { "DUP7", 0, 7, 8, false } }, + { Instruction::DUP8, { "DUP8", 0, 8, 9, false } }, + { Instruction::DUP9, { "DUP9", 0, 9, 10, false } }, + { Instruction::DUP10, { "DUP10", 0, 10, 11, false } }, + { Instruction::DUP11, { "DUP11", 0, 11, 12, false } }, + { Instruction::DUP12, { "DUP12", 0, 12, 13, false } }, + { Instruction::DUP13, { "DUP13", 0, 13, 14, false } }, + { Instruction::DUP14, { "DUP14", 0, 14, 15, false } }, + { Instruction::DUP15, { "DUP15", 0, 15, 16, false } }, + { Instruction::DUP16, { "DUP16", 0, 16, 17, false } }, + { Instruction::SWAP1, { "SWAP1", 0, 2, 2, false } }, + { Instruction::SWAP2, { "SWAP2", 0, 3, 3, false } }, + { Instruction::SWAP3, { "SWAP3", 0, 4, 4, false } }, + { Instruction::SWAP4, { "SWAP4", 0, 5, 5, false } }, + { Instruction::SWAP5, { "SWAP5", 0, 6, 6, false } }, + { Instruction::SWAP6, { "SWAP6", 0, 7, 7, false } }, + { Instruction::SWAP7, { "SWAP7", 0, 8, 8, false } }, + { Instruction::SWAP8, { "SWAP8", 0, 9, 9, false } }, + { Instruction::SWAP9, { "SWAP9", 0, 10, 10, false } }, + { Instruction::SWAP10, { "SWAP10", 0, 11, 11, false } }, + { Instruction::SWAP11, { "SWAP11", 0, 12, 12, false } }, + { Instruction::SWAP12, { "SWAP12", 0, 13, 13, false } }, + { Instruction::SWAP13, { "SWAP13", 0, 14, 14, false } }, + { Instruction::SWAP14, { "SWAP14", 0, 15, 15, false } }, + { Instruction::SWAP15, { "SWAP15", 0, 16, 16, false } }, + { Instruction::SWAP16, { "SWAP16", 0, 17, 17, false } }, + { Instruction::LOG0, { "LOG0", 0, 1, 0, true } }, + { Instruction::LOG1, { "LOG1", 0, 2, 0, true } }, + { Instruction::LOG2, { "LOG2", 0, 3, 0, true } }, + { Instruction::LOG3, { "LOG3", 0, 4, 0, true } }, + { Instruction::LOG4, { "LOG4", 0, 5, 0, true } }, + { Instruction::CREATE, { "CREATE", 0, 3, 1, true } }, + { Instruction::CALL, { "CALL", 0, 7, 1, true } }, + { Instruction::CALLCODE, { "CALLCODE", 0, 7, 1, true } }, + { Instruction::RETURN, { "RETURN", 0, 2, 0, true } }, + { Instruction::SUICIDE, { "SUICIDE", 0, 1, 0, true } } }; string dev::eth::disassemble(bytes const& _mem) diff --git a/libevmcore/Instruction.h b/libevmcore/Instruction.h index 0892c50dc..eb85c0610 100644 --- a/libevmcore/Instruction.h +++ b/libevmcore/Instruction.h @@ -204,6 +204,7 @@ struct InstructionInfo int additional; ///< Additional items required in memory for this instructions (only for PUSH). int args; ///< Number of items required on the stack for this instruction (and, for the purposes of ret, the number taken from the stack). int ret; ///< Number of items placed (back) on the stack by this instruction, assuming args items were removed. + bool sideEffects; ///< false if the only effect on the execution environment (apart from gas usage) is a change to a topmost segment of the stack }; /// Information on all the instructions. diff --git a/libjsqrc/main.js b/libjsqrc/main.js index c07a938e4..6abffb195 100644 --- a/libjsqrc/main.js +++ b/libjsqrc/main.js @@ -66,86 +66,86 @@ var ethMethods = function () { var blockCall = function (args) { - return typeof args[0] === "string" ? "blockByHash" : "blockByNumber"; + return typeof args[0] === "string" ? "eth_blockByHash" : "eth_blockByNumber"; }; var transactionCall = function (args) { - return typeof args[0] === "string" ? 'transactionByHash' : 'transactionByNumber'; + return typeof args[0] === "string" ? 'eth_transactionByHash' : 'eth_transactionByNumber'; }; var uncleCall = function (args) { - return typeof args[0] === "string" ? 'uncleByHash' : 'uncleByNumber'; + return typeof args[0] === "string" ? 'eth_uncleByHash' : 'eth_uncleByNumber'; }; var methods = [ - { name: 'balanceAt', call: 'balanceAt' }, - { name: 'stateAt', call: 'stateAt' }, - { name: 'countAt', call: 'countAt'}, - { name: 'codeAt', call: 'codeAt' }, - { name: 'transact', call: 'transact' }, - { name: 'call', call: 'call' }, + { name: 'balanceAt', call: 'eth_balanceAt' }, + { name: 'stateAt', call: 'eth_stateAt' }, + { name: 'countAt', call: 'eth_countAt'}, + { name: 'codeAt', call: 'eth_codeAt' }, + { name: 'transact', call: 'eth_transact' }, + { name: 'call', call: 'eth_call' }, { name: 'block', call: blockCall }, { name: 'transaction', call: transactionCall }, { name: 'uncle', call: uncleCall }, - { name: 'compilers', call: 'compilers' }, - { name: 'lll', call: 'lll' }, - { name: 'solidity', call: 'solidity' }, - { name: 'contractCreate', call: 'contractCreate' }, - { name: 'contractCall', call: 'contractCall' } + { name: 'compilers', call: 'eth_compilers' }, + { name: 'lll', call: 'eth_lll' }, + { name: 'solidity', call: 'eth_solidity' }, + { name: 'contractCreate', call: 'eth_contractCreate' }, + { name: 'contractCall', call: 'eth_contractCall' } ]; return methods; }; var ethProperties = function () { return [ - { name: 'coinbase', getter: 'coinbase', setter: 'setCoinbase' }, - { name: 'listening', getter: 'listening', setter: 'setListening' }, - { name: 'mining', getter: 'mining', setter: 'setMining' }, - { name: 'gasPrice', getter: 'gasPrice' }, - { name: 'account', getter: 'account' }, - { name: 'accounts', getter: 'accounts' }, - { name: 'peerCount', getter: 'peerCount' }, - { name: 'defaultBlock', getter: 'defaultBlock', setter: 'setDefaultBlock' }, - { name: 'number', getter: 'number'} + { name: 'coinbase', getter: 'eth_coinbase', setter: 'eth_setCoinbase' }, + { name: 'listening', getter: 'eth_listening', setter: 'eth_setListening' }, + { name: 'mining', getter: 'eth_mining', setter: 'eth_setMining' }, + { name: 'gasPrice', getter: 'eth_gasPrice' }, + { name: 'account', getter: 'eth_account' }, + { name: 'accounts', getter: 'eth_accounts' }, + { name: 'peerCount', getter: 'eth_peerCount' }, + { name: 'defaultBlock', getter: 'eth_defaultBlock', setter: 'eth_setDefaultBlock' }, + { name: 'number', getter: 'eth_number'} ]; }; var dbMethods = function () { return [ - { name: 'put', call: 'put' }, - { name: 'get', call: 'get' }, - { name: 'putString', call: 'putString' }, - { name: 'getString', call: 'getString' } + { name: 'put', call: 'db_put' }, + { name: 'get', call: 'db_get' }, + { name: 'putString', call: 'db_putString' }, + { name: 'getString', call: 'db_getString' } ]; }; var shhMethods = function () { return [ - { name: 'post', call: 'post' }, - { name: 'newIdentity', call: 'newIdentity' }, - { name: 'haveIdentity', call: 'haveIdentity' }, - { name: 'newGroup', call: 'newGroup' }, - { name: 'addToGroup', call: 'addToGroup' } + { name: 'post', call: 'shh_post' }, + { name: 'newIdentity', call: 'shh_newIdentity' }, + { name: 'haveIdentity', call: 'shh_haveIdentity' }, + { name: 'newGroup', call: 'shh_newGroup' }, + { name: 'addToGroup', call: 'shh_addToGroup' } ]; }; var ethWatchMethods = function () { var newFilter = function (args) { - return typeof args[0] === 'string' ? 'newFilterString' : 'newFilter'; + return typeof args[0] === 'string' ? 'eth_newFilterString' : 'eth_newFilter'; }; return [ { name: 'newFilter', call: newFilter }, - { name: 'uninstallFilter', call: 'uninstallFilter' }, - { name: 'getMessages', call: 'getMessages' } + { name: 'uninstallFilter', call: 'eth_uninstallFilter' }, + { name: 'getMessages', call: 'eth_getMessages' } ]; }; var shhWatchMethods = function () { return [ - { name: 'newFilter', call: 'shhNewFilter' }, - { name: 'uninstallFilter', call: 'shhUninstallFilter' }, - { name: 'getMessage', call: 'shhGetMessages' } + { name: 'newFilter', call: 'shh_newFilter' }, + { name: 'uninstallFilter', call: 'shh_uninstallFilter' }, + { name: 'getMessage', call: 'shh_getMessages' } ]; }; @@ -303,11 +303,11 @@ setupMethods(web3.shh, shhMethods()); var ethWatch = { - changed: 'changed' + changed: 'eth_changed' }; setupMethods(ethWatch, ethWatchMethods()); var shhWatch = { - changed: 'shhChanged' + changed: 'shh_changed' }; setupMethods(shhWatch, shhWatchMethods()); diff --git a/libjsqrc/setup.js b/libjsqrc/setup.js index 549222119..5142412a6 100644 --- a/libjsqrc/setup.js +++ b/libjsqrc/setup.js @@ -14,7 +14,7 @@ You should have received a copy of the GNU General Public License along with cpp-ethereum. If not, see . */ -/** @file QEthereum.cpp +/** @file setup.js * @authors: * Marek Kotewicz * @date 2014 diff --git a/libqethereum/QEthereum.cpp b/libqethereum/QEthereum.cpp index 42e00958a..5e5253829 100644 --- a/libqethereum/QEthereum.cpp +++ b/libqethereum/QEthereum.cpp @@ -59,13 +59,13 @@ void QWebThree::poll() { if (m_watches.size() > 0) { - QString batch = toJsonRpcBatch(m_watches, "changed"); - emit processData(batch, "changed"); + QString batch = toJsonRpcBatch(m_watches, "eth_changed"); + emit processData(batch, "eth_changed"); } if (m_shhWatches.size() > 0) { - QString batch = toJsonRpcBatch(m_shhWatches, "shhChanged"); - emit processData(batch, "shhChanged"); + QString batch = toJsonRpcBatch(m_shhWatches, "shh_changed"); + emit processData(batch, "shh_changed"); } } @@ -73,13 +73,13 @@ void QWebThree::clearWatches() { if (m_watches.size() > 0) { - QString batch = toJsonRpcBatch(m_watches, "uninstallFilter"); + QString batch = toJsonRpcBatch(m_watches, "eth_uninstallFilter"); m_watches.clear(); emit processData(batch, "internal"); } if (m_shhWatches.size() > 0) { - QString batch = toJsonRpcBatch(m_shhWatches, "shhUninstallFilter"); + QString batch = toJsonRpcBatch(m_shhWatches, "shh_uninstallFilter"); m_shhWatches.clear(); emit processData(batch, "internal"); } @@ -106,7 +106,12 @@ void QWebThree::postMessage(QString _json) QJsonObject f = QJsonDocument::fromJson(_json.toUtf8()).object(); QString method = f["call"].toString(); - if (!method.compare("uninstallFilter") && f["args"].isArray() && f["args"].toArray().size()) + if (!method.compare("eth_uninstallFilter") && f["args"].isArray() && f["args"].toArray().size()) + { + int idToRemove = f["args"].toArray()[0].toInt(); + m_watches.erase(std::remove(m_watches.begin(), m_watches.end(), idToRemove), m_watches.end()); + } + else if (!method.compare("eth_uninstallFilter") && f["args"].isArray() && f["args"].toArray().size()) { int idToRemove = f["args"].toArray()[0].toInt(); m_watches.erase(std::remove(m_watches.begin(), m_watches.end(), idToRemove), m_watches.end()); @@ -129,7 +134,7 @@ void QWebThree::onDataProcessed(QString _json, QString _addInfo) if (!_addInfo.compare("internal")) return; - if (!_addInfo.compare("changed")) + if (!_addInfo.compare("eth_changed")) { QJsonArray resultsArray = QJsonDocument::fromJson(_json.toUtf8()).array(); for (int i = 0; i < resultsArray.size(); i++) @@ -146,7 +151,7 @@ void QWebThree::onDataProcessed(QString _json, QString _addInfo) return; } - if (!_addInfo.compare("shhChanged")) + if (!_addInfo.compare("shh_changed")) { QJsonArray resultsArray = QJsonDocument::fromJson(_json.toUtf8()).array(); for (int i = 0; i < resultsArray.size(); i++) @@ -165,11 +170,11 @@ void QWebThree::onDataProcessed(QString _json, QString _addInfo) QJsonObject f = QJsonDocument::fromJson(_json.toUtf8()).object(); - if ((!_addInfo.compare("newFilter") || !_addInfo.compare("newFilterString")) && f.contains("result")) + if ((!_addInfo.compare("eth_newFilter") || !_addInfo.compare("eth_newFilterString")) && f.contains("result")) m_watches.push_back(f["result"].toInt()); - if (!_addInfo.compare("shhNewFilter") && f.contains("result")) + else if (!_addInfo.compare("shh_newFilter") && f.contains("result")) m_shhWatches.push_back(f["result"].toInt()); - if (!_addInfo.compare("newIdentity") && f.contains("result")) + else if (!_addInfo.compare("shh_newIdentity") && f.contains("result")) emit onNewId(f["result"].toString()); response(formatOutput(f)); diff --git a/libsolidity/Compiler.cpp b/libsolidity/Compiler.cpp index ce87f7bb0..ed2b1f45f 100644 --- a/libsolidity/Compiler.cpp +++ b/libsolidity/Compiler.cpp @@ -32,11 +32,11 @@ using namespace std; namespace dev { namespace solidity { -bytes Compiler::compile(ContractDefinition& _contract) +bytes Compiler::compile(ContractDefinition& _contract, bool _optimize) { Compiler compiler; compiler.compileContract(_contract); - return compiler.m_context.getAssembledBytecode(); + return compiler.m_context.getAssembledBytecode(_optimize); } void Compiler::compileContract(ContractDefinition& _contract) @@ -93,10 +93,11 @@ void Compiler::appendFunctionSelector(vector> con eth::AssemblyItem jumpTableStart = m_context.pushNewTag(); m_context << eth::Instruction::ADD << eth::Instruction::JUMP; - // jump table @todo it could be that the optimizer destroys this - m_context << jumpTableStart; + // jump table, tell the optimizer not to remove the JUMPDESTs + m_context << eth::AssemblyItem(eth::NoOptimizeBegin) << jumpTableStart; for (pair> const& f: publicFunctions) m_context.appendJumpTo(f.second.second) << eth::Instruction::JUMPDEST; + m_context << eth::AssemblyItem(eth::NoOptimizeEnd); m_context << returnTag << eth::Instruction::STOP; diff --git a/libsolidity/Compiler.h b/libsolidity/Compiler.h index 4e4d90d45..d931f5359 100644 --- a/libsolidity/Compiler.h +++ b/libsolidity/Compiler.h @@ -33,11 +33,11 @@ public: Compiler(): m_returnTag(m_context.newTag()) {} void compileContract(ContractDefinition& _contract); - bytes getAssembledBytecode() { return m_context.getAssembledBytecode(); } + bytes getAssembledBytecode(bool _optimize = false) { return m_context.getAssembledBytecode(_optimize); } void streamAssembly(std::ostream& _stream) const { m_context.streamAssembly(_stream); } /// Compile the given contract and return the EVM bytecode. - static bytes compile(ContractDefinition& _contract); + static bytes compile(ContractDefinition& _contract, bool _optimize); private: /// Creates a new compiler context / assembly and packs the current code into the data part. diff --git a/libsolidity/CompilerContext.h b/libsolidity/CompilerContext.h index 9f8658c3d..562c29321 100644 --- a/libsolidity/CompilerContext.h +++ b/libsolidity/CompilerContext.h @@ -84,7 +84,7 @@ public: eth::Assembly const& getAssembly() const { return m_asm; } void streamAssembly(std::ostream& _stream) const { _stream << m_asm; } - bytes getAssembledBytecode() const { return m_asm.assemble(); } + bytes getAssembledBytecode(bool _optimize = false) { return m_asm.optimise(_optimize).assemble(); } private: eth::Assembly m_asm; diff --git a/libsolidity/CompilerStack.cpp b/libsolidity/CompilerStack.cpp index bbd693ae5..c991171a5 100644 --- a/libsolidity/CompilerStack.cpp +++ b/libsolidity/CompilerStack.cpp @@ -34,7 +34,8 @@ namespace dev namespace solidity { -bytes CompilerStack::compile(std::string const& _sourceCode, shared_ptr _scanner) +bytes CompilerStack::compile(std::string const& _sourceCode, shared_ptr _scanner, + bool _optimize) { if (!_scanner) _scanner = make_shared(); @@ -42,7 +43,7 @@ bytes CompilerStack::compile(std::string const& _sourceCode, shared_ptr ASTPointer contract = Parser().parse(_scanner); NameAndTypeResolver().resolveNamesAndTypes(*contract); - return Compiler::compile(*contract); + return Compiler::compile(*contract, _optimize); } } diff --git a/libsolidity/CompilerStack.h b/libsolidity/CompilerStack.h index 9f3f81c04..b003745d2 100644 --- a/libsolidity/CompilerStack.h +++ b/libsolidity/CompilerStack.h @@ -36,7 +36,7 @@ class CompilerStack public: /// Compile the given @a _sourceCode to bytecode. If a scanner is provided, it is used for /// scanning the source code - this is useful for printing exception information. - static bytes compile(std::string const& _sourceCode, std::shared_ptr _scanner = std::shared_ptr()); + static bytes compile(std::string const& _sourceCode, std::shared_ptr _scanner = std::shared_ptr(), bool _optimize = false); }; } diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 6b1ab6d68..f9017026b 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -196,9 +196,11 @@ static dev::eth::MessageFilter toMessageFilter(Json::Value const& _json) if (!_json["topics"].empty()) { if (_json["topics"].isArray()) + { for (auto i: _json["topics"]) if (i.isString()) filter.topic(jsToU256(i.asString())); + } else if(_json["topics"].isString()) filter.topic(jsToU256(_json["topics"].asString())); } @@ -315,7 +317,7 @@ std::shared_ptr WebThreeStubServer::face() const return m_web3.whisper(); } -Json::Value WebThreeStubServer::accounts() +Json::Value WebThreeStubServer::eth_accounts() { Json::Value ret(Json::arrayValue); for (auto i: m_accounts) @@ -323,27 +325,27 @@ Json::Value WebThreeStubServer::accounts() return ret; } -std::string WebThreeStubServer::addToGroup(std::string const& _group, std::string const& _who) +std::string WebThreeStubServer::shh_addToGroup(std::string const& _group, std::string const& _who) { (void)_group; (void)_who; return ""; } -std::string WebThreeStubServer::balanceAt(string const& _address) +std::string WebThreeStubServer::eth_balanceAt(string const& _address) { int block = 0; return toJS(client()->balanceAt(jsToAddress(_address), block)); } -Json::Value WebThreeStubServer::blockByHash(std::string const& _hash) +Json::Value WebThreeStubServer::eth_blockByHash(std::string const& _hash) { if (!client()) return ""; return toJson(client()->blockInfo(jsToFixed<32>(_hash))); } -Json::Value WebThreeStubServer::blockByNumber(int const& _number) +Json::Value WebThreeStubServer::eth_blockByNumber(int const& _number) { if (!client()) return ""; @@ -386,7 +388,7 @@ static TransactionSkeleton toTransaction(Json::Value const& _json) return ret; } -std::string WebThreeStubServer::call(Json::Value const& _json) +std::string WebThreeStubServer::eth_call(Json::Value const& _json) { std::string ret; if (!client()) @@ -410,41 +412,41 @@ std::string WebThreeStubServer::call(Json::Value const& _json) return ret; } -bool WebThreeStubServer::changed(int const& _id) +bool WebThreeStubServer::eth_changed(int const& _id) { if (!client()) return false; return client()->checkWatch(_id); } -std::string WebThreeStubServer::codeAt(string const& _address) +std::string WebThreeStubServer::eth_codeAt(string const& _address) { int block = 0; return client() ? jsFromBinary(client()->codeAt(jsToAddress(_address), block)) : ""; } -std::string WebThreeStubServer::coinbase() +std::string WebThreeStubServer::eth_coinbase() { return client() ? toJS(client()->address()) : ""; } -double WebThreeStubServer::countAt(string const& _address) +double WebThreeStubServer::eth_countAt(string const& _address) { int block = 0; return client() ? (double)(uint64_t)client()->countAt(jsToAddress(_address), block) : 0; } -int WebThreeStubServer::defaultBlock() +int WebThreeStubServer::eth_defaultBlock() { return client() ? client()->getDefault() : 0; } -std::string WebThreeStubServer::gasPrice() +std::string WebThreeStubServer::eth_gasPrice() { return toJS(10 * dev::eth::szabo); } -std::string WebThreeStubServer::get(std::string const& _name, std::string const& _key) +std::string WebThreeStubServer::db_get(std::string const& _name, std::string const& _key) { bytes k = sha3(_name).asBytes() + sha3(_key).asBytes(); string ret; @@ -452,14 +454,14 @@ std::string WebThreeStubServer::get(std::string const& _name, std::string const& return toJS(dev::asBytes(ret)); } -Json::Value WebThreeStubServer::getMessages(int const& _id) +Json::Value WebThreeStubServer::eth_getMessages(int const& _id) { if (!client()) return Json::Value(); return toJson(client()->messages(_id)); } -std::string WebThreeStubServer::getString(std::string const& _name, std::string const& _key) +std::string WebThreeStubServer::db_getString(std::string const& _name, std::string const& _key) { bytes k = sha3(_name).asBytes() + sha3(_key).asBytes(); string ret; @@ -467,22 +469,22 @@ std::string WebThreeStubServer::getString(std::string const& _name, std::string return ret; } -bool WebThreeStubServer::haveIdentity(std::string const& _id) +bool WebThreeStubServer::shh_haveIdentity(std::string const& _id) { return m_ids.count(jsToPublic(_id)) > 0; } -bool WebThreeStubServer::listening() +bool WebThreeStubServer::eth_listening() { return m_web3.isNetworkStarted(); } -bool WebThreeStubServer::mining() +bool WebThreeStubServer::eth_mining() { return client() ? client()->isMining() : false; } -int WebThreeStubServer::newFilter(Json::Value const& _json) +int WebThreeStubServer::eth_newFilter(Json::Value const& _json) { unsigned ret = -1; if (!client()) @@ -491,7 +493,7 @@ int WebThreeStubServer::newFilter(Json::Value const& _json) return ret; } -int WebThreeStubServer::newFilterString(std::string const& _filter) +int WebThreeStubServer::eth_newFilterString(std::string const& _filter) { unsigned ret = -1; if (!client()) @@ -503,14 +505,14 @@ int WebThreeStubServer::newFilterString(std::string const& _filter) return ret; } -std::string WebThreeStubServer::newGroup(std::string const& _id, std::string const& _who) +std::string WebThreeStubServer::shh_newGroup(std::string const& _id, std::string const& _who) { (void)_id; (void)_who; return ""; } -std::string WebThreeStubServer::newIdentity() +std::string WebThreeStubServer::shh_newIdentity() { cnote << this << m_ids; KeyPair kp = KeyPair::create(); @@ -518,7 +520,7 @@ std::string WebThreeStubServer::newIdentity() return toJS(kp.pub()); } -Json::Value WebThreeStubServer::compilers() +Json::Value WebThreeStubServer::eth_compilers() { Json::Value ret(Json::arrayValue); ret.append("lll"); @@ -538,7 +540,7 @@ static bytes paramsToBytes(Json::Value const& _params) return data; } -std::string WebThreeStubServer::contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params) +std::string WebThreeStubServer::eth_contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params) { auto from = m_accounts.begin()->first; for (auto a: m_accounts) @@ -553,7 +555,7 @@ std::string WebThreeStubServer::contractCall(std::string const& _address, std::s return toJS(client()->call(m_accounts[from].secret(), jsToU256(_value), jsToAddress(_address), paramsToBytes(_params), gas, gasPrice)); } -std::string WebThreeStubServer::contractCreate(std::string const& _bytecode, std::string const& _value) +std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode, std::string const& _value) { auto from = m_accounts.begin()->first; for (auto a: m_accounts) @@ -567,28 +569,28 @@ std::string WebThreeStubServer::contractCreate(std::string const& _bytecode, std return toJS(client()->transact(m_accounts[from].secret(), jsToU256(_value), jsToBytes(_bytecode), gas, gasPrice)); } -std::string WebThreeStubServer::lll(std::string const& _code) +std::string WebThreeStubServer::eth_lll(std::string const& _code) { return toJS(dev::eth::compileLLL(_code)); } -std::string WebThreeStubServer::solidity(std::string const& _code) +std::string WebThreeStubServer::eth_solidity(std::string const& _code) { shared_ptr scanner = make_shared(); return toJS(dev::solidity::CompilerStack::compile(_code, scanner)); } -int WebThreeStubServer::number() +int WebThreeStubServer::eth_number() { return client() ? client()->number() + 1 : 0; } -int WebThreeStubServer::peerCount() +int WebThreeStubServer::eth_peerCount() { return m_web3.peerCount(); } -bool WebThreeStubServer::post(Json::Value const& _json) +bool WebThreeStubServer::shh_post(Json::Value const& _json) { cnote << this << m_ids; shh::Message m = toMessage(_json); @@ -605,7 +607,7 @@ bool WebThreeStubServer::post(Json::Value const& _json) return true; } -bool WebThreeStubServer::put(std::string const& _name, std::string const& _key, std::string const& _value) +bool WebThreeStubServer::db_put(std::string const& _name, std::string const& _key, std::string const& _value) { bytes k = sha3(_name).asBytes() + sha3(_key).asBytes(); bytes v = jsToBytes(_value); @@ -613,7 +615,7 @@ bool WebThreeStubServer::put(std::string const& _name, std::string const& _key, return true; } -bool WebThreeStubServer::putString(std::string const& _name, std::string const& _key, std::string const& _value) +bool WebThreeStubServer::db_putString(std::string const& _name, std::string const& _key, std::string const& _value) { bytes k = sha3(_name).asBytes() + sha3(_key).asBytes(); string v = _value; @@ -621,7 +623,7 @@ bool WebThreeStubServer::putString(std::string const& _name, std::string const& return true; } -bool WebThreeStubServer::setCoinbase(std::string const& _address) +bool WebThreeStubServer::eth_setCoinbase(std::string const& _address) { if (!client()) return false; @@ -629,7 +631,7 @@ bool WebThreeStubServer::setCoinbase(std::string const& _address) return true; } -bool WebThreeStubServer::setDefaultBlock(int const& _block) +bool WebThreeStubServer::eth_setDefaultBlock(int const& _block) { if (!client()) return false; @@ -637,7 +639,7 @@ bool WebThreeStubServer::setDefaultBlock(int const& _block) return true; } -bool WebThreeStubServer::setListening(bool const& _listening) +bool WebThreeStubServer::eth_setListening(bool const& _listening) { if (_listening) m_web3.startNetwork(); @@ -646,7 +648,7 @@ bool WebThreeStubServer::setListening(bool const& _listening) return true; } -bool WebThreeStubServer::setMining(bool const& _mining) +bool WebThreeStubServer::eth_setMining(bool const& _mining) { if (!client()) return false; @@ -658,7 +660,7 @@ bool WebThreeStubServer::setMining(bool const& _mining) return true; } -Json::Value WebThreeStubServer::shhChanged(int const& _id) +Json::Value WebThreeStubServer::shh_changed(int const& _id) { Json::Value ret(Json::arrayValue); auto pub = m_shhWatches[_id]; @@ -682,7 +684,7 @@ Json::Value WebThreeStubServer::shhChanged(int const& _id) return ret; } -int WebThreeStubServer::shhNewFilter(Json::Value const& _json) +int WebThreeStubServer::shh_newFilter(Json::Value const& _json) { auto w = toWatch(_json); auto ret = face()->installWatch(w.first); @@ -690,19 +692,19 @@ int WebThreeStubServer::shhNewFilter(Json::Value const& _json) return ret; } -bool WebThreeStubServer::shhUninstallFilter(int const& _id) +bool WebThreeStubServer::shh_uninstallFilter(int const& _id) { face()->uninstallWatch(_id); return true; } -std::string WebThreeStubServer::stateAt(string const& _address, string const& _storage) +std::string WebThreeStubServer::eth_stateAt(string const& _address, string const& _storage) { int block = 0; return client() ? toJS(client()->stateAt(jsToAddress(_address), jsToU256(_storage), block)) : ""; } -std::string WebThreeStubServer::transact(Json::Value const& _json) +std::string WebThreeStubServer::eth_transact(Json::Value const& _json) { std::string ret; if (!client()) @@ -732,35 +734,35 @@ std::string WebThreeStubServer::transact(Json::Value const& _json) return ret; } -Json::Value WebThreeStubServer::transactionByHash(std::string const& _hash, int const& _i) +Json::Value WebThreeStubServer::eth_transactionByHash(std::string const& _hash, int const& _i) { if (!client()) return ""; return toJson(client()->transaction(jsToFixed<32>(_hash), _i)); } -Json::Value WebThreeStubServer::transactionByNumber(int const& _number, int const& _i) +Json::Value WebThreeStubServer::eth_transactionByNumber(int const& _number, int const& _i) { if (!client()) return ""; return toJson(client()->transaction(client()->hashFromNumber(_number), _i)); } -Json::Value WebThreeStubServer::uncleByHash(std::string const& _hash, int const& _i) +Json::Value WebThreeStubServer::eth_uncleByHash(std::string const& _hash, int const& _i) { if (!client()) return ""; return toJson(client()->uncle(jsToFixed<32>(_hash), _i)); } -Json::Value WebThreeStubServer::uncleByNumber(int const& _number, int const& _i) +Json::Value WebThreeStubServer::eth_uncleByNumber(int const& _number, int const& _i) { if (!client()) return ""; return toJson(client()->uncle(client()->hashFromNumber(_number), _i)); } -bool WebThreeStubServer::uninstallFilter(int const& _id) +bool WebThreeStubServer::eth_uninstallFilter(int const& _id) { if (!client()) return false; diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 1ca77b497..2b26f9acf 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -64,53 +64,55 @@ class WebThreeStubServer: public AbstractWebThreeStubServer public: WebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); - virtual Json::Value accounts(); - virtual std::string addToGroup(std::string const& _group, std::string const& _who); - virtual std::string balanceAt(std::string const& _address); - virtual Json::Value blockByHash(std::string const& _hash); - virtual Json::Value blockByNumber(int const& _number); - virtual std::string call(Json::Value const& _json); - virtual bool changed(int const& _id); - virtual std::string codeAt(std::string const& _address); - virtual std::string coinbase(); - virtual Json::Value compilers(); - virtual std::string contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params); - virtual std::string contractCreate(std::string const& _bytecode, std::string const& _value); - virtual double countAt(std::string const& _address); - virtual int defaultBlock(); - virtual std::string gasPrice(); - virtual std::string get(std::string const& _name, std::string const& _key); - virtual Json::Value getMessages(int const& _id); - virtual std::string getString(std::string const& _name, std::string const& _key); - virtual bool haveIdentity(std::string const& _id); - virtual bool listening(); - virtual std::string lll(std::string const& _code); - virtual bool mining(); - virtual int newFilter(Json::Value const& _json); - virtual int newFilterString(std::string const& _filter); - virtual std::string newGroup(std::string const& _id, std::string const& _who); - virtual std::string newIdentity(); - virtual int number(); - virtual int peerCount(); - virtual bool post(Json::Value const& _json); - virtual bool put(std::string const& _name, std::string const& _key, std::string const& _value); - virtual bool putString(std::string const& _name, std::string const& _key, std::string const& _value); - virtual bool setCoinbase(std::string const& _address); - virtual bool setDefaultBlock(int const& _block); - virtual bool setListening(bool const& _listening); - virtual bool setMining(bool const& _mining); - virtual Json::Value shhChanged(int const& _id); - virtual int shhNewFilter(Json::Value const& _json); - virtual bool shhUninstallFilter(int const& _id); - virtual std::string solidity(std::string const& _code); - virtual std::string stateAt(std::string const& _address, std::string const& _storage); - virtual std::string transact(Json::Value const& _json); - virtual Json::Value transactionByHash(std::string const& _hash, int const& _i); - virtual Json::Value transactionByNumber(int const& _number, int const& _i); - virtual Json::Value uncleByHash(std::string const& _hash, int const& _i); - virtual Json::Value uncleByNumber(int const& _number, int const& _i); - virtual bool uninstallFilter(int const& _id); - + virtual Json::Value eth_accounts(); + virtual std::string eth_balanceAt(std::string const& _address); + virtual Json::Value eth_blockByHash(std::string const& _hash); + virtual Json::Value eth_blockByNumber(int const& _number); + virtual std::string eth_call(Json::Value const& _json); + virtual bool eth_changed(int const& _id); + virtual std::string eth_codeAt(std::string const& _address); + virtual std::string eth_coinbase(); + virtual Json::Value eth_compilers(); + virtual std::string eth_contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params); + virtual std::string eth_contractCreate(std::string const& _bytecode, std::string const& _value); + virtual double eth_countAt(std::string const& _address); + virtual int eth_defaultBlock(); + virtual std::string eth_gasPrice(); + virtual Json::Value eth_getMessages(int const& _id); + virtual bool eth_listening(); + virtual bool eth_mining(); + virtual int eth_newFilter(Json::Value const& _json); + virtual int eth_newFilterString(std::string const& _filter); + virtual int eth_number(); + virtual int eth_peerCount(); + virtual bool eth_setCoinbase(std::string const& _address); + virtual bool eth_setDefaultBlock(int const& _block); + virtual bool eth_setListening(bool const& _listening); + virtual std::string eth_lll(std::string const& _s); + virtual bool eth_setMining(bool const& _mining); + virtual std::string eth_solidity(std::string const& _code); + virtual std::string eth_stateAt(std::string const& _address, std::string const& _storage); + virtual std::string eth_transact(Json::Value const& _json); + virtual Json::Value eth_transactionByHash(std::string const& _hash, int const& _i); + virtual Json::Value eth_transactionByNumber(int const& _number, int const& _i); + virtual Json::Value eth_uncleByHash(std::string const& _hash, int const& _i); + virtual Json::Value eth_uncleByNumber(int const& _number, int const& _i); + virtual bool eth_uninstallFilter(int const& _id); + + virtual std::string db_get(std::string const& _name, std::string const& _key); + virtual std::string db_getString(std::string const& _name, std::string const& _key); + virtual bool db_put(std::string const& _name, std::string const& _key, std::string const& _value); + virtual bool db_putString(std::string const& _name, std::string const& _key, std::string const& _value); + + virtual std::string shh_addToGroup(std::string const& _group, std::string const& _who); + virtual Json::Value shh_changed(int const& _id); + virtual bool shh_haveIdentity(std::string const& _id); + virtual int shh_newFilter(Json::Value const& _json); + virtual std::string shh_newGroup(std::string const& _id, std::string const& _who); + virtual std::string shh_newIdentity(); + virtual bool shh_post(Json::Value const& _json); + virtual bool shh_uninstallFilter(int const& _id); + void setAccounts(std::vector const& _accounts); void setIdentities(std::vector const& _ids); std::map const& ids() const { return m_ids; } diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index 97b7a219f..e7d8b22ed 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -13,332 +13,332 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServer(conn) { - this->bindAndAddMethod(new jsonrpc::Procedure("accounts", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::accountsI); - this->bindAndAddMethod(new jsonrpc::Procedure("addToGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::addToGroupI); - this->bindAndAddMethod(new jsonrpc::Procedure("balanceAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::balanceAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("blockByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::blockByHashI); - this->bindAndAddMethod(new jsonrpc::Procedure("blockByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::blockByNumberI); - this->bindAndAddMethod(new jsonrpc::Procedure("call", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::callI); - this->bindAndAddMethod(new jsonrpc::Procedure("changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::changedI); - this->bindAndAddMethod(new jsonrpc::Procedure("codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::codeAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::coinbaseI); - this->bindAndAddMethod(new jsonrpc::Procedure("compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::compilersI); - this->bindAndAddMethod(new jsonrpc::Procedure("contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::contractCallI); - this->bindAndAddMethod(new jsonrpc::Procedure("contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::contractCreateI); - this->bindAndAddMethod(new jsonrpc::Procedure("countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::countAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::defaultBlockI); - this->bindAndAddMethod(new jsonrpc::Procedure("gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::gasPriceI); - this->bindAndAddMethod(new jsonrpc::Procedure("get", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getI); - this->bindAndAddMethod(new jsonrpc::Procedure("getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::getMessagesI); - this->bindAndAddMethod(new jsonrpc::Procedure("getString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::getStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("haveIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::haveIdentityI); - this->bindAndAddMethod(new jsonrpc::Procedure("listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::listeningI); - this->bindAndAddMethod(new jsonrpc::Procedure("lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::lllI); - this->bindAndAddMethod(new jsonrpc::Procedure("mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::miningI); - this->bindAndAddMethod(new jsonrpc::Procedure("newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::newFilterI); - this->bindAndAddMethod(new jsonrpc::Procedure("newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newFilterStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("newGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newGroupI); - this->bindAndAddMethod(new jsonrpc::Procedure("newIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::newIdentityI); - this->bindAndAddMethod(new jsonrpc::Procedure("number", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::numberI); - this->bindAndAddMethod(new jsonrpc::Procedure("peerCount", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::peerCountI); - this->bindAndAddMethod(new jsonrpc::Procedure("post", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::postI); - this->bindAndAddMethod(new jsonrpc::Procedure("put", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putI); - this->bindAndAddMethod(new jsonrpc::Procedure("putString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::putStringI); - this->bindAndAddMethod(new jsonrpc::Procedure("setCoinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::setCoinbaseI); - this->bindAndAddMethod(new jsonrpc::Procedure("setDefaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::setDefaultBlockI); - this->bindAndAddMethod(new jsonrpc::Procedure("setListening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setListeningI); - this->bindAndAddMethod(new jsonrpc::Procedure("setMining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::setMiningI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhChanged", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhChangedI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhNewFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shhNewFilterI); - this->bindAndAddMethod(new jsonrpc::Procedure("shhUninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shhUninstallFilterI); - this->bindAndAddMethod(new jsonrpc::Procedure("solidity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::solidityI); - this->bindAndAddMethod(new jsonrpc::Procedure("stateAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::stateAtI); - this->bindAndAddMethod(new jsonrpc::Procedure("transact", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::transactI); - this->bindAndAddMethod(new jsonrpc::Procedure("transactionByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::transactionByHashI); - this->bindAndAddMethod(new jsonrpc::Procedure("transactionByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::transactionByNumberI); - this->bindAndAddMethod(new jsonrpc::Procedure("uncleByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uncleByHashI); - this->bindAndAddMethod(new jsonrpc::Procedure("uncleByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uncleByNumberI); - this->bindAndAddMethod(new jsonrpc::Procedure("uninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::uninstallFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("db_get", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::db_getI); + this->bindAndAddMethod(new jsonrpc::Procedure("db_getString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::db_getStringI); + this->bindAndAddMethod(new jsonrpc::Procedure("db_put", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::db_putI); + this->bindAndAddMethod(new jsonrpc::Procedure("db_putString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::db_putStringI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_accounts", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_accountsI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_balanceAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_balanceAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_blockByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_blockByHashI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_blockByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_blockByNumberI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_call", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_callI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_changedI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_codeAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_coinbaseI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_contractCallI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCreateI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_getMessagesI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_listeningI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_lllI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_miningI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_newFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_newFilterStringI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_number", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_numberI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_peerCount", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_peerCountI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_setCoinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_setCoinbaseI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_setDefaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_setDefaultBlockI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_setListening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_setListeningI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_setMining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_setMiningI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_solidity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_solidityI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_stateAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_stateAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_transact", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_transactI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_transactionByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_transactionByHashI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_transactionByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_transactionByNumberI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_uncleByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_uncleByHashI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_uncleByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_uncleByNumberI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_uninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_uninstallFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_addToGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::shh_addToGroupI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_changed", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shh_changedI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_haveIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::shh_haveIdentityI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shh_newFilterI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_newGroup", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::shh_newGroupI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_newIdentity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::shh_newIdentityI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_post", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::shh_postI); + this->bindAndAddMethod(new jsonrpc::Procedure("shh_uninstallFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::shh_uninstallFilterI); } - inline virtual void accountsI(const Json::Value& request, Json::Value& response) + inline virtual void db_getI(const Json::Value& request, Json::Value& response) { - response = this->accounts(); + response = this->db_get(request[0u].asString(), request[1u].asString()); } - inline virtual void addToGroupI(const Json::Value& request, Json::Value& response) + inline virtual void db_getStringI(const Json::Value& request, Json::Value& response) { - response = this->addToGroup(request[0u].asString(), request[1u].asString()); + response = this->db_getString(request[0u].asString(), request[1u].asString()); } - inline virtual void balanceAtI(const Json::Value& request, Json::Value& response) + inline virtual void db_putI(const Json::Value& request, Json::Value& response) { - response = this->balanceAt(request[0u].asString()); + response = this->db_put(request[0u].asString(), request[1u].asString(), request[2u].asString()); } - inline virtual void blockByHashI(const Json::Value& request, Json::Value& response) + inline virtual void db_putStringI(const Json::Value& request, Json::Value& response) { - response = this->blockByHash(request[0u].asString()); + response = this->db_putString(request[0u].asString(), request[1u].asString(), request[2u].asString()); } - inline virtual void blockByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void eth_accountsI(const Json::Value& request, Json::Value& response) { - response = this->blockByNumber(request[0u].asInt()); + response = this->eth_accounts(); } - inline virtual void callI(const Json::Value& request, Json::Value& response) + inline virtual void eth_balanceAtI(const Json::Value& request, Json::Value& response) { - response = this->call(request[0u]); + response = this->eth_balanceAt(request[0u].asString()); } - inline virtual void changedI(const Json::Value& request, Json::Value& response) + inline virtual void eth_blockByHashI(const Json::Value& request, Json::Value& response) { - response = this->changed(request[0u].asInt()); + response = this->eth_blockByHash(request[0u].asString()); } - inline virtual void codeAtI(const Json::Value& request, Json::Value& response) + inline virtual void eth_blockByNumberI(const Json::Value& request, Json::Value& response) { - response = this->codeAt(request[0u].asString()); + response = this->eth_blockByNumber(request[0u].asInt()); } - inline virtual void coinbaseI(const Json::Value& request, Json::Value& response) + inline virtual void eth_callI(const Json::Value& request, Json::Value& response) { - response = this->coinbase(); + response = this->eth_call(request[0u]); } - inline virtual void compilersI(const Json::Value& request, Json::Value& response) + inline virtual void eth_changedI(const Json::Value& request, Json::Value& response) { - response = this->compilers(); + response = this->eth_changed(request[0u].asInt()); } - inline virtual void contractCallI(const Json::Value& request, Json::Value& response) + inline virtual void eth_codeAtI(const Json::Value& request, Json::Value& response) { - response = this->contractCall(request[0u].asString(), request[1u].asString(), request[2u]); + response = this->eth_codeAt(request[0u].asString()); } - inline virtual void contractCreateI(const Json::Value& request, Json::Value& response) + inline virtual void eth_coinbaseI(const Json::Value& request, Json::Value& response) { - response = this->contractCreate(request[0u].asString(), request[1u].asString()); + response = this->eth_coinbase(); } - inline virtual void countAtI(const Json::Value& request, Json::Value& response) + inline virtual void eth_compilersI(const Json::Value& request, Json::Value& response) { - response = this->countAt(request[0u].asString()); + response = this->eth_compilers(); } - inline virtual void defaultBlockI(const Json::Value& request, Json::Value& response) + inline virtual void eth_contractCallI(const Json::Value& request, Json::Value& response) { - response = this->defaultBlock(); + response = this->eth_contractCall(request[0u].asString(), request[1u].asString(), request[2u]); } - inline virtual void gasPriceI(const Json::Value& request, Json::Value& response) + inline virtual void eth_contractCreateI(const Json::Value& request, Json::Value& response) { - response = this->gasPrice(); + response = this->eth_contractCreate(request[0u].asString(), request[1u].asString()); } - inline virtual void getI(const Json::Value& request, Json::Value& response) + inline virtual void eth_countAtI(const Json::Value& request, Json::Value& response) { - response = this->get(request[0u].asString(), request[1u].asString()); + response = this->eth_countAt(request[0u].asString()); } - inline virtual void getMessagesI(const Json::Value& request, Json::Value& response) + inline virtual void eth_defaultBlockI(const Json::Value& request, Json::Value& response) { - response = this->getMessages(request[0u].asInt()); + response = this->eth_defaultBlock(); } - inline virtual void getStringI(const Json::Value& request, Json::Value& response) + inline virtual void eth_gasPriceI(const Json::Value& request, Json::Value& response) { - response = this->getString(request[0u].asString(), request[1u].asString()); + response = this->eth_gasPrice(); } - inline virtual void haveIdentityI(const Json::Value& request, Json::Value& response) + inline virtual void eth_getMessagesI(const Json::Value& request, Json::Value& response) { - response = this->haveIdentity(request[0u].asString()); + response = this->eth_getMessages(request[0u].asInt()); } - inline virtual void listeningI(const Json::Value& request, Json::Value& response) + inline virtual void eth_listeningI(const Json::Value& request, Json::Value& response) { - response = this->listening(); + response = this->eth_listening(); } - inline virtual void lllI(const Json::Value& request, Json::Value& response) + inline virtual void eth_lllI(const Json::Value& request, Json::Value& response) { - response = this->lll(request[0u].asString()); + response = this->eth_lll(request[0u].asString()); } - inline virtual void miningI(const Json::Value& request, Json::Value& response) + inline virtual void eth_miningI(const Json::Value& request, Json::Value& response) { - response = this->mining(); + response = this->eth_mining(); } - inline virtual void newFilterI(const Json::Value& request, Json::Value& response) + inline virtual void eth_newFilterI(const Json::Value& request, Json::Value& response) { - response = this->newFilter(request[0u]); + response = this->eth_newFilter(request[0u]); } - inline virtual void newFilterStringI(const Json::Value& request, Json::Value& response) + inline virtual void eth_newFilterStringI(const Json::Value& request, Json::Value& response) { - response = this->newFilterString(request[0u].asString()); + response = this->eth_newFilterString(request[0u].asString()); } - inline virtual void newGroupI(const Json::Value& request, Json::Value& response) + inline virtual void eth_numberI(const Json::Value& request, Json::Value& response) { - response = this->newGroup(request[0u].asString(), request[1u].asString()); + response = this->eth_number(); } - inline virtual void newIdentityI(const Json::Value& request, Json::Value& response) + inline virtual void eth_peerCountI(const Json::Value& request, Json::Value& response) { - response = this->newIdentity(); + response = this->eth_peerCount(); } - inline virtual void numberI(const Json::Value& request, Json::Value& response) + inline virtual void eth_setCoinbaseI(const Json::Value& request, Json::Value& response) { - response = this->number(); + response = this->eth_setCoinbase(request[0u].asString()); } - inline virtual void peerCountI(const Json::Value& request, Json::Value& response) + inline virtual void eth_setDefaultBlockI(const Json::Value& request, Json::Value& response) { - response = this->peerCount(); + response = this->eth_setDefaultBlock(request[0u].asInt()); } - inline virtual void postI(const Json::Value& request, Json::Value& response) + inline virtual void eth_setListeningI(const Json::Value& request, Json::Value& response) { - response = this->post(request[0u]); + response = this->eth_setListening(request[0u].asBool()); } - inline virtual void putI(const Json::Value& request, Json::Value& response) + inline virtual void eth_setMiningI(const Json::Value& request, Json::Value& response) { - response = this->put(request[0u].asString(), request[1u].asString(), request[2u].asString()); + response = this->eth_setMining(request[0u].asBool()); } - inline virtual void putStringI(const Json::Value& request, Json::Value& response) + inline virtual void eth_solidityI(const Json::Value& request, Json::Value& response) { - response = this->putString(request[0u].asString(), request[1u].asString(), request[2u].asString()); + response = this->eth_solidity(request[0u].asString()); } - inline virtual void setCoinbaseI(const Json::Value& request, Json::Value& response) + inline virtual void eth_stateAtI(const Json::Value& request, Json::Value& response) { - response = this->setCoinbase(request[0u].asString()); + response = this->eth_stateAt(request[0u].asString(), request[1u].asString()); } - inline virtual void setDefaultBlockI(const Json::Value& request, Json::Value& response) + inline virtual void eth_transactI(const Json::Value& request, Json::Value& response) { - response = this->setDefaultBlock(request[0u].asInt()); + response = this->eth_transact(request[0u]); } - inline virtual void setListeningI(const Json::Value& request, Json::Value& response) + inline virtual void eth_transactionByHashI(const Json::Value& request, Json::Value& response) { - response = this->setListening(request[0u].asBool()); + response = this->eth_transactionByHash(request[0u].asString(), request[1u].asInt()); } - inline virtual void setMiningI(const Json::Value& request, Json::Value& response) + inline virtual void eth_transactionByNumberI(const Json::Value& request, Json::Value& response) { - response = this->setMining(request[0u].asBool()); + response = this->eth_transactionByNumber(request[0u].asInt(), request[1u].asInt()); } - inline virtual void shhChangedI(const Json::Value& request, Json::Value& response) + inline virtual void eth_uncleByHashI(const Json::Value& request, Json::Value& response) { - response = this->shhChanged(request[0u].asInt()); + response = this->eth_uncleByHash(request[0u].asString(), request[1u].asInt()); } - inline virtual void shhNewFilterI(const Json::Value& request, Json::Value& response) + inline virtual void eth_uncleByNumberI(const Json::Value& request, Json::Value& response) { - response = this->shhNewFilter(request[0u]); + response = this->eth_uncleByNumber(request[0u].asInt(), request[1u].asInt()); } - inline virtual void shhUninstallFilterI(const Json::Value& request, Json::Value& response) + inline virtual void eth_uninstallFilterI(const Json::Value& request, Json::Value& response) { - response = this->shhUninstallFilter(request[0u].asInt()); + response = this->eth_uninstallFilter(request[0u].asInt()); } - inline virtual void solidityI(const Json::Value& request, Json::Value& response) + inline virtual void shh_addToGroupI(const Json::Value& request, Json::Value& response) { - response = this->solidity(request[0u].asString()); + response = this->shh_addToGroup(request[0u].asString(), request[1u].asString()); } - inline virtual void stateAtI(const Json::Value& request, Json::Value& response) + inline virtual void shh_changedI(const Json::Value& request, Json::Value& response) { - response = this->stateAt(request[0u].asString(), request[1u].asString()); + response = this->shh_changed(request[0u].asInt()); } - inline virtual void transactI(const Json::Value& request, Json::Value& response) + inline virtual void shh_haveIdentityI(const Json::Value& request, Json::Value& response) { - response = this->transact(request[0u]); + response = this->shh_haveIdentity(request[0u].asString()); } - inline virtual void transactionByHashI(const Json::Value& request, Json::Value& response) + inline virtual void shh_newFilterI(const Json::Value& request, Json::Value& response) { - response = this->transactionByHash(request[0u].asString(), request[1u].asInt()); + response = this->shh_newFilter(request[0u]); } - inline virtual void transactionByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void shh_newGroupI(const Json::Value& request, Json::Value& response) { - response = this->transactionByNumber(request[0u].asInt(), request[1u].asInt()); + response = this->shh_newGroup(request[0u].asString(), request[1u].asString()); } - inline virtual void uncleByHashI(const Json::Value& request, Json::Value& response) + inline virtual void shh_newIdentityI(const Json::Value& request, Json::Value& response) { - response = this->uncleByHash(request[0u].asString(), request[1u].asInt()); + response = this->shh_newIdentity(); } - inline virtual void uncleByNumberI(const Json::Value& request, Json::Value& response) + inline virtual void shh_postI(const Json::Value& request, Json::Value& response) { - response = this->uncleByNumber(request[0u].asInt(), request[1u].asInt()); + response = this->shh_post(request[0u]); } - inline virtual void uninstallFilterI(const Json::Value& request, Json::Value& response) + inline virtual void shh_uninstallFilterI(const Json::Value& request, Json::Value& response) { - response = this->uninstallFilter(request[0u].asInt()); + response = this->shh_uninstallFilter(request[0u].asInt()); } - virtual Json::Value accounts() = 0; - virtual std::string addToGroup(const std::string& param1, const std::string& param2) = 0; - virtual std::string balanceAt(const std::string& param1) = 0; - virtual Json::Value blockByHash(const std::string& param1) = 0; - virtual Json::Value blockByNumber(const int& param1) = 0; - virtual std::string call(const Json::Value& param1) = 0; - virtual bool changed(const int& param1) = 0; - virtual std::string codeAt(const std::string& param1) = 0; - virtual std::string coinbase() = 0; - virtual Json::Value compilers() = 0; - virtual std::string contractCall(const std::string& param1, const std::string& param2, const Json::Value& param3) = 0; - virtual std::string contractCreate(const std::string& param1, const std::string& param2) = 0; - virtual double countAt(const std::string& param1) = 0; - virtual int defaultBlock() = 0; - virtual std::string gasPrice() = 0; - virtual std::string get(const std::string& param1, const std::string& param2) = 0; - virtual Json::Value getMessages(const int& param1) = 0; - virtual std::string getString(const std::string& param1, const std::string& param2) = 0; - virtual bool haveIdentity(const std::string& param1) = 0; - virtual bool listening() = 0; - virtual std::string lll(const std::string& param1) = 0; - virtual bool mining() = 0; - virtual int newFilter(const Json::Value& param1) = 0; - virtual int newFilterString(const std::string& param1) = 0; - virtual std::string newGroup(const std::string& param1, const std::string& param2) = 0; - virtual std::string newIdentity() = 0; - virtual int number() = 0; - virtual int peerCount() = 0; - virtual bool post(const Json::Value& param1) = 0; - virtual bool put(const std::string& param1, const std::string& param2, const std::string& param3) = 0; - virtual bool putString(const std::string& param1, const std::string& param2, const std::string& param3) = 0; - virtual bool setCoinbase(const std::string& param1) = 0; - virtual bool setDefaultBlock(const int& param1) = 0; - virtual bool setListening(const bool& param1) = 0; - virtual bool setMining(const bool& param1) = 0; - virtual Json::Value shhChanged(const int& param1) = 0; - virtual int shhNewFilter(const Json::Value& param1) = 0; - virtual bool shhUninstallFilter(const int& param1) = 0; - virtual std::string solidity(const std::string& param1) = 0; - virtual std::string stateAt(const std::string& param1, const std::string& param2) = 0; - virtual std::string transact(const Json::Value& param1) = 0; - virtual Json::Value transactionByHash(const std::string& param1, const int& param2) = 0; - virtual Json::Value transactionByNumber(const int& param1, const int& param2) = 0; - virtual Json::Value uncleByHash(const std::string& param1, const int& param2) = 0; - virtual Json::Value uncleByNumber(const int& param1, const int& param2) = 0; - virtual bool uninstallFilter(const int& param1) = 0; + virtual std::string db_get(const std::string& param1, const std::string& param2) = 0; + virtual std::string db_getString(const std::string& param1, const std::string& param2) = 0; + virtual bool db_put(const std::string& param1, const std::string& param2, const std::string& param3) = 0; + virtual bool db_putString(const std::string& param1, const std::string& param2, const std::string& param3) = 0; + virtual Json::Value eth_accounts() = 0; + virtual std::string eth_balanceAt(const std::string& param1) = 0; + virtual Json::Value eth_blockByHash(const std::string& param1) = 0; + virtual Json::Value eth_blockByNumber(const int& param1) = 0; + virtual std::string eth_call(const Json::Value& param1) = 0; + virtual bool eth_changed(const int& param1) = 0; + virtual std::string eth_codeAt(const std::string& param1) = 0; + virtual std::string eth_coinbase() = 0; + virtual Json::Value eth_compilers() = 0; + virtual std::string eth_contractCall(const std::string& param1, const std::string& param2, const Json::Value& param3) = 0; + virtual std::string eth_contractCreate(const std::string& param1, const std::string& param2) = 0; + virtual double eth_countAt(const std::string& param1) = 0; + virtual int eth_defaultBlock() = 0; + virtual std::string eth_gasPrice() = 0; + virtual Json::Value eth_getMessages(const int& param1) = 0; + virtual bool eth_listening() = 0; + virtual std::string eth_lll(const std::string& param1) = 0; + virtual bool eth_mining() = 0; + virtual int eth_newFilter(const Json::Value& param1) = 0; + virtual int eth_newFilterString(const std::string& param1) = 0; + virtual int eth_number() = 0; + virtual int eth_peerCount() = 0; + virtual bool eth_setCoinbase(const std::string& param1) = 0; + virtual bool eth_setDefaultBlock(const int& param1) = 0; + virtual bool eth_setListening(const bool& param1) = 0; + virtual bool eth_setMining(const bool& param1) = 0; + virtual std::string eth_solidity(const std::string& param1) = 0; + virtual std::string eth_stateAt(const std::string& param1, const std::string& param2) = 0; + virtual std::string eth_transact(const Json::Value& param1) = 0; + virtual Json::Value eth_transactionByHash(const std::string& param1, const int& param2) = 0; + virtual Json::Value eth_transactionByNumber(const int& param1, const int& param2) = 0; + virtual Json::Value eth_uncleByHash(const std::string& param1, const int& param2) = 0; + virtual Json::Value eth_uncleByNumber(const int& param1, const int& param2) = 0; + virtual bool eth_uninstallFilter(const int& param1) = 0; + virtual std::string shh_addToGroup(const std::string& param1, const std::string& param2) = 0; + virtual Json::Value shh_changed(const int& param1) = 0; + virtual bool shh_haveIdentity(const std::string& param1) = 0; + virtual int shh_newFilter(const Json::Value& param1) = 0; + virtual std::string shh_newGroup(const std::string& param1, const std::string& param2) = 0; + virtual std::string shh_newIdentity() = 0; + virtual bool shh_post(const Json::Value& param1) = 0; + virtual bool shh_uninstallFilter(const int& param1) = 0; }; #endif //_ABSTRACTWEBTHREESTUBSERVER_H_ diff --git a/libweb3jsonrpc/spec.json b/libweb3jsonrpc/spec.json index a96336f7b..8660b9221 100644 --- a/libweb3jsonrpc/spec.json +++ b/libweb3jsonrpc/spec.json @@ -1,58 +1,58 @@ [ - { "method": "coinbase", "params": [], "order": [], "returns" : "" }, - { "method": "setCoinbase", "params": [""], "order": [], "returns" : true }, - { "method": "listening", "params": [], "order": [], "returns" : false }, - { "method": "setListening", "params": [false], "order" : [], "returns" : true }, - { "method": "mining", "params": [], "order": [], "returns" : false }, - { "method": "setMining", "params": [false], "order" : [], "returns" : true }, - { "method": "gasPrice", "params": [], "order": [], "returns" : "" }, - { "method": "accounts", "params": [], "order": [], "returns" : [] }, - { "method": "peerCount", "params": [], "order": [], "returns" : 0 }, - { "method": "defaultBlock", "params": [], "order": [], "returns" : 0}, - { "method": "setDefaultBlock", "params": [0], "order": [], "returns" : true}, - { "method": "number", "params": [], "order": [], "returns" : 0}, - - { "method": "balanceAt", "params": [""], "order": [], "returns" : ""}, - { "method": "stateAt", "params": ["", ""], "order": [], "returns": ""}, - { "method": "countAt", "params": [""], "order": [], "returns" : 0.0}, - { "method": "codeAt", "params": [""], "order": [], "returns": ""}, - - { "method": "transact", "params": [{}], "order": [], "returns": ""}, - { "method": "call", "params": [{}], "order": [], "returns": ""}, - - { "method": "blockByHash", "params": [""],"order": [], "returns": {}}, - { "method": "blockByNumber", "params": [0],"order": [], "returns": {}}, - { "method": "transactionByHash", "params": ["", 0], "order": [], "returns": {}}, - { "method": "transactionByNumber", "params": [0, 0], "order": [], "returns": {}}, - { "method": "uncleByHash", "params": ["", 0], "order": [], "returns": {}}, - { "method": "uncleByNumber", "params": [0, 0], "order": [], "returns": {}}, - - { "method": "compilers", "params": [], "order": [], "returns": []}, - { "method": "lll", "params": [""], "order": [], "returns": ""}, - { "method": "solidity", "params": [""], "order": [], "returns": ""}, - { "method": "contractCreate", "params": ["", ""], "order": [], "returns": ""}, - { "method": "contractCall", "params": ["", "", []], "order": [], "returns": ""}, - - { "method": "newFilter", "params": [{}], "order": [], "returns": 0}, - { "method": "newFilterString", "params": [""], "order": [], "returns": 0}, - { "method": "uninstallFilter", "params": [0], "order": [], "returns": true}, - { "method": "changed", "params": [0], "order": [], "returns": false}, - { "method": "getMessages", "params": [0], "order": [], "returns": []}, - - { "method": "put", "params": ["", "", ""], "order": [], "returns": true}, - { "method": "get", "params": ["", ""], "order": [], "returns": ""}, - { "method": "putString", "params": ["", "", ""], "order": [], "returns": true}, - { "method": "getString", "params": ["", ""], "order": [], "returns": ""}, - - { "method": "post", "params": [{}], "order": [], "returns": true}, - { "method": "newIdentity", "params": [], "order": [], "returns": ""}, - { "method": "haveIdentity", "params": [""], "order": [], "returns": false}, - { "method": "newGroup", "params": ["", ""], "order": [], "returns": ""}, - { "method": "addToGroup", "params": ["", ""], "order": [], "returns": ""}, + { "method": "eth_coinbase", "params": [], "order": [], "returns" : "" }, + { "method": "eth_setCoinbase", "params": [""], "order": [], "returns" : true }, + { "method": "eth_listening", "params": [], "order": [], "returns" : false }, + { "method": "eth_setListening", "params": [false], "order" : [], "returns" : true }, + { "method": "eth_mining", "params": [], "order": [], "returns" : false }, + { "method": "eth_setMining", "params": [false], "order" : [], "returns" : true }, + { "method": "eth_gasPrice", "params": [], "order": [], "returns" : "" }, + { "method": "eth_accounts", "params": [], "order": [], "returns" : [] }, + { "method": "eth_peerCount", "params": [], "order": [], "returns" : 0 }, + { "method": "eth_defaultBlock", "params": [], "order": [], "returns" : 0}, + { "method": "eth_setDefaultBlock", "params": [0], "order": [], "returns" : true}, + { "method": "eth_number", "params": [], "order": [], "returns" : 0}, + + { "method": "eth_balanceAt", "params": [""], "order": [], "returns" : ""}, + { "method": "eth_stateAt", "params": ["", ""], "order": [], "returns": ""}, + { "method": "eth_countAt", "params": [""], "order": [], "returns" : 0.0}, + { "method": "eth_codeAt", "params": [""], "order": [], "returns": ""}, + + { "method": "eth_transact", "params": [{}], "order": [], "returns": ""}, + { "method": "eth_call", "params": [{}], "order": [], "returns": ""}, + + { "method": "eth_blockByHash", "params": [""],"order": [], "returns": {}}, + { "method": "eth_blockByNumber", "params": [0],"order": [], "returns": {}}, + { "method": "eth_transactionByHash", "params": ["", 0], "order": [], "returns": {}}, + { "method": "eth_transactionByNumber", "params": [0, 0], "order": [], "returns": {}}, + { "method": "eth_uncleByHash", "params": ["", 0], "order": [], "returns": {}}, + { "method": "eth_uncleByNumber", "params": [0, 0], "order": [], "returns": {}}, + + { "method": "eth_compilers", "params": [], "order": [], "returns": []}, + { "method": "eth_lll", "params": [""], "order": [], "returns": ""}, + { "method": "eth_solidity", "params": [""], "order": [], "returns": ""}, + { "method": "eth_contractCreate", "params": ["", ""], "order": [], "returns": ""}, + { "method": "eth_contractCall", "params": ["", "", []], "order": [], "returns": ""}, + + { "method": "eth_newFilter", "params": [{}], "order": [], "returns": 0}, + { "method": "eth_newFilterString", "params": [""], "order": [], "returns": 0}, + { "method": "eth_uninstallFilter", "params": [0], "order": [], "returns": true}, + { "method": "eth_changed", "params": [0], "order": [], "returns": false}, + { "method": "eth_getMessages", "params": [0], "order": [], "returns": []}, + + { "method": "db_put", "params": ["", "", ""], "order": [], "returns": true}, + { "method": "db_get", "params": ["", ""], "order": [], "returns": ""}, + { "method": "db_putString", "params": ["", "", ""], "order": [], "returns": true}, + { "method": "db_getString", "params": ["", ""], "order": [], "returns": ""}, + + { "method": "shh_post", "params": [{}], "order": [], "returns": true}, + { "method": "shh_newIdentity", "params": [], "order": [], "returns": ""}, + { "method": "shh_haveIdentity", "params": [""], "order": [], "returns": false}, + { "method": "shh_newGroup", "params": ["", ""], "order": [], "returns": ""}, + { "method": "shh_addToGroup", "params": ["", ""], "order": [], "returns": ""}, - { "method": "shhNewFilter", "params": [{}], "order": [], "returns": 0}, - { "method": "shhUninstallFilter", "params": [0], "order": [], "returns": true}, - { "method": "shhChanged", "params": [0], "order": [], "returns": []} + { "method": "shh_newFilter", "params": [{}], "order": [], "returns": 0}, + { "method": "shh_uninstallFilter", "params": [0], "order": [], "returns": true}, + { "method": "shh_changed", "params": [0], "order": [], "returns": []} ] diff --git a/solc/main.cpp b/solc/main.cpp index 04fee2905..04fdc0ee1 100644 --- a/solc/main.cpp +++ b/solc/main.cpp @@ -42,7 +42,8 @@ void help() { cout << "Usage solc [OPTIONS] " << endl << "Options:" << endl - << " -h,--help Show this help message and exit." << endl + << " -o,--optimize Optimize the bytecode for size." << endl + << " -h,--help Show this help message and exit." << endl << " -V,--version Show the version and exit." << endl; exit(0); } @@ -58,10 +59,13 @@ void version() int main(int argc, char** argv) { string infile; + bool optimize = false; for (int i = 1; i < argc; ++i) { string arg = argv[i]; - if (arg == "-h" || arg == "--help") + if (arg == "-o" || arg == "--optimize") + optimize = true; + else if (arg == "-h" || arg == "--help") help(); else if (arg == "-V" || arg == "--version") version(); @@ -98,7 +102,7 @@ int main(int argc, char** argv) printer.print(cout); compiler.compileContract(*ast); - instructions = compiler.getAssembledBytecode(); + instructions = compiler.getAssembledBytecode(optimize); } catch (ParserError const& exception) { diff --git a/test/TestHelper.cpp b/test/TestHelper.cpp index ca46c2ca2..c1a141abb 100644 --- a/test/TestHelper.cpp +++ b/test/TestHelper.cpp @@ -253,7 +253,7 @@ bytes importCode(json_spirit::mObject& _o) code.clear(); for (auto const& j: _o["code"].get_array()) code.push_back(toByte(j)); - } + } return code; } @@ -305,6 +305,47 @@ std::string getTestPath() return testPath; } +void userDefinedTest(string testTypeFlag, std::function doTests) +{ + 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 == testTypeFlag) + { + if (i + 1 >= boost::unit_test::framework::master_test_suite().argc) + { + cnote << "Missing filename\nUsage: testeth " << testTypeFlag << " \n"; + return; + } + string filename = boost::unit_test::framework::master_test_suite().argv[i + 1]; + int currentVerbosity = g_logVerbosity; + g_logVerbosity = 12; + try + { + cnote << "Testing user defined test: " << filename; + json_spirit::mValue v; + string s = asString(contents(filename)); + BOOST_REQUIRE_MESSAGE(s.length() > 0, "Contents of " + filename + " is empty. "); + json_spirit::read_string(s, v); + doTests(v, false); + } + catch (Exception const& _e) + { + BOOST_ERROR("Failed Test with Exception: " << diagnostic_information(_e)); + g_logVerbosity = currentVerbosity; + } + catch (std::exception const& _e) + { + BOOST_ERROR("Failed Test with Exception: " << _e.what()); + g_logVerbosity = currentVerbosity; + } + g_logVerbosity = currentVerbosity; + } + else + continue; + } +} + void executeTests(const string& _name, const string& _testPathAppendix, std::function doTests) { string testPath = getTestPath(); diff --git a/test/TestHelper.h b/test/TestHelper.h index a4eb64d84..ef67d52fb 100644 --- a/test/TestHelper.h +++ b/test/TestHelper.h @@ -71,6 +71,7 @@ void checkOutput(bytes const& _output, json_spirit::mObject& _o); void checkStorage(std::map _expectedStore, std::map _resultStore, Address _expectedAddr); void executeTests(const std::string& _name, const std::string& _testPathAppendix, std::function doTests); std::string getTestPath(); +void userDefinedTest(std::string testTypeFlag, std::function doTests); template void checkAddresses(mapType& _expectedAddrs, mapType& _resultAddrs) diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 68c30734a..4c748a954 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -74,14 +74,14 @@ BOOST_FIXTURE_TEST_SUITE(environment, Setup) BOOST_AUTO_TEST_CASE(jsonrpc_defaultBlock) { cnote << "Testing jsonrpc defaultBlock..."; - int defaultBlock = jsonrpcClient->defaultBlock(); + int defaultBlock = jsonrpcClient->eth_defaultBlock(); BOOST_CHECK_EQUAL(defaultBlock, web3->ethereum()->getDefault()); } BOOST_AUTO_TEST_CASE(jsonrpc_gasPrice) { cnote << "Testing jsonrpc gasPrice..."; - string gasPrice = jsonrpcClient->gasPrice(); + string gasPrice = jsonrpcClient->eth_gasPrice(); BOOST_CHECK_EQUAL(gasPrice, toJS(10 * dev::eth::szabo)); } @@ -90,11 +90,11 @@ BOOST_AUTO_TEST_CASE(jsonrpc_isListening) cnote << "Testing jsonrpc isListening..."; web3->startNetwork(); - bool listeningOn = jsonrpcClient->listening(); + bool listeningOn = jsonrpcClient->eth_listening(); BOOST_CHECK_EQUAL(listeningOn, web3->isNetworkStarted()); web3->stopNetwork(); - bool listeningOff = jsonrpcClient->listening(); + bool listeningOff = jsonrpcClient->eth_listening(); BOOST_CHECK_EQUAL(listeningOff, web3->isNetworkStarted()); } @@ -103,11 +103,11 @@ BOOST_AUTO_TEST_CASE(jsonrpc_isMining) cnote << "Testing jsonrpc isMining..."; web3->ethereum()->startMining(); - bool miningOn = jsonrpcClient->mining(); + bool miningOn = jsonrpcClient->eth_mining(); BOOST_CHECK_EQUAL(miningOn, web3->ethereum()->isMining()); web3->ethereum()->stopMining(); - bool miningOff = jsonrpcClient->mining(); + bool miningOff = jsonrpcClient->eth_mining(); BOOST_CHECK_EQUAL(miningOff, web3->ethereum()->isMining()); } @@ -116,7 +116,7 @@ BOOST_AUTO_TEST_CASE(jsonrpc_accounts) cnote << "Testing jsonrpc accounts..."; std::vector keys = {KeyPair::create(), KeyPair::create()}; jsonrpcServer->setAccounts(keys); - Json::Value k = jsonrpcClient->accounts(); + Json::Value k = jsonrpcClient->eth_accounts(); jsonrpcServer->setAccounts({}); BOOST_CHECK_EQUAL(k.isArray(), true); BOOST_CHECK_EQUAL(k.size(), keys.size()); @@ -133,10 +133,10 @@ BOOST_AUTO_TEST_CASE(jsonrpc_accounts) BOOST_AUTO_TEST_CASE(jsonrpc_number) { cnote << "Testing jsonrpc number2..."; - int number = jsonrpcClient->number(); + int number = jsonrpcClient->eth_number(); BOOST_CHECK_EQUAL(number, web3->ethereum()->number() + 1); dev::eth::mine(*(web3->ethereum()), 1); - int numberAfter = jsonrpcClient->number(); + int numberAfter = jsonrpcClient->eth_number(); BOOST_CHECK_EQUAL(number + 1, numberAfter); BOOST_CHECK_EQUAL(numberAfter, web3->ethereum()->number() + 1); } @@ -144,7 +144,7 @@ BOOST_AUTO_TEST_CASE(jsonrpc_number) BOOST_AUTO_TEST_CASE(jsonrpc_peerCount) { cnote << "Testing jsonrpc peerCount..."; - int peerCount = jsonrpcClient->peerCount(); + int peerCount = jsonrpcClient->eth_peerCount(); BOOST_CHECK_EQUAL(web3->peerCount(), peerCount); } @@ -152,10 +152,10 @@ BOOST_AUTO_TEST_CASE(jsonrpc_setListening) { cnote << "Testing jsonrpc setListening..."; - jsonrpcClient->setListening(true); + jsonrpcClient->eth_setListening(true); BOOST_CHECK_EQUAL(web3->isNetworkStarted(), true); - jsonrpcClient->setListening(false); + jsonrpcClient->eth_setListening(false); BOOST_CHECK_EQUAL(web3->isNetworkStarted(), false); } @@ -163,10 +163,10 @@ BOOST_AUTO_TEST_CASE(jsonrpc_setMining) { cnote << "Testing jsonrpc setMining..."; - jsonrpcClient->setMining(true); + jsonrpcClient->eth_setMining(true); BOOST_CHECK_EQUAL(web3->ethereum()->isMining(), true); - jsonrpcClient->setMining(false); + jsonrpcClient->eth_setMining(false); BOOST_CHECK_EQUAL(web3->ethereum()->isMining(), false); } @@ -175,14 +175,14 @@ BOOST_AUTO_TEST_CASE(jsonrpc_stateAt) cnote << "Testing jsonrpc stateAt..."; dev::KeyPair key = KeyPair::create(); auto address = key.address(); - string stateAt = jsonrpcClient->stateAt(toJS(address), "0"); + string stateAt = jsonrpcClient->eth_stateAt(toJS(address), "0"); BOOST_CHECK_EQUAL(toJS(web3->ethereum()->stateAt(address, jsToU256("0"), 0)), stateAt); } BOOST_AUTO_TEST_CASE(jsonrpc_transact) { cnote << "Testing jsonrpc transact..."; - string coinbase = jsonrpcClient->coinbase(); + string coinbase = jsonrpcClient->eth_coinbase(); BOOST_CHECK_EQUAL(jsToAddress(coinbase), web3->ethereum()->address()); dev::KeyPair key = KeyPair::create(); @@ -190,14 +190,14 @@ BOOST_AUTO_TEST_CASE(jsonrpc_transact) auto receiver = KeyPair::create(); web3->ethereum()->setAddress(address); - coinbase = jsonrpcClient->coinbase(); + coinbase = jsonrpcClient->eth_coinbase(); BOOST_CHECK_EQUAL(jsToAddress(coinbase), web3->ethereum()->address()); BOOST_CHECK_EQUAL(jsToAddress(coinbase), address); jsonrpcServer->setAccounts({key}); auto balance = web3->ethereum()->balanceAt(address, 0); - string balanceString = jsonrpcClient->balanceAt(toJS(address)); - double countAt = jsonrpcClient->countAt(toJS(address)); + string balanceString = jsonrpcClient->eth_balanceAt(toJS(address)); + double countAt = jsonrpcClient->eth_countAt(toJS(address)); BOOST_CHECK_EQUAL(countAt, (double)(uint64_t)web3->ethereum()->countAt(address)); BOOST_CHECK_EQUAL(countAt, 0); @@ -206,7 +206,7 @@ BOOST_AUTO_TEST_CASE(jsonrpc_transact) dev::eth::mine(*(web3->ethereum()), 1); balance = web3->ethereum()->balanceAt(address, 0); - balanceString = jsonrpcClient->balanceAt(toJS(address)); + balanceString = jsonrpcClient->eth_balanceAt(toJS(address)); BOOST_CHECK_EQUAL(toJS(balance), balanceString); BOOST_CHECK_EQUAL(jsToDecimal(balanceString), "1500000000000000000"); @@ -223,13 +223,13 @@ BOOST_AUTO_TEST_CASE(jsonrpc_transact) t["gas"] = toJS(gas); t["gasPrice"] = toJS(gasPrice); - jsonrpcClient->transact(t); + jsonrpcClient->eth_transact(t); jsonrpcServer->setAccounts({}); dev::eth::mine(*(web3->ethereum()), 1); - countAt = jsonrpcClient->countAt(toJS(address)); + countAt = jsonrpcClient->eth_countAt(toJS(address)); auto balance2 = web3->ethereum()->balanceAt(receiver.address()); - string balanceString2 = jsonrpcClient->balanceAt(toJS(receiver.address())); + string balanceString2 = jsonrpcClient->eth_balanceAt(toJS(receiver.address())); BOOST_CHECK_EQUAL(countAt, (double)(uint64_t)web3->ethereum()->countAt(address)); BOOST_CHECK_EQUAL(countAt, 1); diff --git a/test/stPreCompiledContractsFiller.json b/test/stPreCompiledContractsFiller.json new file mode 100644 index 000000000..8975f1aea --- /dev/null +++ b/test/stPreCompiledContractsFiller.json @@ -0,0 +1,717 @@ +{ + "CallEcrecover0": { + "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) (CALL 1000 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (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_gas500": { + "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) (CALL 500 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (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_Gas499": { + "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) (CALL 499 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (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_0input": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code": "{ (CALL 1000 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (EXP 2 160)) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallEcrecover1": { + "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 1) (MSTORE 64 0x73b1693892219d736caba55bdb67216e485557ea6b6af75f37096c9aa6a5a75f) (MSTORE 96 0xeeb940b1d03b21e36b0e47e79769f095fe2ab855bd91e3a38756b7d75a9c4549) (CALL 1000 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (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" : "" + } + }, + + "CallEcrecover2": { + "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 33 0x73b1693892219d736caba55bdb67216e485557ea6b6af75f37096c9aa6a5a75f) (MSTORE 65 0xeeb940b1d03b21e36b0e47e79769f095fe2ab855bd91e3a38756b7d75a9c4549) (CALL 1000 1 0 0 97 97 32) [[ 0 ]] (MOD (MLOAD 97) (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" : "" + } + }, + + "CallEcrecover3": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code": "{ (MSTORE 0 0x2f380a2dea7e778d81affc2443403b8fe4644db442ae4862ff5bb3732829cdb9) (MSTORE 32 27) (MSTORE 64 0x6b65ccb0558806e9b097f27a396d08f964e37b8b7af6ceeb516ff86739fbea0a) (MSTORE 96 0x37cbc8d883e129a4b1ef9d5f1df53c4f21a3ef147cf2a50a4ede0eb06ce092d4) (CALL 1000 1 0 0 128 128 32) [[ 0 ]] (MOD (MLOAD 128) (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" : "" + } + }, + + "CallSha256_0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "0x600160005260206000602060006000600260fff1600051600055", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (CALL 500 2 0 0 0 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 5 0xf34578907f) (CALL 500 2 0 0 37 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_3": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xf34578907f) (CALL 500 2 0 0 37 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_4": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 100 2 0 0 32 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_4_gas99": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 99 2 0 0 32 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallSha256_5": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 500 2 0 0 1000000 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "0x600160005260206000602060006000600360fff1600051600055", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (CALL 500 3 0 0 0 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 5 0xf34578907f) (CALL 500 3 0 0 37 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_3": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xf34578907f) (CALL 500 3 0 0 37 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_4": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 100 3 0 0 32 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_4_gas99": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 99 3 0 0 32 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRipemd160_5": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (CALL 500 3 0 0 1000000 0 32) [[ 0 ]] (MLOAD 0)}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + +} + diff --git a/test/stSystemOperationsTestFiller.json b/test/stSystemOperationsTestFiller.json new file mode 100644 index 000000000..e62753089 --- /dev/null +++ b/test/stSystemOperationsTestFiller.json @@ -0,0 +1,1334 @@ +{ + "createNameRegistrator": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0x601080600c6000396000f20060003554156009570060203560003555) [[ 0 ]] (CREATE 23 4 28) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "createNameRegistratorValueTooHigh": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0x601080600c6000396000f20060003554156009570060203560003555) [[ 0 ]] (CREATE 1000 4 28) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "createNameRegistratorOutOfMemoryBonds0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0x601080600c6000396000f20060003554156009570060203560003555) [[ 0 ]] (CREATE 23 0xfffffffffff 28) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "createNameRegistratorOutOfMemoryBonds1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0x601080600c6000396000f20060003554156009570060203560003555) [[ 0 ]] (CREATE 23 4 0xfffffffffff) }", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToNameRegistrator0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToReturn1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 0 2) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x6001600155603760005360026000f2", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "PostToReturn1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) (POST 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 ) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x603760005360026000f2", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "callstatelessToReturn1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALLSTATELESS 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 0 2 ) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x6001600155603760005360026000f2", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "callcodeToReturn1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALLCODE 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 0 2 ) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x6001600155603760005360026000f2", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "CallToNameRegistratorOutOfGas": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 100 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToNameRegistratorTooMuchMemory0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 987654321 64 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToNameRegistratorTooMuchMemory1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 9865432 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToNameRegistratorTooMuchMemory2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 987654 1) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + + "CallToNameRegistratorNotMuchMemory0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 987654 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallToNameRegistratorNotMuchMemory1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xeeffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff00) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALL 500 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 987654 0 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRecursiveBomb0": { + "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" : "{ [[ 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", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ [[ 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" : "365223", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRecursiveBomb2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ [[ 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" : "365224", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "CallRecursiveBomb3": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "20000000", + "nonce" : 0, + "code" : "{ [[ 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" : "" + } + }, + + "suicideCaller": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[0]] (CALLER) (SUICIDE (CALLER))}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "suicideOrigin": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[0]] (ORIGIN) (SUICIDE (ORIGIN))}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "suicideAddress": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[0]] (ADDRESS) (SUICIDE (ADDRESS))}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "suicideNotExistingAccount": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (SUICIDE 0xaa1722f3947def4cf144679da39c4c32bdc35681 )}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "suicideSendEtherToMe": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (SUICIDE (ADDRESS) )}", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "return0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "23", + "code" : "{ (MSTORE8 0 55) (RETURN 0 1)}", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "return1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "23", + "code" : "{ (MSTORE8 0 55) (RETURN 0 2)}", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "return2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "23", + "code" : "{ (MSTORE8 0 55) (RETURN 0 33)}", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "callcodeToNameRegistrator0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ (MSTORE 0 0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff) (MSTORE 32 0xaaffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffaa ) [[ 0 ]] (CALLCODE 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 23 0 64 64 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "0x60003554156009570060203560003555", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "TestNameRegistrator": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "1000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "0x60003554156009570060203560003555", + "storage": {} + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffafffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffa" + } + }, + + "ABAcalls0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ (PC) ]] (CALL 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 24 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : " { [[ (PC) ]] (ADD 1 (CALL 500 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 23 0 0 0 0)) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "ABAcalls1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ (PC) ]] (CALL (- (GAS) 1000) 0x945304eb96065b2a98b57a48a06ae28d285a71b5 24 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : " { [[ (PC) ]] (ADD 1 (CALL (- (GAS) 1000) 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 23 0 0 0 0)) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "1000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "ABAcalls2": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (ADD (SLOAD 0) 1) (CALL (- (GAS) 1000) 0x945304eb96065b2a98b57a48a06ae28d285a71b5 1 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "0", + "code" : " { [[ 0 ]] (ADD (SLOAD 0) 1) (CALL (- (GAS) 1000) 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 0 0 0 0 0) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "ABAcalls3": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1025000", + "nonce" : 0, + "code" : "{ [[ 0 ]] (ADD (SLOAD 0) 1) (CALL (- (GAS) 1000) 0x945304eb96065b2a98b57a48a06ae28d285a71b5 1 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "0", + "code" : " { [[ 0 ]] (ADD (SLOAD 0) 1) (CALL (- (GAS) 1000) 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 0 0 0 0 0) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "ABAcallsSuicide0": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ (PC) ]] (CALL 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 24 0 0 0 0) (SUICIDE 0x945304eb96065b2a98b57a48a06ae28d285a71b5) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "{ [[ (PC) ]] (ADD 1 (CALL 500 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 23 0 0 0 0)) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + }, + + "ABAcallsSuicide1": { + "env" : { + "previousHash" : "5e20a0453cecd065ea59c37ac63e079ee08998b6045136a8ce6635c7912ec0b6", + "currentNumber" : "0", + "currentGasLimit" : "10000000", + "currentDifficulty" : "256", + "currentTimestamp" : 1, + "currentCoinbase" : "2adc25665018aa1fe0e6bc666dac8fc2697ff9ba" + }, + "pre" : { + "095e7baea6a6c7c4c2dfeb977efac326af552d87" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "{ [[ (PC) ]] (CALL 1000 0x945304eb96065b2a98b57a48a06ae28d285a71b5 24 0 0 0 0) }", + "storage": {} + }, + "945304eb96065b2a98b57a48a06ae28d285a71b5" : { + "balance" : "23", + "code" : "{ [[ (PC) ]] (ADD 1 (CALL 500 0x095e7baea6a6c7c4c2dfeb977efac326af552d87 23 0 0 0 0)) (SUICIDE 0x0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6) } ", + "nonce" : "0", + "storage" : { + } + }, + "a94f5374fce5edbc8e2a8697c15331677e6ebf0b" : { + "balance" : "1000000000000000000", + "nonce" : 0, + "code" : "", + "storage": {} + } + }, + "transaction" : { + "nonce" : "0", + "gasPrice" : "1", + "gasLimit" : "10000000", + "to" : "095e7baea6a6c7c4c2dfeb977efac326af552d87", + "value" : "100000", + "secretKey" : "45a915e4d060149eb4365960e6a7a45f334393093061116b197e3240065ff2d8", + "data" : "" + } + } +} diff --git a/test/state.cpp b/test/state.cpp index 935869058..91d9f3e51 100644 --- a/test/state.cpp +++ b/test/state.cpp @@ -43,7 +43,6 @@ namespace dev { namespace test { void doStateTests(json_spirit::mValue& v, bool _fillin) { - cout << "start state test\n"; for (auto& i: v.get_obj()) { cnote << i.first; @@ -118,4 +117,14 @@ BOOST_AUTO_TEST_CASE(stSystemOperationsTest) dev::test::executeTests("stSystemOperationsTest", "/StateTests", dev::test::doStateTests); } +BOOST_AUTO_TEST_CASE(stPreCompiledContracts) +{ + dev::test::executeTests("stPreCompiledContracts", "/StateTests", dev::test::doStateTests); +} + +BOOST_AUTO_TEST_CASE(userDefinedFileState) +{ + dev::test::userDefinedTest("--statetest", dev::test::doStateTests); +} + BOOST_AUTO_TEST_SUITE_END() diff --git a/test/vm.cpp b/test/vm.cpp index 93cf121de..b36d3dc2b 100644 --- a/test/vm.cpp +++ b/test/vm.cpp @@ -20,6 +20,7 @@ * vm test functions. */ +#include #include "vm.h" using namespace std; @@ -423,32 +424,42 @@ BOOST_AUTO_TEST_CASE(vmPushDupSwapTest) dev::test::executeTests("vmPushDupSwapTest", "/VMTests", dev::test::doVMTests); } -BOOST_AUTO_TEST_CASE(userDefinedFile) +BOOST_AUTO_TEST_CASE(vmRandom) { - if (boost::unit_test::framework::master_test_suite().argc == 2) + string testPath = getTestPath(); + testPath += "/VMTests/RandomTests"; + + vector testFiles; + boost::filesystem::directory_iterator iterator(testPath); + for(; iterator != boost::filesystem::directory_iterator(); ++iterator) + if (boost::filesystem::is_regular_file(iterator->path()) && iterator->path().extension() == ".json") + testFiles.push_back(iterator->path()); + + for (auto& path: testFiles) { - string filename = boost::unit_test::framework::master_test_suite().argv[1]; - int currentVerbosity = g_logVerbosity; - g_logVerbosity = 12; try { - cnote << "Testing VM..." << "user defined test"; + cnote << "Testing ..." << path.filename(); json_spirit::mValue v; - string s = asString(contents(filename)); - BOOST_REQUIRE_MESSAGE(s.length() > 0, "Contents of " + filename + " is empty. "); + string s = asString(dev::contents(path.string())); + BOOST_REQUIRE_MESSAGE(s.length() > 0, "Content of " + path.string() + " is empty. Have you cloned the 'tests' repo branch develop and set ETHEREUM_TEST_PATH to its path?"); json_spirit::read_string(s, v); - dev::test::doVMTests(v, false); + doVMTests(v, false); } catch (Exception const& _e) { - BOOST_ERROR("Failed VM Test with Exception: " << diagnostic_information(_e)); + BOOST_ERROR("Failed test with Exception: " << diagnostic_information(_e)); } catch (std::exception const& _e) { - BOOST_ERROR("Failed VM Test with Exception: " << _e.what()); + BOOST_ERROR("Failed test with Exception: " << _e.what()); } - g_logVerbosity = currentVerbosity; } } +BOOST_AUTO_TEST_CASE(userDefinedFileVM) +{ + dev::test::userDefinedTest("--vmtest", dev::test::doVMTests); +} + BOOST_AUTO_TEST_SUITE_END() diff --git a/test/vmArithmeticTestFiller.json b/test/vmArithmeticTestFiller.json index 29d523a36..b93694575 100644 --- a/test/vmArithmeticTestFiller.json +++ b/test/vmArithmeticTestFiller.json @@ -1725,7 +1725,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x62122ff4600016600057", + "code" : "0x62122ff460000b600055", "storage": {} } }, @@ -1753,7 +1753,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x62122f6a600016600057", + "code" : "0x62122f6a60000b600055", "storage": {} } }, @@ -1781,7 +1781,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x6212faf4600116600057", + "code" : "0x6212faf460010b600055", "storage": {} } }, @@ -1809,7 +1809,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x62126af4600116600057", + "code" : "0x62126af460010b600055", "storage": {} } }, @@ -1837,7 +1837,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x62126af4605016600057", + "code" : "0x62126af460500b600055", "storage": {} } }, @@ -2005,7 +2005,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x66f000000000000161ffff16600057", + "code" : "0x66f000000000000161ffff0b600055", "storage": {} } }, @@ -2033,7 +2033,7 @@ "0f572e5295c57f15886f9b263e2f6d2d6c7b5ec6" : { "balance" : "1000000000000000000", "nonce" : 0, - "code" : "0x60ff68f0000000000000000116600057", + "code" : "0x60ff68f000000000000000010b600055", "storage": {} } }, diff --git a/test/webthreestubclient.h b/test/webthreestubclient.h index c494c1bae..cf749aac7 100644 --- a/test/webthreestubclient.h +++ b/test/webthreestubclient.h @@ -19,25 +19,27 @@ class WebThreeStubClient delete this->client; } - Json::Value accounts() throw (jsonrpc::JsonRpcException) + std::string db_get(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("accounts",p); - if (result.isArray()) - return result; + p.append(param1); +p.append(param2); + + Json::Value result = this->client->CallMethod("db_get",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - std::string addToGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + std::string db_getString(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); p.append(param2); - Json::Value result = this->client->CallMethod("addToGroup",p); + Json::Value result = this->client->CallMethod("db_getString",p); if (result.isString()) return result.asString(); else @@ -45,12 +47,54 @@ p.append(param2); } - std::string balanceAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + bool db_put(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); +p.append(param2); +p.append(param3); + + Json::Value result = this->client->CallMethod("db_put",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + + bool db_putString(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); +p.append(param2); +p.append(param3); + + Json::Value result = this->client->CallMethod("db_putString",p); + if (result.isBool()) + return result.asBool(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + + Json::Value eth_accounts() throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p = Json::nullValue; + Json::Value result = this->client->CallMethod("eth_accounts",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + + std::string eth_balanceAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("balanceAt",p); + Json::Value result = this->client->CallMethod("eth_balanceAt",p); if (result.isString()) return result.asString(); else @@ -58,12 +102,12 @@ p.append(param2); } - Json::Value blockByHash(const std::string& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_blockByHash(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("blockByHash",p); + Json::Value result = this->client->CallMethod("eth_blockByHash",p); if (result.isObject()) return result; else @@ -71,12 +115,12 @@ p.append(param2); } - Json::Value blockByNumber(const int& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_blockByNumber(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("blockByNumber",p); + Json::Value result = this->client->CallMethod("eth_blockByNumber",p); if (result.isObject()) return result; else @@ -84,12 +128,12 @@ p.append(param2); } - std::string call(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + std::string eth_call(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("call",p); + Json::Value result = this->client->CallMethod("eth_call",p); if (result.isString()) return result.asString(); else @@ -97,12 +141,12 @@ p.append(param2); } - bool changed(const int& param1) throw (jsonrpc::JsonRpcException) + bool eth_changed(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("changed",p); + Json::Value result = this->client->CallMethod("eth_changed",p); if (result.isBool()) return result.asBool(); else @@ -110,12 +154,12 @@ p.append(param2); } - std::string codeAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + std::string eth_codeAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("codeAt",p); + Json::Value result = this->client->CallMethod("eth_codeAt",p); if (result.isString()) return result.asString(); else @@ -123,11 +167,11 @@ p.append(param2); } - std::string coinbase() throw (jsonrpc::JsonRpcException) + std::string eth_coinbase() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("coinbase",p); + Json::Value result = this->client->CallMethod("eth_coinbase",p); if (result.isString()) return result.asString(); else @@ -135,11 +179,11 @@ p.append(param2); } - Json::Value compilers() throw (jsonrpc::JsonRpcException) + Json::Value eth_compilers() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("compilers",p); + Json::Value result = this->client->CallMethod("eth_compilers",p); if (result.isArray()) return result; else @@ -147,14 +191,14 @@ p.append(param2); } - std::string contractCall(const std::string& param1, const std::string& param2, const Json::Value& param3) throw (jsonrpc::JsonRpcException) + std::string eth_contractCall(const std::string& param1, const std::string& param2, const Json::Value& param3) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); p.append(param2); p.append(param3); - Json::Value result = this->client->CallMethod("contractCall",p); + Json::Value result = this->client->CallMethod("eth_contractCall",p); if (result.isString()) return result.asString(); else @@ -162,13 +206,13 @@ p.append(param3); } - std::string contractCreate(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + std::string eth_contractCreate(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); p.append(param2); - Json::Value result = this->client->CallMethod("contractCreate",p); + Json::Value result = this->client->CallMethod("eth_contractCreate",p); if (result.isString()) return result.asString(); else @@ -176,12 +220,12 @@ p.append(param2); } - double countAt(const std::string& param1) throw (jsonrpc::JsonRpcException) + double eth_countAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("countAt",p); + Json::Value result = this->client->CallMethod("eth_countAt",p); if (result.isDouble()) return result.asDouble(); else @@ -189,11 +233,11 @@ p.append(param2); } - int defaultBlock() throw (jsonrpc::JsonRpcException) + int eth_defaultBlock() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("defaultBlock",p); + Json::Value result = this->client->CallMethod("eth_defaultBlock",p); if (result.isInt()) return result.asInt(); else @@ -201,25 +245,11 @@ p.append(param2); } - std::string gasPrice() throw (jsonrpc::JsonRpcException) + std::string eth_gasPrice() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("gasPrice",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - - std::string get(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("get",p); + Json::Value result = this->client->CallMethod("eth_gasPrice",p); if (result.isString()) return result.asString(); else @@ -227,12 +257,12 @@ p.append(param2); } - Json::Value getMessages(const int& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_getMessages(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("getMessages",p); + Json::Value result = this->client->CallMethod("eth_getMessages",p); if (result.isArray()) return result; else @@ -240,38 +270,11 @@ p.append(param2); } - std::string getString(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("getString",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - - bool haveIdentity(const std::string& param1) throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("haveIdentity",p); - if (result.isBool()) - return result.asBool(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - - bool listening() throw (jsonrpc::JsonRpcException) + bool eth_listening() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("listening",p); + Json::Value result = this->client->CallMethod("eth_listening",p); if (result.isBool()) return result.asBool(); else @@ -279,12 +282,12 @@ p.append(param2); } - std::string lll(const std::string& param1) throw (jsonrpc::JsonRpcException) + std::string eth_lll(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("lll",p); + Json::Value result = this->client->CallMethod("eth_lll",p); if (result.isString()) return result.asString(); else @@ -292,11 +295,11 @@ p.append(param2); } - bool mining() throw (jsonrpc::JsonRpcException) + bool eth_mining() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("mining",p); + Json::Value result = this->client->CallMethod("eth_mining",p); if (result.isBool()) return result.asBool(); else @@ -304,12 +307,12 @@ p.append(param2); } - int newFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + int eth_newFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("newFilter",p); + Json::Value result = this->client->CallMethod("eth_newFilter",p); if (result.isInt()) return result.asInt(); else @@ -317,12 +320,12 @@ p.append(param2); } - int newFilterString(const std::string& param1) throw (jsonrpc::JsonRpcException) + int eth_newFilterString(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("newFilterString",p); + Json::Value result = this->client->CallMethod("eth_newFilterString",p); if (result.isInt()) return result.asInt(); else @@ -330,62 +333,62 @@ p.append(param2); } - std::string newGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + int eth_number() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("newGroup",p); - if (result.isString()) - return result.asString(); + p = Json::nullValue; + Json::Value result = this->client->CallMethod("eth_number",p); + if (result.isInt()) + return result.asInt(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - std::string newIdentity() throw (jsonrpc::JsonRpcException) + int eth_peerCount() throw (jsonrpc::JsonRpcException) { Json::Value p; p = Json::nullValue; - Json::Value result = this->client->CallMethod("newIdentity",p); - if (result.isString()) - return result.asString(); + Json::Value result = this->client->CallMethod("eth_peerCount",p); + if (result.isInt()) + return result.asInt(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - int number() throw (jsonrpc::JsonRpcException) + bool eth_setCoinbase(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("number",p); - if (result.isInt()) - return result.asInt(); + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_setCoinbase",p); + if (result.isBool()) + return result.asBool(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - int peerCount() throw (jsonrpc::JsonRpcException) + bool eth_setDefaultBlock(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; - p = Json::nullValue; - Json::Value result = this->client->CallMethod("peerCount",p); - if (result.isInt()) - return result.asInt(); + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_setDefaultBlock",p); + if (result.isBool()) + return result.asBool(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool post(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + bool eth_setListening(const bool& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("post",p); + Json::Value result = this->client->CallMethod("eth_setListening",p); if (result.isBool()) return result.asBool(); else @@ -393,14 +396,12 @@ p.append(param2); } - bool put(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + bool eth_setMining(const bool& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); -p.append(param3); - Json::Value result = this->client->CallMethod("put",p); + Json::Value result = this->client->CallMethod("eth_setMining",p); if (result.isBool()) return result.asBool(); else @@ -408,105 +409,108 @@ p.append(param3); } - bool putString(const std::string& param1, const std::string& param2, const std::string& param3) throw (jsonrpc::JsonRpcException) + std::string eth_solidity(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); -p.append(param3); - Json::Value result = this->client->CallMethod("putString",p); - if (result.isBool()) - return result.asBool(); + Json::Value result = this->client->CallMethod("eth_solidity",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool setCoinbase(const std::string& param1) throw (jsonrpc::JsonRpcException) + std::string eth_stateAt(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("setCoinbase",p); - if (result.isBool()) - return result.asBool(); + Json::Value result = this->client->CallMethod("eth_stateAt",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool setDefaultBlock(const int& param1) throw (jsonrpc::JsonRpcException) + std::string eth_transact(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("setDefaultBlock",p); - if (result.isBool()) - return result.asBool(); + Json::Value result = this->client->CallMethod("eth_transact",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool setListening(const bool& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_transactionByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("setListening",p); - if (result.isBool()) - return result.asBool(); + Json::Value result = this->client->CallMethod("eth_transactionByHash",p); + if (result.isObject()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool setMining(const bool& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_transactionByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("setMining",p); - if (result.isBool()) - return result.asBool(); + Json::Value result = this->client->CallMethod("eth_transactionByNumber",p); + if (result.isObject()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value shhChanged(const int& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_uncleByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("shhChanged",p); - if (result.isArray()) + Json::Value result = this->client->CallMethod("eth_uncleByHash",p); + if (result.isObject()) return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - int shhNewFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + Json::Value eth_uncleByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("shhNewFilter",p); - if (result.isInt()) - return result.asInt(); + Json::Value result = this->client->CallMethod("eth_uncleByNumber",p); + if (result.isObject()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool shhUninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) + bool eth_uninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("shhUninstallFilter",p); + Json::Value result = this->client->CallMethod("eth_uninstallFilter",p); if (result.isBool()) return result.asBool(); else @@ -514,12 +518,13 @@ p.append(param3); } - std::string solidity(const std::string& param1) throw (jsonrpc::JsonRpcException) + std::string shh_addToGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); +p.append(param2); - Json::Value result = this->client->CallMethod("solidity",p); + Json::Value result = this->client->CallMethod("shh_addToGroup",p); if (result.isString()) return result.asString(); else @@ -527,95 +532,90 @@ p.append(param3); } - std::string stateAt(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) + Json::Value shh_changed(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - Json::Value result = this->client->CallMethod("stateAt",p); - if (result.isString()) - return result.asString(); + Json::Value result = this->client->CallMethod("shh_changed",p); + if (result.isArray()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - std::string transact(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + bool shh_haveIdentity(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("transact",p); - if (result.isString()) - return result.asString(); + Json::Value result = this->client->CallMethod("shh_haveIdentity",p); + if (result.isBool()) + return result.asBool(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value transactionByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) + int shh_newFilter(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - Json::Value result = this->client->CallMethod("transactionByHash",p); - if (result.isObject()) - return result; + Json::Value result = this->client->CallMethod("shh_newFilter",p); + if (result.isInt()) + return result.asInt(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value transactionByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) + std::string shh_newGroup(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); p.append(param2); - Json::Value result = this->client->CallMethod("transactionByNumber",p); - if (result.isObject()) - return result; + Json::Value result = this->client->CallMethod("shh_newGroup",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value uncleByHash(const std::string& param1, const int& param2) throw (jsonrpc::JsonRpcException) + std::string shh_newIdentity() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("uncleByHash",p); - if (result.isObject()) - return result; + p = Json::nullValue; + Json::Value result = this->client->CallMethod("shh_newIdentity",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value uncleByNumber(const int& param1, const int& param2) throw (jsonrpc::JsonRpcException) + bool shh_post(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); -p.append(param2); - Json::Value result = this->client->CallMethod("uncleByNumber",p); - if (result.isObject()) - return result; + Json::Value result = this->client->CallMethod("shh_post",p); + if (result.isBool()) + return result.asBool(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - bool uninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) + bool shh_uninstallFilter(const int& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; p.append(param1); - Json::Value result = this->client->CallMethod("uninstallFilter",p); + Json::Value result = this->client->CallMethod("shh_uninstallFilter",p); if (result.isBool()) return result.asBool(); else From a2349ba485ce97205846f916819facf7ae5c908f Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 11 Nov 2014 09:06:35 +0100 Subject: [PATCH 07/38] contract create and contract call working --- libweb3jsonrpc/WebThreeStubServer.cpp | 18 ++++++++---------- libweb3jsonrpc/WebThreeStubServer.h | 4 ++-- libweb3jsonrpc/abstractwebthreestubserver.h | 12 ++++++------ libweb3jsonrpc/spec.json | 4 ++-- test/webthreestubclient.h | 5 ++--- 5 files changed, 20 insertions(+), 23 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index f9017026b..87cd3c22b 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -528,19 +528,17 @@ Json::Value WebThreeStubServer::eth_compilers() return ret; } -static bytes paramsToBytes(Json::Value const& _params) +static bytes toMethodCall(int const& _index, Json::Value const& _params) { - bytes data; + bytes data(1, _index); if (_params.isArray()) for (auto i: _params) -// data += asBytes(i.asString()); -// data += toBigEndian(jsToU256(i.asString())); - data += asBytes(jsPadded(i.asString(), 33)); + data += asBytes(jsPadded(i.asString(), 32)); cwarn << data; return data; } -std::string WebThreeStubServer::eth_contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params) +std::string WebThreeStubServer::eth_contractCall(std::string const& _address, int const& _index, Json::Value const& _params) { auto from = m_accounts.begin()->first; for (auto a: m_accounts) @@ -551,11 +549,11 @@ std::string WebThreeStubServer::eth_contractCall(std::string const& _address, st auto gasPrice = 10 * dev::eth::szabo; auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); - auto bytes = paramsToBytes(_params); - return toJS(client()->call(m_accounts[from].secret(), jsToU256(_value), jsToAddress(_address), paramsToBytes(_params), gas, gasPrice)); + auto bytes = toMethodCall(_index, _params); + return toJS(client()->call(m_accounts[from].secret(), 0, jsToAddress(_address), toMethodCall(_index, _params), gas, gasPrice)); } -std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode, std::string const& _value) +std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode) { auto from = m_accounts.begin()->first; for (auto a: m_accounts) @@ -566,7 +564,7 @@ std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode, auto gasPrice = 10 * dev::eth::szabo; auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); - return toJS(client()->transact(m_accounts[from].secret(), jsToU256(_value), jsToBytes(_bytecode), gas, gasPrice)); + return toJS(client()->transact(m_accounts[from].secret(), 0, jsToBytes(_bytecode), gas, gasPrice)); } std::string WebThreeStubServer::eth_lll(std::string const& _code) diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 2b26f9acf..3318214f1 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -73,8 +73,8 @@ public: virtual std::string eth_codeAt(std::string const& _address); virtual std::string eth_coinbase(); virtual Json::Value eth_compilers(); - virtual std::string eth_contractCall(std::string const& _address, std::string const& _value, Json::Value const& _params); - virtual std::string eth_contractCreate(std::string const& _bytecode, std::string const& _value); + virtual std::string eth_contractCall(std::string const& _address, int const& _index, Json::Value const& _params); + virtual std::string eth_contractCreate(std::string const& _bytecode); virtual double eth_countAt(std::string const& _address); virtual int eth_defaultBlock(); virtual std::string eth_gasPrice(); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index e7d8b22ed..43a81c1cc 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -26,8 +26,8 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_coinbaseI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_contractCallI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCreateI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_contractCallI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCreateI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); @@ -129,12 +129,12 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_contractCall(request[0u].asString(), request[1u].asString(), request[2u]); + response = this->eth_contractCall(request[0u].asString(), request[1u].asInt(), request[2u]); } inline virtual void eth_contractCreateI(const Json::Value& request, Json::Value& response) { - response = this->eth_contractCreate(request[0u].asString(), request[1u].asString()); + response = this->eth_contractCreate(request[0u].asString()); } inline virtual void eth_countAtI(const Json::Value& request, Json::Value& response) @@ -306,8 +306,8 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_contractCreate",p); if (result.isString()) From 2f50d919ce9d94c011918a5f649c15bc2d449945 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 11 Nov 2014 09:14:50 +0100 Subject: [PATCH 08/38] revert unnecessary changes in main.js --- libjsqrc/main.js | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/libjsqrc/main.js b/libjsqrc/main.js index 6abffb195..da95e7e53 100644 --- a/libjsqrc/main.js +++ b/libjsqrc/main.js @@ -418,8 +418,10 @@ }; Filter.prototype.trigger = function(messages) { - for(var i = 0; i < this.callbacks.length; i++) { - this.callbacks[i].call(this, messages); + if (!(messages instanceof Array) || messages.length) { + for(var i = 0; i < this.callbacks.length; i++) { + this.callbacks[i].call(this, messages); + } } }; @@ -448,7 +450,7 @@ if(data._id) { var cb = web3._callbacks[data._id]; if (cb) { - cb.call(this, data.error, data.data) + cb.call(this, data.error, data.data); delete web3._callbacks[data._id]; } } From ed7cbeaacdac4def4478cc9bfb768ebfc01bb200 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Wed, 12 Nov 2014 20:47:05 +0100 Subject: [PATCH 09/38] contract calls working from js --- libweb3jsonrpc/WebThreeStubServer.cpp | 6 +++--- libweb3jsonrpc/WebThreeStubServer.h | 2 +- libweb3jsonrpc/abstractwebthreestubserver.h | 6 +++--- libweb3jsonrpc/spec.json | 2 +- test/webthreestubclient.h | 3 +-- 5 files changed, 9 insertions(+), 10 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 87cd3c22b..6f7963c1d 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -538,7 +538,7 @@ static bytes toMethodCall(int const& _index, Json::Value const& _params) return data; } -std::string WebThreeStubServer::eth_contractCall(std::string const& _address, int const& _index, Json::Value const& _params) +std::string WebThreeStubServer::eth_contractCall(std::string const& _address, std::string const& _bytes) { auto from = m_accounts.begin()->first; for (auto a: m_accounts) @@ -549,8 +549,8 @@ std::string WebThreeStubServer::eth_contractCall(std::string const& _address, in auto gasPrice = 10 * dev::eth::szabo; auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); - auto bytes = toMethodCall(_index, _params); - return toJS(client()->call(m_accounts[from].secret(), 0, jsToAddress(_address), toMethodCall(_index, _params), gas, gasPrice)); + auto bytes = jsToBytes(_bytes); + return toJS(client()->call(m_accounts[from].secret(), 0, jsToAddress(_address), bytes, gas, gasPrice)); } std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode) diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 3318214f1..bb4f258f6 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -73,7 +73,7 @@ public: virtual std::string eth_codeAt(std::string const& _address); virtual std::string eth_coinbase(); virtual Json::Value eth_compilers(); - virtual std::string eth_contractCall(std::string const& _address, int const& _index, Json::Value const& _params); + virtual std::string eth_contractCall(std::string const& _address, std::string const& _bytes); virtual std::string eth_contractCreate(std::string const& _bytecode); virtual double eth_countAt(std::string const& _address); virtual int eth_defaultBlock(); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index 43a81c1cc..0ae4193fa 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -26,7 +26,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_coinbaseI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER,"param3",jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_contractCallI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCallI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCreateI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); @@ -129,7 +129,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_contractCall(request[0u].asString(), request[1u].asInt(), request[2u]); + response = this->eth_contractCall(request[0u].asString(), request[1u].asString()); } inline virtual void eth_contractCreateI(const Json::Value& request, Json::Value& response) @@ -306,7 +306,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_contractCall",p); if (result.isString()) From 0b236057d8d1ff54bc49b45a6e16d38b224b800c Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Wed, 12 Nov 2014 20:55:23 +0100 Subject: [PATCH 10/38] minified ethereum.js --- libjsqrc/ethereum.min.js | 1 + libjsqrc/js.qrc | 3 +- libjsqrc/main.js | 470 --------------------------------------- libjsqrc/qt.js | 49 ---- libjsqrc/setup.js | 2 + libqethereum/QEthereum.h | 3 +- 6 files changed, 5 insertions(+), 523 deletions(-) create mode 100644 libjsqrc/ethereum.min.js delete mode 100644 libjsqrc/main.js delete mode 100644 libjsqrc/qt.js diff --git a/libjsqrc/ethereum.min.js b/libjsqrc/ethereum.min.js new file mode 100644 index 000000000..1befc1804 --- /dev/null +++ b/libjsqrc/ethereum.min.js @@ -0,0 +1 @@ +require=function t(e,n,r){function i(a,s){if(!n[a]){if(!e[a]){var c="function"==typeof require&&require;if(!s&&c)return c(a,!0);if(o)return o(a,!0);var l=new Error("Cannot find module '"+a+"'");throw l.code="MODULE_NOT_FOUND",l}var u=n[a]={exports:{}};e[a][0].call(u.exports,function(t){var n=e[a][1][t];return i(n?n:t)},u,u.exports,t,e,n,r)}return n[a].exports}for(var o="function"==typeof require&&require,a=0;ar&&(e=t.charCodeAt(r),0!==e);r+=2)n+=String.fromCharCode(parseInt(t.substr(r,2),16));return n},toDecimal:function(t){return parseInt(t,16)},fromAscii:function(t,e){e=void 0===e?32:e;for(var n=this.toHex(t);n.length<2*e;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(t){return new s(t,i)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(t){return new s(t,o)}},on:function(t,e,n){return void 0===g._events[t]&&(g._events[t]={}),g._events[t][e]=n,this},off:function(t,e){return void 0!==g._events[t]&&delete g._events[t][e],this},trigger:function(t,e,n){var r,i=g._events[t];i&&i[e]&&(r=i[e])(n)}},m=g.eth;p(m,c()),v(m,l()),p(g.db,u()),p(g.shh,h()),i={changed:"eth_changed"},p(i,f()),o={changed:"shh_changed"},p(o,d()),a=function(){var t,e;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,t=this,(e=function(){t.provider&&t.provider.poll&&t.polls.forEach(function(e){e.data._id=t.id,t.id++,t.provider.poll(e.data,e.id)}),setTimeout(e,12e3)})()},a.prototype.send=function(t,e){t._id=this.id,e&&(g._callbacks[t._id]=e),t.args=t.args||[],this.id++,void 0!==this.provider?this.provider.send(t):(console.warn("provider is not set"),this.queued.push(t))},a.prototype.set=function(t){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=t,this.ready=!0},a.prototype.sendQueued=function(){for(var t=0;this.queued.length;t++)this.send(this.queued[t])},a.prototype.installed=function(){return void 0!==this.provider},a.prototype.startPolling=function(t,e){this.provider&&this.provider.poll&&this.polls.push({data:t,id:e})},a.prototype.stopPolling=function(t){var e,n;for(e=this.polls.length;e--;)n=this.polls[e],n.id===t&&this.polls.splice(e,1)},g.provider=new a,g.setProvider=function(t){t.onmessage=r,g.provider.set(t),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},s=function(t,e){this.impl=e,this.callbacks=[];var n=this;this.promise=e.newFilter(t),this.promise.then(function(t){n.id=t,g.on(e.changed,t,n.trigger.bind(n)),g.provider.startPolling({call:e.changed,args:[t]},t)})},s.prototype.arrived=function(t){this.changed(t)},s.prototype.changed=function(t){var e=this;this.promise.then(function(){e.callbacks.push(t)})},s.prototype.trigger=function(t){for(var e=0;e es6-promise-2.0.0.js setup.js - main.js - qt.js + ethereum.min.js diff --git a/libjsqrc/main.js b/libjsqrc/main.js deleted file mode 100644 index da95e7e53..000000000 --- a/libjsqrc/main.js +++ /dev/null @@ -1,470 +0,0 @@ -/* - This file is part of ethereum.js. - - ethereum.js is free software: you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - ethereum.js 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with ethereum.js. If not, see . -*/ -/** @file main.js - * @authors: - * Marek Kotewicz - * @date 2014 - */ - -(function(window) { - function isPromise(o) { - return o instanceof Promise - } - - function flattenPromise (obj) { - if (obj instanceof Promise) { - return Promise.resolve(obj); - } - - if (obj instanceof Array) { - return new Promise(function (resolve) { - var promises = obj.map(function (o) { - return flattenPromise(o); - }); - - return Promise.all(promises).then(function (res) { - for (var i = 0; i < obj.length; i++) { - obj[i] = res[i]; - } - resolve(obj); - }); - }); - } - - if (obj instanceof Object) { - return new Promise(function (resolve) { - var keys = Object.keys(obj); - var promises = keys.map(function (key) { - return flattenPromise(obj[key]); - }); - - return Promise.all(promises).then(function (res) { - for (var i = 0; i < keys.length; i++) { - obj[keys[i]] = res[i]; - } - resolve(obj); - }); - }); - } - - return Promise.resolve(obj); - }; - - var ethMethods = function () { - var blockCall = function (args) { - return typeof args[0] === "string" ? "eth_blockByHash" : "eth_blockByNumber"; - }; - - var transactionCall = function (args) { - return typeof args[0] === "string" ? 'eth_transactionByHash' : 'eth_transactionByNumber'; - }; - - var uncleCall = function (args) { - return typeof args[0] === "string" ? 'eth_uncleByHash' : 'eth_uncleByNumber'; - }; - - var methods = [ - { name: 'balanceAt', call: 'eth_balanceAt' }, - { name: 'stateAt', call: 'eth_stateAt' }, - { name: 'countAt', call: 'eth_countAt'}, - { name: 'codeAt', call: 'eth_codeAt' }, - { name: 'transact', call: 'eth_transact' }, - { name: 'call', call: 'eth_call' }, - { name: 'block', call: blockCall }, - { name: 'transaction', call: transactionCall }, - { name: 'uncle', call: uncleCall }, - { name: 'compilers', call: 'eth_compilers' }, - { name: 'lll', call: 'eth_lll' }, - { name: 'solidity', call: 'eth_solidity' }, - { name: 'contractCreate', call: 'eth_contractCreate' }, - { name: 'contractCall', call: 'eth_contractCall' } - ]; - return methods; - }; - - var ethProperties = function () { - return [ - { name: 'coinbase', getter: 'eth_coinbase', setter: 'eth_setCoinbase' }, - { name: 'listening', getter: 'eth_listening', setter: 'eth_setListening' }, - { name: 'mining', getter: 'eth_mining', setter: 'eth_setMining' }, - { name: 'gasPrice', getter: 'eth_gasPrice' }, - { name: 'account', getter: 'eth_account' }, - { name: 'accounts', getter: 'eth_accounts' }, - { name: 'peerCount', getter: 'eth_peerCount' }, - { name: 'defaultBlock', getter: 'eth_defaultBlock', setter: 'eth_setDefaultBlock' }, - { name: 'number', getter: 'eth_number'} - ]; - }; - - var dbMethods = function () { - return [ - { name: 'put', call: 'db_put' }, - { name: 'get', call: 'db_get' }, - { name: 'putString', call: 'db_putString' }, - { name: 'getString', call: 'db_getString' } - ]; - }; - - var shhMethods = function () { - return [ - { name: 'post', call: 'shh_post' }, - { name: 'newIdentity', call: 'shh_newIdentity' }, - { name: 'haveIdentity', call: 'shh_haveIdentity' }, - { name: 'newGroup', call: 'shh_newGroup' }, - { name: 'addToGroup', call: 'shh_addToGroup' } - ]; - }; - - var ethWatchMethods = function () { - var newFilter = function (args) { - return typeof args[0] === 'string' ? 'eth_newFilterString' : 'eth_newFilter'; - }; - - return [ - { name: 'newFilter', call: newFilter }, - { name: 'uninstallFilter', call: 'eth_uninstallFilter' }, - { name: 'getMessages', call: 'eth_getMessages' } - ]; - }; - - var shhWatchMethods = function () { - return [ - { name: 'newFilter', call: 'shh_newFilter' }, - { name: 'uninstallFilter', call: 'shh_uninstallFilter' }, - { name: 'getMessage', call: 'shh_getMessages' } - ]; - }; - - var setupMethods = function (obj, methods) { - methods.forEach(function (method) { - obj[method.name] = function () { - return flattenPromise(Array.prototype.slice.call(arguments)).then(function (args) { - var call = typeof method.call === "function" ? method.call(args) : method.call; - return {call: call, args: args}; - }).then(function (request) { - return new Promise(function (resolve, reject) { - web3.provider.send(request, function (err, result) { - if (!err) { - resolve(result); - return; - } - reject(err); - }); - }); - }).catch(function(err) { - console.error(err); - }); - }; - }); - }; - - var setupProperties = function (obj, properties) { - properties.forEach(function (property) { - var proto = {}; - proto.get = function () { - return new Promise(function(resolve, reject) { - web3.provider.send({call: property.getter}, function(err, result) { - if (!err) { - resolve(result); - return; - } - reject(err); - }); - }); - }; - if (property.setter) { - proto.set = function (val) { - return flattenPromise([val]).then(function (args) { - return new Promise(function (resolve) { - web3.provider.send({call: property.setter, args: args}, function (err, result) { - if (!err) { - resolve(result); - return; - } - reject(err); - }); - }); - }).catch(function (err) { - console.error(err); - }); - } - } - Object.defineProperty(obj, property.name, proto); - }); - }; - - var web3 = { - _callbacks: {}, - _events: {}, - providers: {}, - toHex: function(str) { - var hex = ""; - for(var i = 0; i < str.length; i++) { - var n = str.charCodeAt(i).toString(16); - hex += n.length < 2 ? '0' + n : n; - } - - return hex; - }, - - toAscii: function(hex) { - // Find termination - var str = ""; - var i = 0, l = hex.length; - if (hex.substring(0, 2) == '0x') - i = 2; - for(; i < l; i+=2) { - var code = hex.charCodeAt(i) - if(code == 0) { - break; - } - - str += String.fromCharCode(parseInt(hex.substr(i, 2), 16)); - } - - return str; - }, - - toDecimal: function (val) { - return parseInt(val, 16); - }, - - fromAscii: function(str, pad) { - pad = pad === undefined ? 32 : pad; - var hex = this.toHex(str); - while(hex.length < pad*2) - hex += "00"; - return "0x" + hex; - }, - - eth: { - prototype: Object(), - watch: function (params) { - return new Filter(params, ethWatch); - }, - }, - - db: { - prototype: Object() - }, - - shh: { - prototype: Object(), - watch: function (params) { - return new Filter(params, shhWatch); - } - }, - - on: function(event, id, cb) { - if(web3._events[event] === undefined) { - web3._events[event] = {}; - } - - web3._events[event][id] = cb; - return this - }, - - off: function(event, id) { - if(web3._events[event] !== undefined) { - delete web3._events[event][id]; - } - - return this - }, - - trigger: function(event, id, data) { - var callbacks = web3._events[event]; - if (!callbacks || !callbacks[id]) { - return; - } - var cb = callbacks[id]; - cb(data); - }, - }; - - var eth = web3.eth; - setupMethods(eth, ethMethods()); - setupProperties(eth, ethProperties()); - setupMethods(web3.db, dbMethods()); - setupMethods(web3.shh, shhMethods()); - - var ethWatch = { - changed: 'eth_changed' - }; - setupMethods(ethWatch, ethWatchMethods()); - var shhWatch = { - changed: 'shh_changed' - }; - setupMethods(shhWatch, shhWatchMethods()); - - var ProviderManager = function() { - this.queued = []; - this.polls = []; - this.ready = false; - this.provider = undefined; - this.id = 1; - - var self = this; - var poll = function () { - if (self.provider && self.provider.poll) { - self.polls.forEach(function (data) { - data.data._id = self.id; - self.id++; - self.provider.poll(data.data, data.id); - }); - } - setTimeout(poll, 12000); - }; - poll(); - }; - - ProviderManager.prototype.send = function(data, cb) { - data._id = this.id; - if (cb) { - web3._callbacks[data._id] = cb; - } - - data.args = data.args || []; - this.id++; - - if(this.provider !== undefined) { - this.provider.send(data); - } else { - console.warn("provider is not set"); - this.queued.push(data); - } - }; - - ProviderManager.prototype.set = function(provider) { - if(this.provider !== undefined && this.provider.unload !== undefined) { - this.provider.unload(); - } - - this.provider = provider; - this.ready = true; - }; - - ProviderManager.prototype.sendQueued = function() { - for(var i = 0; this.queued.length; i++) { - // Resend - this.send(this.queued[i]); - } - }; - - ProviderManager.prototype.installed = function() { - return this.provider !== undefined; - }; - - ProviderManager.prototype.startPolling = function (data, pollId) { - if (!this.provider || !this.provider.poll) { - return; - } - this.polls.push({data: data, id: pollId}); - }; - - ProviderManager.prototype.stopPolling = function (pollId) { - for (var i = this.polls.length; i--;) { - var poll = this.polls[i]; - if (poll.id === pollId) { - this.polls.splice(i, 1); - } - } - }; - - web3.provider = new ProviderManager(); - - web3.setProvider = function(provider) { - provider.onmessage = messageHandler; - web3.provider.set(provider); - web3.provider.sendQueued(); - }; - - var Filter = function(options, impl) { - this.impl = impl; - this.callbacks = []; - - var self = this; - this.promise = impl.newFilter(options); - this.promise.then(function (id) { - self.id = id; - web3.on(impl.changed, id, self.trigger.bind(self)); - web3.provider.startPolling({call: impl.changed, args: [id]}, id); - }); - }; - - Filter.prototype.arrived = function(callback) { - this.changed(callback); - } - - Filter.prototype.changed = function(callback) { - var self = this; - this.promise.then(function(id) { - self.callbacks.push(callback); - }); - }; - - Filter.prototype.trigger = function(messages) { - if (!(messages instanceof Array) || messages.length) { - for(var i = 0; i < this.callbacks.length; i++) { - this.callbacks[i].call(this, messages); - } - } - }; - - Filter.prototype.uninstall = function() { - var self = this; - this.promise.then(function (id) { - self.impl.uninstallFilter(id); - web3.provider.stopPolling(id); - web3.off(impl.changed, id); - }); - }; - - Filter.prototype.messages = function() { - var self = this; - return this.promise.then(function (id) { - return self.impl.getMessages(id); - }); - }; - - function messageHandler(data) { - if(data._event !== undefined) { - web3.trigger(data._event, data._id, data.data); - return; - } - - if(data._id) { - var cb = web3._callbacks[data._id]; - if (cb) { - cb.call(this, data.error, data.data); - delete web3._callbacks[data._id]; - } - } - } - - /* - // Install default provider - if(!web3.provider.installed()) { - var sock = new web3.WebSocket("ws://localhost:40404/eth"); - - web3.setProvider(sock); - } - */ - - window.web3 = web3; - -})(this); diff --git a/libjsqrc/qt.js b/libjsqrc/qt.js deleted file mode 100644 index aedd34236..000000000 --- a/libjsqrc/qt.js +++ /dev/null @@ -1,49 +0,0 @@ -/* - This file is part of ethereum.js. - - ethereum.js is free software: you can redistribute it and/or modify - it under the terms of the GNU Lesser General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - ethereum.js 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 Lesser General Public License for more details. - - You should have received a copy of the GNU Lesser General Public License - along with ethereum.js. If not, see . -*/ -/** @file qt.js - * @authors: - * Marek Kotewicz - * @date 2014 - */ - -(function() { - var QtProvider = function() { - this.handlers = []; - - var self = this; - navigator.qt.onmessage = function (message) { - self.handlers.forEach(function (handler) { - handler.call(self, JSON.parse(message.data)); - }); - } - }; - - QtProvider.prototype.send = function(payload) { - navigator.qt.postMessage(JSON.stringify(payload)); - }; - - Object.defineProperty(QtProvider.prototype, "onmessage", { - set: function(handler) { - this.handlers.push(handler); - }, - }); - - if(typeof(web3) !== "undefined" && web3.providers !== undefined) { - web3.providers.QtProvider = QtProvider; - } -})(); - diff --git a/libjsqrc/setup.js b/libjsqrc/setup.js index 5142412a6..b83745c33 100644 --- a/libjsqrc/setup.js +++ b/libjsqrc/setup.js @@ -41,4 +41,6 @@ if (window.Promise === undefined) { window.Promise = ES6Promise.Promise; } +var web3 = require('web3'); web3.setProvider(new web3.providers.QtProvider()); + diff --git a/libqethereum/QEthereum.h b/libqethereum/QEthereum.h index 4f276b7e1..ec7eadaf6 100644 --- a/libqethereum/QEthereum.h +++ b/libqethereum/QEthereum.h @@ -84,8 +84,7 @@ private: _frame->disconnect(); \ _frame->addToJavaScriptWindowObject("_web3", qweb, QWebFrame::ScriptOwnership); \ _frame->evaluateJavaScript(contentsOfQResource(":/js/es6-promise-2.0.0.js")); \ - _frame->evaluateJavaScript(contentsOfQResource(":/js/main.js")); \ - _frame->evaluateJavaScript(contentsOfQResource(":/js/qt.js")); \ + _frame->evaluateJavaScript(contentsOfQResource(":/js/ethereum.min.js")); \ _frame->evaluateJavaScript(contentsOfQResource(":/js/setup.js")); \ } From 7bdc646dccdba745726382c57feaa0f37e4c39ff Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Thu, 13 Nov 2014 12:25:49 +0100 Subject: [PATCH 11/38] removed unnecessary methods from jsonrpc and added contract call tests --- libjsqrc/ethereum.min.js | 2 +- libweb3jsonrpc/WebThreeStubServer.cpp | 60 ++------------------- libweb3jsonrpc/WebThreeStubServer.h | 2 - libweb3jsonrpc/abstractwebthreestubserver.h | 14 ----- libweb3jsonrpc/spec.json | 2 - test/jsonrpc.cpp | 28 ++++++++++ test/webthreestubclient.h | 27 ---------- 7 files changed, 34 insertions(+), 101 deletions(-) diff --git a/libjsqrc/ethereum.min.js b/libjsqrc/ethereum.min.js index 1befc1804..5b1ff1c6f 100644 --- a/libjsqrc/ethereum.min.js +++ b/libjsqrc/ethereum.min.js @@ -1 +1 @@ -require=function t(e,n,r){function i(a,s){if(!n[a]){if(!e[a]){var c="function"==typeof require&&require;if(!s&&c)return c(a,!0);if(o)return o(a,!0);var l=new Error("Cannot find module '"+a+"'");throw l.code="MODULE_NOT_FOUND",l}var u=n[a]={exports:{}};e[a][0].call(u.exports,function(t){var n=e[a][1][t];return i(n?n:t)},u,u.exports,t,e,n,r)}return n[a].exports}for(var o="function"==typeof require&&require,a=0;ar&&(e=t.charCodeAt(r),0!==e);r+=2)n+=String.fromCharCode(parseInt(t.substr(r,2),16));return n},toDecimal:function(t){return parseInt(t,16)},fromAscii:function(t,e){e=void 0===e?32:e;for(var n=this.toHex(t);n.length<2*e;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(t){return new s(t,i)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(t){return new s(t,o)}},on:function(t,e,n){return void 0===g._events[t]&&(g._events[t]={}),g._events[t][e]=n,this},off:function(t,e){return void 0!==g._events[t]&&delete g._events[t][e],this},trigger:function(t,e,n){var r,i=g._events[t];i&&i[e]&&(r=i[e])(n)}},m=g.eth;p(m,c()),v(m,l()),p(g.db,u()),p(g.shh,h()),i={changed:"eth_changed"},p(i,f()),o={changed:"shh_changed"},p(o,d()),a=function(){var t,e;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,t=this,(e=function(){t.provider&&t.provider.poll&&t.polls.forEach(function(e){e.data._id=t.id,t.id++,t.provider.poll(e.data,e.id)}),setTimeout(e,12e3)})()},a.prototype.send=function(t,e){t._id=this.id,e&&(g._callbacks[t._id]=e),t.args=t.args||[],this.id++,void 0!==this.provider?this.provider.send(t):(console.warn("provider is not set"),this.queued.push(t))},a.prototype.set=function(t){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=t,this.ready=!0},a.prototype.sendQueued=function(){for(var t=0;this.queued.length;t++)this.send(this.queued[t])},a.prototype.installed=function(){return void 0!==this.provider},a.prototype.startPolling=function(t,e){this.provider&&this.provider.poll&&this.polls.push({data:t,id:e})},a.prototype.stopPolling=function(t){var e,n;for(e=this.polls.length;e--;)n=this.polls[e],n.id===t&&this.polls.splice(e,1)},g.provider=new a,g.setProvider=function(t){t.onmessage=r,g.provider.set(t),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},s=function(t,e){this.impl=e,this.callbacks=[];var n=this;this.promise=e.newFilter(t),this.promise.then(function(t){n.id=t,g.on(e.changed,t,n.trigger.bind(n)),g.provider.startPolling({call:e.changed,args:[t]},t)})},s.prototype.arrived=function(t){this.changed(t)},s.prototype.changed=function(t){var e=this;this.promise.then(function(){e.callbacks.push(t)})},s.prototype.trigger=function(t){for(var e=0;er&&(t=e.charCodeAt(r),0!==t);r+=2)n+=String.fromCharCode(parseInt(e.substr(r,2),16));return n},toDecimal:function(e){return parseInt(e,16)},fromAscii:function(e,t){t=void 0===t?32:t;for(var n=this.toHex(e);n.length<2*t;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(e){return new a(e,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(e){return new a(e,i)}},on:function(e,t,n){return void 0===g._events[e]&&(g._events[e]={}),g._events[e][t]=n,this},off:function(e,t){return void 0!==g._events[e]&&delete g._events[e][t],this},trigger:function(e,t,n){var r,o=g._events[e];o&&o[t]&&(r=o[t])(n)}},m=g.eth;f(m,c()),v(m,u()),f(g.db,l()),f(g.shh,h()),o={changed:"eth_changed"},f(o,d()),i={changed:"shh_changed"},f(i,p()),s=function(){var e,t;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,e=this,(t=function(){e.provider&&e.provider.poll&&e.polls.forEach(function(t){t.data._id=e.id,e.id++,e.provider.poll(t.data,t.id)}),setTimeout(t,12e3)})()},s.prototype.send=function(e,t){e._id=this.id,t&&(g._callbacks[e._id]=t),e.args=e.args||[],this.id++,void 0!==this.provider?this.provider.send(e):(console.warn("provider is not set"),this.queued.push(e))},s.prototype.set=function(e){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=e,this.ready=!0},s.prototype.sendQueued=function(){for(var e=0;this.queued.length;e++)this.send(this.queued[e])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(e,t){this.provider&&this.provider.poll&&this.polls.push({data:e,id:t})},s.prototype.stopPolling=function(e){var t,n;for(t=this.polls.length;t--;)n=this.polls[t],n.id===e&&this.polls.splice(t,1)},g.provider=new s,g.setProvider=function(e){e.onmessage=r,g.provider.set(e),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},a=function(e,t){this.impl=t,this.callbacks=[];var n=this;this.promise=t.newFilter(e),this.promise.then(function(e){n.id=e,g.on(t.changed,e,n.trigger.bind(n)),g.provider.startPolling({call:t.changed,args:[e]},e)})},a.prototype.arrived=function(e){this.changed(e)},a.prototype.changed=function(e){var t=this;this.promise.then(function(){t.callbacks.push(e)})},a.prototype.trigger=function(e){for(var t=0;tfirst; - for (auto a: m_accounts) - if (client()->balanceAt(a.first) > client()->balanceAt(from)) - from = a.first; - - cwarn << "Silently signing transaction from address" << from.abridged() << ": User validation hook goes here."; - - auto gasPrice = 10 * dev::eth::szabo; - auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); - auto bytes = jsToBytes(_bytes); - return toJS(client()->call(m_accounts[from].secret(), 0, jsToAddress(_address), bytes, gas, gasPrice)); -} - -std::string WebThreeStubServer::eth_contractCreate(std::string const& _bytecode) -{ - auto from = m_accounts.begin()->first; - for (auto a: m_accounts) - if (client()->balanceAt(a.first) > client()->balanceAt(from)) - from = a.first; - - cwarn << "Silently signing transaction from address" << from.abridged() << ": User validation hook goes here."; - - auto gasPrice = 10 * dev::eth::szabo; - auto gas = min(client()->gasLimitRemaining(), client()->balanceAt(from) / gasPrice); - return toJS(client()->transact(m_accounts[from].secret(), 0, jsToBytes(_bytecode), gas, gasPrice)); -} - std::string WebThreeStubServer::eth_lll(std::string const& _code) { return toJS(dev::eth::compileLLL(_code)); diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index bb4f258f6..e358e110c 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -73,8 +73,6 @@ public: virtual std::string eth_codeAt(std::string const& _address); virtual std::string eth_coinbase(); virtual Json::Value eth_compilers(); - virtual std::string eth_contractCall(std::string const& _address, std::string const& _bytes); - virtual std::string eth_contractCreate(std::string const& _bytecode); virtual double eth_countAt(std::string const& _address); virtual int eth_defaultBlock(); virtual std::string eth_gasPrice(); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index 0ae4193fa..dba6e02cd 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -26,8 +26,6 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_codeAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_codeAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_coinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_coinbaseI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCall", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCallI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_contractCreate", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_contractCreateI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); @@ -127,16 +125,6 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_compilers(); } - inline virtual void eth_contractCallI(const Json::Value& request, Json::Value& response) - { - response = this->eth_contractCall(request[0u].asString(), request[1u].asString()); - } - - inline virtual void eth_contractCreateI(const Json::Value& request, Json::Value& response) - { - response = this->eth_contractCreate(request[0u].asString()); - } - inline virtual void eth_countAtI(const Json::Value& request, Json::Value& response) { response = this->eth_countAt(request[0u].asString()); @@ -306,8 +294,6 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerethereum()->setAddress(kp.address()); + jsonrpcServer->setAccounts({kp}); + + dev::eth::mine(*(web3->ethereum()), 1); + char const* sourceCode = "contract test {\n" + " function f(uint a) returns(uint d) { return a * 7; }\n" + "}\n"; + + string compiled = jsonrpcClient->eth_solidity(sourceCode); + + Json::Value create; + create["code"] = compiled; + string contractAddress = jsonrpcClient->eth_transact(create); + dev::eth::mine(*(web3->ethereum()), 1); + + Json::Value call; + call["to"] = contractAddress; + call["data"] = "0x00000000000000000000000000000000000000000000000000000000000000001"; + string result = jsonrpcClient->eth_call(call); + BOOST_CHECK_EQUAL(result, "0x0000000000000000000000000000000000000000000000000000000000000007"); +} + BOOST_AUTO_TEST_SUITE_END() BOOST_AUTO_TEST_SUITE_END() diff --git a/test/webthreestubclient.h b/test/webthreestubclient.h index 6d844de8e..66c4bef35 100644 --- a/test/webthreestubclient.h +++ b/test/webthreestubclient.h @@ -191,33 +191,6 @@ p.append(param3); } - std::string eth_contractCall(const std::string& param1, const std::string& param2) throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p.append(param1); -p.append(param2); - - Json::Value result = this->client->CallMethod("eth_contractCall",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - - std::string eth_contractCreate(const std::string& param1) throw (jsonrpc::JsonRpcException) - { - Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("eth_contractCreate",p); - if (result.isString()) - return result.asString(); - else - throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); - - } - double eth_countAt(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; From 47434e62c328907338d77b27af3c31b77cc76bae Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Thu, 13 Nov 2014 18:29:01 +0100 Subject: [PATCH 12/38] added storageAt which dumps contract storage --- libjsqrc/ethereum.min.js | 2 +- libweb3jsonrpc/WebThreeStubServer.cpp | 15 +++++++++++++++ libweb3jsonrpc/WebThreeStubServer.h | 1 + libweb3jsonrpc/abstractwebthreestubserver.h | 7 +++++++ libweb3jsonrpc/spec.json | 1 + test/webthreestubclient.h | 13 +++++++++++++ 6 files changed, 38 insertions(+), 1 deletion(-) diff --git a/libjsqrc/ethereum.min.js b/libjsqrc/ethereum.min.js index 5b1ff1c6f..125523290 100644 --- a/libjsqrc/ethereum.min.js +++ b/libjsqrc/ethereum.min.js @@ -1 +1 @@ -require=function e(t,n,r){function o(s,a){if(!n[s]){if(!t[s]){var c="function"==typeof require&&require;if(!a&&c)return c(s,!0);if(i)return i(s,!0);var u=new Error("Cannot find module '"+s+"'");throw u.code="MODULE_NOT_FOUND",u}var l=n[s]={exports:{}};t[s][0].call(l.exports,function(e){var n=t[s][1][e];return o(n?n:e)},l,l.exports,e,t,n,r)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;sr&&(t=e.charCodeAt(r),0!==t);r+=2)n+=String.fromCharCode(parseInt(e.substr(r,2),16));return n},toDecimal:function(e){return parseInt(e,16)},fromAscii:function(e,t){t=void 0===t?32:t;for(var n=this.toHex(e);n.length<2*t;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(e){return new a(e,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(e){return new a(e,i)}},on:function(e,t,n){return void 0===g._events[e]&&(g._events[e]={}),g._events[e][t]=n,this},off:function(e,t){return void 0!==g._events[e]&&delete g._events[e][t],this},trigger:function(e,t,n){var r,o=g._events[e];o&&o[t]&&(r=o[t])(n)}},m=g.eth;f(m,c()),v(m,u()),f(g.db,l()),f(g.shh,h()),o={changed:"eth_changed"},f(o,d()),i={changed:"shh_changed"},f(i,p()),s=function(){var e,t;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,e=this,(t=function(){e.provider&&e.provider.poll&&e.polls.forEach(function(t){t.data._id=e.id,e.id++,e.provider.poll(t.data,t.id)}),setTimeout(t,12e3)})()},s.prototype.send=function(e,t){e._id=this.id,t&&(g._callbacks[e._id]=t),e.args=e.args||[],this.id++,void 0!==this.provider?this.provider.send(e):(console.warn("provider is not set"),this.queued.push(e))},s.prototype.set=function(e){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=e,this.ready=!0},s.prototype.sendQueued=function(){for(var e=0;this.queued.length;e++)this.send(this.queued[e])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(e,t){this.provider&&this.provider.poll&&this.polls.push({data:e,id:t})},s.prototype.stopPolling=function(e){var t,n;for(t=this.polls.length;t--;)n=this.polls[t],n.id===e&&this.polls.splice(t,1)},g.provider=new s,g.setProvider=function(e){e.onmessage=r,g.provider.set(e),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},a=function(e,t){this.impl=t,this.callbacks=[];var n=this;this.promise=t.newFilter(e),this.promise.then(function(e){n.id=e,g.on(t.changed,e,n.trigger.bind(n)),g.provider.startPolling({call:t.changed,args:[e]},e)})},a.prototype.arrived=function(e){this.changed(e)},a.prototype.changed=function(e){var t=this;this.promise.then(function(){t.callbacks.push(e)})},a.prototype.trigger=function(e){for(var t=0;tr&&(t=e.charCodeAt(r),0!==t);r+=2)n+=String.fromCharCode(parseInt(e.substr(r,2),16));return n},toDecimal:function(e){return parseInt(e,16)},fromAscii:function(e,t){t=void 0===t?32:t;for(var n=this.toHex(e);n.length<2*t;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(e){return new a(e,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(e){return new a(e,i)}},on:function(e,t,n){return void 0===g._events[e]&&(g._events[e]={}),g._events[e][t]=n,this},off:function(e,t){return void 0!==g._events[e]&&delete g._events[e][t],this},trigger:function(e,t,n){var r,o=g._events[e];o&&o[t]&&(r=o[t])(n)}},m=g.eth;f(m,c()),v(m,u()),f(g.db,l()),f(g.shh,h()),o={changed:"eth_changed"},f(o,d()),i={changed:"shh_changed"},f(i,p()),s=function(){var e,t;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,e=this,(t=function(){e.provider&&e.provider.poll&&e.polls.forEach(function(t){t.data._id=e.id,e.id++,e.provider.poll(t.data,t.id)}),setTimeout(t,12e3)})()},s.prototype.send=function(e,t){e._id=this.id,t&&(g._callbacks[e._id]=t),e.args=e.args||[],this.id++,void 0!==this.provider?this.provider.send(e):(console.warn("provider is not set"),this.queued.push(e))},s.prototype.set=function(e){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=e,this.ready=!0},s.prototype.sendQueued=function(){for(var e=0;this.queued.length;e++)this.send(this.queued[e])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(e,t){this.provider&&this.provider.poll&&this.polls.push({data:e,id:t})},s.prototype.stopPolling=function(e){var t,n;for(t=this.polls.length;t--;)n=this.polls[t],n.id===e&&this.polls.splice(t,1)},g.provider=new s,g.setProvider=function(e){e.onmessage=r,g.provider.set(e),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},a=function(e,t){this.impl=t,this.callbacks=[];var n=this;this.promise=t.newFilter(e),this.promise.then(function(e){n.id=e,g.on(t.changed,e,n.trigger.bind(n)),g.provider.startPolling({call:t.changed,args:[e]},e)})},a.prototype.arrived=function(e){this.changed(e)},a.prototype.changed=function(e){var t=this;this.promise.then(function(){t.callbacks.push(e)})},a.prototype.trigger=function(e){for(var t=0;t const& _storage) +{ + Json::Value res(Json::objectValue); + for (auto i: _storage) + res[toJS(i.first)] = toJS(i.second); + return res; +} + /*static*/ Json::Value toJson(dev::eth::LogEntries const& _es) // commented to avoid warning. Uncomment once in use @ poC-7. { Json::Value res; @@ -651,6 +659,13 @@ std::string WebThreeStubServer::eth_stateAt(string const& _address, string const return client() ? toJS(client()->stateAt(jsToAddress(_address), jsToU256(_storage), block)) : ""; } +Json::Value WebThreeStubServer::eth_storageAt(string const& _address) +{ + if (!client()) + return Json::Value(Json::objectValue); + return toJson(client()->storageAt(jsToAddress(_address))); +} + std::string WebThreeStubServer::eth_transact(Json::Value const& _json) { std::string ret; diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index e358e110c..5207ed1df 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -90,6 +90,7 @@ public: virtual bool eth_setMining(bool const& _mining); virtual std::string eth_solidity(std::string const& _code); virtual std::string eth_stateAt(std::string const& _address, std::string const& _storage); + virtual Json::Value eth_storageAt(std::string const& _address); virtual std::string eth_transact(Json::Value const& _json); virtual Json::Value eth_transactionByHash(std::string const& _hash, int const& _i); virtual Json::Value eth_transactionByNumber(int const& _number, int const& _i); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index dba6e02cd..5fb548103 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -43,6 +43,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_setMining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_setMiningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_solidity", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_solidityI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_stateAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_stateAtI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_storageAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_storageAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_transact", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_transactI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_transactionByHash", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_STRING,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_transactionByHashI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_transactionByNumber", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_OBJECT, "param1",jsonrpc::JSON_INTEGER,"param2",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_transactionByNumberI); @@ -210,6 +211,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_stateAt(request[0u].asString(), request[1u].asString()); } + inline virtual void eth_storageAtI(const Json::Value& request, Json::Value& response) + { + response = this->eth_storageAt(request[0u].asString()); + } + inline virtual void eth_transactI(const Json::Value& request, Json::Value& response) { response = this->eth_transact(request[0u]); @@ -311,6 +317,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_storageAt",p); + if (result.isObject()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + std::string eth_transact(const Json::Value& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; From 0e02c79b801133b8c880615994e5d3c58077aa7b Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Thu, 13 Nov 2014 18:52:21 +0100 Subject: [PATCH 13/38] storage dump test --- test/jsonrpc.cpp | 38 ++++++++++++++++++++++++++++++++++++++ 1 file changed, 38 insertions(+) diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 3f552d47d..d17c5a594 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -266,6 +266,44 @@ BOOST_AUTO_TEST_CASE(simple_contract) BOOST_CHECK_EQUAL(result, "0x0000000000000000000000000000000000000000000000000000000000000007"); } +BOOST_AUTO_TEST_CASE(contract_storage) +{ + cnote << "Testing jsonrpc contract storage..."; + KeyPair kp = KeyPair::create(); + web3->ethereum()->setAddress(kp.address()); + jsonrpcServer->setAccounts({kp}); + + dev::eth::mine(*(web3->ethereum()), 1); + + char const* sourceCode = R"( + contract test { + uint hello; + function writeHello(uint value) returns(bool d){ + hello = value; + return true; + } + } + )"; + + string compiled = jsonrpcClient->eth_solidity(sourceCode); + + Json::Value create; + create["code"] = compiled; + string contractAddress = jsonrpcClient->eth_transact(create); + dev::eth::mine(*(web3->ethereum()), 1); + + Json::Value transact; + transact["to"] = contractAddress; + transact["data"] = "0x00000000000000000000000000000000000000000000000000000000000000003"; + jsonrpcClient->eth_transact(transact); + dev::eth::mine(*(web3->ethereum()), 1); + + Json::Value storage = jsonrpcClient->eth_storageAt(contractAddress); + BOOST_CHECK_EQUAL(storage.getMemberNames().size(), 1); + for (auto name: storage.getMemberNames()) + BOOST_CHECK_EQUAL(storage[name].asString(), "0x03"); +} + BOOST_AUTO_TEST_SUITE_END() BOOST_AUTO_TEST_SUITE_END() From d2427082fa2971922432097aa17f260374826103 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Fri, 14 Nov 2014 13:13:06 +0100 Subject: [PATCH 14/38] improved js interface for contract calling --- libjsqrc/ethereum.min.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libjsqrc/ethereum.min.js b/libjsqrc/ethereum.min.js index 125523290..b23886cab 100644 --- a/libjsqrc/ethereum.min.js +++ b/libjsqrc/ethereum.min.js @@ -1 +1 @@ -require=function e(t,n,r){function o(s,a){if(!n[s]){if(!t[s]){var c="function"==typeof require&&require;if(!a&&c)return c(s,!0);if(i)return i(s,!0);var u=new Error("Cannot find module '"+s+"'");throw u.code="MODULE_NOT_FOUND",u}var l=n[s]={exports:{}};t[s][0].call(l.exports,function(e){var n=t[s][1][e];return o(n?n:e)},l,l.exports,e,t,n,r)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;sr&&(t=e.charCodeAt(r),0!==t);r+=2)n+=String.fromCharCode(parseInt(e.substr(r,2),16));return n},toDecimal:function(e){return parseInt(e,16)},fromAscii:function(e,t){t=void 0===t?32:t;for(var n=this.toHex(e);n.length<2*t;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(e){return new a(e,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(e){return new a(e,i)}},on:function(e,t,n){return void 0===g._events[e]&&(g._events[e]={}),g._events[e][t]=n,this},off:function(e,t){return void 0!==g._events[e]&&delete g._events[e][t],this},trigger:function(e,t,n){var r,o=g._events[e];o&&o[t]&&(r=o[t])(n)}},m=g.eth;f(m,c()),v(m,u()),f(g.db,l()),f(g.shh,h()),o={changed:"eth_changed"},f(o,d()),i={changed:"shh_changed"},f(i,p()),s=function(){var e,t;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,e=this,(t=function(){e.provider&&e.provider.poll&&e.polls.forEach(function(t){t.data._id=e.id,e.id++,e.provider.poll(t.data,t.id)}),setTimeout(t,12e3)})()},s.prototype.send=function(e,t){e._id=this.id,t&&(g._callbacks[e._id]=t),e.args=e.args||[],this.id++,void 0!==this.provider?this.provider.send(e):(console.warn("provider is not set"),this.queued.push(e))},s.prototype.set=function(e){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=e,this.ready=!0},s.prototype.sendQueued=function(){for(var e=0;this.queued.length;e++)this.send(this.queued[e])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(e,t){this.provider&&this.provider.poll&&this.polls.push({data:e,id:t})},s.prototype.stopPolling=function(e){var t,n;for(t=this.polls.length;t--;)n=this.polls[t],n.id===e&&this.polls.splice(t,1)},g.provider=new s,g.setProvider=function(e){e.onmessage=r,g.provider.set(e),g.provider.sendQueued()},g.haveProvider=function(){return!!g.provider.provider},a=function(e,t){this.impl=t,this.callbacks=[];var n=this;this.promise=t.newFilter(e),this.promise.then(function(e){n.id=e,g.on(t.changed,e,n.trigger.bind(n)),g.provider.startPolling({call:t.changed,args:[e]},e)})},a.prototype.arrived=function(e){this.changed(e)},a.prototype.changed=function(e){var t=this;this.promise.then(function(){t.callbacks.push(e)})},a.prototype.trigger=function(e){for(var t=0;tr&&(e=t.charCodeAt(r),0!==e);r+=2)n+=String.fromCharCode(parseInt(t.substr(r,2),16));return n},toDecimal:function(t){return parseInt(t,16)},fromAscii:function(t,e){e=void 0===e?32:e;for(var n=this.toHex(t);n.length<2*e;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(t){return new a(t,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(t){return new a(t,i)}},on:function(t,e,n){return void 0===m._events[t]&&(m._events[t]={}),m._events[t][e]=n,this},off:function(t,e){return void 0!==m._events[t]&&delete m._events[t][e],this},trigger:function(t,e,n){var r,o=m._events[t];o&&o[e]&&(r=o[e])(n)}};v(m.eth,c()),g(m.eth,l()),v(m.db,h()),v(m.shh,p()),o={changed:"eth_changed"},v(o,d()),i={changed:"shh_changed"},v(i,f()),s=function(){var t,e;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,t=this,(e=function(){t.provider&&t.provider.poll&&t.polls.forEach(function(e){e.data._id=t.id,t.id++,t.provider.poll(e.data,e.id)}),setTimeout(e,12e3)})()},s.prototype.send=function(t,e){t._id=this.id,e&&(m._callbacks[t._id]=e),t.args=t.args||[],this.id++,void 0!==this.provider?this.provider.send(t):(console.warn("provider is not set"),this.queued.push(t))},s.prototype.set=function(t){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=t,this.ready=!0},s.prototype.sendQueued=function(){for(var t=0;this.queued.length;t++)this.send(this.queued[t])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(t,e){this.provider&&this.provider.poll&&this.polls.push({data:t,id:e})},s.prototype.stopPolling=function(t){var e,n;for(e=this.polls.length;e--;)n=this.polls[e],n.id===t&&this.polls.splice(e,1)},m.provider=new s,m.setProvider=function(t){t.onmessage=r,m.provider.set(t),m.provider.sendQueued()},m.haveProvider=function(){return!!m.provider.provider},a=function(t,e){this.impl=e,this.callbacks=[];var n=this;this.promise=e.newFilter(t),this.promise.then(function(t){n.id=t,m.on(e.changed,t,n.trigger.bind(n)),m.provider.startPolling({call:e.changed,args:[t]},t)})},a.prototype.arrived=function(t){this.changed(t)},a.prototype.changed=function(t){var e=this;this.promise.then(function(){e.callbacks.push(t)})},a.prototype.trigger=function(t){for(var e=0;e Date: Mon, 10 Nov 2014 17:31:09 +0100 Subject: [PATCH 15/38] Mapping types. --- libsolidity/AST.cpp | 40 +++++-- libsolidity/AST.h | 26 +++- libsolidity/Compiler.cpp | 2 +- libsolidity/CompilerContext.h | 4 +- libsolidity/ExpressionCompiler.cpp | 177 ++++++++++++++++++---------- libsolidity/ExpressionCompiler.h | 77 +++++++----- libsolidity/NameAndTypeResolver.cpp | 5 +- libsolidity/Types.cpp | 6 +- libsolidity/Types.h | 15 ++- test/solidityCompiler.cpp | 2 - test/solidityEndToEndTest.cpp | 167 ++++++++++++++++++++++++++ 11 files changed, 412 insertions(+), 109 deletions(-) diff --git a/libsolidity/AST.cpp b/libsolidity/AST.cpp index 70af8f98e..d5f856dfc 100644 --- a/libsolidity/AST.cpp +++ b/libsolidity/AST.cpp @@ -278,6 +278,15 @@ vector ContractDefinition::getInterfaceFunctions() co return exportedFunctions; } +void FunctionDefinition::checkTypeRequirements() +{ + for (ASTPointer const& var: getParameters() + getReturnParameters()) + if (!var->getType()->canLiveOutsideStorage()) + BOOST_THROW_EXCEPTION(var->createTypeError("Type is required to live outside storage.")); + + m_body->checkTypeRequirements(); +} + void Block::checkTypeRequirements() { for (shared_ptr const& statement: m_statements) @@ -315,7 +324,7 @@ void Return::checkTypeRequirements() void VariableDefinition::checkTypeRequirements() { // Variables can be declared without type (with "var"), in which case the first assignment - // setsthe type. + // sets the type. // Note that assignments before the first declaration are legal because of the special scoping // rules inherited from JavaScript. if (m_value) @@ -329,13 +338,14 @@ void VariableDefinition::checkTypeRequirements() m_variable->setType(m_value->getType()); } } + if (m_variable->getType() && !m_variable->getType()->canLiveOutsideStorage()) + BOOST_THROW_EXCEPTION(m_variable->createTypeError("Type is required to live outside storage.")); } void Assignment::checkTypeRequirements() { m_leftHandSide->checkTypeRequirements(); - if (!m_leftHandSide->isLvalue()) - BOOST_THROW_EXCEPTION(createTypeError("Expression has to be an lvalue.")); + m_leftHandSide->requireLValue(); m_rightHandSide->expectType(*m_leftHandSide->getType()); m_type = m_leftHandSide->getType(); if (m_assigmentOperator != Token::ASSIGN) @@ -359,13 +369,19 @@ void Expression::expectType(Type const& _expectedType) + _expectedType.toString() + ".")); } +void Expression::requireLValue() +{ + if (!isLvalue()) + BOOST_THROW_EXCEPTION(createTypeError("Expression has to be an lvalue.")); + m_lvalueRequested = true; +} + void UnaryOperation::checkTypeRequirements() { // INC, DEC, ADD, SUB, NOT, BIT_NOT, DELETE m_subExpression->checkTypeRequirements(); if (m_operator == Token::Value::INC || m_operator == Token::Value::DEC || m_operator == Token::Value::DELETE) - if (!m_subExpression->isLvalue()) - BOOST_THROW_EXCEPTION(createTypeError("Expression has to be an lvalue.")); + m_subExpression->requireLValue(); m_type = m_subExpression->getType(); if (!m_type->acceptsUnaryOperator(m_operator)) BOOST_THROW_EXCEPTION(createTypeError("Unary operator not compatible with type.")); @@ -416,6 +432,8 @@ void FunctionCall::checkTypeRequirements() } else { + m_expression->requireLValue(); + //@todo would be nice to create a struct type from the arguments // and then ask if that is implicitly convertible to the struct represented by the // function parameters @@ -448,8 +466,15 @@ void MemberAccess::checkTypeRequirements() void IndexAccess::checkTypeRequirements() { - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Index access not yet implemented.")); - // m_type = ; + m_base->checkTypeRequirements(); + m_base->requireLValue(); + if (m_base->getType()->getCategory() != Type::Category::MAPPING) + BOOST_THROW_EXCEPTION(m_base->createTypeError("Indexed expression has to be a mapping (is " + + m_base->getType()->toString() + ")")); + MappingType const& type = dynamic_cast(*m_base->getType()); + m_index->expectType(*type.getKeyType()); + m_type = type.getValueType(); + m_isLvalue = true; } void Identifier::checkTypeRequirements() @@ -481,6 +506,7 @@ void Identifier::checkTypeRequirements() // Calling a function (e.g. function(12), otherContract.function(34)) does not do a type // conversion. m_type = make_shared(*functionDef); + m_isLvalue = true; return; } ContractDefinition* contractDef = dynamic_cast(m_referencedDeclaration); diff --git a/libsolidity/AST.h b/libsolidity/AST.h index 7b266f132..31ca56f76 100644 --- a/libsolidity/AST.h +++ b/libsolidity/AST.h @@ -186,6 +186,8 @@ public: void addLocalVariable(VariableDeclaration const& _localVariable) { m_localVariables.push_back(&_localVariable); } std::vector const& getLocalVariables() const { return m_localVariables; } + /// Checks that all parameters have allowed types and calls checkTypeRequirements on the body. + void checkTypeRequirements(); private: bool m_isPublic; ASTPointer m_parameters; @@ -236,7 +238,7 @@ public: /// Retrieve the element of the type hierarchy this node refers to. Can return an empty shared /// pointer until the types have been resolved using the @ref NameAndTypeResolver. - virtual std::shared_ptr toType() = 0; + virtual std::shared_ptr toType() const = 0; }; /** @@ -252,7 +254,7 @@ public: if (asserts(Token::isElementaryTypeName(_type))) BOOST_THROW_EXCEPTION(InternalCompilerError()); } virtual void accept(ASTVisitor& _visitor) override; - virtual std::shared_ptr toType() override { return Type::fromElementaryTypeName(m_type); } + virtual std::shared_ptr toType() const override { return Type::fromElementaryTypeName(m_type); } Token::Value getTypeName() const { return m_type; } @@ -270,7 +272,7 @@ public: UserDefinedTypeName(Location const& _location, ASTPointer const& _name): TypeName(_location), m_name(_name) {} virtual void accept(ASTVisitor& _visitor) override; - virtual std::shared_ptr toType() override { return Type::fromUserDefinedTypeName(*this); } + virtual std::shared_ptr toType() const override { return Type::fromUserDefinedTypeName(*this); } ASTString const& getName() const { return *m_name; } void setReferencedStruct(StructDefinition& _referencedStruct) { m_referencedStruct = &_referencedStruct; } @@ -292,7 +294,10 @@ public: ASTPointer const& _valueType): TypeName(_location), m_keyType(_keyType), m_valueType(_valueType) {} virtual void accept(ASTVisitor& _visitor) override; - virtual std::shared_ptr toType() override { return Type::fromMapping(*this); } + virtual std::shared_ptr toType() const override { return Type::fromMapping(*this); } + + ElementaryTypeName const& getKeyType() const { return *m_keyType; } + TypeName const& getValueType() const { return *m_valueType; } private: ASTPointer m_keyType; @@ -481,7 +486,7 @@ private: class Expression: public ASTNode { public: - Expression(Location const& _location): ASTNode(_location), m_isLvalue(false) {} + Expression(Location const& _location): ASTNode(_location), m_isLvalue(false), m_lvalueRequested(false) {} virtual void checkTypeRequirements() = 0; std::shared_ptr const& getType() const { return m_type; } @@ -490,6 +495,12 @@ public: /// Helper function, infer the type via @ref checkTypeRequirements and then check that it /// is implicitly convertible to @a _expectedType. If not, throw exception. void expectType(Type const& _expectedType); + /// Checks that this expression is an lvalue and also registers that an address and + /// not a value is generated during compilation. Can be called after checkTypeRequirements() + /// by an enclosing expression. + void requireLValue(); + /// Returns true if @a requireLValue was previously called on this expression. + bool lvalueRequested() const { return m_lvalueRequested; } protected: //! Inferred type of the expression, only filled after a call to checkTypeRequirements(). @@ -497,6 +508,8 @@ protected: //! Whether or not this expression is an lvalue, i.e. something that can be assigned to. //! This is set during calls to @a checkTypeRequirements() bool m_isLvalue; + //! Whether the outer expression requested the address (true) or the value (false) of this expression. + bool m_lvalueRequested; }; /// Assignment, can also be a compound assignment. @@ -543,6 +556,7 @@ public: Token::Value getOperator() const { return m_operator; } bool isPrefixOperation() const { return m_isPrefix; } + Expression& getSubExpression() const { return *m_subExpression; } private: Token::Value m_operator; @@ -635,6 +649,8 @@ public: virtual void accept(ASTVisitor& _visitor) override; virtual void checkTypeRequirements() override; + Expression& getBaseExpression() const { return *m_base; } + Expression& getIndexExpression() const { return *m_index; } private: ASTPointer m_base; ASTPointer m_index; diff --git a/libsolidity/Compiler.cpp b/libsolidity/Compiler.cpp index da28ba8a3..eed886783 100644 --- a/libsolidity/Compiler.cpp +++ b/libsolidity/Compiler.cpp @@ -225,7 +225,7 @@ bool Compiler::visit(IfStatement& _ifStatement) eth::AssemblyItem trueTag = m_context.appendConditionalJump(); if (_ifStatement.getFalseStatement()) _ifStatement.getFalseStatement()->accept(*this); - eth::AssemblyItem endTag = m_context.appendJump(); + eth::AssemblyItem endTag = m_context.appendJumpToNew(); m_context << trueTag; _ifStatement.getTrueStatement().accept(*this); m_context << endTag; diff --git a/libsolidity/CompilerContext.h b/libsolidity/CompilerContext.h index 562c29321..e624222dd 100644 --- a/libsolidity/CompilerContext.h +++ b/libsolidity/CompilerContext.h @@ -65,7 +65,9 @@ public: /// Appends a JUMPI instruction to @a _tag CompilerContext& appendConditionalJumpTo(eth::AssemblyItem const& _tag) { m_asm.appendJumpI(_tag); return *this; } /// Appends a JUMP to a new tag and @returns the tag - eth::AssemblyItem appendJump() { return m_asm.appendJump().tag(); } + eth::AssemblyItem appendJumpToNew() { return m_asm.appendJump().tag(); } + /// Appends a JUMP to a tag already on the stack + CompilerContext& appendJump() { return *this << eth::Instruction::JUMP; } /// Appends a JUMP to a specific tag CompilerContext& appendJumpTo(eth::AssemblyItem const& _tag) { m_asm.appendJump(_tag); return *this; } /// Appends pushing of a new tag and @returns the new tag. diff --git a/libsolidity/ExpressionCompiler.cpp b/libsolidity/ExpressionCompiler.cpp index 05bbb0916..d80b42b35 100644 --- a/libsolidity/ExpressionCompiler.cpp +++ b/libsolidity/ExpressionCompiler.cpp @@ -22,6 +22,7 @@ #include #include +#include #include #include #include @@ -50,14 +51,19 @@ bool ExpressionCompiler::visit(Assignment& _assignment) appendTypeConversion(*_assignment.getRightHandSide().getType(), *_assignment.getType()); m_currentLValue.reset(); _assignment.getLeftHandSide().accept(*this); + if (asserts(m_currentLValue.isValid())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("LValue not retrieved.")); Token::Value op = _assignment.getAssignmentOperator(); if (op != Token::ASSIGN) // compound assignment + { + if (m_currentLValue.storesReferenceOnStack()) + m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2; + m_currentLValue.retrieveValue(_assignment, true); appendOrdinaryBinaryOperatorCode(Token::AssignmentToBinaryOp(op), *_assignment.getType()); - else - m_context << eth::Instruction::POP; + } + m_currentLValue.storeValue(_assignment); - storeInLValue(_assignment); return false; } @@ -76,23 +82,37 @@ void ExpressionCompiler::endVisit(UnaryOperation& _unaryOperation) m_context << eth::Instruction::NOT; break; case Token::DELETE: // delete - { - // a -> a xor a (= 0). // @todo semantics change for complex types - m_context << eth::Instruction::DUP1 << eth::Instruction::XOR; - storeInLValue(_unaryOperation); + if (asserts(m_currentLValue.isValid())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("LValue not retrieved.")); + + m_context << u256(0); + if (m_currentLValue.storesReferenceOnStack()) + m_context << eth::Instruction::SWAP1; + m_currentLValue.storeValue(_unaryOperation); break; - } case Token::INC: // ++ (pre- or postfix) case Token::DEC: // -- (pre- or postfix) + if (asserts(m_currentLValue.isValid())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("LValue not retrieved.")); + m_currentLValue.retrieveValue(_unaryOperation); if (!_unaryOperation.isPrefixOperation()) - m_context << eth::Instruction::DUP1; + { + if (m_currentLValue.storesReferenceOnStack()) + m_context << eth::Instruction::SWAP1 << eth::Instruction::DUP2; + else + m_context << eth::Instruction::DUP1; + } m_context << u256(1); if (_unaryOperation.getOperator() == Token::INC) m_context << eth::Instruction::ADD; else m_context << eth::Instruction::SWAP1 << eth::Instruction::SUB; // @todo avoid the swap - storeInLValue(_unaryOperation, !_unaryOperation.isPrefixOperation()); + // Stack for prefix: [ref] (*ref)+-1 + // Stack for postfix: *ref [ref] (*ref)+-1 + if (m_currentLValue.storesReferenceOnStack()) + m_context << eth::Instruction::SWAP1; + m_currentLValue.storeValue(_unaryOperation, !_unaryOperation.isPrefixOperation()); break; case Token::ADD: // + // unary add, so basically no-op @@ -151,12 +171,6 @@ bool ExpressionCompiler::visit(FunctionCall& _functionCall) { // Calling convention: Caller pushes return address and arguments // Callee removes them and pushes return values - m_currentLValue.reset(); - _functionCall.getExpression().accept(*this); - if (asserts(m_currentLValue.isInCode())) - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Code reference expected.")); - eth::AssemblyItem functionTag(eth::PushTag, m_currentLValue.location); - FunctionDefinition const& function = dynamic_cast(*_functionCall.getExpression().getType()).getFunction(); eth::AssemblyItem returnLabel = m_context.pushNewTag(); @@ -168,8 +182,12 @@ bool ExpressionCompiler::visit(FunctionCall& _functionCall) arguments[i]->accept(*this); appendTypeConversion(*arguments[i]->getType(), *function.getParameters()[i]->getType()); } + m_currentLValue.reset(); + _functionCall.getExpression().accept(*this); + if (asserts(m_currentLValue.isInCode())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Code reference expected.")); - m_context.appendJumpTo(functionTag); + m_context.appendJump(); m_context << returnLabel; // callee adds return parameters, but removes arguments and return label @@ -185,30 +203,33 @@ bool ExpressionCompiler::visit(FunctionCall& _functionCall) void ExpressionCompiler::endVisit(MemberAccess&) { - + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Member access not yet implemented.")); } -void ExpressionCompiler::endVisit(IndexAccess&) +bool ExpressionCompiler::visit(IndexAccess& _indexAccess) { + m_currentLValue.reset(); + _indexAccess.getBaseExpression().accept(*this); + if (asserts(m_currentLValue.isInStorage())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Index access to a non-storage value.")); + _indexAccess.getIndexExpression().accept(*this); + appendTypeConversion(*_indexAccess.getIndexExpression().getType(), + *dynamic_cast(*_indexAccess.getBaseExpression().getType()).getKeyType(), + true); + // @todo move this once we actually use memory + m_context << u256(32) << eth::Instruction::MSTORE << u256(0) << eth::Instruction::MSTORE; + m_context << u256(64) << u256(0) << eth::Instruction::SHA3; + + m_currentLValue = LValue(m_context, LValue::STORAGE); + m_currentLValue.retrieveValueIfLValueNotRequested(_indexAccess); + return false; } void ExpressionCompiler::endVisit(Identifier& _identifier) { - Declaration const* declaration = _identifier.getReferencedDeclaration(); - if (m_context.isLocalVariable(declaration)) - m_currentLValue = LValueLocation(LValueLocation::STACK, - m_context.getBaseStackOffsetOfVariable(*declaration)); - else if (m_context.isStateVariable(declaration)) - m_currentLValue = LValueLocation(LValueLocation::STORAGE, - m_context.getStorageLocationOfVariable(*declaration)); - else if (m_context.isFunctionDefinition(declaration)) - m_currentLValue = LValueLocation(LValueLocation::CODE, - m_context.getFunctionEntryLabel(dynamic_cast(*declaration)).data()); - else - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Identifier type not supported or identifier not found.")); - - retrieveLValueValue(_identifier); + m_currentLValue.fromDeclaration(_identifier, *_identifier.getReferencedDeclaration()); + m_currentLValue.retrieveValueIfLValueNotRequested(_identifier); } void ExpressionCompiler::endVisit(Literal& _literal) @@ -371,66 +392,104 @@ void ExpressionCompiler::appendHighBitsCleanup(IntegerType const& _typeOnStack) m_context << ((u256(1) << _typeOnStack.getNumBits()) - 1) << eth::Instruction::AND; } -void ExpressionCompiler::retrieveLValueValue(Expression const& _expression) +void ExpressionCompiler::LValue::retrieveValue(Expression const& _expression, bool _remove) const { - switch (m_currentLValue.locationType) + switch (m_type) { - case LValueLocation::CODE: - // not stored on the stack + case CODE: + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Tried to retrieve value of a function.")); break; - case LValueLocation::STACK: + case STACK: { - unsigned stackPos = m_context.baseToCurrentStackOffset(unsigned(m_currentLValue.location)); + unsigned stackPos = m_context->baseToCurrentStackOffset(unsigned(m_baseStackOffset)); if (stackPos >= 15) //@todo correct this by fetching earlier or moving to memory BOOST_THROW_EXCEPTION(CompilerError() << errinfo_sourceLocation(_expression.getLocation()) << errinfo_comment("Stack too deep.")); - m_context << eth::dupInstruction(stackPos + 1); + *m_context << eth::dupInstruction(stackPos + 1); break; } - case LValueLocation::STORAGE: - m_context << m_currentLValue.location << eth::Instruction::SLOAD; + case STORAGE: + if (!_remove) + *m_context << eth::Instruction::DUP1; + *m_context << eth::Instruction::SLOAD; break; - case LValueLocation::MEMORY: - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Location type not yet implemented.")); + case MEMORY: + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Location type not yet implemented.")); break; default: - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unsupported location type.")); + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Unsupported location type.")); break; } } -void ExpressionCompiler::storeInLValue(Expression const& _expression, bool _move) +void ExpressionCompiler::LValue::storeValue(Expression const& _expression, bool _move) const { - switch (m_currentLValue.locationType) + switch (m_type) { - case LValueLocation::STACK: + case STACK: { - unsigned stackPos = m_context.baseToCurrentStackOffset(unsigned(m_currentLValue.location)); + unsigned stackPos = m_context->baseToCurrentStackOffset(unsigned(m_baseStackOffset)); if (stackPos > 16) BOOST_THROW_EXCEPTION(CompilerError() << errinfo_sourceLocation(_expression.getLocation()) << errinfo_comment("Stack too deep.")); else if (stackPos > 0) - m_context << eth::swapInstruction(stackPos) << eth::Instruction::POP; + *m_context << eth::swapInstruction(stackPos) << eth::Instruction::POP; if (!_move) - retrieveLValueValue(_expression); + retrieveValue(_expression); break; } - case LValueLocation::STORAGE: + case LValue::STORAGE: if (!_move) - m_context << eth::Instruction::DUP1; - m_context << m_currentLValue.location << eth::Instruction::SSTORE; + *m_context << eth::Instruction::DUP2 << eth::Instruction::SWAP1; + *m_context << eth::Instruction::SSTORE; break; - case LValueLocation::CODE: - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Location type does not support assignment.")); + case LValue::CODE: + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Location type does not support assignment.")); break; - case LValueLocation::MEMORY: - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Location type not yet implemented.")); + case LValue::MEMORY: + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Location type not yet implemented.")); break; default: - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Unsupported location type.")); + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Unsupported location type.")); break; } } +void ExpressionCompiler::LValue::retrieveValueIfLValueNotRequested(const Expression& _expression) +{ + if (!_expression.lvalueRequested()) + { + retrieveValue(_expression, true); + reset(); + } +} + +void ExpressionCompiler::LValue::fromDeclaration( Expression const& _expression, Declaration const& _declaration) +{ + if (m_context->isLocalVariable(&_declaration)) + { + m_type = STACK; + m_baseStackOffset = m_context->getBaseStackOffsetOfVariable(_declaration); + } + else if (m_context->isStateVariable(&_declaration)) + { + m_type = STORAGE; + *m_context << m_context->getStorageLocationOfVariable(_declaration); + } + else if (m_context->isFunctionDefinition(&_declaration)) + { + m_type = CODE; + *m_context << m_context->getFunctionEntryLabel(dynamic_cast(_declaration)).pushTag(); + } + else + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_sourceLocation(_expression.getLocation()) + << errinfo_comment("Identifier type not supported or identifier not found.")); +} + } } diff --git a/libsolidity/ExpressionCompiler.h b/libsolidity/ExpressionCompiler.h index bd5a9f866..f52da29ec 100644 --- a/libsolidity/ExpressionCompiler.h +++ b/libsolidity/ExpressionCompiler.h @@ -20,6 +20,7 @@ * Solidity AST to EVM bytecode compiler for expressions. */ +#include #include #include @@ -49,14 +50,15 @@ public: static void appendTypeConversion(CompilerContext& _context, Type const& _typeOnStack, Type const& _targetType); private: - ExpressionCompiler(CompilerContext& _compilerContext): m_context(_compilerContext) {} + ExpressionCompiler(CompilerContext& _compilerContext): + m_context(_compilerContext), m_currentLValue(m_context) {} virtual bool visit(Assignment& _assignment) override; virtual void endVisit(UnaryOperation& _unaryOperation) override; virtual bool visit(BinaryOperation& _binaryOperation) override; virtual bool visit(FunctionCall& _functionCall) override; virtual void endVisit(MemberAccess& _memberAccess) override; - virtual void endVisit(IndexAccess& _indexAccess) override; + virtual bool visit(IndexAccess& _indexAccess) override; virtual void endVisit(Identifier& _identifier) override; virtual void endVisit(Literal& _literal) override; @@ -79,37 +81,58 @@ private: //// Appends code that cleans higher-order bits for integer types. void appendHighBitsCleanup(IntegerType const& _typeOnStack); - /// Copies the value of the current lvalue to the top of the stack. - void retrieveLValueValue(Expression const& _expression); - /// Stores the value on top of the stack in the current lvalue. Removes it from the stack if - /// @a _move is true. - void storeInLValue(Expression const& _expression, bool _move = false); - /** - * Location of an lvalue, either in code (for a function) on the stack, in the storage or memory. + * Helper class to store and retrieve lvalues to and from various locations. + * All types except STACK store a reference in a slot on the stack, STACK just stores the + * base stack offset of the variable in @a m_baseStackOffset. */ - struct LValueLocation + class LValue { - enum LocationType { INVALID, CODE, STACK, MEMORY, STORAGE }; - - LValueLocation() { reset(); } - LValueLocation(LocationType _type, u256 const& _location): locationType(_type), location(_location) {} - void reset() { locationType = INVALID; location = 0; } - bool isValid() const { return locationType != INVALID; } - bool isInCode() const { return locationType == CODE; } - bool isInOnStack() const { return locationType == STACK; } - bool isInMemory() const { return locationType == MEMORY; } - bool isInStorage() const { return locationType == STORAGE; } - - LocationType locationType; - /// Depending on the type, this is the id of a tag (code), the base offset of a stack - /// variable (@see CompilerContext::getBaseStackOffsetOfVariable) or the offset in - /// storage or memory. - u256 location; + public: + enum LValueType { NONE, CODE, STACK, MEMORY, STORAGE }; + + explicit LValue(CompilerContext& _compilerContext): m_context(&_compilerContext) { reset(); } + LValue(CompilerContext& _compilerContext, LValueType _type, unsigned _baseStackOffset = 0): + m_context(&_compilerContext), m_type(_type), m_baseStackOffset(_baseStackOffset) {} + + /// Set type according to the declaration and retrieve the reference. + /// @a _expression is the current expression, used for error reporting. + void fromDeclaration(Expression const& _expression, Declaration const& _declaration); + void reset() { m_type = NONE; m_baseStackOffset = 0; } + + bool isValid() const { return m_type != NONE; } + bool isInCode() const { return m_type == CODE; } + bool isInOnStack() const { return m_type == STACK; } + bool isInMemory() const { return m_type == MEMORY; } + bool isInStorage() const { return m_type == STORAGE; } + + /// @returns true if this lvalue reference type occupies a slot on the stack. + bool storesReferenceOnStack() const { return m_type == STORAGE || m_type == MEMORY || m_type == CODE; } + + /// Copies the value of the current lvalue to the top of the stack and, if @a _remove is true, + /// also removes the reference from the stack (note that is does not reset the type to @a NONE). + /// @a _expression is the current expression, used for error reporting. + void retrieveValue(Expression const& _expression, bool _remove = false) const; + /// Stores a value (from the stack directly beneath the reference, which is assumed to + /// be on the top of the stack, if any) in the lvalue and removes the reference. + /// Also removes the stored value from the stack if @a _move is + /// true. @a _expression is the current expression, used for error reporting. + void storeValue(Expression const& _expression, bool _move = false) const; + + /// Convenience function to convert the stored reference to a value and reset type to NONE if + /// the reference was not requested by @a _expression. + void retrieveValueIfLValueNotRequested(Expression const& _expression); + + private: + CompilerContext* m_context; + LValueType m_type; + /// If m_type is STACK, this is base stack offset (@see + /// CompilerContext::getBaseStackOffsetOfVariable) of a local variable. + unsigned m_baseStackOffset; }; - LValueLocation m_currentLValue; CompilerContext& m_context; + LValue m_currentLValue; }; diff --git a/libsolidity/NameAndTypeResolver.cpp b/libsolidity/NameAndTypeResolver.cpp index 0578e5996..4a15fe794 100644 --- a/libsolidity/NameAndTypeResolver.cpp +++ b/libsolidity/NameAndTypeResolver.cpp @@ -52,7 +52,7 @@ void NameAndTypeResolver::resolveNamesAndTypes(ContractDefinition& _contract) for (ASTPointer const& function: _contract.getDefinedFunctions()) { m_currentScope = &m_scopes[function.get()]; - function->getBody().checkTypeRequirements(); + function->checkTypeRequirements(); } m_currentScope = &m_scopes[nullptr]; } @@ -186,9 +186,8 @@ bool ReferencesResolver::visit(Return& _return) return true; } -bool ReferencesResolver::visit(Mapping&) +bool ReferencesResolver::visit(Mapping& _mapping) { - // @todo return true; } diff --git a/libsolidity/Types.cpp b/libsolidity/Types.cpp index 3a4112c45..e37ed3e5b 100644 --- a/libsolidity/Types.cpp +++ b/libsolidity/Types.cpp @@ -63,9 +63,11 @@ shared_ptr Type::fromUserDefinedTypeName(UserDefinedTypeName const& _typeN return make_shared(*_typeName.getReferencedStruct()); } -shared_ptr Type::fromMapping(Mapping const&) +shared_ptr Type::fromMapping(Mapping const& _typeName) { - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Mapping types not yet implemented.")); + shared_ptr keyType = _typeName.getKeyType().toType(); + shared_ptr valueType = _typeName.getValueType().toType(); + return make_shared(keyType, valueType); } shared_ptr Type::forLiteral(Literal const& _literal) diff --git a/libsolidity/Types.h b/libsolidity/Types.h index 607ee3a6f..b9bb74dbb 100644 --- a/libsolidity/Types.h +++ b/libsolidity/Types.h @@ -35,7 +35,7 @@ namespace dev namespace solidity { -// @todo realMxN, string, mapping +// @todo realMxN, string /** * Abstract base class that forms the root of the type hierarchy. @@ -78,6 +78,8 @@ public: /// @returns number of bytes required to hold this value in storage. /// For dynamically "allocated" types, it returns the size of the statically allocated head, virtual u256 getStorageSize() const { return 1; } + /// Returns false if the type cannot live outside the storage, i.e. if it includes some mapping. + virtual bool canLiveOutsideStorage() const { return true; } virtual std::string toString() const = 0; virtual u256 literalValue(Literal const&) const @@ -182,6 +184,8 @@ public: virtual bool operator==(Type const& _other) const override; virtual u256 getStorageSize() const; + //@todo it can, if its members can + virtual bool canLiveOutsideStorage() const { return false; } virtual std::string toString() const override { return "struct{...}"; } private: @@ -202,6 +206,7 @@ public: virtual bool operator==(Type const& _other) const override; virtual std::string toString() const override { return "function(...)returns(...)"; } virtual u256 getStorageSize() const { BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Storage size of non-storable function type requested.")); } + virtual bool canLiveOutsideStorage() const { return false; } private: FunctionDefinition const& m_function; @@ -214,11 +219,15 @@ class MappingType: public Type { public: virtual Category getCategory() const override { return Category::MAPPING; } - MappingType() {} + MappingType(std::shared_ptr _keyType, std::shared_ptr _valueType): + m_keyType(_keyType), m_valueType(_valueType) {} virtual bool operator==(Type const& _other) const override; virtual std::string toString() const override { return "mapping(...=>...)"; } + virtual bool canLiveOutsideStorage() const { return false; } + std::shared_ptr getKeyType() const { return m_keyType; } + std::shared_ptr getValueType() const { return m_valueType; } private: std::shared_ptr m_keyType; std::shared_ptr m_valueType; @@ -236,6 +245,7 @@ public: virtual std::string toString() const override { return "void"; } virtual u256 getStorageSize() const { BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Storage size of non-storable void type requested.")); } + virtual bool canLiveOutsideStorage() const { return false; } }; /** @@ -252,6 +262,7 @@ public: virtual bool operator==(Type const& _other) const override; virtual u256 getStorageSize() const { BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Storage size of non-storable type type requested.")); } + virtual bool canLiveOutsideStorage() const { return false; } virtual std::string toString() const override { return "type(" + m_actualType->toString() + ")"; } private: diff --git a/test/solidityCompiler.cpp b/test/solidityCompiler.cpp index 054ad3297..e0635b6ae 100644 --- a/test/solidityCompiler.cpp +++ b/test/solidityCompiler.cpp @@ -128,8 +128,6 @@ BOOST_AUTO_TEST_CASE(different_argument_numbers) byte(Instruction::JUMP), byte(Instruction::JUMPDEST), // stack here: ret e h f(1,2,3) - byte(Instruction::DUP2), - byte(Instruction::POP), byte(Instruction::SWAP1), // stack here: ret e f(1,2,3) h byte(Instruction::POP), diff --git a/test/solidityEndToEndTest.cpp b/test/solidityEndToEndTest.cpp index d905646cb..5e6631df6 100644 --- a/test/solidityEndToEndTest.cpp +++ b/test/solidityEndToEndTest.cpp @@ -32,6 +32,9 @@ using namespace std; namespace dev { +/// Provider another overload for toBigEndian to encode arguments and return values. +inline bytes toBigEndian(bool _value) { return bytes({byte(_value)}); } + namespace solidity { namespace test @@ -137,6 +140,7 @@ private: m_output = executive.out().toVector(); } +protected: Address m_contractAddress; eth::State m_state; u256 const m_gasPrice = 100 * eth::szabo; @@ -496,6 +500,169 @@ BOOST_AUTO_TEST_CASE(state_smoke_test) BOOST_CHECK(callContractFunction(0, bytes(1, 0x00)) == toBigEndian(u256(0x3))); } +BOOST_AUTO_TEST_CASE(simple_mapping) +{ + char const* sourceCode = "contract test {\n" + " mapping(uint8 => uint8) table;\n" + " function get(uint8 k) returns (uint8 v) {\n" + " return table[k];\n" + " }\n" + " function set(uint8 k, uint8 v) {\n" + " table[k] = v;\n" + " }\n" + "}"; + compileAndRun(sourceCode); + + BOOST_CHECK(callContractFunction(0, bytes({0x00})) == bytes({0x00})); + BOOST_CHECK(callContractFunction(0, bytes({0x01})) == bytes({0x00})); + BOOST_CHECK(callContractFunction(0, bytes({0xa7})) == bytes({0x00})); + callContractFunction(1, bytes({0x01, 0xa1})); + BOOST_CHECK(callContractFunction(0, bytes({0x00})) == bytes({0x00})); + BOOST_CHECK(callContractFunction(0, bytes({0x01})) == bytes({0xa1})); + BOOST_CHECK(callContractFunction(0, bytes({0xa7})) == bytes({0x00})); + callContractFunction(1, bytes({0x00, 0xef})); + BOOST_CHECK(callContractFunction(0, bytes({0x00})) == bytes({0xef})); + BOOST_CHECK(callContractFunction(0, bytes({0x01})) == bytes({0xa1})); + BOOST_CHECK(callContractFunction(0, bytes({0xa7})) == bytes({0x00})); + callContractFunction(1, bytes({0x01, 0x05})); + BOOST_CHECK(callContractFunction(0, bytes({0x00})) == bytes({0xef})); + BOOST_CHECK(callContractFunction(0, bytes({0x01})) == bytes({0x05})); + BOOST_CHECK(callContractFunction(0, bytes({0xa7})) == bytes({0x00})); +} + +BOOST_AUTO_TEST_CASE(mapping_state) +{ + char const* sourceCode = "contract Ballot {\n" + " mapping(address => bool) canVote;\n" + " mapping(address => uint) voteCount;\n" + " mapping(address => bool) voted;\n" + " function getVoteCount(address addr) returns (uint retVoteCount) {\n" + " return voteCount[addr];\n" + " }\n" + " function grantVoteRight(address addr) {\n" + " canVote[addr] = true;\n" + " }\n" + " function vote(address voter, address vote) returns (bool success) {\n" + " if (!canVote[voter] || voted[voter]) return false;\n" + " voted[voter] = true;\n" + " voteCount[vote] = voteCount[vote] + 1;\n" + " return true;\n" + " }\n" + "}\n"; + compileAndRun(sourceCode); + class Ballot + { + public: + u256 getVoteCount(u160 _address) { return m_voteCount[_address]; } + void grantVoteRight(u160 _address) { m_canVote[_address] = true; } + bool vote(u160 _voter, u160 _vote) + { + if (!m_canVote[_voter] || m_voted[_voter]) return false; + m_voted[_voter] = true; + m_voteCount[_vote]++; + return true; + } + private: + map m_canVote; + map m_voteCount; + map m_voted; + } ballot; + + auto getVoteCount = bind(&Ballot::getVoteCount, &ballot, _1); + auto grantVoteRight = bind(&Ballot::grantVoteRight, &ballot, _1); + auto vote = bind(&Ballot::vote, &ballot, _1, _2); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); + // voting without vote right shourd be rejected + testSolidityAgainstCpp(2, vote, u160(0), u160(2)); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); + // grant vote rights + testSolidityAgainstCpp(1, grantVoteRight, u160(0)); + testSolidityAgainstCpp(1, grantVoteRight, u160(1)); + // vote, should increase 2's vote count + testSolidityAgainstCpp(2, vote, u160(0), u160(2)); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); + // vote again, should be rejected + testSolidityAgainstCpp(2, vote, u160(0), u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); + // vote without right to vote + testSolidityAgainstCpp(2, vote, u160(2), u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); + // grant vote right and now vote again + testSolidityAgainstCpp(1, grantVoteRight, u160(2)); + testSolidityAgainstCpp(2, vote, u160(2), u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(0)); + testSolidityAgainstCpp(0, getVoteCount, u160(1)); + testSolidityAgainstCpp(0, getVoteCount, u160(2)); +} + +BOOST_AUTO_TEST_CASE(mapping_state_inc_dec) +{ + char const* sourceCode = "contract test {\n" + " uint value;\n" + " mapping(uint => uint) table;\n" + " function f(uint x) returns (uint y) {\n" + " value = x;\n" + " if (x > 0) table[++value] = 8;\n" + " if (x > 1) value--;\n" + " if (x > 2) table[value]++;\n" + " return --table[value++];\n" + " }\n" + "}\n"; + compileAndRun(sourceCode); + + u256 value = 0; + map table; + auto f = [&](u256 const& _x) -> u256 + { + value = _x; + if (_x > 0) + table[++value] = 8; + if (_x > 1) + value --; + if (_x > 2) + table[value]++; + return --table[value++]; + }; + testSolidityAgainstCppOnRange(0, f, 0, 5); +} + +BOOST_AUTO_TEST_CASE(multi_level_mapping) +{ + char const* sourceCode = "contract test {\n" + " mapping(uint => mapping(uint => uint)) table;\n" + " function f(uint x, uint y, uint z) returns (uint w) {\n" + " if (z == 0) return table[x][y];\n" + " else return table[x][y] = z;\n" + " }\n" + "}\n"; + compileAndRun(sourceCode); + + map> table; + auto f = [&](u256 const& _x, u256 const& _y, u256 const& _z) -> u256 + { + if (_z == 0) return table[_x][_y]; + else return table[_x][_y] = _z; + }; + testSolidityAgainstCpp(0, f, u256(4), u256(5), u256(0)); + testSolidityAgainstCpp(0, f, u256(5), u256(4), u256(0)); + testSolidityAgainstCpp(0, f, u256(4), u256(5), u256(9)); + testSolidityAgainstCpp(0, f, u256(4), u256(5), u256(0)); + testSolidityAgainstCpp(0, f, u256(5), u256(4), u256(0)); + testSolidityAgainstCpp(0, f, u256(5), u256(4), u256(7)); + testSolidityAgainstCpp(0, f, u256(4), u256(5), u256(0)); + testSolidityAgainstCpp(0, f, u256(5), u256(4), u256(0)); +} + BOOST_AUTO_TEST_SUITE_END() } From bbc3a1b37e72d9d27a70c5d82eda219836017d3d Mon Sep 17 00:00:00 2001 From: Christian Date: Thu, 13 Nov 2014 01:12:57 +0100 Subject: [PATCH 16/38] Struct types. --- libsolidity/AST.cpp | 13 +++++- libsolidity/AST.h | 5 ++- libsolidity/ExpressionCompiler.cpp | 17 ++++++-- libsolidity/NameAndTypeResolver.cpp | 29 ++++++++++++-- libsolidity/NameAndTypeResolver.h | 11 ++++-- libsolidity/Types.cpp | 55 +++++++++++++++++++++++++- libsolidity/Types.h | 16 +++++--- test/solidityEndToEndTest.cpp | 37 +++++++++++++++++ test/solidityNameAndTypeResolution.cpp | 38 ++++++++++++++++++ 9 files changed, 201 insertions(+), 20 deletions(-) diff --git a/libsolidity/AST.cpp b/libsolidity/AST.cpp index d5f856dfc..e8bdecf31 100644 --- a/libsolidity/AST.cpp +++ b/libsolidity/AST.cpp @@ -460,8 +460,17 @@ bool FunctionCall::isTypeConversion() const void MemberAccess::checkTypeRequirements() { - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Member access not yet implemented.")); - // m_type = ; + m_expression->checkTypeRequirements(); + m_expression->requireLValue(); + if (m_expression->getType()->getCategory() != Type::Category::STRUCT) + BOOST_THROW_EXCEPTION(createTypeError("Member access to a non-struct (is " + + m_expression->getType()->toString() + ")")); + StructType const& type = dynamic_cast(*m_expression->getType()); + unsigned memberIndex = type.memberNameToIndex(*m_memberName); + if (memberIndex >= type.getMemberCount()) + BOOST_THROW_EXCEPTION(createTypeError("Member \"" + *m_memberName + "\" not found in " + type.toString())); + m_type = type.getMemberByIndex(memberIndex).getType(); + m_isLvalue = true; } void IndexAccess::checkTypeRequirements() diff --git a/libsolidity/AST.h b/libsolidity/AST.h index 31ca56f76..80c7dd198 100644 --- a/libsolidity/AST.h +++ b/libsolidity/AST.h @@ -146,7 +146,7 @@ private: /** * Parameter list, used as function parameter list and return list. * None of the parameters is allowed to contain mappings (not even recursively - * inside structs), but (@todo) this is not yet enforced. + * inside structs). */ class ParameterList: public ASTNode { @@ -368,7 +368,6 @@ private: /** * Statement in which a break statement is legal. - * @todo actually check this requirement. */ class BreakableStatement: public Statement { @@ -629,6 +628,7 @@ public: ASTPointer const& _memberName): Expression(_location), m_expression(_expression), m_memberName(_memberName) {} virtual void accept(ASTVisitor& _visitor) override; + Expression& getExpression() const { return *m_expression; } ASTString const& getMemberName() const { return *m_memberName; } virtual void checkTypeRequirements() override; @@ -651,6 +651,7 @@ public: Expression& getBaseExpression() const { return *m_base; } Expression& getIndexExpression() const { return *m_index; } + private: ASTPointer m_base; ASTPointer m_index; diff --git a/libsolidity/ExpressionCompiler.cpp b/libsolidity/ExpressionCompiler.cpp index d80b42b35..f37ce39ce 100644 --- a/libsolidity/ExpressionCompiler.cpp +++ b/libsolidity/ExpressionCompiler.cpp @@ -49,7 +49,6 @@ bool ExpressionCompiler::visit(Assignment& _assignment) { _assignment.getRightHandSide().accept(*this); appendTypeConversion(*_assignment.getRightHandSide().getType(), *_assignment.getType()); - m_currentLValue.reset(); _assignment.getLeftHandSide().accept(*this); if (asserts(m_currentLValue.isValid())) BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("LValue not retrieved.")); @@ -63,6 +62,7 @@ bool ExpressionCompiler::visit(Assignment& _assignment) appendOrdinaryBinaryOperatorCode(Token::AssignmentToBinaryOp(op), *_assignment.getType()); } m_currentLValue.storeValue(_assignment); + m_currentLValue.reset(); return false; } @@ -90,6 +90,7 @@ void ExpressionCompiler::endVisit(UnaryOperation& _unaryOperation) if (m_currentLValue.storesReferenceOnStack()) m_context << eth::Instruction::SWAP1; m_currentLValue.storeValue(_unaryOperation); + m_currentLValue.reset(); break; case Token::INC: // ++ (pre- or postfix) case Token::DEC: // -- (pre- or postfix) @@ -113,6 +114,7 @@ void ExpressionCompiler::endVisit(UnaryOperation& _unaryOperation) if (m_currentLValue.storesReferenceOnStack()) m_context << eth::Instruction::SWAP1; m_currentLValue.storeValue(_unaryOperation, !_unaryOperation.isPrefixOperation()); + m_currentLValue.reset(); break; case Token::ADD: // + // unary add, so basically no-op @@ -182,10 +184,10 @@ bool ExpressionCompiler::visit(FunctionCall& _functionCall) arguments[i]->accept(*this); appendTypeConversion(*arguments[i]->getType(), *function.getParameters()[i]->getType()); } - m_currentLValue.reset(); _functionCall.getExpression().accept(*this); if (asserts(m_currentLValue.isInCode())) BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Code reference expected.")); + m_currentLValue.reset(); m_context.appendJump(); m_context << returnLabel; @@ -201,9 +203,16 @@ bool ExpressionCompiler::visit(FunctionCall& _functionCall) return false; } -void ExpressionCompiler::endVisit(MemberAccess&) +void ExpressionCompiler::endVisit(MemberAccess& _memberAccess) { - BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Member access not yet implemented.")); + if (asserts(m_currentLValue.isInStorage())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Member access to a non-storage value.")); + StructType const& type = dynamic_cast(*_memberAccess.getExpression().getType()); + unsigned memberIndex = type.memberNameToIndex(_memberAccess.getMemberName()); + if (asserts(memberIndex <= type.getMemberCount())) + BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Member not found in struct during compilation.")); + m_context << type.getStorageOffsetOfMember(memberIndex) << eth::Instruction::ADD; + m_currentLValue.retrieveValueIfLValueNotRequested(_memberAccess); } bool ExpressionCompiler::visit(IndexAccess& _indexAccess) diff --git a/libsolidity/NameAndTypeResolver.cpp b/libsolidity/NameAndTypeResolver.cpp index 4a15fe794..5bc406855 100644 --- a/libsolidity/NameAndTypeResolver.cpp +++ b/libsolidity/NameAndTypeResolver.cpp @@ -37,7 +37,10 @@ void NameAndTypeResolver::resolveNamesAndTypes(ContractDefinition& _contract) reset(); DeclarationRegistrationHelper registrar(m_scopes, _contract); m_currentScope = &m_scopes[&_contract]; - //@todo structs + for (ASTPointer const& structDef: _contract.getDefinedStructs()) + ReferencesResolver resolver(*structDef, *this, nullptr); + for (ASTPointer const& structDef: _contract.getDefinedStructs()) + checkForRecursion(*structDef); for (ASTPointer const& variable: _contract.getStateVariables()) ReferencesResolver resolver(*variable, *this, nullptr); for (ASTPointer const& function: _contract.getDefinedFunctions()) @@ -70,6 +73,24 @@ Declaration* NameAndTypeResolver::getNameFromCurrentScope(ASTString const& _name return m_currentScope->resolveName(_name, _recursive); } +void NameAndTypeResolver::checkForRecursion(StructDefinition const& _struct) +{ + set definitionsSeen; + vector queue = {&_struct}; + while (!queue.empty()) + { + StructDefinition const* def = queue.back(); + queue.pop_back(); + if (definitionsSeen.count(def)) + BOOST_THROW_EXCEPTION(ParserError() << errinfo_sourceLocation(def->getLocation()) + << errinfo_comment("Recursive struct definition.")); + definitionsSeen.insert(def); + for (ASTPointer const& member: def->getMembers()) + if (member->getType()->getCategory() == Type::Category::STRUCT) + queue.push_back(dynamic_cast(*member->getTypeName()).getReferencedStruct()); + } +} + void NameAndTypeResolver::reset() { m_scopes.clear(); @@ -163,8 +184,8 @@ void DeclarationRegistrationHelper::registerDeclaration(Declaration& _declaratio } ReferencesResolver::ReferencesResolver(ASTNode& _root, NameAndTypeResolver& _resolver, - ParameterList* _returnParameters): - m_resolver(_resolver), m_returnParameters(_returnParameters) + ParameterList* _returnParameters, bool _allowLazyTypes): + m_resolver(_resolver), m_returnParameters(_returnParameters), m_allowLazyTypes(_allowLazyTypes) { _root.accept(*this); } @@ -175,6 +196,8 @@ void ReferencesResolver::endVisit(VariableDeclaration& _variable) // or mapping if (_variable.getTypeName()) _variable.setType(_variable.getTypeName()->toType()); + else if (!m_allowLazyTypes) + BOOST_THROW_EXCEPTION(_variable.createTypeError("Explicit type needed.")); // otherwise we have a "var"-declaration whose type is resolved by the first assignment } diff --git a/libsolidity/NameAndTypeResolver.h b/libsolidity/NameAndTypeResolver.h index 909024942..d335807e5 100644 --- a/libsolidity/NameAndTypeResolver.h +++ b/libsolidity/NameAndTypeResolver.h @@ -55,10 +55,13 @@ public: Declaration* getNameFromCurrentScope(ASTString const& _name, bool _recursive = true); private: + /// Throws if @a _struct contains a recursive loop. Note that recursion via mappings is fine. + void checkForRecursion(StructDefinition const& _struct); void reset(); - /// Maps nodes declaring a scope to scopes, i.e. ContractDefinition, FunctionDeclaration and - /// StructDefinition (@todo not yet implemented), where nullptr denotes the global scope. + /// Maps nodes declaring a scope to scopes, i.e. ContractDefinition and FunctionDeclaration, + /// where nullptr denotes the global scope. Note that structs are not scope since they do + /// not contain code. std::map m_scopes; Scope* m_currentScope; @@ -99,7 +102,8 @@ private: class ReferencesResolver: private ASTVisitor { public: - ReferencesResolver(ASTNode& _root, NameAndTypeResolver& _resolver, ParameterList* _returnParameters); + ReferencesResolver(ASTNode& _root, NameAndTypeResolver& _resolver, + ParameterList* _returnParameters, bool _allowLazyTypes = true); private: virtual void endVisit(VariableDeclaration& _variable) override; @@ -110,6 +114,7 @@ private: NameAndTypeResolver& m_resolver; ParameterList* m_returnParameters; + bool m_allowLazyTypes; }; } diff --git a/libsolidity/Types.cpp b/libsolidity/Types.cpp index e37ed3e5b..63bad5d61 100644 --- a/libsolidity/Types.cpp +++ b/libsolidity/Types.cpp @@ -80,7 +80,7 @@ shared_ptr Type::forLiteral(Literal const& _literal) case Token::NUMBER: return IntegerType::smallestTypeForLiteral(_literal.getValue()); case Token::STRING_LITERAL: - return shared_ptr(); // @todo + return shared_ptr(); // @todo add string literals default: return shared_ptr(); } @@ -231,6 +231,48 @@ u256 StructType::getStorageSize() const return max(1, size); } +bool StructType::canLiveOutsideStorage() const +{ + for (unsigned i = 0; i < getMemberCount(); ++i) + if (!getMemberByIndex(i).getType()->canLiveOutsideStorage()) + return false; + return true; +} + +string StructType::toString() const +{ + return string("struct ") + m_struct.getName(); +} + +unsigned StructType::getMemberCount() const +{ + return m_struct.getMembers().size(); +} + +unsigned StructType::memberNameToIndex(string const& _name) const +{ + vector> const& members = m_struct.getMembers(); + for (unsigned index = 0; index < members.size(); ++index) + if (members[index]->getName() == _name) + return index; + return unsigned(-1); +} + +VariableDeclaration const& StructType::getMemberByIndex(unsigned _index) const +{ + return *m_struct.getMembers()[_index]; +} + +u256 StructType::getStorageOffsetOfMember(unsigned _index) const +{ + //@todo cache member offset? + u256 offset; + vector> const& members = m_struct.getMembers(); + for (unsigned index = 0; index < _index; ++index) + offset += getMemberByIndex(index).getType()->getStorageSize(); + return offset; +} + bool FunctionType::operator==(Type const& _other) const { if (_other.getCategory() != getCategory()) @@ -239,6 +281,12 @@ bool FunctionType::operator==(Type const& _other) const return other.m_function == m_function; } +string FunctionType::toString() const +{ + //@todo nice string for function types + return "function(...)returns(...)"; +} + bool MappingType::operator==(Type const& _other) const { if (_other.getCategory() != getCategory()) @@ -247,6 +295,11 @@ bool MappingType::operator==(Type const& _other) const return *other.m_keyType == *m_keyType && *other.m_valueType == *m_valueType; } +string MappingType::toString() const +{ + return "mapping(" + getKeyType()->toString() + " => " + getValueType()->toString() + ")"; +} + bool TypeType::operator==(Type const& _other) const { if (_other.getCategory() != getCategory()) diff --git a/libsolidity/Types.h b/libsolidity/Types.h index b9bb74dbb..726470172 100644 --- a/libsolidity/Types.h +++ b/libsolidity/Types.h @@ -184,9 +184,14 @@ public: virtual bool operator==(Type const& _other) const override; virtual u256 getStorageSize() const; - //@todo it can, if its members can - virtual bool canLiveOutsideStorage() const { return false; } - virtual std::string toString() const override { return "struct{...}"; } + virtual bool canLiveOutsideStorage() const; + virtual std::string toString() const override; + + unsigned getMemberCount() const; + /// Returns the index of the member with name @a _name or unsigned(-1) if it does not exist. + unsigned memberNameToIndex(std::string const& _name) const; + VariableDeclaration const& getMemberByIndex(unsigned _index) const; + u256 getStorageOffsetOfMember(unsigned _index) const; private: StructDefinition const& m_struct; @@ -204,7 +209,7 @@ public: FunctionDefinition const& getFunction() const { return m_function; } virtual bool operator==(Type const& _other) const override; - virtual std::string toString() const override { return "function(...)returns(...)"; } + virtual std::string toString() const override; virtual u256 getStorageSize() const { BOOST_THROW_EXCEPTION(InternalCompilerError() << errinfo_comment("Storage size of non-storable function type requested.")); } virtual bool canLiveOutsideStorage() const { return false; } @@ -223,11 +228,12 @@ public: m_keyType(_keyType), m_valueType(_valueType) {} virtual bool operator==(Type const& _other) const override; - virtual std::string toString() const override { return "mapping(...=>...)"; } + virtual std::string toString() const override; virtual bool canLiveOutsideStorage() const { return false; } std::shared_ptr getKeyType() const { return m_keyType; } std::shared_ptr getValueType() const { return m_valueType; } + private: std::shared_ptr m_keyType; std::shared_ptr m_valueType; diff --git a/test/solidityEndToEndTest.cpp b/test/solidityEndToEndTest.cpp index 5e6631df6..617cbabc9 100644 --- a/test/solidityEndToEndTest.cpp +++ b/test/solidityEndToEndTest.cpp @@ -663,6 +663,43 @@ BOOST_AUTO_TEST_CASE(multi_level_mapping) testSolidityAgainstCpp(0, f, u256(5), u256(4), u256(0)); } +BOOST_AUTO_TEST_CASE(structs) +{ + char const* sourceCode = "contract test {\n" + " struct s1 {\n" + " uint8 x;\n" + " bool y;\n" + " }\n" + " struct s2 {\n" + " uint32 z;\n" + " s1 s1data;\n" + " mapping(uint8 => s2) recursive;\n" + " }\n" + " s2 data;\n" + " function check() returns (bool ok) {\n" + " return data.z == 1 && data.s1data.x == 2 && \n" + " data.s1data.y == true && \n" + " data.recursive[3].recursive[4].z == 5 && \n" + " data.recursive[4].recursive[3].z == 6 && \n" + " data.recursive[0].s1data.y == false && \n" + " data.recursive[4].z == 9;\n" + " }\n" + " function set() {\n" + " data.z = 1;\n" + " data.s1data.x = 2;\n" + " data.s1data.y = true;\n" + " data.recursive[3].recursive[4].z = 5;\n" + " data.recursive[4].recursive[3].z = 6;\n" + " data.recursive[0].s1data.y = false;\n" + " data.recursive[4].z = 9;\n" + " }\n" + "}\n"; + compileAndRun(sourceCode); + BOOST_CHECK(callContractFunction(0) == bytes({0x00})); + BOOST_CHECK(callContractFunction(1) == bytes()); + BOOST_CHECK(callContractFunction(0) == bytes({0x01})); +} + BOOST_AUTO_TEST_SUITE_END() } diff --git a/test/solidityNameAndTypeResolution.cpp b/test/solidityNameAndTypeResolution.cpp index f46ad6733..930bba0e3 100644 --- a/test/solidityNameAndTypeResolution.cpp +++ b/test/solidityNameAndTypeResolution.cpp @@ -121,6 +121,44 @@ BOOST_AUTO_TEST_CASE(reference_to_later_declaration) BOOST_CHECK_NO_THROW(parseTextAndResolveNames(text)); } +BOOST_AUTO_TEST_CASE(struct_definition_directly_recursive) +{ + char const* text = "contract test {\n" + " struct MyStructName {\n" + " address addr;\n" + " MyStructName x;\n" + " }\n" + "}\n"; + BOOST_CHECK_THROW(parseTextAndResolveNames(text), ParserError); +} + +BOOST_AUTO_TEST_CASE(struct_definition_indirectly_recursive) +{ + char const* text = "contract test {\n" + " struct MyStructName1 {\n" + " address addr;\n" + " uint256 count;\n" + " MyStructName2 x;\n" + " }\n" + " struct MyStructName2 {\n" + " MyStructName1 x;\n" + " }\n" + "}\n"; + BOOST_CHECK_THROW(parseTextAndResolveNames(text), ParserError); +} + +BOOST_AUTO_TEST_CASE(struct_definition_recursion_via_mapping) +{ + char const* text = "contract test {\n" + " struct MyStructName1 {\n" + " address addr;\n" + " uint256 count;\n" + " mapping(uint => MyStructName1) x;\n" + " }\n" + "}\n"; + BOOST_CHECK_NO_THROW(parseTextAndResolveNames(text)); +} + BOOST_AUTO_TEST_CASE(type_inference_smoke_test) { char const* text = "contract test {\n" From 64044e71a5ecc26f767e683540b82fbcd87e11eb Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Fri, 14 Nov 2014 14:21:02 +0100 Subject: [PATCH 17/38] common changes after merge --- libweb3jsonrpc/WebThreeStubServer.cpp | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 22e871559..c0c50f9bd 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -531,8 +531,7 @@ std::string WebThreeStubServer::eth_lll(std::string const& _code) std::string WebThreeStubServer::eth_solidity(std::string const& _code) { - shared_ptr scanner = make_shared(); - return toJS(dev::solidity::CompilerStack::compile(_code, scanner)); + return toJS(dev::solidity::CompilerStack::staticCompile(_code, false)); } int WebThreeStubServer::eth_number() From ecf4ede0308a3bb7cc8a970e638c16b4dafc5aef Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Sun, 16 Nov 2014 22:00:41 +0100 Subject: [PATCH 18/38] Clean up Alex's Windows mess :-P --- windows/LibEthereum.vcxproj | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/windows/LibEthereum.vcxproj b/windows/LibEthereum.vcxproj index 0578a8f16..06f868023 100644 --- a/windows/LibEthereum.vcxproj +++ b/windows/LibEthereum.vcxproj @@ -68,14 +68,14 @@ true + - + - @@ -568,4 +568,4 @@ - \ No newline at end of file + From 0f7e159df48eea17819fda72471d4c416ce132d8 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Sun, 16 Nov 2014 22:35:14 +0100 Subject: [PATCH 19/38] Brain-dead MSVC strikes again. --- libdevcrypto/ECDHE.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libdevcrypto/ECDHE.cpp b/libdevcrypto/ECDHE.cpp index dd72e8176..deae3bc6d 100644 --- a/libdevcrypto/ECDHE.cpp +++ b/libdevcrypto/ECDHE.cpp @@ -76,7 +76,7 @@ void ECDHEKeyExchange::exchange(bytes& o_exchange) memcpy(&exchange[exchange.size() - sizeof(p)], p.data(), sizeof(p)); // protocol parameters; should be fixed size - bytes v({0x80}); + bytes v(1, 0x80); exchange.resize(exchange.size() + v.size()); memcpy(&exchange[exchange.size() - v.size()], v.data(), v.size()); From 6af670af27f74e9cb5c8566d1e5a226adbd7bfb6 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Sun, 16 Nov 2014 23:02:53 +0100 Subject: [PATCH 20/38] Windows build fix. --- test/crypto.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/crypto.cpp b/test/crypto.cpp index d8bd25035..08236135a 100644 --- a/test/crypto.cpp +++ b/test/crypto.cpp @@ -139,7 +139,7 @@ BOOST_AUTO_TEST_CASE(cryptopp_ecdsa_sipaseckp256k1) Secret secret(sha3(sbytes)); KeyPair key(secret); - bytes m({0xFF}); + bytes m(1, 0xff); int tests = 2; while (m[0]++, tests--) { From 3ba250c61ff3a5755c8433362a8f93792fbce1ad Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 17 Nov 2014 13:13:18 +0100 Subject: [PATCH 21/38] fixed #502 --- libweb3jsonrpc/WebThreeStubServer.cpp | 83 +++++++++++++++++---------- 1 file changed, 53 insertions(+), 30 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 256f6d564..9526b2f9b 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -131,28 +131,34 @@ static dev::eth::MessageFilter toMessageFilter(Json::Value const& _json) if (!_json.isObject() || _json.empty()) return filter; - if (!_json["earliest"].empty()) + if (_json["earliest"].isInt()) filter.withEarliest(_json["earliest"].asInt()); - if (!_json["latest"].empty()) + if (_json["latest"].isInt()) filter.withLatest(_json["lastest"].asInt()); - if (!_json["max"].empty()) + if (_json["max"].isInt()) filter.withMax(_json["max"].asInt()); - if (!_json["skip"].empty()) + if (_json["skip"].isInt()) filter.withSkip(_json["skip"].asInt()); if (!_json["from"].empty()) { if (_json["from"].isArray()) + { for (auto i : _json["from"]) - filter.from(jsToAddress(i.asString())); - else + if (i.isString()) + filter.from(jsToAddress(i.asString())); + } + else if (_json["from"].isString()) filter.from(jsToAddress(_json["from"].asString())); } if (!_json["to"].empty()) { if (_json["to"].isArray()) + { for (auto i : _json["to"]) - filter.to(jsToAddress(i.asString())); - else + if (i.isString()) + filter.to(jsToAddress(i.asString())); + } + else if (_json["to"].isString()) filter.to(jsToAddress(_json["to"].asString())); } if (!_json["altered"].empty()) @@ -177,28 +183,34 @@ static dev::eth::MessageFilter toMessageFilter(Json::Value const& _json) if (!_json.isObject() || _json.empty()) return filter; - if (!_json["earliest"].empty()) + if (_json["earliest"].isInt()) filter.withEarliest(_json["earliest"].asInt()); - if (!_json["latest"].empty()) + if (_json["latest"].isInt()) filter.withLatest(_json["lastest"].asInt()); - if (!_json["max"].empty()) + if (_json["max"].isInt()) filter.withMax(_json["max"].asInt()); - if (!_json["skip"].empty()) + if (_json["skip"].isInt()) filter.withSkip(_json["skip"].asInt()); if (!_json["from"].empty()) { if (_json["from"].isArray()) + { for (auto i : _json["from"]) - filter.from(jsToAddress(i.asString())); - else + if (i.isString()) + filter.from(jsToAddress(i.asString())); + } + else if (_json["from"].isString()) filter.from(jsToAddress(_json["from"].asString())); } if (!_json["address"].empty()) { if (_json["address"].isArray()) + { for (auto i : _json["address"]) - filter.address(jsToAddress(i.asString())); - else + if (i.isString()) + filter.address(jsToAddress(i.asString())); + } + else if (_json["address"].isString()) filter.from(jsToAddress(_json["address"].asString())); } if (!_json["topics"].empty()) @@ -218,11 +230,11 @@ static dev::eth::MessageFilter toMessageFilter(Json::Value const& _json) static shh::Message toMessage(Json::Value const& _json) { shh::Message ret; - if (!_json["from"].empty()) + if (_json["from"].isString()) ret.setFrom(jsToPublic(_json["from"].asString())); - if (!_json["to"].empty()) + if (_json["to"].isString()) ret.setTo(jsToPublic(_json["to"].asString())); - if (!_json["payload"].empty()) + if (_json["payload"].isString()) ret.setPayload(jsToBytes(_json["payload"].asString())); return ret; } @@ -233,9 +245,9 @@ static shh::Envelope toSealed(Json::Value const& _json, shh::Message const& _m, unsigned workToProve = 50; shh::BuildTopic bt; - if (!_json["ttl"].empty()) + if (_json["ttl"].isInt()) ttl = _json["ttl"].asInt(); - if (!_json["workToProve"].empty()) + if (_json["workToProve"].isInt()) workToProve = _json["workToProve"].asInt(); if (!_json["topic"].empty()) { @@ -243,7 +255,8 @@ static shh::Envelope toSealed(Json::Value const& _json, shh::Message const& _m, bt.shift(jsToBytes(_json["topic"].asString())); else if (_json["topic"].isArray()) for (auto i: _json["topic"]) - bt.shift(jsToBytes(i.asString())); + if (i.isString()) + bt.shift(jsToBytes(i.asString())); } return _m.seal(_from, bt, ttl, workToProve); } @@ -253,7 +266,7 @@ static pair toWatch(Json::Value const& _json) shh::BuildTopicMask bt; Public to; - if (!_json["to"].empty()) + if (_json["to"].isString()) to = jsToPublic(_json["to"].asString()); if (!_json["topic"].empty()) @@ -361,19 +374,29 @@ static TransactionSkeleton toTransaction(Json::Value const& _json) if (!_json.isObject() || _json.empty()) return ret; - if (!_json["from"].empty()) + if (_json["from"].isString()) ret.from = jsToAddress(_json["from"].asString()); - if (!_json["to"].empty()) + if (_json["to"].isString()) ret.to = jsToAddress(_json["to"].asString()); - if (!_json["value"].empty()) + if (_json["value"].isString()) ret.value = jsToU256(_json["value"].asString()); if (!_json["gas"].empty()) - ret.gas = jsToU256(_json["gas"].asString()); + { + if (_json["gas"].isString()) + ret.gas = jsToU256(_json["gas"].asString()); + else if (_json["gas"].isInt()) + ret.gas = u256(_json["gas"].asInt()); + } if (!_json["gasPrice"].empty()) - ret.gasPrice = jsToU256(_json["gasPrice"].asString()); - if (!_json["data"].empty() && _json["data"].isString()) + { + if (_json["gasPrice"].isString()) + ret.gasPrice = jsToU256(_json["gasPrice"].asString()); + else if (_json["gasPrice"].isInt()) + ret.gas = u256(_json["gas"].asInt()); + } + if (_json["data"].isString()) ret.data = jsToBytes(_json["data"].asString()); - else if (!_json["code"].empty() && _json["code"].isString()) + else if (_json["code"].isString()) ret.data = jsToBytes(_json["code"].asString()); return ret; } From 4c4dd302f27404997f0b7b2c62e994d65fb843f1 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 17 Nov 2014 14:04:57 +0100 Subject: [PATCH 22/38] ethereum.js not minified, serpent compiler, jsonrpc handles compilers exceptions --- libjsqrc/ethereum.js | 1034 +++++++++++++++++++ libjsqrc/ethereum.min.js | 1 - libjsqrc/js.qrc | 2 +- libweb3jsonrpc/CMakeLists.txt | 1 + libweb3jsonrpc/WebThreeStubServer.cpp | 45 +- libweb3jsonrpc/WebThreeStubServer.h | 1 + libweb3jsonrpc/abstractwebthreestubserver.h | 7 + libweb3jsonrpc/spec.json | 1 + test/webthreestubclient.h | 13 + 9 files changed, 1101 insertions(+), 4 deletions(-) create mode 100644 libjsqrc/ethereum.js delete mode 100644 libjsqrc/ethereum.min.js diff --git a/libjsqrc/ethereum.js b/libjsqrc/ethereum.js new file mode 100644 index 000000000..e65489a66 --- /dev/null +++ b/libjsqrc/ethereum.js @@ -0,0 +1,1034 @@ +require=(function e(t,n,r){function s(o,u){if(!n[o]){if(!t[o]){var a=typeof require=="function"&&require;if(!u&&a)return a(o,!0);if(i)return i(o,!0);var f=new Error("Cannot find module '"+o+"'");throw f.code="MODULE_NOT_FOUND",f}var l=n[o]={exports:{}};t[o][0].call(l.exports,function(e){var n=t[o][1][e];return s(n?n:e)},l,l.exports,e,t,n,r)}return n[o].exports}var i=typeof require=="function"&&require;for(var o=0;o. +*/ +/** @file abi.js + * @authors: + * Marek Kotewicz + * @date 2014 + */ + +var findIndex = function (array, callback) { + var end = false; + var i = 0; + for (; i < array.length && !end; i++) { + end = callback(array[i]); + } + return end ? i - 1 : -1; +}; + +var findMethodIndex = function (json, methodName) { + return findIndex(json, function (method) { + return method.name === methodName; + }); +}; + +var padLeft = function (number, n) { + return (new Array(n * 2 - number.toString().length + 1)).join("0") + number; +}; + +var setupInputTypes = function () { + var prefixedType = function (prefix) { + return function (type, value) { + var expected = prefix; + if (type.indexOf(expected) !== 0) { + return false; + } + + var padding = parseInt(type.slice(expected.length)) / 8; + return padLeft(value, padding); + }; + }; + + var namedType = function (name, padding, formatter) { + return function (type, value) { + if (type !== name) { + return false; + } + + return padLeft(formatter ? value : formatter(value), padding); + }; + }; + + var formatBool = function (value) { + return value ? '1' : '0'; + }; + + return [ + prefixedType('uint'), + prefixedType('int'), + namedType('address', 20), + namedType('bool', 1, formatBool), + ]; +}; + +var inputTypes = setupInputTypes(); + +var toAbiInput = function (json, methodName, params) { + var bytes = ""; + var index = findMethodIndex(json, methodName); + + if (index === -1) { + return; + } + + // it needs to be checked in WebThreeStubServer + // something wrong might be with this additional zero + bytes = bytes + index + 'x' + '0'; + var method = json[index]; + + for (var i = 0; i < method.inputs.length; i++) { + var found = false; + for (var j = 0; j < inputTypes.length && !found; j++) { + var val = parseInt(params[i]).toString(16); + found = inputTypes[j](method.inputs[i].type, val); + } + if (!found) { + console.error('unsupported json type: ' + method.inputs[i].type); + } + bytes += found; + } + return bytes; +}; + +var setupOutputTypes = function () { + var prefixedType = function (prefix) { + return function (type) { + var expected = prefix; + if (type.indexOf(expected) !== 0) { + return -1; + } + + var padding = parseInt(type.slice(expected.length)) / 8; + return padding * 2; + }; + }; + + var namedType = function (name, padding) { + return function (type) { + return name === type ? padding * 2: -1; + }; + }; + + var formatInt = function (value) { + return parseInt(value, 16); + }; + + var formatBool = function (value) { + return value === '1' ? true : false; + }; + + return [ + { padding: prefixedType('uint'), format: formatInt }, + { padding: prefixedType('int'), format: formatInt }, + { padding: namedType('address', 20) }, + { padding: namedType('bool', 1), format: formatBool } + ]; +}; + +var outputTypes = setupOutputTypes(); + +var fromAbiOutput = function (json, methodName, output) { + var index = findMethodIndex(json, methodName); + + if (index === -1) { + return; + } + + output = output.slice(2); + + var result = []; + var method = json[index]; + for (var i = 0; i < method.outputs.length; i++) { + var padding = -1; + for (var j = 0; j < outputTypes.length && padding === -1; j++) { + padding = outputTypes[j].padding(method.outputs[i].type); + } + + if (padding === -1) { + // not found output parsing + continue; + } + var res = output.slice(0, padding); + var formatter = outputTypes[j - 1].format; + result.push(formatter ? formatter(res): res); + output = output.slice(padding); + } + + return result; +}; + +var inputParser = function (json) { + var parser = {}; + json.forEach(function (method) { + parser[method.name] = function () { + var params = Array.prototype.slice.call(arguments); + return toAbiInput(json, method.name, params); + }; + }); + + return parser; +}; + +var outputParser = function (json) { + var parser = {}; + json.forEach(function (method) { + parser[method.name] = function (output) { + return fromAbiOutput(json, method.name, output); + }; + }); + + return parser; +}; + +module.exports = { + inputParser: inputParser, + outputParser: outputParser +}; + + +},{}],2:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ +/** @file websocket.js + * @authors: + * Marek Kotewicz + * Marian Oancea + * @date 2014 + */ + +/* + * @brief if qt object is available, uses QtProvider, + * if not tries to connect over websockets + * if it fails, it uses HttpRpcProvider + */ +if ("build" !== 'build') {/* + var WebSocket = require('ws'); // jshint ignore:line + var web3 = require('./web3'); // jshint ignore:line +*/} + +var AutoProvider = function (userOptions) { + if (web3.haveProvider()) { + return; + } + + // before we determine what provider we are, we have to cache request + this.sendQueue = []; + this.onmessageQueue = []; + + if (navigator.qt) { + this.provider = new web3.providers.QtProvider(); + return; + } + + userOptions = userOptions || {}; + var options = { + httprpc: userOptions.httprpc || 'http://localhost:8080', + websockets: userOptions.websockets || 'ws://localhost:40404/eth' + }; + + var self = this; + var closeWithSuccess = function (success) { + ws.close(); + if (success) { + self.provider = new web3.providers.WebSocketProvider(options.websockets); + } else { + self.provider = new web3.providers.HttpRpcProvider(options.httprpc); + self.poll = self.provider.poll.bind(self.provider); + } + self.sendQueue.forEach(function (payload) { + self.provider(payload); + }); + self.onmessageQueue.forEach(function (handler) { + self.provider.onmessage = handler; + }); + }; + + var ws = new WebSocket(options.websockets); + + ws.onopen = function() { + closeWithSuccess(true); + }; + + ws.onerror = function() { + closeWithSuccess(false); + }; +}; + +AutoProvider.prototype.send = function (payload) { + if (this.provider) { + this.provider.send(payload); + return; + } + this.sendQueue.push(payload); +}; + +Object.defineProperty(AutoProvider.prototype, 'onmessage', { + set: function (handler) { + if (this.provider) { + this.provider.onmessage = handler; + return; + } + this.onmessageQueue.push(handler); + } +}); + +module.exports = AutoProvider; + +},{}],3:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ +/** @file httprpc.js + * @authors: + * Marek Kotewicz + * Marian Oancea + * @date 2014 + */ + +if ("build" !== "build") {/* + var XMLHttpRequest = require('xmlhttprequest').XMLHttpRequest; // jshint ignore:line +*/} + +var HttpRpcProvider = function (host) { + this.handlers = []; + this.host = host; +}; + +function formatJsonRpcObject(object) { + return { + jsonrpc: '2.0', + method: object.call, + params: object.args, + id: object._id + }; +} + +function formatJsonRpcMessage(message) { + var object = JSON.parse(message); + + return { + _id: object.id, + data: object.result, + error: object.error + }; +} + +HttpRpcProvider.prototype.sendRequest = function (payload, cb) { + var data = formatJsonRpcObject(payload); + + var request = new XMLHttpRequest(); + request.open("POST", this.host, true); + request.send(JSON.stringify(data)); + request.onreadystatechange = function () { + if (request.readyState === 4 && cb) { + cb(request); + } + }; +}; + +HttpRpcProvider.prototype.send = function (payload) { + var self = this; + this.sendRequest(payload, function (request) { + self.handlers.forEach(function (handler) { + handler.call(self, formatJsonRpcMessage(request.responseText)); + }); + }); +}; + +HttpRpcProvider.prototype.poll = function (payload, id) { + var self = this; + this.sendRequest(payload, function (request) { + var parsed = JSON.parse(request.responseText); + if (parsed.error || (parsed.result instanceof Array ? parsed.result.length === 0 : !parsed.result)) { + return; + } + self.handlers.forEach(function (handler) { + handler.call(self, {_event: payload.call, _id: id, data: parsed.result}); + }); + }); +}; + +Object.defineProperty(HttpRpcProvider.prototype, "onmessage", { + set: function (handler) { + this.handlers.push(handler); + } +}); + +module.exports = HttpRpcProvider; + +},{}],4:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ +/** @file main.js + * @authors: + * Jeffrey Wilcke + * Marek Kotewicz + * Marian Oancea + * @date 2014 + */ + +var abi = require('./abi'); + +function flattenPromise (obj) { + if (obj instanceof Promise) { + return Promise.resolve(obj); + } + + if (obj instanceof Array) { + return new Promise(function (resolve) { + var promises = obj.map(function (o) { + return flattenPromise(o); + }); + + return Promise.all(promises).then(function (res) { + for (var i = 0; i < obj.length; i++) { + obj[i] = res[i]; + } + resolve(obj); + }); + }); + } + + if (obj instanceof Object) { + return new Promise(function (resolve) { + var keys = Object.keys(obj); + var promises = keys.map(function (key) { + return flattenPromise(obj[key]); + }); + + return Promise.all(promises).then(function (res) { + for (var i = 0; i < keys.length; i++) { + obj[keys[i]] = res[i]; + } + resolve(obj); + }); + }); + } + + return Promise.resolve(obj); +} + +var ethMethods = function () { + var blockCall = function (args) { + return typeof args[0] === "string" ? "eth_blockByHash" : "eth_blockByNumber"; + }; + + var transactionCall = function (args) { + return typeof args[0] === "string" ? 'eth_transactionByHash' : 'eth_transactionByNumber'; + }; + + var uncleCall = function (args) { + return typeof args[0] === "string" ? 'eth_uncleByHash' : 'eth_uncleByNumber'; + }; + + var methods = [ + { name: 'balanceAt', call: 'eth_balanceAt' }, + { name: 'stateAt', call: 'eth_stateAt' }, + { name: 'storageAt', call: 'eth_storageAt' }, + { name: 'countAt', call: 'eth_countAt'}, + { name: 'codeAt', call: 'eth_codeAt' }, + { name: 'transact', call: 'eth_transact' }, + { name: 'call', call: 'eth_call' }, + { name: 'block', call: blockCall }, + { name: 'transaction', call: transactionCall }, + { name: 'uncle', call: uncleCall }, + { name: 'compilers', call: 'eth_compilers' }, + { name: 'lll', call: 'eth_lll' }, + { name: 'solidity', call: 'eth_solidity' }, + { name: 'serpent', call: 'eth_serpent' } + ]; + return methods; +}; + +var ethProperties = function () { + return [ + { name: 'coinbase', getter: 'eth_coinbase', setter: 'eth_setCoinbase' }, + { name: 'listening', getter: 'eth_listening', setter: 'eth_setListening' }, + { name: 'mining', getter: 'eth_mining', setter: 'eth_setMining' }, + { name: 'gasPrice', getter: 'eth_gasPrice' }, + { name: 'account', getter: 'eth_account' }, + { name: 'accounts', getter: 'eth_accounts' }, + { name: 'peerCount', getter: 'eth_peerCount' }, + { name: 'defaultBlock', getter: 'eth_defaultBlock', setter: 'eth_setDefaultBlock' }, + { name: 'number', getter: 'eth_number'} + ]; +}; + +var dbMethods = function () { + return [ + { name: 'put', call: 'db_put' }, + { name: 'get', call: 'db_get' }, + { name: 'putString', call: 'db_putString' }, + { name: 'getString', call: 'db_getString' } + ]; +}; + +var shhMethods = function () { + return [ + { name: 'post', call: 'shh_post' }, + { name: 'newIdentity', call: 'shh_newIdentity' }, + { name: 'haveIdentity', call: 'shh_haveIdentity' }, + { name: 'newGroup', call: 'shh_newGroup' }, + { name: 'addToGroup', call: 'shh_addToGroup' } + ]; +}; + +var ethWatchMethods = function () { + var newFilter = function (args) { + return typeof args[0] === 'string' ? 'eth_newFilterString' : 'eth_newFilter'; + }; + + return [ + { name: 'newFilter', call: newFilter }, + { name: 'uninstallFilter', call: 'eth_uninstallFilter' }, + { name: 'getMessages', call: 'eth_getMessages' } + ]; +}; + +var shhWatchMethods = function () { + return [ + { name: 'newFilter', call: 'shh_newFilter' }, + { name: 'uninstallFilter', call: 'shh_uninstallFilter' }, + { name: 'getMessage', call: 'shh_getMessages' } + ]; +}; + +var setupMethods = function (obj, methods) { + methods.forEach(function (method) { + obj[method.name] = function () { + return flattenPromise(Array.prototype.slice.call(arguments)).then(function (args) { + var call = typeof method.call === "function" ? method.call(args) : method.call; + return {call: call, args: args}; + }).then(function (request) { + return new Promise(function (resolve, reject) { + web3.provider.send(request, function (err, result) { + if (!err) { + resolve(result); + return; + } + reject(err); + }); + }); + }).catch(function(err) { + console.error(err); + }); + }; + }); +}; + +var setupProperties = function (obj, properties) { + properties.forEach(function (property) { + var proto = {}; + proto.get = function () { + return new Promise(function(resolve, reject) { + web3.provider.send({call: property.getter}, function(err, result) { + if (!err) { + resolve(result); + return; + } + reject(err); + }); + }); + }; + if (property.setter) { + proto.set = function (val) { + return flattenPromise([val]).then(function (args) { + return new Promise(function (resolve) { + web3.provider.send({call: property.setter, args: args}, function (err, result) { + if (!err) { + resolve(result); + return; + } + reject(err); + }); + }); + }).catch(function (err) { + console.error(err); + }); + }; + } + Object.defineProperty(obj, property.name, proto); + }); +}; + +var web3 = { + _callbacks: {}, + _events: {}, + providers: {}, + toHex: function(str) { + var hex = ""; + for(var i = 0; i < str.length; i++) { + var n = str.charCodeAt(i).toString(16); + hex += n.length < 2 ? '0' + n : n; + } + + return hex; + }, + + toAscii: function(hex) { + // Find termination + var str = ""; + var i = 0, l = hex.length; + if (hex.substring(0, 2) === '0x') + i = 2; + for(; i < l; i+=2) { + var code = hex.charCodeAt(i); + if(code === 0) { + break; + } + + str += String.fromCharCode(parseInt(hex.substr(i, 2), 16)); + } + + return str; + }, + + toDecimal: function (val) { + return parseInt(val, 16); + }, + + fromAscii: function(str, pad) { + pad = pad === undefined ? 32 : pad; + var hex = this.toHex(str); + while(hex.length < pad*2) + hex += "00"; + return "0x" + hex; + }, + + eth: { + prototype: Object(), // jshint ignore:line + watch: function (params) { + return new Filter(params, ethWatch); + } + }, + + db: { + prototype: Object() // jshint ignore:line + }, + + shh: { + prototype: Object(), // jshint ignore:line + watch: function (params) { + return new Filter(params, shhWatch); + } + }, + + on: function(event, id, cb) { + if(web3._events[event] === undefined) { + web3._events[event] = {}; + } + + web3._events[event][id] = cb; + return this; + }, + + off: function(event, id) { + if(web3._events[event] !== undefined) { + delete web3._events[event][id]; + } + + return this; + }, + + trigger: function(event, id, data) { + var callbacks = web3._events[event]; + if (!callbacks || !callbacks[id]) { + return; + } + var cb = callbacks[id]; + cb(data); + } +}; + +setupMethods(web3.eth, ethMethods()); +setupProperties(web3.eth, ethProperties()); +setupMethods(web3.db, dbMethods()); +setupMethods(web3.shh, shhMethods()); + +var ethWatch = { + changed: 'eth_changed' +}; +setupMethods(ethWatch, ethWatchMethods()); +var shhWatch = { + changed: 'shh_changed' +}; +setupMethods(shhWatch, shhWatchMethods()); + +var ProviderManager = function() { + this.queued = []; + this.polls = []; + this.ready = false; + this.provider = undefined; + this.id = 1; + + var self = this; + var poll = function () { + if (self.provider && self.provider.poll) { + self.polls.forEach(function (data) { + data.data._id = self.id; + self.id++; + self.provider.poll(data.data, data.id); + }); + } + setTimeout(poll, 12000); + }; + poll(); +}; + +ProviderManager.prototype.send = function(data, cb) { + data._id = this.id; + if (cb) { + web3._callbacks[data._id] = cb; + } + + data.args = data.args || []; + this.id++; + + if(this.provider !== undefined) { + this.provider.send(data); + } else { + console.warn("provider is not set"); + this.queued.push(data); + } +}; + +ProviderManager.prototype.set = function(provider) { + if(this.provider !== undefined && this.provider.unload !== undefined) { + this.provider.unload(); + } + + this.provider = provider; + this.ready = true; +}; + +ProviderManager.prototype.sendQueued = function() { + for(var i = 0; this.queued.length; i++) { + // Resend + this.send(this.queued[i]); + } +}; + +ProviderManager.prototype.installed = function() { + return this.provider !== undefined; +}; + +ProviderManager.prototype.startPolling = function (data, pollId) { + if (!this.provider || !this.provider.poll) { + return; + } + this.polls.push({data: data, id: pollId}); +}; + +ProviderManager.prototype.stopPolling = function (pollId) { + for (var i = this.polls.length; i--;) { + var poll = this.polls[i]; + if (poll.id === pollId) { + this.polls.splice(i, 1); + } + } +}; + +web3.provider = new ProviderManager(); + +web3.setProvider = function(provider) { + provider.onmessage = messageHandler; + web3.provider.set(provider); + web3.provider.sendQueued(); +}; + +web3.haveProvider = function() { + return !!web3.provider.provider; +}; + +var Filter = function(options, impl) { + this.impl = impl; + this.callbacks = []; + + var self = this; + this.promise = impl.newFilter(options); + this.promise.then(function (id) { + self.id = id; + web3.on(impl.changed, id, self.trigger.bind(self)); + web3.provider.startPolling({call: impl.changed, args: [id]}, id); + }); +}; + +Filter.prototype.arrived = function(callback) { + this.changed(callback); +}; + +Filter.prototype.changed = function(callback) { + var self = this; + this.promise.then(function(id) { + self.callbacks.push(callback); + }); +}; + +Filter.prototype.trigger = function(messages) { + for(var i = 0; i < this.callbacks.length; i++) { + this.callbacks[i].call(this, messages); + } +}; + +Filter.prototype.uninstall = function() { + var self = this; + this.promise.then(function (id) { + self.impl.uninstallFilter(id); + web3.provider.stopPolling(id); + web3.off(impl.changed, id); + }); +}; + +Filter.prototype.messages = function() { + var self = this; + return this.promise.then(function (id) { + return self.impl.getMessages(id); + }); +}; + +function messageHandler(data) { + if(data._event !== undefined) { + web3.trigger(data._event, data._id, data.data); + return; + } + + if(data._id) { + var cb = web3._callbacks[data._id]; + if (cb) { + cb.call(this, data.error, data.data); + delete web3._callbacks[data._id]; + } + } +} + +web3.contract = function (address, desc) { + var inputParser = abi.inputParser(desc); + var outputParser = abi.outputParser(desc); + + var contract = {}; + + desc.forEach(function (method) { + contract[method.name] = function () { + var params = Array.prototype.slice.call(arguments); + var parsed = inputParser[method.name].apply(null, params); + + var onSuccess = function (result) { + return outputParser[method.name](result); + }; + + return { + call: function (extra) { + extra = extra || {}; + extra.to = address; + extra.data = parsed; + return web3.eth.call(extra).then(onSuccess); + }, + transact: function (extra) { + extra = extra || {}; + extra.to = address; + extra.data = parsed; + return web3.eth.transact(extra).then(onSuccess); + } + }; + }; + }); + + return contract; +}; + +module.exports = web3; + + +},{"./abi":1}],5:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ +/** @file qt.js + * @authors: + * Jeffrey Wilcke + * Marek Kotewicz + * @date 2014 + */ + +var QtProvider = function() { + this.handlers = []; + + var self = this; + navigator.qt.onmessage = function (message) { + self.handlers.forEach(function (handler) { + handler.call(self, JSON.parse(message.data)); + }); + }; +}; + +QtProvider.prototype.send = function(payload) { + navigator.qt.postMessage(JSON.stringify(payload)); +}; + +Object.defineProperty(QtProvider.prototype, "onmessage", { + set: function(handler) { + this.handlers.push(handler); + } +}); + +module.exports = QtProvider; + +},{}],6:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ +/** @file websocket.js + * @authors: + * Jeffrey Wilcke + * Marek Kotewicz + * Marian Oancea + * @date 2014 + */ + +if ("build" !== "build") {/* + var WebSocket = require('ws'); // jshint ignore:line +*/} + +var WebSocketProvider = function(host) { + // onmessage handlers + this.handlers = []; + // queue will be filled with messages if send is invoked before the ws is ready + this.queued = []; + this.ready = false; + + this.ws = new WebSocket(host); + + var self = this; + this.ws.onmessage = function(event) { + for(var i = 0; i < self.handlers.length; i++) { + self.handlers[i].call(self, JSON.parse(event.data), event); + } + }; + + this.ws.onopen = function() { + self.ready = true; + + for(var i = 0; i < self.queued.length; i++) { + // Resend + self.send(self.queued[i]); + } + }; +}; + +WebSocketProvider.prototype.send = function(payload) { + if(this.ready) { + var data = JSON.stringify(payload); + + this.ws.send(data); + } else { + this.queued.push(payload); + } +}; + +WebSocketProvider.prototype.onMessage = function(handler) { + this.handlers.push(handler); +}; + +WebSocketProvider.prototype.unload = function() { + this.ws.close(); +}; +Object.defineProperty(WebSocketProvider.prototype, "onmessage", { + set: function(provider) { this.onMessage(provider); } +}); + +module.exports = WebSocketProvider; + +},{}],"web3":[function(require,module,exports){ +var web3 = require('./lib/main'); +web3.providers.WebSocketProvider = require('./lib/websocket'); +web3.providers.HttpRpcProvider = require('./lib/httprpc'); +web3.providers.QtProvider = require('./lib/qt'); +web3.providers.AutoProvider = require('./lib/autoprovider'); + +module.exports = web3; + +},{"./lib/autoprovider":2,"./lib/httprpc":3,"./lib/main":4,"./lib/qt":5,"./lib/websocket":6}]},{},[]) + + +//# sourceMappingURL=ethereum.js.map \ No newline at end of file diff --git a/libjsqrc/ethereum.min.js b/libjsqrc/ethereum.min.js deleted file mode 100644 index b23886cab..000000000 --- a/libjsqrc/ethereum.min.js +++ /dev/null @@ -1 +0,0 @@ -require=function t(e,n,r){function o(s,a){if(!n[s]){if(!e[s]){var u="function"==typeof require&&require;if(!a&&u)return u(s,!0);if(i)return i(s,!0);var c=new Error("Cannot find module '"+s+"'");throw c.code="MODULE_NOT_FOUND",c}var l=n[s]={exports:{}};e[s][0].call(l.exports,function(t){var n=e[s][1][t];return o(n?n:t)},l,l.exports,t,e,n,r)}return n[s].exports}for(var i="function"==typeof require&&require,s=0;sr&&(e=t.charCodeAt(r),0!==e);r+=2)n+=String.fromCharCode(parseInt(t.substr(r,2),16));return n},toDecimal:function(t){return parseInt(t,16)},fromAscii:function(t,e){e=void 0===e?32:e;for(var n=this.toHex(t);n.length<2*e;)n+="00";return"0x"+n},eth:{prototype:Object(),watch:function(t){return new a(t,o)}},db:{prototype:Object()},shh:{prototype:Object(),watch:function(t){return new a(t,i)}},on:function(t,e,n){return void 0===m._events[t]&&(m._events[t]={}),m._events[t][e]=n,this},off:function(t,e){return void 0!==m._events[t]&&delete m._events[t][e],this},trigger:function(t,e,n){var r,o=m._events[t];o&&o[e]&&(r=o[e])(n)}};v(m.eth,c()),g(m.eth,l()),v(m.db,h()),v(m.shh,p()),o={changed:"eth_changed"},v(o,d()),i={changed:"shh_changed"},v(i,f()),s=function(){var t,e;this.queued=[],this.polls=[],this.ready=!1,this.provider=void 0,this.id=1,t=this,(e=function(){t.provider&&t.provider.poll&&t.polls.forEach(function(e){e.data._id=t.id,t.id++,t.provider.poll(e.data,e.id)}),setTimeout(e,12e3)})()},s.prototype.send=function(t,e){t._id=this.id,e&&(m._callbacks[t._id]=e),t.args=t.args||[],this.id++,void 0!==this.provider?this.provider.send(t):(console.warn("provider is not set"),this.queued.push(t))},s.prototype.set=function(t){void 0!==this.provider&&void 0!==this.provider.unload&&this.provider.unload(),this.provider=t,this.ready=!0},s.prototype.sendQueued=function(){for(var t=0;this.queued.length;t++)this.send(this.queued[t])},s.prototype.installed=function(){return void 0!==this.provider},s.prototype.startPolling=function(t,e){this.provider&&this.provider.poll&&this.polls.push({data:t,id:e})},s.prototype.stopPolling=function(t){var e,n;for(e=this.polls.length;e--;)n=this.polls[e],n.id===t&&this.polls.splice(e,1)},m.provider=new s,m.setProvider=function(t){t.onmessage=r,m.provider.set(t),m.provider.sendQueued()},m.haveProvider=function(){return!!m.provider.provider},a=function(t,e){this.impl=e,this.callbacks=[];var n=this;this.promise=e.newFilter(t),this.promise.then(function(t){n.id=t,m.on(e.changed,t,n.trigger.bind(n)),m.provider.startPolling({call:e.changed,args:[t]},t)})},a.prototype.arrived=function(t){this.changed(t)},a.prototype.changed=function(t){var e=this;this.promise.then(function(){e.callbacks.push(t)})},a.prototype.trigger=function(t){for(var e=0;e es6-promise-2.0.0.js setup.js - ethereum.min.js + ethereum.js diff --git a/libweb3jsonrpc/CMakeLists.txt b/libweb3jsonrpc/CMakeLists.txt index 2f2219461..0c6afd2b1 100644 --- a/libweb3jsonrpc/CMakeLists.txt +++ b/libweb3jsonrpc/CMakeLists.txt @@ -19,6 +19,7 @@ target_link_libraries(${EXECUTABLE} webthree) target_link_libraries(${EXECUTABLE} secp256k1) target_link_libraries(${EXECUTABLE} gmp) target_link_libraries(${EXECUTABLE} solidity) +target_link_libraries(${EXECUTABLE} serpent) if(MINIUPNPC_LS) target_link_libraries(${EXECUTABLE} ${MINIUPNPC_LS}) endif() diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 9526b2f9b..ecbbacba7 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -33,6 +33,8 @@ #include #include #include +#include +#include using namespace std; using namespace dev; @@ -538,17 +540,56 @@ Json::Value WebThreeStubServer::eth_compilers() Json::Value ret(Json::arrayValue); ret.append("lll"); ret.append("solidity"); + ret.append("serpent"); return ret; } std::string WebThreeStubServer::eth_lll(std::string const& _code) { - return toJS(dev::eth::compileLLL(_code)); + string res; + vector errors; + res = toJS(dev::eth::compileLLL(_code, true, &errors)); + cwarn << "LLL compilation errors: " << errors; + return res; +} + +std::string WebThreeStubServer::eth_serpent(std::string const& _code) +{ + string res; + try + { + res = toJS(dev::asBytes(::compile(_code))); + } + catch (string err) + { + cwarn << "Solidity compilation error: " << err; + } + catch (...) + { + cwarn << "Uncought serpent compilation exception"; + } + return res; } std::string WebThreeStubServer::eth_solidity(std::string const& _code) { - return toJS(dev::solidity::CompilerStack::staticCompile(_code, false)); + string res; + dev::solidity::CompilerStack compiler; + try + { + res = toJS(compiler.compile(_code, true)); + } + catch (dev::Exception const& exception) + { + ostringstream error; + solidity::SourceReferenceFormatter::printExceptionInformation(error, exception, "Error", compiler.getScanner()); + cwarn << "Solidity compilation error: " << error.str(); + } + catch (...) + { + cwarn << "Uncought solidity compilation exception"; + } + return res; } int WebThreeStubServer::eth_number() diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 5207ed1df..7d25f5954 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -87,6 +87,7 @@ public: virtual bool eth_setDefaultBlock(int const& _block); virtual bool eth_setListening(bool const& _listening); virtual std::string eth_lll(std::string const& _s); + virtual std::string eth_serpent(std::string const& _s); virtual bool eth_setMining(bool const& _mining); virtual std::string eth_solidity(std::string const& _code); virtual std::string eth_stateAt(std::string const& _address, std::string const& _storage); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index 5fb548103..b86576572 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -37,6 +37,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_newFilterStringI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_number", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_numberI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_peerCount", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_peerCountI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_serpent", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_serpentI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_setCoinbase", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_setCoinbaseI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_setDefaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_setDefaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_setListening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, "param1",jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_setListeningI); @@ -181,6 +182,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_peerCount(); } + inline virtual void eth_serpentI(const Json::Value& request, Json::Value& response) + { + response = this->eth_serpent(request[0u].asString()); + } + inline virtual void eth_setCoinbaseI(const Json::Value& request, Json::Value& response) { response = this->eth_setCoinbase(request[0u].asString()); @@ -311,6 +317,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_serpent",p); + if (result.isString()) + return result.asString(); + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + bool eth_setCoinbase(const std::string& param1) throw (jsonrpc::JsonRpcException) { Json::Value p; From 5d55344f3a121fbe08644a50a11e63ad71dd630d Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 17 Nov 2014 16:01:48 +0100 Subject: [PATCH 23/38] common changes in ethereum.js --- libjsqrc/ethereum.js | 111 ++++++++++++++++++++++++--------------- libqethereum/QEthereum.h | 2 +- 2 files changed, 71 insertions(+), 42 deletions(-) diff --git a/libjsqrc/ethereum.js b/libjsqrc/ethereum.js index e65489a66..bd5b4fb4e 100644 --- a/libjsqrc/ethereum.js +++ b/libjsqrc/ethereum.js @@ -319,6 +319,71 @@ module.exports = AutoProvider; You should have received a copy of the GNU Lesser General Public License along with ethereum.js. If not, see . */ +/** @file contract.js + * @authors: + * Marek Kotewicz + * @date 2014 + */ + +if ("build" !== 'build') {/* + var web3 = require('./web3'); // jshint ignore:line +*/} +var abi = require('./abi'); + +var contract = function (address, desc) { + var inputParser = abi.inputParser(desc); + var outputParser = abi.outputParser(desc); + + var contract = {}; + + desc.forEach(function (method) { + contract[method.name] = function () { + var params = Array.prototype.slice.call(arguments); + var parsed = inputParser[method.name].apply(null, params); + + var onSuccess = function (result) { + return outputParser[method.name](result); + }; + + return { + call: function (extra) { + extra = extra || {}; + extra.to = address; + extra.data = parsed; + return web3.eth.call(extra).then(onSuccess); + }, + transact: function (extra) { + extra = extra || {}; + extra.to = address; + extra.data = parsed; + return web3.eth.transact(extra).then(onSuccess); + } + }; + }; + }); + + return contract; +}; + +module.exports = contract; + +},{"./abi":1}],4:[function(require,module,exports){ +/* + This file is part of ethereum.js. + + ethereum.js is free software: you can redistribute it and/or modify + it under the terms of the GNU Lesser General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + ethereum.js 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 Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public License + along with ethereum.js. If not, see . +*/ /** @file httprpc.js * @authors: * Marek Kotewicz @@ -397,7 +462,7 @@ Object.defineProperty(HttpRpcProvider.prototype, "onmessage", { module.exports = HttpRpcProvider; -},{}],4:[function(require,module,exports){ +},{}],5:[function(require,module,exports){ /* This file is part of ethereum.js. @@ -422,8 +487,6 @@ module.exports = HttpRpcProvider; * @date 2014 */ -var abi = require('./abi'); - function flattenPromise (obj) { if (obj instanceof Promise) { return Promise.resolve(obj); @@ -856,45 +919,10 @@ function messageHandler(data) { } } -web3.contract = function (address, desc) { - var inputParser = abi.inputParser(desc); - var outputParser = abi.outputParser(desc); - - var contract = {}; - - desc.forEach(function (method) { - contract[method.name] = function () { - var params = Array.prototype.slice.call(arguments); - var parsed = inputParser[method.name].apply(null, params); - - var onSuccess = function (result) { - return outputParser[method.name](result); - }; - - return { - call: function (extra) { - extra = extra || {}; - extra.to = address; - extra.data = parsed; - return web3.eth.call(extra).then(onSuccess); - }, - transact: function (extra) { - extra = extra || {}; - extra.to = address; - extra.data = parsed; - return web3.eth.transact(extra).then(onSuccess); - } - }; - }; - }); - - return contract; -}; - module.exports = web3; -},{"./abi":1}],5:[function(require,module,exports){ +},{}],6:[function(require,module,exports){ /* This file is part of ethereum.js. @@ -941,7 +969,7 @@ Object.defineProperty(QtProvider.prototype, "onmessage", { module.exports = QtProvider; -},{}],6:[function(require,module,exports){ +},{}],7:[function(require,module,exports){ /* This file is part of ethereum.js. @@ -1025,10 +1053,11 @@ web3.providers.WebSocketProvider = require('./lib/websocket'); web3.providers.HttpRpcProvider = require('./lib/httprpc'); web3.providers.QtProvider = require('./lib/qt'); web3.providers.AutoProvider = require('./lib/autoprovider'); +web3.contract = require('./lib/contract'); module.exports = web3; -},{"./lib/autoprovider":2,"./lib/httprpc":3,"./lib/main":4,"./lib/qt":5,"./lib/websocket":6}]},{},[]) +},{"./lib/autoprovider":2,"./lib/contract":3,"./lib/httprpc":4,"./lib/main":5,"./lib/qt":6,"./lib/websocket":7}]},{},[]) //# sourceMappingURL=ethereum.js.map \ No newline at end of file diff --git a/libqethereum/QEthereum.h b/libqethereum/QEthereum.h index 7644152de..6a4e640e5 100644 --- a/libqethereum/QEthereum.h +++ b/libqethereum/QEthereum.h @@ -85,7 +85,7 @@ private: _frame->addToJavaScriptWindowObject("_web3", qweb, QWebFrame::ScriptOwnership); \ _frame->addToJavaScriptWindowObject("env", _env, QWebFrame::QtOwnership); \ _frame->evaluateJavaScript(contentsOfQResource(":/js/es6-promise-2.0.0.js")); \ - _frame->evaluateJavaScript(contentsOfQResource(":/js/ethereum.min.js")); \ + _frame->evaluateJavaScript(contentsOfQResource(":/js/ethereum.js")); \ _frame->evaluateJavaScript(contentsOfQResource(":/js/setup.js")); \ } From 9cf1fb0dc7cfadd985c359110b429b39fe5ccdc1 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Mon, 17 Nov 2014 20:16:40 +0100 Subject: [PATCH 24/38] transact value may be int --- libweb3jsonrpc/WebThreeStubServer.cpp | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index ecbbacba7..c83d3f763 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -380,8 +380,13 @@ static TransactionSkeleton toTransaction(Json::Value const& _json) ret.from = jsToAddress(_json["from"].asString()); if (_json["to"].isString()) ret.to = jsToAddress(_json["to"].asString()); - if (_json["value"].isString()) - ret.value = jsToU256(_json["value"].asString()); + if (!_json["value"].empty()) + { + if (_json["value"].isString()) + ret.value = jsToU256(_json["value"].asString()); + else if (_json["value"].isInt()) + ret.value = u256(_json["value"].asInt()); + } if (!_json["gas"].empty()) { if (_json["gas"].isString()) From 3a1b83538bf43401f6269e055afd3b8ffbbf2e8a Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 10:45:40 +0100 Subject: [PATCH 25/38] migration to log filters, not finished --- alethzero/MainWin.cpp | 17 ++++- alethzero/MainWin.h | 1 + libethereum/Client.cpp | 92 ++++++++++-------------- libethereum/Client.h | 14 ++-- libethereum/Interface.h | 20 ++++-- libethereum/State.cpp | 6 +- libethereum/State.h | 2 +- libweb3jsonrpc/WebThreeStubServer.cpp | 100 +++----------------------- 8 files changed, 89 insertions(+), 163 deletions(-) diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index 280a70fe1..6bad7ea75 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -241,13 +241,22 @@ void Main::onKeysChanged() installBalancesWatch(); } -unsigned Main::installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f) +unsigned Main::installWatch(dev::eth::LogFilter const& _tf, std::function const& _f) { auto ret = ethereum()->installWatch(_tf); m_handlers[ret] = _f; return ret; } +unsigned Main::installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f) +{ +// auto ret = ethereum()->installWatch(_tf); +// m_handlers[ret] = _f; +// return ret; +} + + + unsigned Main::installWatch(dev::h256 _tf, std::function const& _f) { auto ret = ethereum()->installWatch(_tf); @@ -263,8 +272,10 @@ void Main::uninstallWatch(unsigned _w) void Main::installWatches() { - installWatch(dev::eth::MessageFilter().altered(c_config, 0), [=](){ installNameRegWatch(); }); - installWatch(dev::eth::MessageFilter().altered(c_config, 1), [=](){ installCurrenciesWatch(); }); + installWatch(dev::eth::LogFilter().address(c_config), [=]() { installNameRegWatch(); }); + installWatch(dev::eth::LogFilter().address(c_config), [=]() { installCurrenciesWatch(); }); +// installWatch(dev::eth::MessageFilter().altered(c_config, 0), [=](){ installNameRegWatch(); }); +// installWatch(dev::eth::MessageFilter().altered(c_config, 1), [=](){ installCurrenciesWatch(); }); installWatch(dev::eth::PendingChangedFilter, [=](){ onNewPending(); }); installWatch(dev::eth::ChainChangedFilter, [=](){ onNewBlock(); }); } diff --git a/alethzero/MainWin.h b/alethzero/MainWin.h index 14877f610..a401333a5 100644 --- a/alethzero/MainWin.h +++ b/alethzero/MainWin.h @@ -189,6 +189,7 @@ private: dev::u256 value() const; dev::u256 gasPrice() const; + unsigned installWatch(dev::eth::LogFilter const& _tf, std::function const& _f); unsigned installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f); unsigned installWatch(dev::h256 _tf, std::function const& _f); void uninstallWatch(unsigned _w); diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 0be499541..71638ce8f 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -159,7 +159,7 @@ void Client::clearPending() if (!m_postMine.pending().size()) return; for (unsigned i = 0; i < m_postMine.pending().size(); ++i) - appendFromNewPending(m_postMine.oldBloom(i), changeds); + appendFromNewPending(m_postMine.logBloom(i), changeds); changeds.insert(PendingChangedFilter); m_postMine = m_preMine; } @@ -181,7 +181,7 @@ unsigned Client::installWatch(h256 _h) return ret; } -unsigned Client::installWatch(MessageFilter const& _f) +unsigned Client::installWatch(LogFilter const& _f) { lock_guard l(m_filterLock); @@ -222,7 +222,7 @@ void Client::noteChanged(h256Set const& _filters) } } -void Client::appendFromNewPending(h256 _bloom, h256Set& o_changed) const +void Client::appendFromNewPending(LogBloom _bloom, h256Set& o_changed) const { lock_guard l(m_filterLock); for (pair const& i: m_filters) @@ -232,12 +232,19 @@ void Client::appendFromNewPending(h256 _bloom, h256Set& o_changed) const void Client::appendFromNewBlock(h256 _block, h256Set& o_changed) const { - auto d = m_bc.details(_block); - +// auto d = m_bc.details(_block); + auto d = m_bc.logBlooms(_block); + lock_guard l(m_filterLock); for (pair const& i: m_filters) - if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.bloom)) - o_changed.insert(i.first); + for (auto b: d.blooms) + if (i.second.filter.matches(b)) + { + o_changed.insert(i.first); + break; + } +// if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.bloom)) +// o_changed.insert(i.first); } void Client::setForceMining(bool _enable) @@ -440,7 +447,7 @@ void Client::doWork() // returns h256s as blooms, once for each transaction. cwork << "postSTATE <== TQ"; - h256s newPendingBlooms = m_postMine.sync(m_tq); + h512s newPendingBlooms = m_postMine.sync(m_tq); if (newPendingBlooms.size()) { for (auto i: newPendingBlooms) @@ -564,9 +571,9 @@ BlockInfo Client::uncle(h256 _blockHash, unsigned _i) const return BlockInfo::fromHeader(b[2][_i].data()); } -PastMessages Client::messages(MessageFilter const& _f) const +LogEntries Client::logs(LogFilter const& _f) const { - PastMessages ret; + LogEntries ret; unsigned begin = min(m_bc.number(), (unsigned)_f.latest()); unsigned end = min(begin, (unsigned)_f.earliest()); unsigned m = _f.max(); @@ -578,23 +585,22 @@ PastMessages Client::messages(MessageFilter const& _f) const ReadGuard l(x_stateDB); for (unsigned i = 0; i < m_postMine.pending().size(); ++i) { - // Might have a transaction that contains a matching message. - Manifest const& ms = m_postMine.changesFromPending(i); - PastMessages pm = _f.matches(ms, i); - if (pm.size()) + // Might have a transaction that contains a matching log. + TransactionReceipt const& tr = m_postMine.receipt(i); + LogEntries le = _f.matches(tr); + if (le.size()) { - auto ts = time(0); - for (unsigned j = 0; j < pm.size() && ret.size() != m; ++j) + for (unsigned j = 0; j < le.size() && ret.size() != m; ++j) if (s) s--; else - // Have a transaction that contains a matching message. - ret.insert(ret.begin(), pm[j].polish(h256(), ts, m_bc.number() + 1, m_postMine.address())); + ret.insert(ret.begin(), le[j]); } } } #if ETH_DEBUG + // fill these params unsigned skipped = 0; unsigned falsePos = 0; #endif @@ -602,50 +608,28 @@ PastMessages Client::messages(MessageFilter const& _f) const unsigned n = begin; for (; ret.size() != m && n != end; n--, h = m_bc.details(h).parent) { - auto d = m_bc.details(h); #if ETH_DEBUG int total = 0; #endif - if (_f.matches(d.bloom)) - { - // Might have a block that contains a transaction that contains a matching message. - auto bs = m_bc.blooms(h).blooms; - Manifests ms; - BlockInfo bi; - for (unsigned i = 0; i < bs.size(); ++i) - if (_f.matches(bs[i])) + //? check block bloom + for (TransactionReceipt receipt: m_bc.receipts(h).receipts) + if (_f.matches(receipt.bloom())) + { + LogEntries le = _f.matches(receipt); + if (le.size()) { - // Might have a transaction that contains a matching message. - if (ms.empty()) - ms = m_bc.traces(h).traces; - Manifest const& changes = ms[i]; - PastMessages pm = _f.matches(changes, i); - if (pm.size()) - { #if ETH_DEBUG - total += pm.size(); + total += le.size(); #endif - if (!bi) - bi.populate(m_bc.block(h)); - auto ts = bi.timestamp; - auto cb = bi.coinbaseAddress; - for (unsigned j = 0; j < pm.size() && ret.size() != m; ++j) - if (s) - s--; - else - // Have a transaction that contains a matching message. - ret.push_back(pm[j].polish(h, ts, n, cb)); + for (unsigned j = 0; j < le.size() && ret.size() != m; ++j) + { + if (s) + s--; + else + ret.insert(ret.begin(), le[j]); } } -#if ETH_DEBUG - if (!total) - falsePos++; - } - else - skipped++; -#else - } -#endif + } if (n == end) break; } diff --git a/libethereum/Client.h b/libethereum/Client.h index 8ec65c199..283251e24 100644 --- a/libethereum/Client.h +++ b/libethereum/Client.h @@ -79,9 +79,11 @@ static const int GenesisBlock = INT_MIN; struct InstalledFilter { - InstalledFilter(MessageFilter const& _f): filter(_f) {} +// InstalledFilter(MessageFilter const& _f): filter(_f) {} +// MessageFilter filter; + InstalledFilter(LogFilter const& _f): filter(_f) {} - MessageFilter filter; + LogFilter filter; unsigned refCount = 1; }; @@ -152,14 +154,14 @@ public: virtual bytes codeAt(Address _a, int _block) const; virtual std::map storageAt(Address _a, int _block) const; - virtual unsigned installWatch(MessageFilter const& _filter); + virtual unsigned installWatch(LogFilter const& _filter); virtual unsigned installWatch(h256 _filterId); virtual void uninstallWatch(unsigned _watchId); virtual bool peekWatch(unsigned _watchId) const { std::lock_guard l(m_filterLock); try { return m_watches.at(_watchId).changes != 0; } catch (...) { return false; } } virtual bool checkWatch(unsigned _watchId) { std::lock_guard l(m_filterLock); bool ret = false; try { ret = m_watches.at(_watchId).changes != 0; m_watches.at(_watchId).changes = 0; } catch (...) {} return ret; } - virtual PastMessages messages(unsigned _watchId) const { try { std::lock_guard l(m_filterLock); return messages(m_filters.at(m_watches.at(_watchId).id).filter); } catch (...) { return PastMessages(); } } - virtual PastMessages messages(MessageFilter const& _filter) const; + virtual LogEntries logs(unsigned _watchId) const { try { std::lock_guard l(m_filterLock); return logs(m_filters.at(m_watches.at(_watchId).id).filter); } catch (...) { return LogEntries(); } } + virtual LogEntries logs(LogFilter const& _filter) const; // [EXTRA API]: @@ -259,7 +261,7 @@ private: /// Collate the changed filters for the bloom filter of the given pending transaction. /// Insert any filters that are activated into @a o_changed. - void appendFromNewPending(h256 _pendingTransactionBloom, h256Set& o_changed) const; + void appendFromNewPending(LogBloom _pendingTransactionBloom, h256Set& o_changed) const; /// Collate the changed filters for the hash of the given block. /// Insert any filters that are activated into @a o_changed. diff --git a/libethereum/Interface.h b/libethereum/Interface.h index 7ae650590..add9a1bda 100644 --- a/libethereum/Interface.h +++ b/libethereum/Interface.h @@ -84,13 +84,18 @@ public: virtual bytes codeAt(Address _a, int _block) const = 0; virtual std::map storageAt(Address _a, int _block) const = 0; - // [MESSAGE API] - - virtual PastMessages messages(unsigned _watchId) const = 0; - virtual PastMessages messages(MessageFilter const& _filter) const = 0; +// // [MESSAGE API] +// +// virtual PastMessages messages(unsigned _watchId) const = 0; +// virtual PastMessages messages(MessageFilter const& _filter) const = 0; + + // [LOGS API] + + virtual LogEntries logs(unsigned _watchId) const = 0; + virtual LogEntries logs(LogFilter const& _filter) const = 0; /// Install, uninstall and query watches. - virtual unsigned installWatch(MessageFilter const& _filter) = 0; + virtual unsigned installWatch(LogFilter const& _filter) = 0; virtual unsigned installWatch(h256 _filterId) = 0; virtual void uninstallWatch(unsigned _watchId) = 0; virtual bool peekWatch(unsigned _watchId) const = 0; @@ -175,12 +180,13 @@ class Watch: public boost::noncopyable public: Watch() {} Watch(Interface& _c, h256 _f): m_c(&_c), m_id(_c.installWatch(_f)) {} - Watch(Interface& _c, MessageFilter const& _tf): m_c(&_c), m_id(_c.installWatch(_tf)) {} + Watch(Interface& _c, LogFilter const& _tf): m_c(&_c), m_id(_c.installWatch(_tf)) {} ~Watch() { if (m_c) m_c->uninstallWatch(m_id); } bool check() { return m_c ? m_c->checkWatch(m_id) : false; } bool peek() { return m_c ? m_c->peekWatch(m_id) : false; } - PastMessages messages() const { return m_c->messages(m_id); } +// PastMessages messages() const { return m_c->messages(m_id); } + LogEntries logs() const { return m_c->logs(m_id); } private: Interface* m_c = nullptr; diff --git a/libethereum/State.cpp b/libethereum/State.cpp index 69faf983c..a37c26645 100644 --- a/libethereum/State.cpp +++ b/libethereum/State.cpp @@ -534,10 +534,10 @@ bool State::cull(TransactionQueue& _tq) const return ret; } -h256s State::sync(TransactionQueue& _tq, bool* o_transactionQueueChanged) +h512s State::sync(TransactionQueue& _tq, bool* o_transactionQueueChanged) { // TRANSACTIONS - h256s ret; + h512s ret; auto ts = _tq.transactions(); for (int goodTxs = 1; goodTxs;) @@ -552,7 +552,7 @@ h256s State::sync(TransactionQueue& _tq, bool* o_transactionQueueChanged) uncommitToMine(); // boost::timer t; execute(i.second); - ret.push_back(m_receipts.back().changes().bloom()); + ret.push_back(m_receipts.back().bloom()); _tq.noteGood(i); ++goodTxs; // cnote << "TX took:" << t.elapsed() * 1000; diff --git a/libethereum/State.h b/libethereum/State.h index d3c7fa313..9c41843ff 100644 --- a/libethereum/State.h +++ b/libethereum/State.h @@ -147,7 +147,7 @@ public: /// @returns a list of bloom filters one for each transaction placed from the queue into the state. /// @a o_transactionQueueChanged boolean pointer, the value of which will be set to true if the transaction queue /// changed and the pointer is non-null - h256s sync(TransactionQueue& _tq, bool* o_transactionQueueChanged = nullptr); + h512s sync(TransactionQueue& _tq, bool* o_transactionQueueChanged = nullptr); /// Like sync but only operate on _tq, killing the invalid/old ones. bool cull(TransactionQueue& _tq) const; diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index c83d3f763..6bedfed3f 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -59,34 +59,6 @@ static Json::Value toJson(dev::eth::BlockInfo const& _bi) return res; } -static Json::Value toJson(dev::eth::PastMessage const& _t) -{ - Json::Value res; - res["input"] = jsFromBinary(_t.input); - res["output"] = jsFromBinary(_t.output); - res["to"] = toJS(_t.to); - res["from"] = toJS(_t.from); - res["value"] = jsToDecimal(toJS(_t.value)); - res["origin"] = toJS(_t.origin); - res["timestamp"] = toJS(_t.timestamp); - res["coinbase"] = toJS(_t.coinbase); - res["block"] = toJS(_t.block); - Json::Value path; - for (int i: _t.path) - path.append(i); - res["path"] = path; - res["number"] = (int)_t.number; - return res; -} - -static Json::Value toJson(dev::eth::PastMessages const& _pms) -{ - Json::Value res; - for (dev::eth::PastMessage const& t: _pms) - res.append(toJson(t)); - return res; -} - static Json::Value toJson(dev::eth::Transaction const& _t) { Json::Value res; @@ -111,15 +83,7 @@ static Json::Value toJson(dev::eth::LogEntry const& _e) return res; } -static Json::Value toJson(std::map const& _storage) -{ - Json::Value res(Json::objectValue); - for (auto i: _storage) - res[toJS(i.first)] = toJS(i.second); - return res; -} - -/*static*/ Json::Value toJson(dev::eth::LogEntries const& _es) // commented to avoid warning. Uncomment once in use @ poC-7. +static Json::Value toJson(dev::eth::LogEntries const& _es) // commented to avoid warning. Uncomment once in use @ poC-7. { Json::Value res; for (dev::eth::LogEntry const& e: _es) @@ -127,59 +91,15 @@ static Json::Value toJson(std::map const& _storage) return res; } -static dev::eth::MessageFilter toMessageFilter(Json::Value const& _json) +static Json::Value toJson(std::map const& _storage) { - dev::eth::MessageFilter filter; - if (!_json.isObject() || _json.empty()) - return filter; - - if (_json["earliest"].isInt()) - filter.withEarliest(_json["earliest"].asInt()); - if (_json["latest"].isInt()) - filter.withLatest(_json["lastest"].asInt()); - if (_json["max"].isInt()) - filter.withMax(_json["max"].asInt()); - if (_json["skip"].isInt()) - filter.withSkip(_json["skip"].asInt()); - if (!_json["from"].empty()) - { - if (_json["from"].isArray()) - { - for (auto i : _json["from"]) - if (i.isString()) - filter.from(jsToAddress(i.asString())); - } - else if (_json["from"].isString()) - filter.from(jsToAddress(_json["from"].asString())); - } - if (!_json["to"].empty()) - { - if (_json["to"].isArray()) - { - for (auto i : _json["to"]) - if (i.isString()) - filter.to(jsToAddress(i.asString())); - } - else if (_json["to"].isString()) - filter.to(jsToAddress(_json["to"].asString())); - } - if (!_json["altered"].empty()) - { - if (_json["altered"].isArray()) - for (auto i: _json["altered"]) - if (i.isObject()) - filter.altered(jsToAddress(i["id"].asString()), jsToU256(i["at"].asString())); - else - filter.altered((jsToAddress(i.asString()))); - else if (_json["altered"].isObject()) - filter.altered(jsToAddress(_json["altered"]["id"].asString()), jsToU256(_json["altered"]["at"].asString())); - else - filter.altered(jsToAddress(_json["altered"].asString())); - } - return filter; + Json::Value res(Json::objectValue); + for (auto i: _storage) + res[toJS(i.first)] = toJS(i.second); + return res; } -/*static*/ dev::eth::LogFilter toLogFilter(Json::Value const& _json) // commented to avoid warning. Uncomment once in use @ PoC-7. +static dev::eth::LogFilter toLogFilter(Json::Value const& _json) // commented to avoid warning. Uncomment once in use @ PoC-7. { dev::eth::LogFilter filter; if (!_json.isObject() || _json.empty()) @@ -478,7 +398,8 @@ Json::Value WebThreeStubServer::eth_getMessages(int const& _id) { if (!client()) return Json::Value(); - return toJson(client()->messages(_id)); +// return toJson(client()->messages(_id)); + return toJson(client()->logs(_id)); } std::string WebThreeStubServer::db_getString(std::string const& _name, std::string const& _key) @@ -509,7 +430,8 @@ int WebThreeStubServer::eth_newFilter(Json::Value const& _json) unsigned ret = -1; if (!client()) return ret; - ret = client()->installWatch(toMessageFilter(_json)); +// ret = client()->installWatch(toMessageFilter(_json)); + ret = client()->installWatch(toLogFilter(_json)); return ret; } From c04f252b29707f767329417a58168e1b0c6e2a96 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 11:14:28 +0100 Subject: [PATCH 26/38] changes in az mainwin --- alethzero/MainWin.cpp | 21 +++++---------------- alethzero/MainWin.h | 1 - 2 files changed, 5 insertions(+), 17 deletions(-) diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index 6bad7ea75..460669cf9 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -248,15 +248,6 @@ unsigned Main::installWatch(dev::eth::LogFilter const& _tf, std::function const& _f) -{ -// auto ret = ethereum()->installWatch(_tf); -// m_handlers[ret] = _f; -// return ret; -} - - - unsigned Main::installWatch(dev::h256 _tf, std::function const& _f) { auto ret = ethereum()->installWatch(_tf); @@ -274,8 +265,6 @@ void Main::installWatches() { installWatch(dev::eth::LogFilter().address(c_config), [=]() { installNameRegWatch(); }); installWatch(dev::eth::LogFilter().address(c_config), [=]() { installCurrenciesWatch(); }); -// installWatch(dev::eth::MessageFilter().altered(c_config, 0), [=](){ installNameRegWatch(); }); -// installWatch(dev::eth::MessageFilter().altered(c_config, 1), [=](){ installCurrenciesWatch(); }); installWatch(dev::eth::PendingChangedFilter, [=](){ onNewPending(); }); installWatch(dev::eth::ChainChangedFilter, [=](){ onNewBlock(); }); } @@ -283,18 +272,18 @@ void Main::installWatches() void Main::installNameRegWatch() { uninstallWatch(m_nameRegFilter); - m_nameRegFilter = installWatch(dev::eth::MessageFilter().altered((u160)ethereum()->stateAt(c_config, 0)), [=](){ onNameRegChange(); }); + m_nameRegFilter = installWatch(dev::eth::LogFilter().address((u160)ethereum()->stateAt(c_config, 0)), [=](){ onNameRegChange(); }); } void Main::installCurrenciesWatch() { uninstallWatch(m_currenciesFilter); - m_currenciesFilter = installWatch(dev::eth::MessageFilter().altered((u160)ethereum()->stateAt(c_config, 1)), [=](){ onCurrenciesChange(); }); + m_currenciesFilter = installWatch(dev::eth::LogFilter().address((u160)ethereum()->stateAt(c_config, 1)), [=](){ onCurrenciesChange(); }); } void Main::installBalancesWatch() { - dev::eth::MessageFilter tf; + dev::eth::LogFilter tf; vector
altCoins; Address coinsAddr = right160(ethereum()->stateAt(c_config, 1)); @@ -302,9 +291,9 @@ void Main::installBalancesWatch() altCoins.push_back(right160(ethereum()->stateAt(coinsAddr, i + 1))); for (auto i: m_myKeys) { - tf.altered(i.address()); + tf.address(i.address()); for (auto c: altCoins) - tf.altered(c, (u160)i.address()); + tf.address(c); } uninstallWatch(m_balancesFilter); diff --git a/alethzero/MainWin.h b/alethzero/MainWin.h index a401333a5..50b9df413 100644 --- a/alethzero/MainWin.h +++ b/alethzero/MainWin.h @@ -190,7 +190,6 @@ private: dev::u256 gasPrice() const; unsigned installWatch(dev::eth::LogFilter const& _tf, std::function const& _f); - unsigned installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f); unsigned installWatch(dev::h256 _tf, std::function const& _f); void uninstallWatch(unsigned _w); From 28d69e0981e575fd1a68e39a2683808f7aebf432 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 11:46:57 +0100 Subject: [PATCH 27/38] common changes --- alethzero/OurWebThreeStubServer.cpp | 2 +- alethzero/OurWebThreeStubServer.h | 2 +- test/jsonrpc.cpp | 8 ++++---- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/alethzero/OurWebThreeStubServer.cpp b/alethzero/OurWebThreeStubServer.cpp index a40727e1e..fec0f9e8d 100644 --- a/alethzero/OurWebThreeStubServer.cpp +++ b/alethzero/OurWebThreeStubServer.cpp @@ -24,7 +24,7 @@ using namespace std; using namespace dev; using namespace dev::eth; -OurWebThreeStubServer::OurWebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts): +OurWebThreeStubServer::OurWebThreeStubServer(jsonrpc::AbstractServerConnector& _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts): WebThreeStubServer(_conn, _web3, _accounts) {} diff --git a/alethzero/OurWebThreeStubServer.h b/alethzero/OurWebThreeStubServer.h index b3492df5e..ef13964b9 100644 --- a/alethzero/OurWebThreeStubServer.h +++ b/alethzero/OurWebThreeStubServer.h @@ -29,7 +29,7 @@ class OurWebThreeStubServer: public QObject, public WebThreeStubServer Q_OBJECT public: - OurWebThreeStubServer(jsonrpc::AbstractServerConnector* _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); + OurWebThreeStubServer(jsonrpc::AbstractServerConnector& _conn, dev::WebThreeDirect& _web3, std::vector const& _accounts); virtual std::string shh_newIdentity() override; diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 4c748a954..727791f6e 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -29,8 +29,8 @@ #include #include #include -#include -#include +#include +#include #include #include "JsonSpiritHeaders.h" #include "TestHelper.h" @@ -61,11 +61,11 @@ struct Setup web3->setIdealPeerCount(5); web3->ethereum()->setForceMining(true); - jsonrpcServer = unique_ptr(new WebThreeStubServer(new jsonrpc::CorsHttpServer(8080), *web3, {})); + jsonrpcServer = unique_ptr(new WebThreeStubServer(jsonrpc::CorsHttpServer(8080), *web3, {})); jsonrpcServer->setIdentities({}); jsonrpcServer->StartListening(); - jsonrpcClient = unique_ptr(new WebThreeStubClient(new jsonrpc::HttpClient("http://localhost:8080"))); + jsonrpcClient = unique_ptr(new WebThreeStubClient(jsonrpc::HttpClient("http://localhost:8080"))); } }; From b876f24ea94feb67033030bca5287c2753b3dbc5 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 11:56:09 +0100 Subject: [PATCH 28/38] common changes --- libethereum/Client.cpp | 17 +++++------------ 1 file changed, 5 insertions(+), 12 deletions(-) diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 71638ce8f..01aa75b9a 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -232,18 +232,11 @@ void Client::appendFromNewPending(LogBloom _bloom, h256Set& o_changed) const void Client::appendFromNewBlock(h256 _block, h256Set& o_changed) const { -// auto d = m_bc.details(_block); - auto d = m_bc.logBlooms(_block); - - lock_guard l(m_filterLock); - for (pair const& i: m_filters) - for (auto b: d.blooms) - if (i.second.filter.matches(b)) - { - o_changed.insert(i.first); - break; - } -// if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.bloom)) +// auto d = m_bc.info(_block); +// +// lock_guard l(m_filterLock); +// for (pair const& i: m_filters) +// if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.logBloom)) // o_changed.insert(i.first); } From 908e0c498a0e8c38d7ab72ea377ee736d9334b0c Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 12:00:58 +0100 Subject: [PATCH 29/38] Remove overly verbose log. --- stdserv.js | 2 +- test/crypto.cpp | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/stdserv.js b/stdserv.js index fe681414e..676aaa949 100644 --- a/stdserv.js +++ b/stdserv.js @@ -17,7 +17,7 @@ config.then(function() { web3.eth.accounts.then(function(accounts) { var funded = send(accounts[0], '100000000000000000000', accounts[1]); - funded.then(function(){ env.note("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"); regName(accounts[1], 'Gav Would'); env.note("!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!"); approve(accounts[1], exchange); }); + funded.then(function(){ regName(accounts[1], 'Gav Would'); approve(accounts[1], exchange); }); regName(accounts[0], 'Gav'); approve(accounts[0], exchange).then(function(){ offer(accounts[0], coin, '5000', '0', '5000000000000000000'); }); diff --git a/test/crypto.cpp b/test/crypto.cpp index 08236135a..87047f0d4 100644 --- a/test/crypto.cpp +++ b/test/crypto.cpp @@ -140,7 +140,7 @@ BOOST_AUTO_TEST_CASE(cryptopp_ecdsa_sipaseckp256k1) KeyPair key(secret); bytes m(1, 0xff); - int tests = 2; + int tests = 2 while (m[0]++, tests--) { h256 hm(sha3(m)); From 5c17838ca13dc489fd9d4e699dffb81c582cb0a5 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 12:01:25 +0100 Subject: [PATCH 30/38] Build fix. --- test/crypto.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/test/crypto.cpp b/test/crypto.cpp index 87047f0d4..08236135a 100644 --- a/test/crypto.cpp +++ b/test/crypto.cpp @@ -140,7 +140,7 @@ BOOST_AUTO_TEST_CASE(cryptopp_ecdsa_sipaseckp256k1) KeyPair key(secret); bytes m(1, 0xff); - int tests = 2 + int tests = 2; while (m[0]++, tests--) { h256 hm(sha3(m)); From 67bc10efd67a43fb5f27d5d731210487af508b66 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 12:22:10 +0100 Subject: [PATCH 31/38] fixed test --- test/jsonrpc.cpp | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/test/jsonrpc.cpp b/test/jsonrpc.cpp index 727791f6e..25468dcc0 100644 --- a/test/jsonrpc.cpp +++ b/test/jsonrpc.cpp @@ -61,11 +61,12 @@ struct Setup web3->setIdealPeerCount(5); web3->ethereum()->setForceMining(true); - jsonrpcServer = unique_ptr(new WebThreeStubServer(jsonrpc::CorsHttpServer(8080), *web3, {})); + auto server = new jsonrpc::CorsHttpServer(8080); + jsonrpcServer = unique_ptr(new WebThreeStubServer(*server, *web3, {})); jsonrpcServer->setIdentities({}); jsonrpcServer->StartListening(); - - jsonrpcClient = unique_ptr(new WebThreeStubClient(jsonrpc::HttpClient("http://localhost:8080"))); + auto client = new jsonrpc::HttpClient("http://localhost:8080"); + jsonrpcClient = unique_ptr(new WebThreeStubClient(*client)); } }; From 7a0cb2bf23e346d5458ad8aba4f2ef4764de3a53 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 12:41:10 +0100 Subject: [PATCH 32/38] Renaming and fixes. --- alethzero/MainWin.cpp | 3 ++- libethereum/BlockChain.h | 4 ++++ libethereum/Client.cpp | 12 ++++++------ libjsqrc/ethereum.js | 6 ++++-- libweb3jsonrpc/WebThreeStubServer.cpp | 2 +- libweb3jsonrpc/WebThreeStubServer.h | 2 +- libweb3jsonrpc/abstractwebthreestubserver.h | 8 ++++---- libweb3jsonrpc/spec.json | 2 +- test/webthreestubclient.h | 4 ++-- third/MainWin.cpp | 17 +++++++---------- third/MainWin.h | 4 ++-- 11 files changed, 34 insertions(+), 30 deletions(-) diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index 460669cf9..6aaf6fc18 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -1292,7 +1292,7 @@ void Main::on_blocks_currentItemChanged() Transaction tx(block[1][txi].data()); auto ss = tx.safeSender(); h256 th = sha3(rlpList(ss, tx.nonce())); - auto receipt = ethereum()->blockChain().receipts(h).receipts[txi]; + TransactionReceipt receipt = ethereum()->blockChain().receipts(h).receipts[txi]; s << "

" << th << "

"; s << "

" << h << "[" << txi << "]

"; s << "
From: " << pretty(ss).toHtmlEscaped().toStdString() << " " << ss; @@ -1308,6 +1308,7 @@ void Main::on_blocks_currentItemChanged() s << "
R: " << hex << nouppercase << tx.signature().r << ""; s << "
S: " << hex << nouppercase << tx.signature().s << ""; s << "
Msg: " << tx.sha3(eth::WithoutSignature) << ""; + s << "
Log Bloom: " << receipt.bloom() << "
"; s << "
Hex: " << toHex(block[1][txi].data()) << "
"; auto r = receipt.rlp(); s << "
Receipt: " << toString(RLP(r)) << "
"; diff --git a/libethereum/BlockChain.h b/libethereum/BlockChain.h index 49f7b149e..74d94e164 100644 --- a/libethereum/BlockChain.h +++ b/libethereum/BlockChain.h @@ -93,6 +93,10 @@ public: /// Returns true if the given block is known (though not necessarily a part of the canon chain). bool isKnown(h256 _hash) const; + /// Get the familial details concerning a block (or the most recent mined if none given). Thread-safe. + BlockInfo info(h256 _hash) const { return BlockInfo(block(_hash)); } + BlockInfo info() const { return BlockInfo(block()); } + /// Get the familial details concerning a block (or the most recent mined if none given). Thread-safe. BlockDetails details(h256 _hash) const { return queryExtras(_hash, m_details, x_details, NullBlockDetails); } BlockDetails details() const { return details(currentHash()); } diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 01aa75b9a..79001d2fb 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -232,12 +232,12 @@ void Client::appendFromNewPending(LogBloom _bloom, h256Set& o_changed) const void Client::appendFromNewBlock(h256 _block, h256Set& o_changed) const { -// auto d = m_bc.info(_block); -// -// lock_guard l(m_filterLock); -// for (pair const& i: m_filters) -// if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.logBloom)) -// o_changed.insert(i.first); + auto d = m_bc.info(_block); + + lock_guard l(m_filterLock); + for (pair const& i: m_filters) + if ((unsigned)i.second.filter.latest() >= d.number && (unsigned)i.second.filter.earliest() <= d.number && i.second.filter.matches(d.logBloom)) + o_changed.insert(i.first); } void Client::setForceMining(bool _enable) diff --git a/libjsqrc/ethereum.js b/libjsqrc/ethereum.js index bd5b4fb4e..43ac12fd8 100644 --- a/libjsqrc/ethereum.js +++ b/libjsqrc/ethereum.js @@ -599,7 +599,7 @@ var ethWatchMethods = function () { return [ { name: 'newFilter', call: newFilter }, { name: 'uninstallFilter', call: 'eth_uninstallFilter' }, - { name: 'getMessages', call: 'eth_getMessages' } + { name: 'logs', call: 'eth_getMessages' } ]; }; @@ -904,6 +904,8 @@ Filter.prototype.messages = function() { }); }; +Filter.prototype.logs = Filter.prototype.messages; + function messageHandler(data) { if(data._event !== undefined) { web3.trigger(data._event, data._id, data.data); @@ -1060,4 +1062,4 @@ module.exports = web3; },{"./lib/autoprovider":2,"./lib/contract":3,"./lib/httprpc":4,"./lib/main":5,"./lib/qt":6,"./lib/websocket":7}]},{},[]) -//# sourceMappingURL=ethereum.js.map \ No newline at end of file +//# sourceMappingURL=ethereum.js.map diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 6bedfed3f..2676913e5 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -394,7 +394,7 @@ std::string WebThreeStubServer::db_get(std::string const& _name, std::string con return toJS(dev::asBytes(ret)); } -Json::Value WebThreeStubServer::eth_getMessages(int const& _id) +Json::Value WebThreeStubServer::eth_getLogs(int const& _id) { if (!client()) return Json::Value(); diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 7d25f5954..007c06cb8 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -76,7 +76,7 @@ public: virtual double eth_countAt(std::string const& _address); virtual int eth_defaultBlock(); virtual std::string eth_gasPrice(); - virtual Json::Value eth_getMessages(int const& _id); + virtual Json::Value eth_getLogs(int const& _id); virtual bool eth_listening(); virtual bool eth_mining(); virtual int eth_newFilter(Json::Value const& _json); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index b86576572..fd3f8b051 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -29,7 +29,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_getMessagesI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_getLogs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_getLogsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_listeningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_lllI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_miningI); @@ -142,9 +142,9 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_gasPrice(); } - inline virtual void eth_getMessagesI(const Json::Value& request, Json::Value& response) + inline virtual void eth_getLogsI(const Json::Value& request, Json::Value& response) { - response = this->eth_getMessages(request[0u].asInt()); + response = this->eth_getLogs(request[0u].asInt()); } inline virtual void eth_listeningI(const Json::Value& request, Json::Value& response) @@ -309,7 +309,7 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_getMessages",p); + Json::Value result = this->client->CallMethod("eth_getLogs",p); if (result.isArray()) return result; else diff --git a/third/MainWin.cpp b/third/MainWin.cpp index c2dcb7ce2..299aafaaa 100644 --- a/third/MainWin.cpp +++ b/third/MainWin.cpp @@ -182,7 +182,7 @@ void Main::onKeysChanged() installBalancesWatch(); } -unsigned Main::installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f) +unsigned Main::installWatch(dev::eth::LogFilter const& _tf, std::function const& _f) { auto ret = ethereum()->installWatch(_tf); m_handlers[ret] = _f; @@ -198,37 +198,34 @@ unsigned Main::installWatch(dev::h256 _tf, std::function const& _f) void Main::installWatches() { - installWatch(dev::eth::MessageFilter().altered(c_config, 0), [=](){ installNameRegWatch(); }); - installWatch(dev::eth::MessageFilter().altered(c_config, 1), [=](){ installCurrenciesWatch(); }); + installWatch(dev::eth::LogFilter().topic((u256)(u160)c_config).topic((u256)0), [=](){ installNameRegWatch(); }); + installWatch(dev::eth::LogFilter().topic((u256)(u160)c_config).topic((u256)1), [=](){ installCurrenciesWatch(); }); installWatch(dev::eth::ChainChangedFilter, [=](){ onNewBlock(); }); } void Main::installNameRegWatch() { ethereum()->uninstallWatch(m_nameRegFilter); - m_nameRegFilter = installWatch(dev::eth::MessageFilter().altered((u160)ethereum()->stateAt(c_config, 0)), [=](){ onNameRegChange(); }); + m_nameRegFilter = installWatch(dev::eth::LogFilter().topic(ethereum()->stateAt(c_config, 0)), [=](){ onNameRegChange(); }); } void Main::installCurrenciesWatch() { ethereum()->uninstallWatch(m_currenciesFilter); - m_currenciesFilter = installWatch(dev::eth::MessageFilter().altered((u160)ethereum()->stateAt(c_config, 1)), [=](){ onCurrenciesChange(); }); + m_currenciesFilter = installWatch(dev::eth::LogFilter().topic(ethereum()->stateAt(c_config, 1)), [=](){ onCurrenciesChange(); }); } void Main::installBalancesWatch() { - dev::eth::MessageFilter tf; + dev::eth::LogFilter tf; vector
altCoins; Address coinsAddr = right160(ethereum()->stateAt(c_config, 1)); for (unsigned i = 0; i < ethereum()->stateAt(coinsAddr, 0); ++i) altCoins.push_back(right160(ethereum()->stateAt(coinsAddr, i + 1))); for (auto i: m_myKeys) - { - tf.altered(i.address()); for (auto c: altCoins) - tf.altered(c, (u160)i.address()); - } + tf.address(c).topic((u256)(u160)i.address()); ethereum()->uninstallWatch(m_balancesFilter); m_balancesFilter = installWatch(tf, [=](){ onBalancesChange(); }); diff --git a/third/MainWin.h b/third/MainWin.h index 607d65fee..478fb6fb6 100644 --- a/third/MainWin.h +++ b/third/MainWin.h @@ -40,7 +40,7 @@ namespace dev { class WebThreeDirect; namespace eth { class Client; class State; -class MessageFilter; +class LogFilter; } namespace shh { class WhisperHost; @@ -95,7 +95,7 @@ private: void readSettings(bool _skipGeometry = false); void writeSettings(); - unsigned installWatch(dev::eth::MessageFilter const& _tf, std::function const& _f); + unsigned installWatch(dev::eth::LogFilter const& _tf, std::function const& _f); unsigned installWatch(dev::h256 _tf, std::function const& _f); void onNewBlock(); From e2948c7040188bb047e48be0a7acbdeef97596a2 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 12:41:53 +0100 Subject: [PATCH 33/38] logs in spec --- libweb3jsonrpc/abstractwebthreestubserver.h | 19 +++++++---- libweb3jsonrpc/spec.json | 3 +- test/webthreestubclient.h | 35 ++++++++++++++------- 3 files changed, 39 insertions(+), 18 deletions(-) diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index b86576572..c1208b5c4 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -28,10 +28,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_filterLogs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_filterLogsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_getMessages", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_getMessagesI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_listeningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_lllI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_logs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_logsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_miningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_newFilterI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_newFilterStringI); @@ -137,14 +138,14 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_defaultBlock(); } - inline virtual void eth_gasPriceI(const Json::Value& request, Json::Value& response) + inline virtual void eth_filterLogsI(const Json::Value& request, Json::Value& response) { - response = this->eth_gasPrice(); + response = this->eth_filterLogs(request[0u].asInt()); } - inline virtual void eth_getMessagesI(const Json::Value& request, Json::Value& response) + inline virtual void eth_gasPriceI(const Json::Value& request, Json::Value& response) { - response = this->eth_getMessages(request[0u].asInt()); + response = this->eth_gasPrice(); } inline virtual void eth_listeningI(const Json::Value& request, Json::Value& response) @@ -157,6 +158,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_lll(request[0u].asString()); } + inline virtual void eth_logsI(const Json::Value& request, Json::Value& response) + { + response = this->eth_logs(request[0u]); + } + inline virtual void eth_miningI(const Json::Value& request, Json::Value& response) { response = this->eth_mining(); @@ -308,10 +314,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_gasPrice",p); - if (result.isString()) - return result.asString(); + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_filterLogs",p); + if (result.isArray()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value eth_getMessages(const int& param1) throw (jsonrpc::JsonRpcException) + std::string eth_gasPrice() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("eth_getMessages",p); - if (result.isArray()) - return result; + p = Json::nullValue; + Json::Value result = this->client->CallMethod("eth_gasPrice",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); @@ -266,6 +266,19 @@ p.append(param3); } + Json::Value eth_logs(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_logs",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + bool eth_mining() throw (jsonrpc::JsonRpcException) { Json::Value p; From 89ee4a3d2bdc1c58b144e96d99e3ae3328082ffc Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 13:08:33 +0100 Subject: [PATCH 34/38] More fixes for logging. --- alethzero/MainWin.cpp | 5 +--- libethereum/Client.cpp | 33 ++++++++++++++++----------- libethereum/MessageFilter.h | 1 - libethereum/State.cpp | 4 ++-- libweb3jsonrpc/WebThreeStubServer.cpp | 13 +---------- 5 files changed, 24 insertions(+), 32 deletions(-) diff --git a/alethzero/MainWin.cpp b/alethzero/MainWin.cpp index 6aaf6fc18..66fa00b36 100644 --- a/alethzero/MainWin.cpp +++ b/alethzero/MainWin.cpp @@ -290,11 +290,8 @@ void Main::installBalancesWatch() for (unsigned i = 0; i < ethereum()->stateAt(coinsAddr, 0); ++i) altCoins.push_back(right160(ethereum()->stateAt(coinsAddr, i + 1))); for (auto i: m_myKeys) - { - tf.address(i.address()); for (auto c: altCoins) - tf.address(c); - } + tf.address(c).topic(h256(i.address(), h256::AlignRight)); uninstallWatch(m_balancesFilter); m_balancesFilter = installWatch(tf, [=](){ onBalancesChange(); }); diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 79001d2fb..6405134c7 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -604,30 +604,37 @@ LogEntries Client::logs(LogFilter const& _f) const #if ETH_DEBUG int total = 0; #endif - //? check block bloom - for (TransactionReceipt receipt: m_bc.receipts(h).receipts) - if (_f.matches(receipt.bloom())) + // check block bloom + if (_f.matches(m_bc.info(h).logBloom)) + for (TransactionReceipt receipt: m_bc.receipts(h).receipts) { - LogEntries le = _f.matches(receipt); - if (le.size()) + if (_f.matches(receipt.bloom())) { + LogEntries le = _f.matches(receipt); + if (le.size()) + { #if ETH_DEBUG - total += le.size(); + total += le.size(); #endif - for (unsigned j = 0; j < le.size() && ret.size() != m; ++j) - { - if (s) - s--; - else - ret.insert(ret.begin(), le[j]); + for (unsigned j = 0; j < le.size() && ret.size() != m; ++j) + { + if (s) + s--; + else + ret.insert(ret.begin(), le[j]); + } } } + if (!total) + falsePos++; } + else + skipped++; if (n == end) break; } #if ETH_DEBUG -// cdebug << (begin - n) << "searched; " << skipped << "skipped; " << falsePos << "false +ves"; + cdebug << (begin - n) << "searched; " << skipped << "skipped; " << falsePos << "false +ves"; #endif return ret; } diff --git a/libethereum/MessageFilter.h b/libethereum/MessageFilter.h index 5602d7a17..482c68ef6 100644 --- a/libethereum/MessageFilter.h +++ b/libethereum/MessageFilter.h @@ -90,7 +90,6 @@ public: LogEntries matches(TransactionReceipt const& _r) const; LogFilter address(Address _a) { m_addresses.insert(_a); return *this; } - LogFilter from(Address _a) { return topic(u256((u160)_a) + 1); } LogFilter topic(h256 const& _t) { m_topics.insert(_t); return *this; } LogFilter withMax(unsigned _m) { m_max = _m; return *this; } LogFilter withSkip(unsigned _m) { m_skip = _m; return *this; } diff --git a/libethereum/State.cpp b/libethereum/State.cpp index a37c26645..34d9eae99 100644 --- a/libethereum/State.cpp +++ b/libethereum/State.cpp @@ -802,7 +802,7 @@ void State::commitToMine(BlockChain const& _bc) { uncommitToMine(); - cnote << "Committing to mine on block" << m_previousBlock.hash.abridged(); +// cnote << "Committing to mine on block" << m_previousBlock.hash.abridged(); #ifdef ETH_PARANOIA commit(); cnote << "Pre-reward stateRoot:" << m_state.root(); @@ -877,7 +877,7 @@ void State::commitToMine(BlockChain const& _bc) // Commit any and all changes to the trie that are in the cache, then update the state root accordingly. commit(); - cnote << "Post-reward stateRoot:" << m_state.root().abridged(); +// cnote << "Post-reward stateRoot:" << m_state.root().abridged(); // cnote << m_state; // cnote << *this; diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 2676913e5..6589c9068 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -113,17 +113,6 @@ static dev::eth::LogFilter toLogFilter(Json::Value const& _json) // commented to filter.withMax(_json["max"].asInt()); if (_json["skip"].isInt()) filter.withSkip(_json["skip"].asInt()); - if (!_json["from"].empty()) - { - if (_json["from"].isArray()) - { - for (auto i : _json["from"]) - if (i.isString()) - filter.from(jsToAddress(i.asString())); - } - else if (_json["from"].isString()) - filter.from(jsToAddress(_json["from"].asString())); - } if (!_json["address"].empty()) { if (_json["address"].isArray()) @@ -133,7 +122,7 @@ static dev::eth::LogFilter toLogFilter(Json::Value const& _json) // commented to filter.address(jsToAddress(i.asString())); } else if (_json["address"].isString()) - filter.from(jsToAddress(_json["address"].asString())); + filter.address(jsToAddress(_json["address"].asString())); } if (!_json["topics"].empty()) { From ee7c423868695f3b2c68b1fa6d07c7d588599ce7 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 13:09:05 +0100 Subject: [PATCH 35/38] common changes --- libjsqrc/ethereum.js | 19 ++++++----- libweb3jsonrpc/WebThreeStubServer.cpp | 12 +++++-- libweb3jsonrpc/WebThreeStubServer.h | 3 +- libweb3jsonrpc/abstractwebthreestubserver.h | 19 +++++++---- libweb3jsonrpc/spec.json | 3 +- test/webthreestubclient.h | 35 ++++++++++++++------- 6 files changed, 59 insertions(+), 32 deletions(-) diff --git a/libjsqrc/ethereum.js b/libjsqrc/ethereum.js index 43ac12fd8..cbff8b341 100644 --- a/libjsqrc/ethereum.js +++ b/libjsqrc/ethereum.js @@ -217,7 +217,7 @@ module.exports = { You should have received a copy of the GNU Lesser General Public License along with ethereum.js. If not, see . */ -/** @file websocket.js +/** @file autoprovider.js * @authors: * Marek Kotewicz * Marian Oancea @@ -231,7 +231,7 @@ module.exports = { */ if ("build" !== 'build') {/* var WebSocket = require('ws'); // jshint ignore:line - var web3 = require('./web3'); // jshint ignore:line + var web3 = require('./main.js'); // jshint ignore:line */} var AutoProvider = function (userOptions) { @@ -247,13 +247,13 @@ var AutoProvider = function (userOptions) { this.provider = new web3.providers.QtProvider(); return; } - + userOptions = userOptions || {}; var options = { httprpc: userOptions.httprpc || 'http://localhost:8080', websockets: userOptions.websockets || 'ws://localhost:40404/eth' }; - + var self = this; var closeWithSuccess = function (success) { ws.close(); @@ -274,7 +274,7 @@ var AutoProvider = function (userOptions) { var ws = new WebSocket(options.websockets); ws.onopen = function() { - closeWithSuccess(true); + closeWithSuccess(true); }; ws.onerror = function() { @@ -553,7 +553,8 @@ var ethMethods = function () { { name: 'compilers', call: 'eth_compilers' }, { name: 'lll', call: 'eth_lll' }, { name: 'solidity', call: 'eth_solidity' }, - { name: 'serpent', call: 'eth_serpent' } + { name: 'serpent', call: 'eth_serpent' }, + { name: 'logs', call: 'eth_logs' } ]; return methods; }; @@ -599,7 +600,7 @@ var ethWatchMethods = function () { return [ { name: 'newFilter', call: newFilter }, { name: 'uninstallFilter', call: 'eth_uninstallFilter' }, - { name: 'logs', call: 'eth_getMessages' } + { name: 'getMessages', call: 'eth_filterLogs' } ]; }; @@ -904,8 +905,6 @@ Filter.prototype.messages = function() { }); }; -Filter.prototype.logs = Filter.prototype.messages; - function messageHandler(data) { if(data._event !== undefined) { web3.trigger(data._event, data._id, data.data); @@ -1062,4 +1061,4 @@ module.exports = web3; },{"./lib/autoprovider":2,"./lib/contract":3,"./lib/httprpc":4,"./lib/main":5,"./lib/qt":6,"./lib/websocket":7}]},{},[]) -//# sourceMappingURL=ethereum.js.map +//# sourceMappingURL=ethereum.js.map \ No newline at end of file diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 2676913e5..410f2d3cd 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -394,14 +394,20 @@ std::string WebThreeStubServer::db_get(std::string const& _name, std::string con return toJS(dev::asBytes(ret)); } -Json::Value WebThreeStubServer::eth_getLogs(int const& _id) +Json::Value WebThreeStubServer::eth_filterLogs(int const& _id) { if (!client()) - return Json::Value(); -// return toJson(client()->messages(_id)); + return Json::Value(Json::arrayValue); return toJson(client()->logs(_id)); } +Json::Value WebThreeStubServer::eth_logs(Json::Value const& _json) +{ + if (!client()) + return Json::Value(Json::arrayValue); + return toJson(client()->logs(toLogFilter(_json))); +} + std::string WebThreeStubServer::db_getString(std::string const& _name, std::string const& _key) { bytes k = sha3(_name).asBytes() + sha3(_key).asBytes(); diff --git a/libweb3jsonrpc/WebThreeStubServer.h b/libweb3jsonrpc/WebThreeStubServer.h index 007c06cb8..cf969186d 100644 --- a/libweb3jsonrpc/WebThreeStubServer.h +++ b/libweb3jsonrpc/WebThreeStubServer.h @@ -76,7 +76,8 @@ public: virtual double eth_countAt(std::string const& _address); virtual int eth_defaultBlock(); virtual std::string eth_gasPrice(); - virtual Json::Value eth_getLogs(int const& _id); + virtual Json::Value eth_filterLogs(int const& _id); + virtual Json::Value eth_logs(Json::Value const& _json); virtual bool eth_listening(); virtual bool eth_mining(); virtual int eth_newFilter(Json::Value const& _json); diff --git a/libweb3jsonrpc/abstractwebthreestubserver.h b/libweb3jsonrpc/abstractwebthreestubserver.h index fd3f8b051..c1208b5c4 100644 --- a/libweb3jsonrpc/abstractwebthreestubserver.h +++ b/libweb3jsonrpc/abstractwebthreestubserver.h @@ -28,10 +28,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerbindAndAddMethod(new jsonrpc::Procedure("eth_compilers", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, NULL), &AbstractWebThreeStubServer::eth_compilersI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_countAt", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_REAL, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_countAtI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_defaultBlock", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_defaultBlockI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_filterLogs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_filterLogsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_gasPrice", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_gasPriceI); - this->bindAndAddMethod(new jsonrpc::Procedure("eth_getLogs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_INTEGER, NULL), &AbstractWebThreeStubServer::eth_getLogsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_listening", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_listeningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_lll", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_STRING, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_lllI); + this->bindAndAddMethod(new jsonrpc::Procedure("eth_logs", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_ARRAY, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_logsI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_mining", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_BOOLEAN, NULL), &AbstractWebThreeStubServer::eth_miningI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilter", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_OBJECT, NULL), &AbstractWebThreeStubServer::eth_newFilterI); this->bindAndAddMethod(new jsonrpc::Procedure("eth_newFilterString", jsonrpc::PARAMS_BY_POSITION, jsonrpc::JSON_INTEGER, "param1",jsonrpc::JSON_STRING, NULL), &AbstractWebThreeStubServer::eth_newFilterStringI); @@ -137,14 +138,14 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_defaultBlock(); } - inline virtual void eth_gasPriceI(const Json::Value& request, Json::Value& response) + inline virtual void eth_filterLogsI(const Json::Value& request, Json::Value& response) { - response = this->eth_gasPrice(); + response = this->eth_filterLogs(request[0u].asInt()); } - inline virtual void eth_getLogsI(const Json::Value& request, Json::Value& response) + inline virtual void eth_gasPriceI(const Json::Value& request, Json::Value& response) { - response = this->eth_getLogs(request[0u].asInt()); + response = this->eth_gasPrice(); } inline virtual void eth_listeningI(const Json::Value& request, Json::Value& response) @@ -157,6 +158,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServereth_lll(request[0u].asString()); } + inline virtual void eth_logsI(const Json::Value& request, Json::Value& response) + { + response = this->eth_logs(request[0u]); + } + inline virtual void eth_miningI(const Json::Value& request, Json::Value& response) { response = this->eth_mining(); @@ -308,10 +314,11 @@ class AbstractWebThreeStubServer : public jsonrpc::AbstractServerclient->CallMethod("eth_gasPrice",p); - if (result.isString()) - return result.asString(); + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_filterLogs",p); + if (result.isArray()) + return result; else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); } - Json::Value eth_getLogs(const int& param1) throw (jsonrpc::JsonRpcException) + std::string eth_gasPrice() throw (jsonrpc::JsonRpcException) { Json::Value p; - p.append(param1); - - Json::Value result = this->client->CallMethod("eth_getLogs",p); - if (result.isArray()) - return result; + p = Json::nullValue; + Json::Value result = this->client->CallMethod("eth_gasPrice",p); + if (result.isString()) + return result.asString(); else throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); @@ -266,6 +266,19 @@ p.append(param3); } + Json::Value eth_logs(const Json::Value& param1) throw (jsonrpc::JsonRpcException) + { + Json::Value p; + p.append(param1); + + Json::Value result = this->client->CallMethod("eth_logs",p); + if (result.isArray()) + return result; + else + throw jsonrpc::JsonRpcException(jsonrpc::Errors::ERROR_CLIENT_INVALID_RESPONSE, result.toStyledString()); + + } + bool eth_mining() throw (jsonrpc::JsonRpcException) { Json::Value p; From d59a5713500d35157e0a9c322e3c3ee743cfc612 Mon Sep 17 00:00:00 2001 From: Marek Kotewicz Date: Tue, 18 Nov 2014 13:11:12 +0100 Subject: [PATCH 36/38] logs method in ethereum.js --- libjsqrc/ethereum.js | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/libjsqrc/ethereum.js b/libjsqrc/ethereum.js index cbff8b341..cc8afc932 100644 --- a/libjsqrc/ethereum.js +++ b/libjsqrc/ethereum.js @@ -905,6 +905,10 @@ Filter.prototype.messages = function() { }); }; +Filter.prototype.logs = function () { + return this.messages(); +}; + function messageHandler(data) { if(data._event !== undefined) { web3.trigger(data._event, data._id, data.data); From e81197606ae29c4be3ac37ad4e8aaf699fbcd039 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 13:21:36 +0100 Subject: [PATCH 37/38] Log & watches. --- libethereum/Client.cpp | 2 ++ 1 file changed, 2 insertions(+) diff --git a/libethereum/Client.cpp b/libethereum/Client.cpp index 6405134c7..183a072e3 100644 --- a/libethereum/Client.cpp +++ b/libethereum/Client.cpp @@ -224,6 +224,7 @@ void Client::noteChanged(h256Set const& _filters) void Client::appendFromNewPending(LogBloom _bloom, h256Set& o_changed) const { + // TODO: more precise check on whether the txs match. lock_guard l(m_filterLock); for (pair const& i: m_filters) if ((unsigned)i.second.filter.latest() > m_bc.number() && i.second.filter.matches(_bloom)) @@ -232,6 +233,7 @@ void Client::appendFromNewPending(LogBloom _bloom, h256Set& o_changed) const void Client::appendFromNewBlock(h256 _block, h256Set& o_changed) const { + // TODO: more precise check on whether the txs match. auto d = m_bc.info(_block); lock_guard l(m_filterLock); From 85e3bd49397bfbba564148796704f938f6af87c2 Mon Sep 17 00:00:00 2001 From: Gav Wood Date: Tue, 18 Nov 2014 13:40:32 +0100 Subject: [PATCH 38/38] Allow data to be passed in old way. --- libweb3jsonrpc/WebThreeStubServer.cpp | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) diff --git a/libweb3jsonrpc/WebThreeStubServer.cpp b/libweb3jsonrpc/WebThreeStubServer.cpp index 6a91080e3..8ee9ee722 100644 --- a/libweb3jsonrpc/WebThreeStubServer.cpp +++ b/libweb3jsonrpc/WebThreeStubServer.cpp @@ -310,9 +310,16 @@ static TransactionSkeleton toTransaction(Json::Value const& _json) else if (_json["gasPrice"].isInt()) ret.gas = u256(_json["gas"].asInt()); } - if (_json["data"].isString()) - ret.data = jsToBytes(_json["data"].asString()); - else if (_json["code"].isString()) + if (!_json["data"].empty()) + { + if (_json["data"].isString()) // ethereum.js has preconstructed the data array + ret.data = jsToBytes(_json["data"].asString()); + else if (_json["data"].isArray()) // old style: array of 32-byte-padded values. TODO: remove PoC-8 + for (auto i: _json["data"]) + dev::operator +=(ret.data, padded(jsToBytes(i.asString()), 32)); + } + + if (_json["code"].isString()) ret.data = jsToBytes(_json["code"].asString()); return ret; }