From 82a84a06da88706fd57b937049d7756cf853b5aa Mon Sep 17 00:00:00 2001 From: serkixenos Date: Thu, 12 May 2022 13:54:52 +0200 Subject: [PATCH 01/36] Update README instructions for docker build --- README.md | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/README.md b/README.md index fc96f957..c626bf9d 100644 --- a/README.md +++ b/README.md @@ -165,6 +165,18 @@ docker pull datasecuritynode/peerplays:latest ### Building docker images manually ``` +# Checkout the code +git clone https://gitlab.com/PBSA/peerplays.git +cd peerplays + +# Checkout the branch you want +# E.g. +# git checkout beatrice +# git checkout develop +git checkout master + +git submodule update --init --recursive + # Execute from the project root, must be a docker group member # Build docker image, using Ubuntu 20.04 base From 23cdcec381fa2866c6b24684da99971671bb9165 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 13 May 2022 03:26:30 +0200 Subject: [PATCH 02/36] Update README instructions for starting docker containers --- README.md | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index c626bf9d..12949dd5 100644 --- a/README.md +++ b/README.md @@ -188,7 +188,11 @@ docker build --no-cache -f Dockerfile.18.04 -t peerplays-18-04 . ### Start docker image ``` -docker start peerplays +# Start docker image, using Ubuntu 20.04 base +docker run peerplays:latest + +# Start docker image, using Ubuntu 18.04 base +docker run peerplays-18-04:latest ``` Rest of the instructions on starting the chain remains same. From d13551a2773d93cdfc5ec6d63fe38229f1cc7757 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Thu, 12 May 2022 01:31:13 +0200 Subject: [PATCH 03/36] Remove fc based RNG --- libraries/fc | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/fc b/libraries/fc index 6171e973..e7369949 160000 --- a/libraries/fc +++ b/libraries/fc @@ -1 +1 @@ -Subproject commit 6171e973c7fcfc9e0a39eaee2f05da84416a90e6 +Subproject commit e7369949bea26f3201d8442ba78286a88df74762 From b4501167eef2ad3b78d5f3d54c70a60e8e4e556f Mon Sep 17 00:00:00 2001 From: serkixenos Date: Thu, 12 May 2022 13:54:52 +0200 Subject: [PATCH 04/36] Update README instructions for docker build From 8f32e4cdb5ac6acbd76c00ac8d73144479fdc858 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 13 May 2022 03:26:30 +0200 Subject: [PATCH 05/36] Update README instructions for starting docker containers From 3152d47eea662b3fab71af1105d13e41f6669cbd Mon Sep 17 00:00:00 2001 From: serkixenos Date: Mon, 16 May 2022 20:46:40 +0200 Subject: [PATCH 06/36] Update GitLab CI file, more manual build options --- .gitlab-ci.yml | 44 ++++++++++++++++++++++++++++++++++++++++++-- 1 file changed, 42 insertions(+), 2 deletions(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index e65c81c8..fb2ed763 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -29,6 +29,18 @@ build: tags: - builder +test: + stage: test + dependencies: + - build + script: + - ./build/libraries/fc/tests/all_tests + - ./build/tests/betting_test --log_level=message + - ./build/tests/chain_test --log_level=message + - ./build/tests/cli_test --log_level=message + tags: + - builder + dockerize: stage: build variables: @@ -41,13 +53,37 @@ dockerize: - docker push $IMAGE tags: - builder + when: + manual + timeout: + 3h + +build-testnet: + stage: build + script: + - rm -rf .git/modules/docs .git/modules/libraries/fc ./docs ./libraries/fc + - git submodule sync + - git submodule update --init --recursive + - rm -rf build + - mkdir build + - cd build + - cmake -DCMAKE_BUILD_TYPE=Release -DBUILD_PEERPLAYS_TESTNET=1 .. + - make -j$(nproc) + artifacts: + untracked: true + paths: + - build/libraries/ + - build/programs/ + - build/tests/ + tags: + - builder when: manual timeout: 3h -test: +test-testnet: stage: test dependencies: - - build + - build-testnet script: - ./build/libraries/fc/tests/all_tests - ./build/tests/betting_test --log_level=message @@ -55,3 +91,7 @@ test: - ./build/tests/cli_test --log_level=message tags: - builder + when: + manual + timeout: + 1h From ab32415d0c118ab8e71f9037dabd6dc22b503d8c Mon Sep 17 00:00:00 2001 From: serkixenos Date: Thu, 19 May 2022 18:02:09 +0200 Subject: [PATCH 07/36] Update GitLab CI file, more manual build options --- .gitlab-ci.yml | 40 +++++++++++++++++++++++++++++++++------- 1 file changed, 33 insertions(+), 7 deletions(-) diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index fb2ed763..b16716ca 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -8,8 +8,9 @@ include: stages: - build - test + - dockerize -build: +build-mainnet: stage: build script: - rm -rf .git/modules/docs .git/modules/libraries/fc ./docs ./libraries/fc @@ -29,10 +30,10 @@ build: tags: - builder -test: +test-mainnet: stage: test dependencies: - - build + - build-mainnet script: - ./build/libraries/fc/tests/all_tests - ./build/tests/betting_test --log_level=message @@ -41,16 +42,20 @@ test: tags: - builder -dockerize: - stage: build +dockerize-mainnet: + stage: dockerize + dependencies: + - test-mainnet variables: - IMAGE: $CI_REGISTRY_IMAGE/$CI_COMMIT_REF_SLUG:$CI_COMMIT_SHA + IMAGE: $CI_REGISTRY_IMAGE/mainnet/$CI_COMMIT_REF_SLUG:$CI_COMMIT_SHA before_script: - docker info - docker login -u "$CI_REGISTRY_USER" -p "$CI_REGISTRY_PASSWORD" $CI_REGISTRY script: - - docker build -t $IMAGE . + - docker build --no-cache -t $IMAGE . - docker push $IMAGE + after_script: + - docker rmi $IMAGE tags: - builder when: @@ -95,3 +100,24 @@ test-testnet: manual timeout: 1h + +dockerize-testnet: + stage: dockerize + dependencies: + - test-testnet + variables: + IMAGE: $CI_REGISTRY_IMAGE/testnet/$CI_COMMIT_REF_SLUG:$CI_COMMIT_SHA + before_script: + - docker info + - docker login -u "$CI_REGISTRY_USER" -p "$CI_REGISTRY_PASSWORD" $CI_REGISTRY + script: + - docker build --no-cache -t $IMAGE . + - docker push $IMAGE + after_script: + - docker rmi $IMAGE + tags: + - builder + when: + manual + timeout: + 3h From b3e426999d7ff78032a5873d3c6d05e076c4abe1 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Wed, 25 May 2022 16:48:38 +0200 Subject: [PATCH 08/36] Remove unused libreadline-dev library --- Dockerfile | 1 - Dockerfile.18.04 | 1 - README.md | 13 +++++++------ 3 files changed, 7 insertions(+), 8 deletions(-) diff --git a/Dockerfile b/Dockerfile index e90e5380..7a76c136 100644 --- a/Dockerfile +++ b/Dockerfile @@ -23,7 +23,6 @@ RUN \ libbz2-dev \ libcurl4-openssl-dev \ libncurses-dev \ - libreadline-dev \ libsnappy-dev \ libssl-dev \ libtool \ diff --git a/Dockerfile.18.04 b/Dockerfile.18.04 index 5e928263..d3fa1d75 100644 --- a/Dockerfile.18.04 +++ b/Dockerfile.18.04 @@ -21,7 +21,6 @@ RUN \ libbz2-dev \ libcurl4-openssl-dev \ libncurses-dev \ - libreadline-dev \ libsnappy-dev \ libssl-dev \ libtool \ diff --git a/README.md b/README.md index 12949dd5..a8d98021 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,7 @@ Following dependencies are needed for a clean install of Ubuntu 20.04: sudo apt-get install \ apt-utils autoconf bash build-essential ca-certificates clang-format cmake \ dnsutils doxygen expect git graphviz libboost-all-dev libbz2-dev \ - libcurl4-openssl-dev libncurses-dev libreadline-dev libsnappy-dev \ + libcurl4-openssl-dev libncurses-dev libsnappy-dev \ libssl-dev libtool libzip-dev locales lsb-release mc nano net-tools ntp \ openssh-server pkg-config perl python3 python3-jinja2 sudo \ systemd-coredump wget @@ -74,11 +74,12 @@ sudo make install # this can install the executable files under /usr/local Following dependencies are needed for a clean install of Ubuntu 18.04: ``` sudo apt-get install \ - apt-utils autoconf bash build-essential ca-certificates dnsutils doxygen \ - expect git graphviz libbz2-dev libcurl4-openssl-dev libncurses-dev \ - libreadline-dev libsnappy-dev libssl-dev libtool libzip-dev locales \ - lsb-release mc nano net-tools ntp openssh-server pkg-config perl \ - python3 python3-jinja2 sudo systemd-coredump wget + apt-utils autoconf bash build-essential ca-certificates clang-format \ + dnsutils doxygen expect git graphviz libbz2-dev \ + libcurl4-openssl-dev libncurses-dev libsnappy-dev \ + libssl-dev libtool libzip-dev locales lsb-release mc nano net-tools ntp \ + openssh-server pkg-config perl python3 python3-jinja2 sudo \ + systemd-coredump wget ``` Install Boost libraries from source From bc7d03cb22399be94b83fab6f19746a91571e9c1 Mon Sep 17 00:00:00 2001 From: Davor Hirunda Date: Thu, 2 Jun 2022 16:18:15 +0000 Subject: [PATCH 09/36] Fix for scheduler wrong state --- .../chain/include/graphene/chain/global_property_object.hpp | 1 + libraries/net/node.cpp | 1 + 2 files changed, 2 insertions(+) diff --git a/libraries/chain/include/graphene/chain/global_property_object.hpp b/libraries/chain/include/graphene/chain/global_property_object.hpp index 0f95a6e3..53bdec08 100644 --- a/libraries/chain/include/graphene/chain/global_property_object.hpp +++ b/libraries/chain/include/graphene/chain/global_property_object.hpp @@ -131,6 +131,7 @@ namespace graphene { namespace chain { }} FC_REFLECT_DERIVED( graphene::chain::dynamic_global_property_object, (graphene::db::object), + (random) (head_block_number) (head_block_id) (time) diff --git a/libraries/net/node.cpp b/libraries/net/node.cpp index 3222da08..37db57e2 100644 --- a/libraries/net/node.cpp +++ b/libraries/net/node.cpp @@ -91,6 +91,7 @@ #define DEFAULT_LOGGER "p2p" #define P2P_IN_DEDICATED_THREAD 1 +#define DISABLE_WITNESS_HF_CHECK 1 #define INVOCATION_COUNTER(name) \ static unsigned total_ ## name ## _counter = 0; \ From 03e37896d5d2cd03a2ce21c5a0f833b27a40606c Mon Sep 17 00:00:00 2001 From: Davor Hirunda Date: Wed, 8 Jun 2022 22:02:40 +0000 Subject: [PATCH 10/36] Cancel the thread for sync blocks --- libraries/app/application.cpp | 9 +++++++++ libraries/net/node.cpp | 4 +++- 2 files changed, 12 insertions(+), 1 deletion(-) diff --git a/libraries/app/application.cpp b/libraries/app/application.cpp index 19f1ed10..fd4c0620 100644 --- a/libraries/app/application.cpp +++ b/libraries/app/application.cpp @@ -48,6 +48,7 @@ #include #include +#include #include #include @@ -107,6 +108,7 @@ public: fc::optional _lock_file; bool _is_block_producer = false; bool _force_validate = false; + std::atomic_bool _running{true}; void reset_p2p_node(const fc::path &data_dir) { try { @@ -450,6 +452,12 @@ public: */ virtual bool handle_block(const graphene::net::block_message &blk_msg, bool sync_mode, std::vector &contained_transaction_message_ids) override { + + // check point for the threads which may be cancled on application shutdown + if(!_running.load()) { + return true; + } + try { auto latency = fc::time_point::now() - blk_msg.block.timestamp; FC_ASSERT((latency.count() / 1000) > -5000, "Rejecting block with timestamp in the future"); @@ -1008,6 +1016,7 @@ void application::shutdown_plugins() { return; } void application::shutdown() { + my->_running.store(false); if (my->_p2p_network) my->_p2p_network->close(); if (my->_chain_db) diff --git a/libraries/net/node.cpp b/libraries/net/node.cpp index 37db57e2..8a92dd89 100644 --- a/libraries/net/node.cpp +++ b/libraries/net/node.cpp @@ -888,7 +888,7 @@ namespace graphene { namespace net { namespace detail { void node_impl::p2p_network_connect_loop() { VERIFY_CORRECT_THREAD(); - while (!_p2p_network_connect_loop_done.canceled()) + while (!_p2p_network_connect_loop_done.canceled() && !_node_is_shutting_down) { try { @@ -3962,6 +3962,8 @@ namespace graphene { namespace net { namespace detail { { VERIFY_CORRECT_THREAD(); + _node_is_shutting_down = true; + try { _potential_peer_db.close(); From 7fd12ccce8798687bc5b86ff7d21d9a0c52a3e6c Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Thu, 9 Jun 2022 21:41:19 +0300 Subject: [PATCH 11/36] #386 - check valid() for optional --- libraries/chain/db_block.cpp | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/libraries/chain/db_block.cpp b/libraries/chain/db_block.cpp index 67601c2e..5f53b603 100644 --- a/libraries/chain/db_block.cpp +++ b/libraries/chain/db_block.cpp @@ -433,7 +433,12 @@ processed_transaction database::push_proposal(const proposal_object& proposal) { for( size_t i=old_applied_ops_size,n=_applied_ops.size(); iresult = result; else { From 3294480e20d8ee010b7aec3d391e54e9f32bd252 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Mon, 16 May 2022 20:46:40 +0200 Subject: [PATCH 12/36] Update GitLab CI file, more manual build options From f03cc7ee9050bea3c64e8460dc89f84164a6ef92 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Mon, 4 Apr 2022 23:22:34 -0400 Subject: [PATCH 13/36] Sidechain API, SONs listener log From 092a46ae6137a99025ddfb8e5ac13093b6243282 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Wed, 15 Jun 2022 05:31:41 +0200 Subject: [PATCH 14/36] Remove unscheduled hardfork CORE 210 --- .gitlab-ci.yml | 6 ++++-- libraries/chain/db_block.cpp | 2 +- libraries/chain/db_notify.cpp | 10 +++------- libraries/chain/hardfork.d/CORE_210.hf | 10 ---------- libraries/chain/proposal_evaluator.cpp | 6 ++---- libraries/chain/proposal_object.cpp | 2 +- .../plugins/account_history/account_history_plugin.cpp | 6 ++---- .../plugins/elasticsearch/elasticsearch_plugin.cpp | 6 ++---- 8 files changed, 15 insertions(+), 33 deletions(-) delete mode 100644 libraries/chain/hardfork.d/CORE_210.hf diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml index b16716ca..cda41654 100644 --- a/.gitlab-ci.yml +++ b/.gitlab-ci.yml @@ -82,8 +82,10 @@ build-testnet: - build/tests/ tags: - builder - when: manual - timeout: 3h + when: + manual + timeout: + 3h test-testnet: stage: test diff --git a/libraries/chain/db_block.cpp b/libraries/chain/db_block.cpp index 5f53b603..c475813b 100644 --- a/libraries/chain/db_block.cpp +++ b/libraries/chain/db_block.cpp @@ -811,7 +811,7 @@ processed_transaction database::_apply_transaction(const signed_transaction& trx return get_account_custom_authorities(id, op); }; trx.verify_authority( chain_id, get_active, get_owner, get_custom, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(head_block_time()), + true, get_global_properties().parameters.max_authority_depth ); } diff --git a/libraries/chain/db_notify.cpp b/libraries/chain/db_notify.cpp index c5986fad..62d6d2bf 100644 --- a/libraries/chain/db_notify.cpp +++ b/libraries/chain/db_notify.cpp @@ -625,7 +625,6 @@ void database::notify_changed_objects() if( _undo_db.enabled() ) { const auto& head_undo = _undo_db.head(); - auto chain_time = head_block_time(); // New if( !new_objects.empty() ) @@ -637,8 +636,7 @@ void database::notify_changed_objects() new_ids.push_back(item); auto obj = find_object(item); if(obj != nullptr) - get_relevant_accounts(obj, new_accounts_impacted, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(chain_time)); + get_relevant_accounts(obj, new_accounts_impacted, true); } GRAPHENE_TRY_NOTIFY( new_objects, new_ids, new_accounts_impacted) @@ -652,8 +650,7 @@ void database::notify_changed_objects() for( const auto& item : head_undo.old_values ) { changed_ids.push_back(item.first); - get_relevant_accounts(item.second.get(), changed_accounts_impacted, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(chain_time)); + get_relevant_accounts(item.second.get(), changed_accounts_impacted, true); } GRAPHENE_TRY_NOTIFY( changed_objects, changed_ids, changed_accounts_impacted) @@ -670,8 +667,7 @@ void database::notify_changed_objects() removed_ids.emplace_back( item.first ); auto obj = item.second.get(); removed.emplace_back( obj ); - get_relevant_accounts(obj, removed_accounts_impacted, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(chain_time)); + get_relevant_accounts(obj, removed_accounts_impacted, true); } GRAPHENE_TRY_NOTIFY( removed_objects, removed_ids, removed, removed_accounts_impacted) diff --git a/libraries/chain/hardfork.d/CORE_210.hf b/libraries/chain/hardfork.d/CORE_210.hf deleted file mode 100644 index cf3bdade..00000000 --- a/libraries/chain/hardfork.d/CORE_210.hf +++ /dev/null @@ -1,10 +0,0 @@ -// #210 Check authorities on custom_operation -#ifndef HARDFORK_CORE_210_TIME -#ifdef BUILD_PEERPLAYS_TESTNET -#define HARDFORK_CORE_210_TIME (fc::time_point_sec::from_iso_string("2030-01-01T00:00:00")) // (Not yet scheduled) -#else -#define HARDFORK_CORE_210_TIME (fc::time_point_sec::from_iso_string("2030-01-01T00:00:00")) // (Not yet scheduled) -#endif -// Bugfix: pre-HF 210, custom_operation's required_auths field was ignored. -#define MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(chain_time) (chain_time <= HARDFORK_CORE_210_TIME) -#endif diff --git a/libraries/chain/proposal_evaluator.cpp b/libraries/chain/proposal_evaluator.cpp index ac8ef601..28500304 100644 --- a/libraries/chain/proposal_evaluator.cpp +++ b/libraries/chain/proposal_evaluator.cpp @@ -302,8 +302,7 @@ void_result proposal_create_evaluator::do_evaluate( const proposal_create_operat vector other; for( auto& op : o.proposed_ops ) { - operation_get_required_authorities( op.op, auths, auths, other, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(block_time) ); + operation_get_required_authorities( op.op, auths, auths, other, true ); } FC_ASSERT( other.size() == 0 ); // TODO: what about other??? @@ -352,8 +351,7 @@ object_id_type proposal_create_evaluator::do_apply( const proposal_create_operat // TODO: consider caching values from evaluate? for( auto& op : _proposed_trx.operations ) - operation_get_required_authorities( op, required_active, proposal.required_owner_approvals, other, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(chain_time) ); + operation_get_required_authorities( op, required_active, proposal.required_owner_approvals, other, true); //All accounts which must provide both owner and active authority should be omitted from the active authority set; //owner authority approval implies active authority approval. diff --git a/libraries/chain/proposal_object.cpp b/libraries/chain/proposal_object.cpp index 662c700a..67eef6c7 100644 --- a/libraries/chain/proposal_object.cpp +++ b/libraries/chain/proposal_object.cpp @@ -39,7 +39,7 @@ bool proposal_object::is_authorized_to_execute( database& db ) const [&]( account_id_type id ){ return &id(db).owner; }, [&]( account_id_type id, const operation& op ){ return db.get_account_custom_authorities(id, op); }, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS( db.head_block_time() ), + true, db.get_global_properties().parameters.max_authority_depth, true, /* allow committee */ available_active_approvals, diff --git a/libraries/plugins/account_history/account_history_plugin.cpp b/libraries/plugins/account_history/account_history_plugin.cpp index db3fa464..60ce64f8 100644 --- a/libraries/plugins/account_history/account_history_plugin.cpp +++ b/libraries/plugins/account_history/account_history_plugin.cpp @@ -126,14 +126,12 @@ void account_history_plugin_impl::update_account_histories( const signed_block& flat_set impacted; vector other; // fee payer is added here - operation_get_required_authorities( op.op, impacted, impacted, other, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS( db.head_block_time() ) ); + operation_get_required_authorities( op.op, impacted, impacted, other, true ); if( op.op.which() == operation::tag< account_create_operation >::value ) impacted.insert( op.result.get() ); else - graphene::chain::operation_get_impacted_accounts( op.op, impacted, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS(db.head_block_time()) ); + graphene::chain::operation_get_impacted_accounts( op.op, impacted, true ); if( op.op.which() == operation::tag< lottery_end_operation >::value ) { auto lop = op.op.get< lottery_end_operation >(); diff --git a/libraries/plugins/elasticsearch/elasticsearch_plugin.cpp b/libraries/plugins/elasticsearch/elasticsearch_plugin.cpp index 491c011d..e306054a 100644 --- a/libraries/plugins/elasticsearch/elasticsearch_plugin.cpp +++ b/libraries/plugins/elasticsearch/elasticsearch_plugin.cpp @@ -173,14 +173,12 @@ bool elasticsearch_plugin_impl::update_account_histories( const signed_block& b flat_set impacted; vector other; // fee_payer is added here - operation_get_required_authorities( op.op, impacted, impacted, other, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS( db.head_block_time() ) ); + operation_get_required_authorities( op.op, impacted, impacted, other, true ); if( op.op.which() == operation::tag< account_create_operation >::value ) impacted.insert( op.result.get() ); else - operation_get_impacted_accounts( op.op, impacted, - MUST_IGNORE_CUSTOM_OP_REQD_AUTHS( db.head_block_time() ) ); + operation_get_impacted_accounts( op.op, impacted, true ); for( auto& a : other ) for( auto& item : a.account_auths ) From c102bef768b4abaef4b7acf1d475fffcaafdfd77 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Tue, 26 Apr 2022 13:09:41 +0000 Subject: [PATCH 15/36] #345 double-free-or-corruption --- .../graphene/peerplays_sidechain/sidechain_net_handler.hpp | 2 ++ .../plugins/peerplays_sidechain/sidechain_net_handler.cpp | 4 +++- 2 files changed, 5 insertions(+), 1 deletion(-) diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp index 3aa4465c..a9257e54 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp @@ -1,5 +1,6 @@ #pragma once +#include #include #include @@ -60,6 +61,7 @@ protected: std::map private_keys; std::vector son_listener_log; + std::mutex son_listener_log_mutex; void on_applied_block(const signed_block &b); diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp index 45fab4ee..7c87a9ef 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp @@ -619,13 +619,15 @@ void sidechain_net_handler::settle_sidechain_transactions() { } void sidechain_net_handler::add_to_son_listener_log(std::string trx_id) { + const std::lock_guard lock(son_listener_log_mutex); son_listener_log.insert(son_listener_log.begin(), trx_id); if (son_listener_log.size() > 33) { - son_listener_log.erase(son_listener_log.end()); + son_listener_log.pop_back(); } } std::vector sidechain_net_handler::get_son_listener_log() { + const std::lock_guard lock(son_listener_log_mutex); return son_listener_log; } From 4d112936d23ca045a94e3c7560c06667dcafec93 Mon Sep 17 00:00:00 2001 From: hirunda Date: Fri, 6 May 2022 13:08:34 +0200 Subject: [PATCH 16/36] Replace fc::random with std random generator --- libraries/net/node.cpp | 9 +++++++-- libraries/wallet/wallet.cpp | 10 +++++++--- tests/common/tournament_helper.cpp | 9 ++++++--- 3 files changed, 20 insertions(+), 8 deletions(-) diff --git a/libraries/net/node.cpp b/libraries/net/node.cpp index 8a92dd89..9118939d 100644 --- a/libraries/net/node.cpp +++ b/libraries/net/node.cpp @@ -30,6 +30,8 @@ #include #include #include +#include + #include #include @@ -67,7 +69,6 @@ #include #include #include -#include #include #include @@ -828,7 +829,11 @@ namespace graphene { namespace net { namespace detail { _maximum_blocks_per_peer_during_syncing(GRAPHENE_NET_MAX_BLOCKS_PER_PEER_DURING_SYNCING) { _rate_limiter.set_actual_rate_time_constant(fc::seconds(2)); - fc::rand_bytes(&_node_id.data[0], (int)_node_id.size()); + + using bytes_randomizer = std::independent_bits_engine; + std::random_device rd; + bytes_randomizer br(rd()); + std::generate(std::begin(_node_id.data), std::end(_node_id.data), std::ref(br)); } node_impl::~node_impl() diff --git a/libraries/wallet/wallet.cpp b/libraries/wallet/wallet.cpp index 0232bc44..d2fac215 100644 --- a/libraries/wallet/wallet.cpp +++ b/libraries/wallet/wallet.cpp @@ -29,6 +29,7 @@ #include #include #include +#include #include #include @@ -62,7 +63,6 @@ #include #include #include -#include #include #include @@ -7365,8 +7365,12 @@ signed_transaction wallet_api::rps_throw(game_id_type game_id, // construct the complete throw, the commit, and reveal rock_paper_scissors_throw full_throw; - fc::rand_bytes((char*)&full_throw.nonce1, sizeof(full_throw.nonce1)); - fc::rand_bytes((char*)&full_throw.nonce2, sizeof(full_throw.nonce2)); + std::random_device rd; + std::mt19937_64 gen(rd()); + std::uniform_int_distribution dis; + full_throw.nonce1 = dis(gen); + full_throw.nonce2 = dis(gen); + full_throw.gesture = gesture; rock_paper_scissors_throw_commit commit_throw; diff --git a/tests/common/tournament_helper.cpp b/tests/common/tournament_helper.cpp index 4cb27b08..b3172d8e 100644 --- a/tests/common/tournament_helper.cpp +++ b/tests/common/tournament_helper.cpp @@ -27,7 +27,7 @@ #include #include -#include +#include using namespace graphene::chain; @@ -276,8 +276,11 @@ void tournaments_helper::rps_throw(const game_id_type& game_id, // construct the complete throw, the commit, and reveal rock_paper_scissors_throw full_throw; - fc::rand_bytes((char*)&full_throw.nonce1, sizeof(full_throw.nonce1)); - fc::rand_bytes((char*)&full_throw.nonce2, sizeof(full_throw.nonce2)); + std::random_device rd; + std::mt19937_64 gen(rd()); + std::uniform_int_distribution dis; + full_throw.nonce1 = dis(gen); + full_throw.nonce2 = dis(gen); full_throw.gesture = gesture; rock_paper_scissors_throw_commit commit_throw; From d78e0d0e4847f16caf94371a3fefef13621f30a1 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Wed, 15 Jun 2022 06:30:33 +0200 Subject: [PATCH 17/36] Silence SON logs when not needed --- libraries/chain/db_maint.cpp | 10 +++++----- libraries/net/node.cpp | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/libraries/chain/db_maint.cpp b/libraries/chain/db_maint.cpp index 56ac6fd0..0c6843d9 100644 --- a/libraries/chain/db_maint.cpp +++ b/libraries/chain/db_maint.cpp @@ -660,6 +660,10 @@ void database::update_active_committee_members() void database::update_active_sons() { try { + if (head_block_time() < HARDFORK_SON_TIME) { + return; + } + assert( _son_count_histogram_buffer.size() > 0 ); share_type stake_target = (_total_voting_stake-_son_count_histogram_buffer[0]) / 2; @@ -759,11 +763,7 @@ void database::update_active_sons() } } - if (son_sets_equal) { - ilog( "Active SONs set NOT CHANGED" ); - } else { - ilog( "Active SONs set CHANGED" ); - + if (!son_sets_equal) { update_son_wallet(new_active_sons); update_son_statuses(cur_active_sons, new_active_sons); } diff --git a/libraries/net/node.cpp b/libraries/net/node.cpp index 9118939d..ce40cdf0 100644 --- a/libraries/net/node.cpp +++ b/libraries/net/node.cpp @@ -1337,7 +1337,7 @@ namespace graphene { namespace net { namespace detail { // reconnect with the rest of the network, or it might just futher isolate us. { // As usual, the first step is to walk through all our peers and figure out which - // peers need action (disconneting, sending keepalives, etc), then we walk through + // peers need action (disconneting, sending keepalives, etc), then we walk through // those lists yielding at our leisure later. ASSERT_TASK_NOT_PREEMPTED(); From bcdb355f48d8f1056e963c10123d173745ce1f31 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Mon, 9 May 2022 16:07:07 +0200 Subject: [PATCH 18/36] Fix P2P port/endpoint error message --- libraries/net/node.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/net/node.cpp b/libraries/net/node.cpp index ce40cdf0..6ea68832 100644 --- a/libraries/net/node.cpp +++ b/libraries/net/node.cpp @@ -4581,7 +4581,7 @@ namespace graphene { namespace net { namespace detail { error_message_stream << "Unable to listen for connections on port " << listen_endpoint.port() << ", retrying in a few seconds\n"; error_message_stream << "You can wait for it to become available, or restart this program using\n"; - error_message_stream << "the --p2p-port option to specify another port\n"; + error_message_stream << "the --p2p-endpoint option to specify another port\n"; first = false; } else From 1788038224a3882e7ea70f00cac221e55978ac8d Mon Sep 17 00:00:00 2001 From: serkixenos Date: Thu, 16 Jun 2022 02:04:58 +0200 Subject: [PATCH 19/36] Add hardcoded seed nodes to the config file --- libraries/app/application.cpp | 82 ++++++++++++---------------------- programs/witness_node/main.cpp | 6 --- 2 files changed, 28 insertions(+), 60 deletions(-) diff --git a/libraries/app/application.cpp b/libraries/app/application.cpp index fd4c0620..1d9066cf 100644 --- a/libraries/app/application.cpp +++ b/libraries/app/application.cpp @@ -117,67 +117,29 @@ public: _p2p_network->load_configuration(data_dir / "p2p"); _p2p_network->set_node_delegate(this); + vector all_seeds; + if (_options->count("seed-node")) { auto seeds = _options->at("seed-node").as>(); - for (const string &endpoint_string : seeds) { - try { - std::vector endpoints = resolve_string_to_ip_endpoints(endpoint_string); - for (const fc::ip::endpoint &endpoint : endpoints) { - ilog("Adding seed node ${endpoint}", ("endpoint", endpoint)); - _p2p_network->add_node(endpoint); - _p2p_network->connect_to_endpoint(endpoint); - } - } catch (const fc::exception &e) { - wlog("caught exception ${e} while adding seed node ${endpoint}", - ("e", e.to_detail_string())("endpoint", endpoint_string)); - } - } + all_seeds.insert(all_seeds.end(), seeds.begin(), seeds.end()); } if (_options->count("seed-nodes")) { auto seeds_str = _options->at("seed-nodes").as(); auto seeds = fc::json::from_string(seeds_str).as>(2); - for (const string &endpoint_string : seeds) { - try { - std::vector endpoints = resolve_string_to_ip_endpoints(endpoint_string); - for (const fc::ip::endpoint &endpoint : endpoints) { - ilog("Adding seed node ${endpoint}", ("endpoint", endpoint)); - _p2p_network->add_node(endpoint); - } - } catch (const fc::exception &e) { - wlog("caught exception ${e} while adding seed node ${endpoint}", - ("e", e.to_detail_string())("endpoint", endpoint_string)); - } - } - } else { - // t.me/peerplays #seednodes - vector seeds = { -#ifdef BUILD_PEERPLAYS_TESTNET + all_seeds.insert(all_seeds.end(), seeds.begin(), seeds.end()); + } -#else - "51.222.110.110:9777", - "95.216.90.243:9777", - "96.46.48.98:19777", - "96.46.48.98:29777", - "96.46.48.98:39777", - "96.46.48.98:49777", - "96.46.48.98:59777", - "seed.i9networks.net.br:9777", - "witness.serverpit.com:9777" -#endif - }; - - for (const string &endpoint_string : seeds) { - try { - std::vector endpoints = resolve_string_to_ip_endpoints(endpoint_string); - for (const fc::ip::endpoint &endpoint : endpoints) { - ilog("Adding seed node ${endpoint}", ("endpoint", endpoint)); - _p2p_network->add_node(endpoint); - } - } catch (const fc::exception &e) { - wlog("caught exception ${e} while adding seed node ${endpoint}", - ("e", e.to_detail_string())("endpoint", endpoint_string)); + for (const string &endpoint_string : all_seeds) { + try { + std::vector endpoints = resolve_string_to_ip_endpoints(endpoint_string); + for (const fc::ip::endpoint &endpoint : endpoints) { + ilog("Adding seed node ${endpoint}", ("endpoint", endpoint)); + _p2p_network->add_node(endpoint); } + } catch (const fc::exception &e) { + wlog("caught exception ${e} while adding seed node ${endpoint}", + ("e", e.to_detail_string())("endpoint", endpoint_string)); } } @@ -454,7 +416,7 @@ public: std::vector &contained_transaction_message_ids) override { // check point for the threads which may be cancled on application shutdown - if(!_running.load()) { + if (!_running.load()) { return true; } @@ -868,9 +830,21 @@ application::~application() { void application::set_program_options(boost::program_options::options_description &cli, boost::program_options::options_description &cfg) const { + + std::vector seed_nodes = { +#ifdef BUILD_PEERPLAYS_TESTNET +#else + "51.222.110.110:9777", + "95.216.90.243:9777", + "seed.i9networks.net.br:9777", + "witness.serverpit.com:9777" +#endif + }; + std::string seed_nodes_str = fc::json::to_string(seed_nodes); + cfg.add_options()("p2p-endpoint", bpo::value()->default_value("0.0.0.0:9777"), "Endpoint for P2P node to listen on"); cfg.add_options()("seed-node,s", bpo::value>()->composing(), "P2P nodes to connect to on startup (may specify multiple times)"); - cfg.add_options()("seed-nodes", bpo::value()->composing(), "JSON array of P2P nodes to connect to on startup"); + cfg.add_options()("seed-nodes", bpo::value()->composing()->default_value(seed_nodes_str), "JSON array of P2P nodes to connect to on startup"); cfg.add_options()("checkpoint,c", bpo::value>()->composing(), "Pairs of [BLOCK_NUM,BLOCK_ID] that should be enforced as checkpoints."); cfg.add_options()("rpc-endpoint", bpo::value()->default_value("127.0.0.1:8090"), "Endpoint for websocket RPC to listen on"); cfg.add_options()("rpc-tls-endpoint", bpo::value()->implicit_value("127.0.0.1:8089"), "Endpoint for TLS websocket RPC to listen on"); diff --git a/programs/witness_node/main.cpp b/programs/witness_node/main.cpp index af5086b2..c5eea447 100644 --- a/programs/witness_node/main.cpp +++ b/programs/witness_node/main.cpp @@ -79,18 +79,12 @@ int main(int argc, char** argv) { node->set_program_options(cli, cfg); cfg_options.add(cfg); - cfg_options.add_options() - ("plugins", bpo::value()->default_value("witness account_history market_history accounts_list affiliate_stats bookie"), - "Space-separated list of plugins to activate"); - auto witness_plug = node->register_plugin(); auto debug_witness_plug = node->register_plugin(); auto history_plug = node->register_plugin(); auto elasticsearch_plug = node->register_plugin(); auto es_objects_plug = node->register_plugin(); auto market_history_plug = node->register_plugin(); - //auto generate_genesis_plug = node->register_plugin(); - //auto generate_uia_sharedrop_genesis_plug = node->register_plugin(); auto list_plug = node->register_plugin(); auto affiliate_stats_plug = node->register_plugin(); auto bookie_plug = node->register_plugin(); From 9012e86bd1ad5bd58b262f0a4e3e6236cbdbd266 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 17 Jun 2022 00:10:21 +0200 Subject: [PATCH 20/36] Add more mainnet seed nodes --- libraries/app/application.cpp | 3 +++ 1 file changed, 3 insertions(+) diff --git a/libraries/app/application.cpp b/libraries/app/application.cpp index 1d9066cf..5f41df22 100644 --- a/libraries/app/application.cpp +++ b/libraries/app/application.cpp @@ -836,6 +836,9 @@ void application::set_program_options(boost::program_options::options_descriptio #else "51.222.110.110:9777", "95.216.90.243:9777", + "ca.peerplays.info", + "de.peerplays.xyz", + "pl.peerplays.org", "seed.i9networks.net.br:9777", "witness.serverpit.com:9777" #endif From 0a38927b0e12c553e2511c8be2642b03839d7017 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 17 Jun 2022 19:03:27 +0200 Subject: [PATCH 21/36] Allow querying witness_node version by API --- libraries/app/database_api.cpp | 25 +++++++++++++++++++ .../app/include/graphene/app/database_api.hpp | 15 +++++++++++ 2 files changed, 40 insertions(+) diff --git a/libraries/app/database_api.cpp b/libraries/app/database_api.cpp index a9ea9774..1095bbeb 100644 --- a/libraries/app/database_api.cpp +++ b/libraries/app/database_api.cpp @@ -29,12 +29,15 @@ #include #include +#include + #include #include #include #include +#include #include #include #include @@ -90,6 +93,7 @@ public: processed_transaction get_transaction(uint32_t block_num, uint32_t trx_in_block) const; // Globals + version_info get_version_info() const; chain_property_object get_chain_properties() const; global_property_object get_global_properties() const; fc::variant_object get_config() const; @@ -563,6 +567,27 @@ processed_transaction database_api_impl::get_transaction(uint32_t block_num, uin // // ////////////////////////////////////////////////////////////////////// +version_info database_api::get_version_info() const { + return my->get_version_info(); +} + +version_info database_api_impl::get_version_info() const { + + std::string witness_version(graphene::utilities::git_revision_description); + const size_t pos = witness_version.find('/'); + if (pos != std::string::npos && witness_version.size() > pos) + witness_version = witness_version.substr(pos + 1); + + version_info vi; + vi.version = witness_version; + vi.git_revision = graphene::utilities::git_revision_sha; + vi.built = std::string(__DATE__) + " at " + std::string(__TIME__); + vi.openssl = OPENSSL_VERSION_TEXT; + vi.boost = boost::replace_all_copy(std::string(BOOST_LIB_VERSION), "_", "."); + + return vi; +} + chain_property_object database_api::get_chain_properties() const { return my->get_chain_properties(); } diff --git a/libraries/app/include/graphene/app/database_api.hpp b/libraries/app/include/graphene/app/database_api.hpp index 93a2b88c..679d8a4c 100644 --- a/libraries/app/include/graphene/app/database_api.hpp +++ b/libraries/app/include/graphene/app/database_api.hpp @@ -130,6 +130,14 @@ struct gpos_info { share_type account_vested_balance; }; +struct version_info { + string version; + string git_revision; + string built; + string openssl; + string boost; +}; + /** * @brief The database_api class implements the RPC API for the chain database. * @@ -218,6 +226,11 @@ public: // Globals // ///////////// + /** + * @brief Retrieve the @ref version_info associated with the witness node + */ + version_info get_version_info() const; + /** * @brief Retrieve the @ref chain_property_object associated with the chain */ @@ -1040,6 +1053,7 @@ FC_REFLECT(graphene::app::market_ticker, (base)(quote)(latest)(lowest_ask)(highe FC_REFLECT(graphene::app::market_volume, (base)(quote)(base_volume)(quote_volume)); FC_REFLECT(graphene::app::market_trade, (date)(price)(amount)(value)); FC_REFLECT(graphene::app::gpos_info, (vesting_factor)(award)(total_amount)(current_subperiod)(last_voted_time)(allowed_withdraw_amount)(account_vested_balance)); +FC_REFLECT(graphene::app::version_info, (version)(git_revision)(built)(openssl)(boost)); FC_API(graphene::app::database_api, // Objects @@ -1060,6 +1074,7 @@ FC_API(graphene::app::database_api, (get_recent_transaction_by_id) // Globals + (get_version_info) (get_chain_properties) (get_global_properties) (get_config) From d650e197a984b7f65e328399593191fc73920f52 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Mon, 20 Jun 2022 14:07:17 +0200 Subject: [PATCH 22/36] Add port to sync node endpoints --- libraries/app/application.cpp | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/libraries/app/application.cpp b/libraries/app/application.cpp index 5f41df22..34a49e3d 100644 --- a/libraries/app/application.cpp +++ b/libraries/app/application.cpp @@ -836,9 +836,9 @@ void application::set_program_options(boost::program_options::options_descriptio #else "51.222.110.110:9777", "95.216.90.243:9777", - "ca.peerplays.info", - "de.peerplays.xyz", - "pl.peerplays.org", + "ca.peerplays.info:9777", + "de.peerplays.xyz:9777", + "pl.peerplays.org:9777", "seed.i9networks.net.br:9777", "witness.serverpit.com:9777" #endif From d234c3a8f8e2579ed97d3ec82f2a4c1701de483d Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 24 Jun 2022 14:38:23 +0200 Subject: [PATCH 23/36] Set HARDFORK_SON3_TIME to 2022-07-16T00:00:00 --- libraries/chain/hardfork.d/SON3.hf | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/libraries/chain/hardfork.d/SON3.hf b/libraries/chain/hardfork.d/SON3.hf index 36347c09..d9556e30 100644 --- a/libraries/chain/hardfork.d/SON3.hf +++ b/libraries/chain/hardfork.d/SON3.hf @@ -1,7 +1,7 @@ #ifndef HARDFORK_SON3_TIME #ifdef BUILD_PEERPLAYS_TESTNET -#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-05-31T00:00:00")) +#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-07-16T00:00:00")) #else -#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-05-31T00:00:00")) +#define HARDFORK_SON3_TIME (fc::time_point_sec::from_iso_string("2022-07-16T00:00:00")) #endif #endif From a30325660dcfefb88b694b975f8896ab5c736813 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Fri, 4 Nov 2022 07:51:22 +0200 Subject: [PATCH 24/36] #470 Don't use admin_nodeInfo when get network_id --- .../sidechain_net_handler_ethereum.hpp | 2 +- .../sidechain_net_handler_ethereum.cpp | 17 +++++++++-------- 2 files changed, 10 insertions(+), 9 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp index 3944d0a2..322cf5f9 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp @@ -15,9 +15,9 @@ class ethereum_rpc_client : public rpc_client { public: ethereum_rpc_client(const std::string &url, const std::string &user_name, const std::string &password, bool debug_rpc_calls); - std::string admin_node_info(); std::string eth_get_block_by_number(std::string block_number, bool full_block); std::string eth_get_logs(std::string wallet_contract_address); + std::string eth_chainId(); std::string net_version(); std::string eth_get_transaction_count(const std::string ¶ms); std::string eth_gas_price(); diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index 02ec5bce..c71c4748 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -28,10 +28,6 @@ ethereum_rpc_client::ethereum_rpc_client(const std::string &url, const std::stri rpc_client(url, user_name, password, debug_rpc_calls) { } -std::string ethereum_rpc_client::admin_node_info() { - return send_post_request("admin_nodeInfo", "", debug_rpc_calls); -} - std::string ethereum_rpc_client::eth_get_block_by_number(std::string block_number, bool full_block) { const std::string params = "[ \"" + block_number + "\", " + (full_block ? "true" : "false") + "]"; return send_post_request("eth_getBlockByNumber", params, debug_rpc_calls); @@ -43,6 +39,10 @@ std::string ethereum_rpc_client::eth_get_logs(std::string wallet_contract_addres return retrieve_value_from_reply(reply_str, ""); } +std::string ethereum_rpc_client::eth_chainId() { + return send_post_request("eth_chainId", "", debug_rpc_calls); +} + std::string ethereum_rpc_client::net_version() { return send_post_request("net_version", "", debug_rpc_calls); } @@ -56,13 +56,14 @@ std::string ethereum_rpc_client::eth_gas_price() { } std::string ethereum_rpc_client::get_chain_id() { - const std::string reply_str = net_version(); - return retrieve_value_from_reply(reply_str, ""); + const std::string reply_str = eth_chainId(); + const auto chain_id_string = retrieve_value_from_reply(reply_str, ""); + return chain_id_string.empty() ? "" : std::to_string(ethereum::from_hex(chain_id_string)); } std::string ethereum_rpc_client::get_network_id() { - const std::string reply_str = admin_node_info(); - return retrieve_value_from_reply(reply_str, "protocols.eth.network"); + const std::string reply_str = net_version(); + return retrieve_value_from_reply(reply_str, ""); } std::string ethereum_rpc_client::get_nonce(const std::string &address) { From 759dac5d413d70226683ce9176dbf305249a6f21 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Mon, 7 Nov 2022 12:16:59 +0200 Subject: [PATCH 25/36] #476 - fix calculating v value from chain id --- .../plugins/peerplays_sidechain/ethereum/transaction.cpp | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp index a75327c3..e243670d 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp @@ -100,14 +100,14 @@ signed_transaction raw_transaction::sign(const std::string &private_key) const { for (int i = 1; i < 33; i++) r.emplace_back((char)result.at(i)); - bytes v = bytes{char(recid + from_hex(chain_id) * 2 + 35)}; + unsigned int v = recid + from_hex(chain_id) * 2 + 35; bytes s; for (int i = 33; i < 65; i++) s.emplace_back((char)result.at(i)); tr.r = fc::to_hex((char *)&r[0], r.size()); - tr.v = fc::to_hex((char *)&v[0], v.size()); + tr.v = to_hex(v); tr.s = fc::to_hex((char *)&s[0], s.size()); return tr; @@ -157,8 +157,8 @@ signed_transaction::signed_transaction(const std::string &raw_tx) : std::string signed_transaction::recover(const std::string &chain_id) const { fc::ecc::compact_signature input64; fc::from_hex(r, (char *)&input64.at(1), 32); - fc::from_hex(v, (char *)&input64.at(0), 1); - int recid = input64.at(0) - from_hex(chain_id) * 2 - 35; + const int recid = from_hex(v) - from_hex(chain_id) * 2 - 35; + fc::from_hex(std::to_string(recid), (char *)&input64.at(0), 1); fc::from_hex(s, (char *)&input64.at(33), 32); secp256k1_ecdsa_recoverable_signature sig; From 9620e3c21187c6fa5385a72a7651634a4b126fa6 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Mon, 14 Nov 2022 13:42:23 +0000 Subject: [PATCH 26/36] #481 ethereum listener --- .../peerplays_sidechain/ethereum/utils.hpp | 8 ++-- .../sidechain_net_handler_ethereum.hpp | 3 +- .../sidechain_net_handler_ethereum.cpp | 47 +++++++++++++------ 3 files changed, 39 insertions(+), 19 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp index b4461713..13a89278 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp @@ -15,12 +15,14 @@ std::string add_0x(const std::string &s); std::string remove_0x(const std::string &s); template -std::string to_hex(const T &val) { +std::string to_hex(const T &val, bool add_front_zero = true) { std::stringstream stream; stream << std::hex << val; std::string result(stream.str()); - if (result.size() % 2) - result = "0" + result; + if(add_front_zero) { + if (result.size() % 2) + result = "0" + result; + } return result; } diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp index 322cf5f9..ccc1aad4 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp @@ -15,6 +15,7 @@ class ethereum_rpc_client : public rpc_client { public: ethereum_rpc_client(const std::string &url, const std::string &user_name, const std::string &password, bool debug_rpc_calls); + std::string eth_blockNumber(); std::string eth_get_block_by_number(std::string block_number, bool full_block); std::string eth_get_logs(std::string wallet_contract_address); std::string eth_chainId(); @@ -69,7 +70,7 @@ private: boost::signals2::signal event_received; void schedule_ethereum_listener(); void ethereum_listener_loop(); - void handle_event(const std::string &event_data); + void handle_event(const std::string &block_number); }; }} // namespace graphene::peerplays_sidechain diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index c71c4748..ce0e29e9 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -28,6 +28,11 @@ ethereum_rpc_client::ethereum_rpc_client(const std::string &url, const std::stri rpc_client(url, user_name, password, debug_rpc_calls) { } +std::string ethereum_rpc_client::eth_blockNumber() { + const std::string reply_str = send_post_request("eth_blockNumber", "", debug_rpc_calls); + return retrieve_value_from_reply(reply_str, ""); +} + std::string ethereum_rpc_client::eth_get_block_by_number(std::string block_number, bool full_block) { const std::string params = "[ \"" + block_number + "\", " + (full_block ? "true" : "false") + "]"; return send_post_request("eth_getBlockByNumber", params, debug_rpc_calls); @@ -159,7 +164,8 @@ sidechain_net_handler_ethereum::sidechain_net_handler_ethereum(peerplays_sidecha ilog("Running on Ethereum network, chain id ${chain_id_str}, network id ${network_id_str}", ("chain_id_str", chain_id_str)("network_id_str", network_id_str)); - last_block_received = 0; + const auto block_number = rpc_client->eth_blockNumber(); + last_block_received = !block_number.empty() ? ethereum::from_hex(block_number) : 0; schedule_ethereum_listener(); event_received.connect([this](const std::string &event_data) { std::thread(&sidechain_net_handler_ethereum::handle_event, this, event_data).detach(); @@ -707,32 +713,43 @@ void sidechain_net_handler_ethereum::schedule_ethereum_listener() { void sidechain_net_handler_ethereum::ethereum_listener_loop() { schedule_ethereum_listener(); - const std::string reply = rpc_client->eth_get_block_by_number("latest", false); + const auto reply = rpc_client->eth_blockNumber(); //std::string reply = rpc_client->eth_get_logs(wallet_contract_address); + if (!reply.empty()) { - std::stringstream ss(reply); - boost::property_tree::ptree json; - boost::property_tree::read_json(ss, json); - if (json.count("result")) { - std::string head_block_number_s = json.get("result.number"); - uint64_t head_block_number = std::strtoul(head_block_number_s.c_str(), nullptr, 16); - if (head_block_number != last_block_received) { - std::string event_data = std::to_string(head_block_number); - handle_event(event_data); - last_block_received = head_block_number; + uint64_t head_block_number = ethereum::from_hex(reply); + + if (head_block_number != last_block_received) { + //! Check that current block number is greater than last one + if (head_block_number < last_block_received) { + wlog("Head block ${head_block_number} is greater than last received block ${last_block_received}", ("head_block_number", head_block_number)("last_block_received", last_block_received)); + return; } + + //! Send event data for all blocks that passed + for (uint64_t i = last_block_received + 1; i <= head_block_number; ++i) { + const std::string block_number = ethereum::add_0x(ethereum::to_hex(i, false)); + handle_event(block_number); + } + + last_block_received = head_block_number; } } } -void sidechain_net_handler_ethereum::handle_event(const std::string &event_data) { - const std::string block = rpc_client->eth_get_block_by_number("latest", true); +void sidechain_net_handler_ethereum::handle_event(const std::string &block_number) { + const std::string block = rpc_client->eth_get_block_by_number(block_number, true); if (block != "") { - add_to_son_listener_log("BLOCK : " + event_data); + add_to_son_listener_log("BLOCK : " + block_number); std::stringstream ss(block); boost::property_tree::ptree block_json; boost::property_tree::read_json(ss, block_json); + if (block_json.get("result") == "null") { + wlog("No data for block ${block_number}", ("block_number", block_number)); + return; + } + size_t tx_idx = -1; for (const auto &tx_child : block_json.get_child("result.transactions")) { boost::property_tree::ptree tx = tx_child.second; From 8853a767529c9b3839d2e7ff0203a11efcd8d86e Mon Sep 17 00:00:00 2001 From: Milos Milosevic Date: Tue, 15 Nov 2022 22:33:04 +0000 Subject: [PATCH 27/36] #433 Down active sons are not substituted --- libraries/app/database_api.cpp | 2 +- libraries/chain/db_getter.cpp | 4 ++-- tests/cli/son.cpp | 12 ++++++------ tests/tests/son_operations_tests.cpp | 6 +++--- 4 files changed, 12 insertions(+), 12 deletions(-) diff --git a/libraries/app/database_api.cpp b/libraries/app/database_api.cpp index a385ba47..64fb82c2 100644 --- a/libraries/app/database_api.cpp +++ b/libraries/app/database_api.cpp @@ -1912,7 +1912,7 @@ map database_api_impl::get_son_network_status_by_sidechain( if (time_point_sec(sso.last_active_timestamp.at(sidechain) + fc::seconds(gpo.parameters.son_down_time())) > _db.head_block_time()) { status = "OK, irregular SON heartbeat, but not triggering SON down proposal"; } else { - status = "NOT OK, irregular SON heartbeat, triggering SON down proposal]"; + status = "NOT OK, irregular SON heartbeat, triggering SON down proposal"; } } } else { diff --git a/libraries/chain/db_getter.cpp b/libraries/chain/db_getter.cpp index 0bb9b10b..1b61ee79 100644 --- a/libraries/chain/db_getter.cpp +++ b/libraries/chain/db_getter.cpp @@ -236,7 +236,7 @@ std::set database::get_sons_to_be_deregistered() // TODO : We need to add a function that returns if we can deregister SON // i.e. with introduction of PW code, we have to make a decision if the SON // is needed for release of funds from the PW - if (head_block_time() - stats.last_down_timestamp.at(sidechain) < fc::seconds(get_global_properties().parameters.son_deregister_time())) { + if (head_block_time() - stats.last_active_timestamp.at(sidechain) < fc::seconds(get_global_properties().parameters.son_deregister_time())) { need_to_be_deregistered = false; } } @@ -311,7 +311,7 @@ bool database::is_son_dereg_valid( son_id_type son_id ) if(status_son_dereg_valid) { - if(head_block_time() - son->statistics(*this).last_down_timestamp.at(sidechain) < fc::seconds(get_global_properties().parameters.son_deregister_time())) + if(head_block_time() - son->statistics(*this).last_active_timestamp.at(sidechain) < fc::seconds(get_global_properties().parameters.son_deregister_time())) { status_son_dereg_valid = false; } diff --git a/tests/cli/son.cpp b/tests/cli/son.cpp index 7858664c..83db8d48 100644 --- a/tests/cli/son.cpp +++ b/tests/cli/son.cpp @@ -1313,7 +1313,7 @@ BOOST_FIXTURE_TEST_CASE( get_son_network_status, cli_fixture ) (inner_iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(0).son_id)) { BOOST_TEST_MESSAGE("status: "<< inner_iter->second); - BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else if((inner_iter->first == gpo.active_sons.at(sidechain_type::bitcoin).at(1).son_id) && (inner_iter->first == gpo.active_sons.at(sidechain_type::hive).at(1).son_id) && @@ -1342,14 +1342,14 @@ BOOST_FIXTURE_TEST_CASE( get_son_network_status, cli_fixture ) (inner_iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(0).son_id)) { BOOST_TEST_MESSAGE("status: "<< inner_iter->second); - BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else if((inner_iter->first == gpo.active_sons.at(sidechain_type::bitcoin).at(1).son_id) && (inner_iter->first == gpo.active_sons.at(sidechain_type::hive).at(1).son_id) && (inner_iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(1).son_id)) { BOOST_TEST_MESSAGE("status: "<< inner_iter->second); - BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(inner_iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else{ BOOST_TEST_MESSAGE("status: "<< inner_iter->second); @@ -1517,7 +1517,7 @@ BOOST_FIXTURE_TEST_CASE( get_son_network_status_by_sidechain, cli_fixture ) (iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(0).son_id)) { BOOST_TEST_MESSAGE("status: "<< iter->second); - BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else if((iter->first == gpo.active_sons.at(sidechain_type::bitcoin).at(1).son_id) && (iter->first == gpo.active_sons.at(sidechain_type::hive).at(1).son_id) && @@ -1545,14 +1545,14 @@ BOOST_FIXTURE_TEST_CASE( get_son_network_status_by_sidechain, cli_fixture ) (iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(0).son_id)) { BOOST_TEST_MESSAGE("status: "<< iter->second); - BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else if((iter->first == gpo.active_sons.at(sidechain_type::bitcoin).at(1).son_id) && (iter->first == gpo.active_sons.at(sidechain_type::hive).at(1).son_id) && (iter->first == gpo.active_sons.at(sidechain_type::ethereum).at(1).son_id)) { BOOST_TEST_MESSAGE("status: "<< iter->second); - BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal]"); + BOOST_CHECK(iter->second == "NOT OK, irregular SON heartbeat, triggering SON down proposal"); } else{ BOOST_TEST_MESSAGE("status: "<< iter->second); diff --git a/tests/tests/son_operations_tests.cpp b/tests/tests/son_operations_tests.cpp index a128b474..23ddfd1c 100644 --- a/tests/tests/son_operations_tests.cpp +++ b/tests/tests/son_operations_tests.cpp @@ -208,9 +208,9 @@ try { db.modify( *son_stats_obj, [&]( son_statistics_object& _s) { - _s.last_down_timestamp[sidechain_type::bitcoin] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); - _s.last_down_timestamp[sidechain_type::hive] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); - _s.last_down_timestamp[sidechain_type::ethereum] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); + _s.last_active_timestamp[sidechain_type::bitcoin] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); + _s.last_active_timestamp[sidechain_type::hive] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); + _s.last_active_timestamp[sidechain_type::ethereum] = fc::time_point_sec(db.head_block_time() - db.get_global_properties().parameters.son_deregister_time()); }); auto deposit_vesting = db.get(vesting_balance_id_type(0)); From 811d68ef4d700f7a5717433faf79dd4dcea65970 Mon Sep 17 00:00:00 2001 From: Davor Hirunda Date: Tue, 15 Nov 2022 22:34:05 +0000 Subject: [PATCH 28/36] Fix for undo crash --- libraries/chain/hardfork.d/SIDECHAIN.hf | 7 +++++ .../chain/sidechain_address_evaluator.cpp | 27 +++++++++++-------- tests/tests/sidechain_addresses_test.cpp | 14 +++++----- 3 files changed, 30 insertions(+), 18 deletions(-) create mode 100644 libraries/chain/hardfork.d/SIDECHAIN.hf diff --git a/libraries/chain/hardfork.d/SIDECHAIN.hf b/libraries/chain/hardfork.d/SIDECHAIN.hf new file mode 100644 index 00000000..3a0a3990 --- /dev/null +++ b/libraries/chain/hardfork.d/SIDECHAIN.hf @@ -0,0 +1,7 @@ +#ifndef HARDFORK_SIDECHAIN_DELETE_TIME +#ifdef BUILD_PEERPLAYS_TESTNET +#define HARDFORK_SIDECHAIN_DELETE_TIME (fc::time_point_sec::from_iso_string("2022-11-16T02:00:00")) +#else +#define HARDFORK_SIDECHAIN_DELETE_TIME (fc::time_point_sec::from_iso_string("2022-11-16T02:00:00")) +#endif +#endif diff --git a/libraries/chain/sidechain_address_evaluator.cpp b/libraries/chain/sidechain_address_evaluator.cpp index 0efd54cf..3cffc61e 100644 --- a/libraries/chain/sidechain_address_evaluator.cpp +++ b/libraries/chain/sidechain_address_evaluator.cpp @@ -22,12 +22,14 @@ object_id_type add_sidechain_address_evaluator::do_apply(const sidechain_address const auto &sidechain_addresses_idx = db().get_index_type().indices().get(); const auto &addr_itr = sidechain_addresses_idx.find(std::make_tuple(op.sidechain_address_account, op.sidechain, time_point_sec::maximum())); - if (addr_itr != sidechain_addresses_idx.end()) - { - //db().modify(*addr_itr, [&](sidechain_address_object &sao) { - // sao.expires = db().head_block_time(); - //}); - db().remove(*addr_itr); + if (addr_itr != sidechain_addresses_idx.end()) { + if (db().head_block_time() >= HARDFORK_SIDECHAIN_DELETE_TIME) { + db().remove(*addr_itr); + } else { + db().modify(*addr_itr, [&](sidechain_address_object &sao) { + sao.expires = db().head_block_time(); + }); + } } const auto& new_sidechain_address_object = db().create( [&]( sidechain_address_object& obj ){ @@ -106,11 +108,14 @@ void_result delete_sidechain_address_evaluator::do_apply(const sidechain_address { try { const auto& idx = db().get_index_type().indices().get(); auto sidechain_address = idx.find(op.sidechain_address_id); - if(sidechain_address != idx.end()) { - //db().modify(*sidechain_address, [&](sidechain_address_object &sao) { - // sao.expires = db().head_block_time(); - //}); - db().remove(*sidechain_address); + if (sidechain_address != idx.end()) { + if (db().head_block_time() >= HARDFORK_SIDECHAIN_DELETE_TIME) { + db().remove(*sidechain_address); + } else { + db().modify(*sidechain_address, [&](sidechain_address_object &sao) { + sao.expires = db().head_block_time(); + }); + } } return void_result(); } FC_CAPTURE_AND_RETHROW( (op) ) } diff --git a/tests/tests/sidechain_addresses_test.cpp b/tests/tests/sidechain_addresses_test.cpp index 5f4885e6..8c3229d3 100644 --- a/tests/tests/sidechain_addresses_test.cpp +++ b/tests/tests/sidechain_addresses_test.cpp @@ -244,6 +244,9 @@ BOOST_AUTO_TEST_CASE( sidechain_address_delete_test ) { BOOST_TEST_MESSAGE("sidechain_address_delete_test"); + generate_blocks(HARDFORK_SIDECHAIN_DELETE_TIME); + generate_block(); + INVOKE(sidechain_address_add_test); GET_ACTOR(alice); @@ -266,18 +269,12 @@ BOOST_AUTO_TEST_CASE( sidechain_address_delete_test ) { sign(trx, alice_private_key); PUSH_TX(db, trx, ~0); } - //time_point_sec now = db.head_block_time(); - generate_block(); + generate_block(); { BOOST_TEST_MESSAGE("Check sidechain_address_delete_operation results"); const auto& idx = db.get_index_type().indices().get(); - //BOOST_REQUIRE( idx.size() == 1 ); - //auto obj = idx.find( boost::make_tuple( alice_id, sidechain_type::bitcoin, time_point_sec::maximum() ) ); - //BOOST_REQUIRE( obj == idx.end() ); - //auto expired_obj = idx.find( boost::make_tuple( alice_id, sidechain_type::bitcoin, now ) ); - //BOOST_REQUIRE( expired_obj != idx.end() ); BOOST_REQUIRE( idx.size() == 0 ); } } @@ -286,6 +283,9 @@ BOOST_AUTO_TEST_CASE(sidechain_address_delete_create_test) { BOOST_TEST_MESSAGE("sidechain_address_delete_create_test"); + generate_blocks(HARDFORK_SIDECHAIN_DELETE_TIME); + generate_block(); + INVOKE(sidechain_address_add_test); GET_ACTOR(alice); From 022fdeb40a3344c0e5e5d47d74369e1b7bb21f94 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Tue, 22 Nov 2022 20:44:07 +0000 Subject: [PATCH 29/36] #478 estimate transaction fee --- .../peerplays_sidechain_plugin.hpp | 1 + .../peerplays_sidechain/sidechain_api.hpp | 3 +- .../sidechain_net_handler.hpp | 1 + .../sidechain_net_handler_bitcoin.hpp | 1 + .../sidechain_net_handler_ethereum.hpp | 3 + .../sidechain_net_handler_hive.hpp | 1 + .../sidechain_net_handler_peerplays.hpp | 1 + .../peerplays_sidechain_plugin.cpp | 14 ++++ .../peerplays_sidechain/sidechain_api.cpp | 9 +++ .../sidechain_net_handler_bitcoin.cpp | 5 ++ .../sidechain_net_handler_ethereum.cpp | 47 +++++++++++++ .../sidechain_net_handler_hive.cpp | 5 ++ .../sidechain_net_handler_peerplays.cpp | 5 ++ .../wallet/include/graphene/wallet/wallet.hpp | 15 +++++ libraries/wallet/wallet.cpp | 67 +++++++++++++++++++ 15 files changed, 177 insertions(+), 1 deletion(-) diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/peerplays_sidechain_plugin.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/peerplays_sidechain_plugin.hpp index 114f9bc7..d890ae68 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/peerplays_sidechain_plugin.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/peerplays_sidechain_plugin.hpp @@ -54,6 +54,7 @@ public: void log_son_proposal_retry(sidechain_type sidechain, int op_type, object_id_type object_id); bool can_son_participate(sidechain_type sidechain, int op_type, object_id_type object_id); std::map> get_son_listener_log(); + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain); }; }} // namespace graphene::peerplays_sidechain diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_api.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_api.hpp index b4636537..5d6df6af 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_api.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_api.hpp @@ -26,9 +26,10 @@ public: std::shared_ptr my; std::map> get_son_listener_log(); + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain); }; }} // namespace graphene::peerplays_sidechain FC_API(graphene::peerplays_sidechain::sidechain_api, - (get_son_listener_log)) + (get_son_listener_log)(estimate_withdrawal_transaction_fee)) diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp index a9257e54..fc295b4c 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp @@ -50,6 +50,7 @@ public: void add_to_son_listener_log(std::string trx_id); std::vector get_son_listener_log(); + virtual optional estimate_withdrawal_transaction_fee() const = 0; protected: peerplays_sidechain_plugin &plugin; diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_bitcoin.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_bitcoin.hpp index 62eeeab6..eaa48526 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_bitcoin.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_bitcoin.hpp @@ -106,6 +106,7 @@ public: std::string process_sidechain_transaction(const sidechain_transaction_object &sto); std::string send_sidechain_transaction(const sidechain_transaction_object &sto); bool settle_sidechain_transaction(const sidechain_transaction_object &sto, asset &settle_amount); + virtual optional estimate_withdrawal_transaction_fee() const override; private: std::string ip; diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp index ccc1aad4..e6e8f298 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_ethereum.hpp @@ -22,12 +22,14 @@ public: std::string net_version(); std::string eth_get_transaction_count(const std::string ¶ms); std::string eth_gas_price(); + std::string eth_estimateGas(const std::string ¶ms); std::string get_chain_id(); std::string get_network_id(); std::string get_nonce(const std::string &address); std::string get_gas_price(); std::string get_gas_limit(); + std::string get_estimate_gas(const std::string ¶ms); std::string eth_send_transaction(const std::string ¶ms); std::string eth_send_raw_transaction(const std::string ¶ms); @@ -47,6 +49,7 @@ public: std::string process_sidechain_transaction(const sidechain_transaction_object &sto); std::string send_sidechain_transaction(const sidechain_transaction_object &sto); bool settle_sidechain_transaction(const sidechain_transaction_object &sto, asset &settle_amount); + virtual optional estimate_withdrawal_transaction_fee() const override; private: std::string rpc_url; diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_hive.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_hive.hpp index 72539db2..440a2520 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_hive.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_hive.hpp @@ -45,6 +45,7 @@ public: std::string process_sidechain_transaction(const sidechain_transaction_object &sto); std::string send_sidechain_transaction(const sidechain_transaction_object &sto); bool settle_sidechain_transaction(const sidechain_transaction_object &sto, asset &settle_amount); + virtual optional estimate_withdrawal_transaction_fee() const override; private: std::string rpc_url; diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_peerplays.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_peerplays.hpp index 69eea1a9..139db7bf 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_peerplays.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler_peerplays.hpp @@ -19,6 +19,7 @@ public: std::string process_sidechain_transaction(const sidechain_transaction_object &sto); std::string send_sidechain_transaction(const sidechain_transaction_object &sto); bool settle_sidechain_transaction(const sidechain_transaction_object &sto, asset &settle_amount); + virtual optional estimate_withdrawal_transaction_fee() const override; private: }; diff --git a/libraries/plugins/peerplays_sidechain/peerplays_sidechain_plugin.cpp b/libraries/plugins/peerplays_sidechain/peerplays_sidechain_plugin.cpp index 27784720..c8da6ce6 100644 --- a/libraries/plugins/peerplays_sidechain/peerplays_sidechain_plugin.cpp +++ b/libraries/plugins/peerplays_sidechain/peerplays_sidechain_plugin.cpp @@ -48,6 +48,7 @@ public: void log_son_proposal_retry(sidechain_type sidechain, int op_type, object_id_type object_id); bool can_son_participate(sidechain_type sidechain, int op_type, object_id_type object_id); std::map> get_son_listener_log(); + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain); void schedule_heartbeat_loop(); void heartbeat_loop(); @@ -626,6 +627,15 @@ std::map> peerplays_sidechain_plugin_im return result; } +optional peerplays_sidechain_plugin_impl::estimate_withdrawal_transaction_fee(sidechain_type sidechain) { + if (!net_handlers.at(sidechain)) { + wlog("Net handler is null for sidechain: ${sidechain}", ("sidechain", sidechain)); + return optional(); + } + + return net_handlers.at(sidechain)->estimate_withdrawal_transaction_fee(); +} + void peerplays_sidechain_plugin_impl::approve_proposals(sidechain_type sidechain) { // prevent approving duplicate proposals with lock for parallel execution. // We can have the same propsals, but in the case of parallel execution we can run @@ -922,4 +932,8 @@ std::map> peerplays_sidechain_plugin::g return my->get_son_listener_log(); } +optional peerplays_sidechain_plugin::estimate_withdrawal_transaction_fee(sidechain_type sidechain) { + return my->estimate_withdrawal_transaction_fee(sidechain); +} + }} // namespace graphene::peerplays_sidechain diff --git a/libraries/plugins/peerplays_sidechain/sidechain_api.cpp b/libraries/plugins/peerplays_sidechain/sidechain_api.cpp index 2a85d034..833d91ff 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_api.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_api.cpp @@ -12,6 +12,7 @@ public: std::shared_ptr get_plugin(); std::map> get_son_listener_log(); + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain); private: app::application &app; @@ -32,6 +33,10 @@ std::map> sidechain_api_impl::get_son_l return get_plugin()->get_son_listener_log(); } +optional sidechain_api_impl::estimate_withdrawal_transaction_fee(sidechain_type sidechain) { + return get_plugin()->estimate_withdrawal_transaction_fee(sidechain); +} + } // namespace detail sidechain_api::sidechain_api(graphene::app::application &_app) : @@ -45,4 +50,8 @@ std::map> sidechain_api::get_son_listen return my->get_son_listener_log(); } +optional sidechain_api::estimate_withdrawal_transaction_fee(sidechain_type sidechain) { + return my->estimate_withdrawal_transaction_fee(sidechain); +} + }} // namespace graphene::peerplays_sidechain diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_bitcoin.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_bitcoin.cpp index ea4621c0..862f991a 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_bitcoin.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_bitcoin.cpp @@ -1002,6 +1002,11 @@ bool sidechain_net_handler_bitcoin::settle_sidechain_transaction(const sidechain return false; } +optional sidechain_net_handler_bitcoin::estimate_withdrawal_transaction_fee() const { + wlog("estimate_withdrawal_transaction_fee not implemented for sidechain: ${sidechain}", ("sidechain", sidechain)); + return optional{}; +} + std::string sidechain_net_handler_bitcoin::create_primary_wallet_address(const std::vector &son_pubkeys) { using namespace bitcoin; diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index ce0e29e9..c827a721 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -60,6 +60,10 @@ std::string ethereum_rpc_client::eth_gas_price() { return send_post_request("eth_gasPrice", "", debug_rpc_calls); } +std::string ethereum_rpc_client::eth_estimateGas(const std::string ¶ms) { + return send_post_request("eth_estimateGas", params, debug_rpc_calls); +} + std::string ethereum_rpc_client::get_chain_id() { const std::string reply_str = eth_chainId(); const auto chain_id_string = retrieve_value_from_reply(reply_str, ""); @@ -100,6 +104,11 @@ std::string ethereum_rpc_client::get_gas_limit() { return std::string{}; } +std::string ethereum_rpc_client::get_estimate_gas(const std::string ¶ms) { + const std::string reply_str = eth_estimateGas(params); + return retrieve_value_from_reply(reply_str, ""); +} + std::string ethereum_rpc_client::eth_send_transaction(const std::string ¶ms) { return send_post_request("eth_sendTransaction", "[" + params + "]", debug_rpc_calls); } @@ -651,6 +660,44 @@ bool sidechain_net_handler_ethereum::settle_sidechain_transaction(const sidechai return false; } +optional sidechain_net_handler_ethereum::estimate_withdrawal_transaction_fee() const { + const auto &gpo = database.get_global_properties(); + if (gpo.active_sons.at(sidechain).empty()) { + wlog("No active sons for sidechain: ${sidechain}", ("sidechain", sidechain)); + return optional{}; + } + + const auto &active_son = gpo.active_sons.at(sidechain).at(0); + const auto &s_idx = database.get_index_type().indices().get(); + const auto son = s_idx.find(active_son.son_id); + if (son == s_idx.end()) { + wlog("Can't find son for id: ${son_id}", ("son_id", active_son.son_id)); + return optional{}; + } + + if (!son->sidechain_public_keys.contains(sidechain)) { + wlog("No public keys for current son: ${account_id}", ("account_id", son->son_account)); + return optional{}; + } + + const auto &assets_by_symbol = database.get_index_type().indices().get(); + auto asset_itr = assets_by_symbol.find("ETH"); + if (asset_itr == assets_by_symbol.end()) { + wlog("Could not find asset matching ETH"); + return optional{}; + } + + const auto &public_key = son->sidechain_public_keys.at(sidechain); + const ethereum::withdrawal_encoder encoder; + const auto data = encoder.encode(public_key, 1 * 10000000000, son_wallet_withdraw_id_type{0}.operator object_id_type().operator std::string()); + const std::string params = "[{\"from\":\"" + ethereum::add_0x(public_key) + "\", \"to\":\"" + wallet_contract_address + "\", \"data\":\"" + data + "\"}]"; + + const auto estimate_gas = ethereum::from_hex(rpc_client->get_estimate_gas(params)); + const auto gas_price = ethereum::from_hex(rpc_client->get_gas_price()); + const auto eth_gas_fee = double(estimate_gas * gas_price) / double{1000000000000000000}; + return asset_itr->amount_from_string(std::to_string(eth_gas_fee)); +} + std::string sidechain_net_handler_ethereum::create_primary_wallet_transaction(const std::vector &son_pubkeys, const std::string &object_id) { std::vector> owners_weights; for (auto &son : son_pubkeys) { diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp index a4c06175..63ae22c6 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp @@ -806,6 +806,11 @@ bool sidechain_net_handler_hive::settle_sidechain_transaction(const sidechain_tr return false; } +optional sidechain_net_handler_hive::estimate_withdrawal_transaction_fee() const { + wlog("estimate_withdrawal_transaction_fee not implemented for sidechain: ${sidechain}", ("sidechain", sidechain)); + return optional{}; +} + void sidechain_net_handler_hive::schedule_hive_listener() { fc::time_point now = fc::time_point::now(); int64_t time_to_next = 1000; diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_peerplays.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_peerplays.cpp index b2945251..76fbbb3e 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_peerplays.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_peerplays.cpp @@ -290,4 +290,9 @@ bool sidechain_net_handler_peerplays::settle_sidechain_transaction(const sidecha return true; } +optional sidechain_net_handler_peerplays::estimate_withdrawal_transaction_fee() const { + wlog("estimate_withdrawal_transaction_fee not implemented for sidechain: ${sidechain}", ("sidechain", sidechain)); + return optional{}; +} + }} // namespace graphene::peerplays_sidechain diff --git a/libraries/wallet/include/graphene/wallet/wallet.hpp b/libraries/wallet/include/graphene/wallet/wallet.hpp index aac79252..6a0b5ee5 100644 --- a/libraries/wallet/include/graphene/wallet/wallet.hpp +++ b/libraries/wallet/include/graphene/wallet/wallet.hpp @@ -2676,6 +2676,19 @@ class wallet_api */ std::map> get_son_listener_log() const; + /** + * @brief Estimate transaction fee for withdrawal + * @param sidechain Sidechain type (bitcoin, HIVE, etc) + * @return Transaction fee + */ + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain) const; + + /** + * @brief Estimate gas fee for withdrawal transaction for ETH + * @return Gas fee in ETH + */ + std::string eth_estimate_withdrawal_transaction_fee() const; + fc::signal lock_changed; std::shared_ptr my; void encrypt_keys(); @@ -2976,4 +2989,6 @@ FC_API( graphene::wallet::wallet_api, (get_voters_by_id) (get_voters) (get_son_listener_log) + (estimate_withdrawal_transaction_fee) + (eth_estimate_withdrawal_transaction_fee) ) diff --git a/libraries/wallet/wallet.cpp b/libraries/wallet/wallet.cpp index d8d79c4b..6b1b2eb1 100644 --- a/libraries/wallet/wallet.cpp +++ b/libraries/wallet/wallet.cpp @@ -3291,6 +3291,25 @@ public: return sign_transaction(trx, broadcast); } FC_CAPTURE_AND_RETHROW((order_id)) } + sidechain_type get_sidechain_type_from_asset(asset_id_type asset_id) const + { + const auto& gpo = _remote_db->get_global_properties(); + + if(asset_id == gpo.parameters.btc_asset()) + return sidechain_type::bitcoin; + + if(asset_id == gpo.parameters.eth_asset()) + return sidechain_type::ethereum; + + if(asset_id == gpo.parameters.hbd_asset()) + return sidechain_type::hive; + + if(asset_id == gpo.parameters.hive_asset()) + return sidechain_type::hive; + + return sidechain_type::unknown; + } + signed_transaction transfer(string from, string to, string amount, string asset_symbol, string memo, bool broadcast = false) { try { @@ -3323,6 +3342,19 @@ public: set_operation_fees( tx, _remote_db->get_global_properties().parameters.current_fees); tx.validate(); + //! For sidechain withdrawal check if amount is greater than fee + if(to_id == _remote_db->get_global_properties().parameters.son_account()) { + const auto sidechain = get_sidechain_type_from_asset(asset_obj->id); + const auto transaction_fee = estimate_withdrawal_transaction_fee(sidechain); + + if(transaction_fee) { + if (*transaction_fee >= xfer_op.amount) { + FC_THROW("Transaction fee: ${sidechain_fee}, would be grater than transfer amount ${amount}", + ("sidechain_fee", get_asset(transaction_fee->asset_id).amount_to_pretty_string(transaction_fee->amount))("amount", get_asset(xfer_op.amount.asset_id).amount_to_pretty_string(xfer_op.amount.amount))); + } + } + } + return sign_transaction(tx, broadcast); } FC_CAPTURE_AND_RETHROW( (from)(to)(amount)(asset_symbol)(memo)(broadcast) ) } @@ -4222,6 +4254,31 @@ public: FC_CAPTURE_AND_RETHROW() } + optional estimate_withdrawal_transaction_fee(sidechain_type sidechain) + { + use_sidechain_api(); + try + { + return (*_remote_sidechain)->estimate_withdrawal_transaction_fee(sidechain); + } + FC_CAPTURE_AND_RETHROW() + } + + std::string eth_estimate_withdrawal_transaction_fee() + { + try + { + const auto transaction_fee = estimate_withdrawal_transaction_fee(sidechain_type::ethereum); + if(transaction_fee) + { + return get_asset(transaction_fee->asset_id).amount_to_pretty_string(transaction_fee->amount); + } + + return "Can't get fee value"; + } + FC_CAPTURE_AND_RETHROW() + } + string _wallet_filename; wallet_data _wallet; @@ -7273,6 +7330,16 @@ std::map> wallet_api::get_son_listener_ return my->get_son_listener_log(); } +optional wallet_api::estimate_withdrawal_transaction_fee(sidechain_type sidechain) const +{ + return my->estimate_withdrawal_transaction_fee(sidechain); +} + +std::string wallet_api::eth_estimate_withdrawal_transaction_fee() const +{ + return my->eth_estimate_withdrawal_transaction_fee(); +} + // default ctor necessary for FC_REFLECT signed_block_with_info::signed_block_with_info( const signed_block& block ) : signed_block( block ) From b7113c4ff3495c6bb310ed60505dcbb3654c6316 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Mon, 28 Nov 2022 09:35:00 +0200 Subject: [PATCH 30/36] #478 - fix information warning --- libraries/wallet/wallet.cpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/libraries/wallet/wallet.cpp b/libraries/wallet/wallet.cpp index 6b1b2eb1..7eefae27 100644 --- a/libraries/wallet/wallet.cpp +++ b/libraries/wallet/wallet.cpp @@ -3349,7 +3349,7 @@ public: if(transaction_fee) { if (*transaction_fee >= xfer_op.amount) { - FC_THROW("Transaction fee: ${sidechain_fee}, would be grater than transfer amount ${amount}", + FC_THROW("Transaction fee: ${sidechain_fee}, is greater than transferred amount ${amount}", ("sidechain_fee", get_asset(transaction_fee->asset_id).amount_to_pretty_string(transaction_fee->amount))("amount", get_asset(xfer_op.amount.asset_id).amount_to_pretty_string(xfer_op.amount.amount))); } } From c3eab0a80b015cea267ca9b283dc7c9e85aebce8 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Thu, 1 Dec 2022 01:53:39 +0000 Subject: [PATCH 31/36] #479 - Send one transaction for all owners --- .../peerplays_sidechain/ethereum/encoders.cpp | 57 ++++++++++- .../ethereum/transaction.cpp | 70 ++++++++------ .../peerplays_sidechain/ethereum/types.cpp | 31 ++++++ .../peerplays_sidechain/ethereum/encoders.hpp | 60 +++++------- .../ethereum/transaction.hpp | 89 +---------------- .../peerplays_sidechain/ethereum/types.hpp | 13 +++ .../peerplays_sidechain/ethereum/utils.hpp | 2 +- .../sidechain_net_handler_ethereum.cpp | 96 +++++++++++-------- .../ethereum_transaction_tests.cpp | 40 ++++++-- 9 files changed, 254 insertions(+), 204 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp b/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp index ad42088b..feab921f 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp @@ -2,7 +2,6 @@ #include #include -#include #include @@ -19,12 +18,16 @@ std::string base_encoder::encode_address(const std::string &value) { std::string base_encoder::encode_string(const std::string &value) { std::string data = (boost::format("%x") % boost::io::group(std::setw(64), std::setfill('0'), value.size())).str(); - data += boost::algorithm::hex(value) + std::string((64 - value.size() * 2 % 64), '0'); + data += boost::algorithm::hex(value); + if (value.size() % 32 != 0) { + data += std::string((64 - value.size() * 2 % 64), '0'); + } return data; } //! update_owners_encoder -std::string update_owners_encoder::encode(const std::vector> &owners_weights, const std::string &object_id) const { +const std::string update_owners_encoder::function_signature = "f6afbeff"; //! updateOwners_(address,(address,uint256)[],string) +std::string update_owners_encoder::encode(const std::vector> &owners_weights, const std::string &object_id) { std::string data = "0x" + function_signature; data += base_encoder::encode_uint256(64); data += base_encoder::encode_uint256((owners_weights.size() * 2 + 3) * 32); @@ -39,7 +42,8 @@ std::string update_owners_encoder::encode(const std::vector &transactions) const { + std::string data = "0x" + function_signature; + data += base_encoder::encode_uint256(32); + data += base_encoder::encode_uint256(transactions.size()); + size_t offset = (transactions.size()) * 32; + for (const auto &transaction : transactions) { + data += base_encoder::encode_uint256(offset); + const auto transaction_data = remove_0x(transaction.data); + offset += 5 * 32 + transaction_data.size() / 2; + if (transaction_data.size() / 2 % 32 != 0) { + offset += 32 - transaction_data.size() / 2 % 32; + } + } + for (const auto &transaction : transactions) { + data += base_encoder::encode_uint256(4 * 32); + data += base_encoder::encode_address(transaction.sign.v); + data += base_encoder::encode_address(transaction.sign.r); + data += base_encoder::encode_address(transaction.sign.s); + const auto transaction_data = remove_0x(transaction.data); + data += base_encoder::encode_uint256(transaction_data.size() / 2); + data += transaction_data; + if (transaction_data.size() % 64 != 0) { + data += std::string((64 - transaction_data.size() % 64), '0'); + } + } + + return data; +} + //! rlp_encoder std::string rlp_encoder::encode(const std::string &s) { return encode_rlp(hex2bytes(s)); diff --git a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp index e243670d..dd1179b4 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp @@ -22,7 +22,43 @@ const secp256k1_context *eth_context() { return ctx; } -//! transaction +bytes keccak_hash(const std::string &data) { + bytes hash; + hash.resize(32); + const auto transaction_string = boost::algorithm::unhex(remove_0x(data)); + keccak_256((const unsigned char *)transaction_string.data(), transaction_string.size(), (unsigned char *)hash.data()); + + return hash; +} + +signature sign_hash(const bytes &hash, const std::string &chain_id, const std::string &private_key) { + const bytes priv_key = parse_hex(private_key); + + int recid = 0; + secp256k1_ecdsa_recoverable_signature sig; + FC_ASSERT(secp256k1_ecdsa_sign_recoverable(eth_context(), &sig, (const unsigned char *)hash.data(), (const unsigned char *)priv_key.data(), NULL, NULL)); + fc::ecc::compact_signature result; + FC_ASSERT(secp256k1_ecdsa_recoverable_signature_serialize_compact(eth_context(), (unsigned char *)result.begin() + 1, &recid, &sig)); + + unsigned int v = recid + from_hex(chain_id) * 2 + 35; + + bytes r; + for (int i = 1; i < 33; i++) + r.emplace_back((char)result.at(i)); + + bytes s; + for (int i = 33; i < 65; i++) + s.emplace_back((char)result.at(i)); + + signature eth_sig; + eth_sig.v = to_hex(v); + eth_sig.r = fc::to_hex((char *)&r[0], r.size()); + eth_sig.s = fc::to_hex((char *)&s[0], s.size()); + + return eth_sig; +} + +//! base_transaction base_transaction::base_transaction(const std::string &raw_tx) { } @@ -70,12 +106,7 @@ raw_transaction::raw_transaction(const std::string &raw_tx) : } bytes raw_transaction::hash() const { - bytes hash; - hash.resize(32); - const auto transaction_string = boost::algorithm::unhex(remove_0x(serialize())); - keccak_256((const unsigned char *)transaction_string.data(), transaction_string.size(), (unsigned char *)hash.data()); - - return hash; + return keccak_hash(serialize()); } signed_transaction raw_transaction::sign(const std::string &private_key) const { @@ -88,27 +119,10 @@ signed_transaction raw_transaction::sign(const std::string &private_key) const { tr.value = value; tr.data = data; - const bytes priv_key = parse_hex(private_key); - - int recid = 0; - secp256k1_ecdsa_recoverable_signature sig; - FC_ASSERT(secp256k1_ecdsa_sign_recoverable(eth_context(), &sig, (const unsigned char *)hash().data(), (const unsigned char *)priv_key.data(), NULL, NULL)); - fc::ecc::compact_signature result; - FC_ASSERT(secp256k1_ecdsa_recoverable_signature_serialize_compact(eth_context(), (unsigned char *)result.begin() + 1, &recid, &sig)); - - bytes r; - for (int i = 1; i < 33; i++) - r.emplace_back((char)result.at(i)); - - unsigned int v = recid + from_hex(chain_id) * 2 + 35; - - bytes s; - for (int i = 33; i < 65; i++) - s.emplace_back((char)result.at(i)); - - tr.r = fc::to_hex((char *)&r[0], r.size()); - tr.v = to_hex(v); - tr.s = fc::to_hex((char *)&s[0], s.size()); + const auto sig = sign_hash(hash(), chain_id, private_key); + tr.v = sig.v; + tr.r = sig.r; + tr.s = sig.s; return tr; } diff --git a/libraries/plugins/peerplays_sidechain/ethereum/types.cpp b/libraries/plugins/peerplays_sidechain/ethereum/types.cpp index f85d0e61..e33e0c4a 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/types.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/types.cpp @@ -1,5 +1,36 @@ #include +#include +#include + namespace graphene { namespace peerplays_sidechain { namespace ethereum { +signature::signature(const std::string &sign) { + deserialize(sign); +} + +std::string signature::serialize() const { + boost::property_tree::ptree pt; + pt.put("v", v); + pt.put("r", r); + pt.put("s", s); + + std::stringstream ss; + boost::property_tree::json_parser::write_json(ss, pt); + return ss.str(); +} + +void signature::deserialize(const std::string &raw_tx) { + std::stringstream ss_tx(raw_tx); + boost::property_tree::ptree tx_json; + boost::property_tree::read_json(ss_tx, tx_json); + + if (tx_json.count("v")) + v = tx_json.get("v"); + if (tx_json.count("r")) + r = tx_json.get("r"); + if (tx_json.count("s")) + s = tx_json.get("s"); +} + }}} // namespace graphene::peerplays_sidechain::ethereum diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/encoders.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/encoders.hpp index 1ff97978..ce02f7ed 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/encoders.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/encoders.hpp @@ -4,8 +4,18 @@ #include #include +#include + namespace graphene { namespace peerplays_sidechain { namespace ethereum { +const std::string update_owners_function_signature = "9d608673"; //! updateOwners((bytes,(uint8,bytes32,bytes32))[]) +const std::string withdrawal_function_signature = "daac6c81"; //! withdraw((bytes,(uint8,bytes32,bytes32))[]) + +struct encoded_sign_transaction { + std::string data; + signature sign; +}; + class base_encoder { public: static std::string encode_uint256(boost::multiprecision::uint256_t value); @@ -15,16 +25,27 @@ public: class update_owners_encoder { public: - const std::string function_signature = "23ab6adf"; //! updateOwners((address,uint256)[],string) + static const std::string function_signature; - std::string encode(const std::vector> &owners_weights, const std::string &object_id) const; + static std::string encode(const std::vector> &owners_weights, const std::string &object_id); }; class withdrawal_encoder { public: - const std::string function_signature = "e088747b"; //! withdraw(address,uint256,string) + static const std::string function_signature; - std::string encode(const std::string &to, boost::multiprecision::uint256_t amount, const std::string &object_id) const; + static std::string encode(const std::string &to, boost::multiprecision::uint256_t amount, const std::string &object_id); +}; + +class signature_encoder { +public: + const std::string function_signature; + + signature_encoder(const std::string &function_hash); + + static std::string get_function_signature_from_transaction(const std::string &transaction); + + std::string encode(const std::vector &transactions) const; }; class rlp_encoder { @@ -39,35 +60,4 @@ private: static void hex2bin(const char *src, char *target); }; -/*class ethereum_function_call_encoder { -public: - enum operation_t { - OPERATION_CALL, - OPERATION_DELEGATE_CALL - }; - - static constexpr const char *const default_prev_addr = "0000000000000000000000000000000000000001"; - - std::string encode_function_signature(const std::string &function_signature); - std::string encode_address(const std::string &addr); - std::string encode_uint256(const std::string &value); - std::string encode_uint8(uint8_t value); - std::string encode_bytes(const std::string &values); -}; - -class safe_transaction_encoder { -public: - static constexpr const char *const default_safe_tx_gas = "0"; - static constexpr const char *const default_data_gas = "0"; - static constexpr const char *const default_gas_price = "0"; - static constexpr const char *const default_gas_token = "0000000000000000000000000000000000000000"; - static constexpr const char *const default_refund_receiver = "0000000000000000000000000000000000000000"; - - std::string create_safe_address(const std::vector &owner_addresses, uint32_t threshold); - std::string build_transaction(const std::string &safe_account_addr, const std::string &value, const std::string &data, uint8_t operation, const std::string &safeTxGas, const std::string &dataGas, const std::string &gasPrice, const std::string &gasToken, const std::string &refundReceiver); - -private: - ethereum_function_call_encoder m_ethereum_function_call_encoder; -};*/ - }}} // namespace graphene::peerplays_sidechain::ethereum diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/transaction.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/transaction.hpp index 693c7284..77ef444b 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/transaction.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/transaction.hpp @@ -8,6 +8,9 @@ namespace graphene { namespace peerplays_sidechain { namespace ethereum { +bytes keccak_hash(const std::string &data); +signature sign_hash(const bytes &hash, const std::string &chain_id, const std::string &private_key); + class base_transaction { public: base_transaction() = default; @@ -75,89 +78,3 @@ public: }; }}} // namespace graphene::peerplays_sidechain::ethereum - -// Example 1 -//{ -// "blockHash": "0x64a6706ecaf5a97b7f3e047abb20ff223ce82c6994d80e68fdb1fdfb38d0209c", -// "blockNumber": "0xe5827c", -// "from": "0x8614c67e085f2334010f2a28e806c6f1cc176d12", -// "gas": "0x38822", -// "gasPrice": "0xce42cba69", -// "maxFeePerGas": "0xddb4d8d16", -// "maxPriorityFeePerGas": "0x3b9aca00", -// "hash": "0xeac92ea09fa8eb3ca2fb0d156cceb38ae69d4345869d41e8e49d5ecbcbb622dc", -// "input": "0x5ae401dc0000000000000000000000000000000000000000000000000000000062bb57cf00000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000e4472b43f300000000000000000000000000000000000000000000000002514d9d7d7d8000000000000000000000000000000000000000000007dced93dd41fd3e1f9e80c200000000000000000000000000000000000000000000000000000000000000800000000000000000000000008614c67e085f2334010f2a28e806c6f1cc176d120000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000059c12ed5aaf25adbc6e15f9cc9bab2dde03121500000000000000000000000000000000000000000000000000000000", -// "nonce": "0x32", -// "to": "0x68b3465833fb72a70ecdf485e0e4c7bd8665fc45", -// "transactionIndex": "0xb6", -// "value": "0x2514d9d7d7d8000", -// "type": "0x2", -// "accessList": [], -// "chainId": "0x1", -// "v": "0x1", -// "r": "0x2f8d6a9c737ed98792bafc903b8f1aa54adc731bd3cf9a8b25246a1c9095a28c", -// "s": "0x782c40e64b47a221a07612c822c08763f626e53c4b00b73f4c5ba86304c43f14" -//} -// -//"0xf9021332850ce42cba69830388229468b3465833fb72a70ecdf485e0e4c7bd8665fc458802514d9d7d7d8000b901a45ae401dc0000000000000000000000000000000000000000000000000000000062bb57cf00000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000e4472b43f300000000000000000000000000000000000000000000000002514d9d7d7d8000000000000000000000000000000000000000000007dced93dd41fd3e1f9e80c200000000000000000000000000000000000000000000000000000000000000800000000000000000000000008614c67e085f2334010f2a28e806c6f1cc176d120000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000059c12ed5aaf25adbc6e15f9cc9bab2dde0312150000000000000000000000000000000000000000000000000000000001a02f8d6a9c737ed98792bafc903b8f1aa54adc731bd3cf9a8b25246a1c9095a28ca0782c40e64b47a221a07612c822c08763f626e53c4b00b73f4c5ba86304c43f14" -// -//{ -// "nonce": 50, -// "gasPrice": { -// "_hex": "0x0ce42cba69" -// }, -// "gasLimit": { -// "_hex": "0x038822" -// }, -// "to": "0x68b3465833fb72a70ecdf485e0e4c7bd8665fc45", -// "value": { -// "_hex": "0x02514d9d7d7d8000" -// }, -// "data": "0x5ae401dc0000000000000000000000000000000000000000000000000000000062bb57cf00000000000000000000000000000000000000000000000000000000000000400000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000e4472b43f300000000000000000000000000000000000000000000000002514d9d7d7d8000000000000000000000000000000000000000000007dced93dd41fd3e1f9e80c200000000000000000000000000000000000000000000000000000000000000800000000000000000000000008614c67e085f2334010f2a28e806c6f1cc176d120000000000000000000000000000000000000000000000000000000000000002000000000000000000000000c02aaa39b223fe8d0a0e5c4f27ead9083c756cc2000000000000000000000000059c12ed5aaf25adbc6e15f9cc9bab2dde03121500000000000000000000000000000000000000000000000000000000", -// "v": 1, -// "r": "0x2f8d6a9c737ed98792bafc903b8f1aa54adc731bd3cf9a8b25246a1c9095a28c", -// "s": "0x782c40e64b47a221a07612c822c08763f626e53c4b00b73f4c5ba86304c43f14" -//} - -// Example 2 -//{ -// "blockHash": "0xe2ae3afd86dc7343c7fb753441447a0a51bb19499325ad6e278256f0cd1b5894", -// "blockNumber": "0xe58271", -// "from": "0xb895ade6d337fbb8cb97f2ea7da43106c7f5cc26", -// "gas": "0x5208", -// "gasPrice": "0xe6f3b322e", -// "maxFeePerGas": "0x1322455fd3", -// "maxPriorityFeePerGas": "0x53724e00", -// "hash": "0xed29b56e52ad2d452e25b8ec70c37f59d935cd6d0f8fe8e83b256f3ffdfd3fce", -// "input": "0x", -// "nonce": "0x37", -// "to": "0x176386b6ffc469ac049f9ec1f6cc0efd1d09b373", -// "transactionIndex": "0x8a", -// "value": "0x4563918244f40000", -// "type": "0x2", -// "accessList": [], -// "chainId": "0x1", -// "v": "0x0", -// "r": "0xdcc588257770e08660cb809e71b293f556cd5f5323e832d96ee896ff8830ca4c", -// "s": "0x28c7ce6a539d9318688687097a2db29e15c32ba8c085275fdd3dddf047d4bd1a" -//} -// -//"0xf86c37850e6f3b322e82520894176386b6ffc469ac049f9ec1f6cc0efd1d09b373884563918244f400008000a0dcc588257770e08660cb809e71b293f556cd5f5323e832d96ee896ff8830ca4ca028c7ce6a539d9318688687097a2db29e15c32ba8c085275fdd3dddf047d4bd1a" -// -//{ -// "nonce": 55, -// "gasPrice": { -// "_hex": "0x0e6f3b322e" -// }, -// "gasLimit": { -// "_hex": "0x5208" -// }, -// "to": "0x176386b6ffc469ac049f9ec1f6cc0efd1d09b373", -// "value": { -// "_hex": "0x4563918244f40000" -// }, -// "data": "0x", -// "v": 0, -// "r": "0xdcc588257770e08660cb809e71b293f556cd5f5323e832d96ee896ff8830ca4c", -// "s": "0x28c7ce6a539d9318688687097a2db29e15c32ba8c085275fdd3dddf047d4bd1a" -//} diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/types.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/types.hpp index 963244fa..3acc8b8f 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/types.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/types.hpp @@ -9,4 +9,17 @@ typedef uint64_t network_id_type; using bytes = std::vector; +class signature { +public: + std::string v; + std::string r; + std::string s; + + signature() = default; + signature(const std::string &sign); + + std::string serialize() const; + void deserialize(const std::string &sign); +}; + }}} // namespace graphene::peerplays_sidechain::ethereum diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp index 13a89278..b2db9331 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp @@ -19,7 +19,7 @@ std::string to_hex(const T &val, bool add_front_zero = true) { std::stringstream stream; stream << std::hex << val; std::string result(stream.str()); - if(add_front_zero) { + if (add_front_zero) { if (result.size() % 2) result = "0" + result; } diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index c827a721..951228d5 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -585,33 +585,65 @@ std::string sidechain_net_handler_ethereum::process_sidechain_transaction(const std::string sidechain_net_handler_ethereum::send_sidechain_transaction(const sidechain_transaction_object &sto) { boost::property_tree::ptree pt; boost::property_tree::ptree pt_array; + + std::vector transactions; for (const auto &signature : sto.signatures) { - const auto &transaction = signature.second; //! Check if we have this signed transaction, if not, don't send it - if (transaction.empty()) + if (signature.second.empty()) continue; + ethereum::encoded_sign_transaction transaction{sto.transaction, ethereum::signature{signature.second}}; + transactions.emplace_back(transaction); + } + + const auto ¤t_son = plugin.get_current_son_object(sidechain); + FC_ASSERT(current_son.sidechain_public_keys.contains(sidechain), "No public keys for current son: ${account_id}", ("account_id", current_son.son_account)); + const auto &public_key = current_son.sidechain_public_keys.at(sidechain); + + const auto function_signature = ethereum::signature_encoder::get_function_signature_from_transaction(sto.transaction); + if (function_signature.empty()) { + elog("Function signature is empty for transaction id ${id}, transaction ${transaction}", ("id", sto.id)("transaction", sto.transaction)); + return std::string{}; //! Return empty string, as we have error in sending + } + + const ethereum::signature_encoder encoder{function_signature}; #ifdef SEND_RAW_TRANSACTION - const std::string sidechain_transaction = rpc_client->eth_send_raw_transaction(transaction); + ethereum::raw_transaction raw_tr; + raw_tr.nonce = rpc_client->get_nonce(ethereum::add_0x(public_key)); + raw_tr.gas_price = rpc_client->get_gas_price(); + raw_tr.gas_limit = rpc_client->get_gas_limit(); + raw_tr.to = wallet_contract_address; + raw_tr.value = ""; + raw_tr.data = encoder.encode(transactions); + raw_tr.chain_id = ethereum::add_0x(ethereum::to_hex(chain_id)); + + const auto sign_tr = raw_tr.sign(get_private_key(public_key)); + const std::string sidechain_transaction = rpc_client->eth_send_raw_transaction(sign_tr.serialize()); #else - const std::string sidechain_transaction = rpc_client->eth_send_transaction(transaction); + ethereum::transaction raw_tr; + raw_tr.data = encoder.encode(transactions); + raw_tr.to = wallet_contract_address; + raw_tr.from = ethereum::add_0x(public_key); + + const auto sign_tr = raw_tr.sign(get_private_key(public_key)); + const std::string sidechain_transaction = rpc_client->eth_send_transaction(sign_tr.serialize()); #endif - std::stringstream ss_tx(sidechain_transaction); - boost::property_tree::ptree tx_json; - boost::property_tree::read_json(ss_tx, tx_json); - if (tx_json.count("result") && !tx_json.count("error")) { - boost::property_tree::ptree node; - node.put("transaction", transaction); - node.put("transaction_receipt", tx_json.get("result")); - pt_array.push_back(std::make_pair("", node)); - } else { - //! Fixme - //! How should we proceed with error in eth_send_transaction - elog("Error in eth_send_transaction for transaction ${id}, transaction ${transaction}", ("id", sto.id)("transaction", transaction)); - return std::string{}; //! Return empty string, as we have error in sending - } + std::stringstream ss_tx(sidechain_transaction); + boost::property_tree::ptree tx_json; + boost::property_tree::read_json(ss_tx, tx_json); + if (tx_json.count("result") && !tx_json.count("error")) { + boost::property_tree::ptree node; + node.put("transaction", sto.transaction); + node.put("sidechain_transaction", sidechain_transaction); + node.put("transaction_receipt", tx_json.get("result")); + pt_array.push_back(std::make_pair("", node)); + } else { + //! Fixme + //! How should we proceed with error in eth_send_transaction + elog("Error in eth send transaction for transaction id ${id}, transaction ${transaction}, sidechain_transaction ${sidechain_transaction}", ("id", sto.id)("transaction", sto.transaction)("sidechain_transaction", sidechain_transaction)); + return std::string{}; //! Return empty string, as we have error in sending } pt.add_child("result_array", pt_array); @@ -705,8 +737,7 @@ std::string sidechain_net_handler_ethereum::create_primary_wallet_transaction(co owners_weights.emplace_back(std::make_pair(pub_key_str, son.weight)); } - const ethereum::update_owners_encoder encoder; - return encoder.encode(owners_weights, object_id); + return ethereum::update_owners_encoder::encode(owners_weights, object_id); } std::string sidechain_net_handler_ethereum::create_deposit_transaction(const son_wallet_deposit_object &swdo) { @@ -714,8 +745,7 @@ std::string sidechain_net_handler_ethereum::create_deposit_transaction(const son } std::string sidechain_net_handler_ethereum::create_withdrawal_transaction(const son_wallet_withdraw_object &swwo) { - const ethereum::withdrawal_encoder encoder; - return encoder.encode(swwo.withdraw_address.substr(2), swwo.withdraw_amount.value * 10000000000, swwo.id.operator std::string()); + return ethereum::withdrawal_encoder::encode(swwo.withdraw_address.substr(2), swwo.withdraw_amount.value * 10000000000, swwo.id.operator std::string()); } std::string sidechain_net_handler_ethereum::sign_transaction(const sidechain_transaction_object &sto) { @@ -724,25 +754,11 @@ std::string sidechain_net_handler_ethereum::sign_transaction(const sidechain_tra const auto &public_key = current_son.sidechain_public_keys.at(sidechain); -#ifdef SEND_RAW_TRANSACTION - ethereum::raw_transaction raw_tr; - raw_tr.nonce = rpc_client->get_nonce(ethereum::add_0x(public_key)); - raw_tr.gas_price = rpc_client->get_gas_price(); - raw_tr.gas_limit = rpc_client->get_gas_limit(); - raw_tr.to = wallet_contract_address; - raw_tr.value = ""; - raw_tr.data = sto.transaction; - raw_tr.chain_id = ethereum::add_0x(ethereum::to_hex(chain_id)); + //! We need to change v value according to chain_id + auto signature = ethereum::sign_hash(ethereum::keccak_hash(sto.transaction), ethereum::add_0x(ethereum::to_hex(chain_id)), get_private_key(public_key)); + signature.v = ethereum::to_hex(ethereum::from_hex(signature.v) - 2 * chain_id - 35 + 27); - const auto sign_tr = raw_tr.sign(get_private_key(public_key)); - return sign_tr.serialize(); -#else - ethereum::transaction sign_transaction; - sign_transaction.data = sto.transaction; - sign_transaction.to = wallet_contract_address; - sign_transaction.from = "0x" + public_key; - return sign_transaction.sign(get_private_key(public_key)).serialize(); -#endif + return signature.serialize(); } void sidechain_net_handler_ethereum::schedule_ethereum_listener() { diff --git a/tests/peerplays_sidechain/ethereum_transaction_tests.cpp b/tests/peerplays_sidechain/ethereum_transaction_tests.cpp index 769c35b1..5bcc0543 100644 --- a/tests/peerplays_sidechain/ethereum_transaction_tests.cpp +++ b/tests/peerplays_sidechain/ethereum_transaction_tests.cpp @@ -9,12 +9,22 @@ using namespace graphene::peerplays_sidechain::ethereum; BOOST_AUTO_TEST_SUITE(ethereum_transaction_tests) BOOST_AUTO_TEST_CASE(withdrawal_encoder_test) { - const withdrawal_encoder encoder; - const auto tx = encoder.encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.0"); - BOOST_CHECK_EQUAL(tx, "0xe088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E300000000000000000000000000000000000000000000000000000"); + const auto tx = withdrawal_encoder::encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.0"); + BOOST_CHECK_EQUAL(tx, "0xcf7c8f6d0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E300000000000000000000000000000000000000000000000000000"); - const auto tx1 = encoder.encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.1"); - BOOST_CHECK_EQUAL(tx1, "0xe088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); + const auto tx1 = withdrawal_encoder::encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.1"); + BOOST_CHECK_EQUAL(tx1, "0xcf7c8f6d0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); +} + +BOOST_AUTO_TEST_CASE(withdrawal_signature_encoder_test) { + const signature_encoder encoder{withdrawal_function_signature}; + + encoded_sign_transaction transaction; + transaction.data = "0xcf7c8f6d0000000000000000000000005c79a9f5767e3c1b926f963fa24e21d8a04289ae0000000000000000000000000000000000000000000000001bc16d674ec8000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33372E300000000000000000000000000000000000000000000000000000"; + transaction.sign = sign_hash(keccak_hash(transaction.data), "0x21", "eb5749a569e6141a3b08249d4a0d84f9ef22c67651ba29adb8eb6fd43fc83060" ); + + const auto tx = encoder.encode({transaction}); + BOOST_CHECK_EQUAL(tx, "0xdaac6c8100000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000065ef357c2788df103d443e3c4a9e0864d6f52fbaab479684b8eb6ea09422b6b54310ca0511c6cc02402a668a73f9613c00f6f535dbd2d78468ecba540a8a0dba3d00000000000000000000000000000000000000000000000000000000000000a4cf7c8f6d0000000000000000000000005c79a9f5767e3c1b926f963fa24e21d8a04289ae0000000000000000000000000000000000000000000000001bc16d674ec8000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33372E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(update_owners_encoder_test) { @@ -22,13 +32,23 @@ BOOST_AUTO_TEST_CASE(update_owners_encoder_test) { owners_weights.emplace_back("5FbBb31BE52608D2F52247E8400B7fCaA9E0bC12", 1); owners_weights.emplace_back("76ce31bd03f601c3fc13732def921c5bac282676", 1); - const update_owners_encoder encoder; - const auto tx = encoder.encode(owners_weights, "1.35.0"); - BOOST_CHECK_EQUAL(tx, "0x23ab6adf000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"); + const auto tx = update_owners_encoder::encode(owners_weights, "1.35.0"); + BOOST_CHECK_EQUAL(tx, "0xf6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"); owners_weights.emplace_back("09ee460834498a4ee361beb819470061b7381b49", 1); - const auto tx1 = encoder.encode(owners_weights, "1.36.1"); - BOOST_CHECK_EQUAL(tx1, "0x23ab6adf0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000000030000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac282676000000000000000000000000000000000000000000000000000000000000000100000000000000000000000009ee460834498a4ee361beb819470061b7381b4900000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); + const auto tx1 = update_owners_encoder::encode(owners_weights, "1.36.1"); + BOOST_CHECK_EQUAL(tx1, "0xf6afbeff0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000000030000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac282676000000000000000000000000000000000000000000000000000000000000000100000000000000000000000009ee460834498a4ee361beb819470061b7381b4900000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); +} + +BOOST_AUTO_TEST_CASE(update_owners_signature_encoder_test) { + const signature_encoder encoder{update_owners_function_signature}; + + encoded_sign_transaction transaction; + transaction.data = "0xf6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"; + transaction.sign = sign_hash(keccak_hash(transaction.data), "0x21", "eb5749a569e6141a3b08249d4a0d84f9ef22c67651ba29adb8eb6fd43fc83060" ); + + const auto tx = encoder.encode({transaction}); + BOOST_CHECK_EQUAL(tx, "0x9d608673000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000000665762851a05348a4900393b3f2778c5078689422e43e3a2aa9b517a4141133bd42c08169979785256a2f26d1da13e297125ee84c2d79be07212cfde592fc03dbb0000000000000000000000000000000000000000000000000000000000000124f6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(raw_transaction_serialization_test) { From 42b3890a7c3e9abfa79dd24baef68d50466e2068 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Tue, 6 Dec 2022 12:17:09 +0000 Subject: [PATCH 32/36] #482 burn eth from son account --- .../sidechain_net_handler_ethereum.cpp | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-) diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index 951228d5..8faa5cdd 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -686,8 +686,18 @@ bool sidechain_net_handler_ethereum::settle_sidechain_transaction(const sidechai if (count != json.get_child("result_array").size()) { wlog("Not all receipts received for transaction ${id}", ("id", sto.id)); return false; - } else + } else { + if (sto.object_id.is()) { + settle_amount = asset(0, database.get_global_properties().parameters.eth_asset()); + } + + if (sto.object_id.is()) { + auto swwo = database.get(sto.object_id); + settle_amount = asset(swwo.withdraw_amount, database.get_global_properties().parameters.eth_asset()); + } + return true; + } return false; } From ab1e08a7566ab5dd62322909a7b473492b65f029 Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Thu, 8 Dec 2022 14:02:53 +0000 Subject: [PATCH 33/36] #479 one bunch transaction --- .../peerplays_sidechain/ethereum/encoders.cpp | 4 ++-- .../sidechain_net_handler_ethereum.cpp | 3 +-- .../ethereum_transaction_tests.cpp | 16 ++++++++-------- 3 files changed, 11 insertions(+), 12 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp b/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp index feab921f..ce1e0083 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/encoders.cpp @@ -26,7 +26,7 @@ std::string base_encoder::encode_string(const std::string &value) { } //! update_owners_encoder -const std::string update_owners_encoder::function_signature = "f6afbeff"; //! updateOwners_(address,(address,uint256)[],string) +const std::string update_owners_encoder::function_signature = "23ab6adf"; //! updateOwners((address,uint256)[],string) std::string update_owners_encoder::encode(const std::vector> &owners_weights, const std::string &object_id) { std::string data = "0x" + function_signature; data += base_encoder::encode_uint256(64); @@ -42,7 +42,7 @@ std::string update_owners_encoder::encode(const std::vector sidechain_net_handler_ethereum::estimate_withdrawal_transaction_ } const auto &public_key = son->sidechain_public_keys.at(sidechain); - const ethereum::withdrawal_encoder encoder; - const auto data = encoder.encode(public_key, 1 * 10000000000, son_wallet_withdraw_id_type{0}.operator object_id_type().operator std::string()); + const auto data = ethereum::withdrawal_encoder::encode(public_key, 1 * 10000000000, son_wallet_withdraw_id_type{0}.operator object_id_type().operator std::string()); const std::string params = "[{\"from\":\"" + ethereum::add_0x(public_key) + "\", \"to\":\"" + wallet_contract_address + "\", \"data\":\"" + data + "\"}]"; const auto estimate_gas = ethereum::from_hex(rpc_client->get_estimate_gas(params)); diff --git a/tests/peerplays_sidechain/ethereum_transaction_tests.cpp b/tests/peerplays_sidechain/ethereum_transaction_tests.cpp index 5bcc0543..47cc090c 100644 --- a/tests/peerplays_sidechain/ethereum_transaction_tests.cpp +++ b/tests/peerplays_sidechain/ethereum_transaction_tests.cpp @@ -10,21 +10,21 @@ BOOST_AUTO_TEST_SUITE(ethereum_transaction_tests) BOOST_AUTO_TEST_CASE(withdrawal_encoder_test) { const auto tx = withdrawal_encoder::encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.0"); - BOOST_CHECK_EQUAL(tx, "0xcf7c8f6d0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E300000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx, "0xe088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E300000000000000000000000000000000000000000000000000000"); const auto tx1 = withdrawal_encoder::encode("5fbbb31be52608d2f52247e8400b7fcaa9e0bc12", 10000000000, "1.36.1"); - BOOST_CHECK_EQUAL(tx1, "0xcf7c8f6d0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx1, "0xe088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(withdrawal_signature_encoder_test) { const signature_encoder encoder{withdrawal_function_signature}; encoded_sign_transaction transaction; - transaction.data = "0xcf7c8f6d0000000000000000000000005c79a9f5767e3c1b926f963fa24e21d8a04289ae0000000000000000000000000000000000000000000000001bc16d674ec8000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33372E300000000000000000000000000000000000000000000000000000"; + transaction.data = "0xe088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E300000000000000000000000000000000000000000000000000000"; transaction.sign = sign_hash(keccak_hash(transaction.data), "0x21", "eb5749a569e6141a3b08249d4a0d84f9ef22c67651ba29adb8eb6fd43fc83060" ); const auto tx = encoder.encode({transaction}); - BOOST_CHECK_EQUAL(tx, "0xdaac6c8100000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000065ef357c2788df103d443e3c4a9e0864d6f52fbaab479684b8eb6ea09422b6b54310ca0511c6cc02402a668a73f9613c00f6f535dbd2d78468ecba540a8a0dba3d00000000000000000000000000000000000000000000000000000000000000a4cf7c8f6d0000000000000000000000005c79a9f5767e3c1b926f963fa24e21d8a04289ae0000000000000000000000000000000000000000000000001bc16d674ec8000000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33372E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx, "0xdaac6c8100000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000001000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000800000000000000000000000000000000000000000000000000000000000000065c4622d2ff2b2d89c5c6f8225ab0f979bc69d4fcd4fd47db757b66fb8a39e2bc5522be5d101aa11e66da78db973f136b323be10bd107ff0b648f06b4c71ef2a4f00000000000000000000000000000000000000000000000000000000000000a4e088747b0000000000000000000000005fbbb31be52608d2f52247e8400b7fcaa9e0bc1200000000000000000000000000000000000000000000000000000002540be40000000000000000000000000000000000000000000000000000000000000000600000000000000000000000000000000000000000000000000000000000000006312E33362E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(update_owners_encoder_test) { @@ -33,22 +33,22 @@ BOOST_AUTO_TEST_CASE(update_owners_encoder_test) { owners_weights.emplace_back("76ce31bd03f601c3fc13732def921c5bac282676", 1); const auto tx = update_owners_encoder::encode(owners_weights, "1.35.0"); - BOOST_CHECK_EQUAL(tx, "0xf6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx, "0x23ab6adf000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"); owners_weights.emplace_back("09ee460834498a4ee361beb819470061b7381b49", 1); const auto tx1 = update_owners_encoder::encode(owners_weights, "1.36.1"); - BOOST_CHECK_EQUAL(tx1, "0xf6afbeff0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000000030000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac282676000000000000000000000000000000000000000000000000000000000000000100000000000000000000000009ee460834498a4ee361beb819470061b7381b4900000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx1, "0x23ab6adf0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000012000000000000000000000000000000000000000000000000000000000000000030000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac282676000000000000000000000000000000000000000000000000000000000000000100000000000000000000000009ee460834498a4ee361beb819470061b7381b4900000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33362E310000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(update_owners_signature_encoder_test) { const signature_encoder encoder{update_owners_function_signature}; encoded_sign_transaction transaction; - transaction.data = "0xf6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"; + transaction.data = "0x23ab6adf000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E300000000000000000000000000000000000000000000000000000"; transaction.sign = sign_hash(keccak_hash(transaction.data), "0x21", "eb5749a569e6141a3b08249d4a0d84f9ef22c67651ba29adb8eb6fd43fc83060" ); const auto tx = encoder.encode({transaction}); - BOOST_CHECK_EQUAL(tx, "0x9d608673000000000000000000000000000000000000000000000000000000000000002000000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000008000000000000000000000000000000000000000000000000000000000000000665762851a05348a4900393b3f2778c5078689422e43e3a2aa9b517a4141133bd42c08169979785256a2f26d1da13e297125ee84c2d79be07212cfde592fc03dbb0000000000000000000000000000000000000000000000000000000000000124f6afbeff000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); + BOOST_CHECK_EQUAL(tx, "0x9d6086730000000000000000000000000000000000000000000000000000000000000020000000000000000000000000000000000000000000000000000000000000000100000000000000000000000000000000000000000000000000000000000000200000000000000000000000000000000000000000000000000000000000000080000000000000000000000000000000000000000000000000000000000000006698877eafa525c1a55f6b5e0a7187dfae484c97d9f77c4421a00276a9408a3e713d24402b44c05a883142fcffa84e1a802be37c17bb360f6f4810eb0415c8bbfd000000000000000000000000000000000000000000000000000000000000012423ab6adf000000000000000000000000000000000000000000000000000000000000004000000000000000000000000000000000000000000000000000000000000000e000000000000000000000000000000000000000000000000000000000000000020000000000000000000000005FbBb31BE52608D2F52247E8400B7fCaA9E0bC12000000000000000000000000000000000000000000000000000000000000000100000000000000000000000076ce31bd03f601c3fc13732def921c5bac28267600000000000000000000000000000000000000000000000000000000000000010000000000000000000000000000000000000000000000000000000000000006312E33352E30000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000"); } BOOST_AUTO_TEST_CASE(raw_transaction_serialization_test) { From 4883dfe38d0eb3dfa71fcc2203b220a802e3453f Mon Sep 17 00:00:00 2001 From: Vlad Dobromyslov Date: Thu, 8 Dec 2022 14:03:14 +0000 Subject: [PATCH 34/36] #484 multiple eth withdrawals --- .../ethereum/transaction.cpp | 8 ++--- .../peerplays_sidechain/ethereum/utils.cpp | 20 +++++++++++ .../peerplays_sidechain/ethereum/utils.hpp | 4 +++ .../sidechain_net_handler.hpp | 9 ++--- .../sidechain_net_handler.cpp | 36 ++++++++++++------- .../sidechain_net_handler_ethereum.cpp | 2 +- 6 files changed, 57 insertions(+), 22 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp index dd1179b4..9a1383df 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/transaction.cpp @@ -210,8 +210,8 @@ std::string signed_transaction::serialize() const { rlp_encoder::encode(remove_0x(value)) + rlp_encoder::encode(remove_0x(data)) + rlp_encoder::encode(remove_0x(v)) + - rlp_encoder::encode(remove_0x(r)) + - rlp_encoder::encode(remove_0x(s)); + rlp_encoder::encode(remove_leading_00(remove_0x(r))) + + rlp_encoder::encode(remove_leading_00(remove_0x(s))); return add_0x(bytes2hex(rlp_encoder::encode_length(serialized.size(), 192) + serialized)); } @@ -234,9 +234,9 @@ void signed_transaction::deserialize(const std::string &raw_tx) { boost::algorithm::to_lower(data); v = add_0x(rlp_array.at(6)); boost::algorithm::to_lower(v); - r = add_0x(rlp_array.at(7)); + r = add_0x(add_leading_00(rlp_array.at(7))); boost::algorithm::to_lower(r); - s = add_0x(rlp_array.at(8)); + s = add_0x(add_leading_00(rlp_array.at(8))); boost::algorithm::to_lower(s); } diff --git a/libraries/plugins/peerplays_sidechain/ethereum/utils.cpp b/libraries/plugins/peerplays_sidechain/ethereum/utils.cpp index ce64e1ae..0f34cd9c 100644 --- a/libraries/plugins/peerplays_sidechain/ethereum/utils.cpp +++ b/libraries/plugins/peerplays_sidechain/ethereum/utils.cpp @@ -49,4 +49,24 @@ std::string remove_0x(const std::string &s) { return s; } +std::string add_leading_00(const std::string &s) { + std::string result = s; + + while (result.size() < 64) { + result = "00" + result; + } + + return result; +} + +std::string remove_leading_00(const std::string &s) { + std::string result = s; + + while (result.size() > 1 && result.substr(0, 2) == "00") { + result = result.substr(2); + } + + return result; +} + }}} // namespace graphene::peerplays_sidechain::ethereum diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp index b2db9331..4ac70094 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/ethereum/utils.hpp @@ -14,6 +14,10 @@ std::string add_0x(const std::string &s); std::string remove_0x(const std::string &s); +std::string add_leading_00(const std::string &s); + +std::string remove_leading_00(const std::string &s); + template std::string to_hex(const T &val, bool add_front_zero = true) { std::stringstream stream; diff --git a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp index fc295b4c..0e7e2fc1 100644 --- a/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp +++ b/libraries/plugins/peerplays_sidechain/include/graphene/peerplays_sidechain/sidechain_net_handler.hpp @@ -20,10 +20,11 @@ public: sidechain_net_handler(peerplays_sidechain_plugin &_plugin, const boost::program_options::variables_map &options); virtual ~sidechain_net_handler(); - sidechain_type get_sidechain(); - std::vector get_sidechain_deposit_addresses(); - std::vector get_sidechain_withdraw_addresses(); - std::string get_private_key(std::string public_key); + sidechain_type get_sidechain() const; + std::vector get_sidechain_deposit_addresses() const; + std::vector get_sidechain_withdraw_addresses() const; + std::vector get_sidechain_transaction_objects(sidechain_transaction_status status) const; + std::string get_private_key(std::string public_key) const; bool proposal_exists(int32_t operation_tag, const object_id_type &object_id, boost::optional proposal_op = boost::none); bool signer_expected(const sidechain_transaction_object &sto, son_id_type signer); diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp index 971df7c7..38345935 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler.cpp @@ -21,11 +21,11 @@ sidechain_net_handler::sidechain_net_handler(peerplays_sidechain_plugin &_plugin sidechain_net_handler::~sidechain_net_handler() { } -sidechain_type sidechain_net_handler::get_sidechain() { +sidechain_type sidechain_net_handler::get_sidechain() const { return sidechain; } -std::vector sidechain_net_handler::get_sidechain_deposit_addresses() { +std::vector sidechain_net_handler::get_sidechain_deposit_addresses() const { std::vector result; const auto &sidechain_addresses_idx = database.get_index_type(); @@ -38,7 +38,7 @@ std::vector sidechain_net_handler::get_sidechain_deposit_addresses( return result; } -std::vector sidechain_net_handler::get_sidechain_withdraw_addresses() { +std::vector sidechain_net_handler::get_sidechain_withdraw_addresses() const { std::vector result; const auto &sidechain_addresses_idx = database.get_index_type(); @@ -51,7 +51,20 @@ std::vector sidechain_net_handler::get_sidechain_withdraw_addresses return result; } -std::string sidechain_net_handler::get_private_key(std::string public_key) { +std::vector sidechain_net_handler::get_sidechain_transaction_objects(sidechain_transaction_status status) const { + std::vector result; + + const auto &idx = database.get_index_type().indices().get(); + const auto &idx_range = idx.equal_range(std::make_tuple(sidechain, status)); + std::for_each(idx_range.first, idx_range.second, + [&result](const sidechain_transaction_object &sto) { + result.push_back(sto); + }); + + return result; +} + +std::string sidechain_net_handler::get_private_key(std::string public_key) const { auto private_key_itr = private_keys.find(public_key); if (private_key_itr != private_keys.end()) { return private_key_itr->second; @@ -473,10 +486,9 @@ void sidechain_net_handler::process_withdrawals() { } void sidechain_net_handler::process_sidechain_transactions() { - const auto &idx = database.get_index_type().indices().get(); - const auto &idx_range = idx.equal_range(std::make_tuple(sidechain, sidechain_transaction_status::valid)); + const auto stos = get_sidechain_transaction_objects(sidechain_transaction_status::valid); - std::for_each(idx_range.first, idx_range.second, [&](const sidechain_transaction_object &sto) { + std::for_each(stos.cbegin(), stos.cend(), [&](const sidechain_transaction_object &sto) { if ((sto.id == object_id_type(0, 0, 0)) || !signer_expected(sto, plugin.get_current_son_id(sidechain))) { return; } @@ -520,10 +532,9 @@ void sidechain_net_handler::process_sidechain_transactions() { } void sidechain_net_handler::send_sidechain_transactions() { - const auto &idx = database.get_index_type().indices().get(); - const auto &idx_range = idx.equal_range(std::make_tuple(sidechain, sidechain_transaction_status::complete)); + const auto stos = get_sidechain_transaction_objects(sidechain_transaction_status::complete); - std::for_each(idx_range.first, idx_range.second, [&](const sidechain_transaction_object &sto) { + std::for_each(stos.cbegin(), stos.cend(), [&](const sidechain_transaction_object &sto) { if (sto.id == object_id_type(0, 0, 0)) { return; } @@ -555,10 +566,9 @@ void sidechain_net_handler::send_sidechain_transactions() { } void sidechain_net_handler::settle_sidechain_transactions() { - const auto &idx = database.get_index_type().indices().get(); - const auto &idx_range = idx.equal_range(std::make_tuple(sidechain, sidechain_transaction_status::sent)); + const auto stos = get_sidechain_transaction_objects(sidechain_transaction_status::sent); - std::for_each(idx_range.first, idx_range.second, [&](const sidechain_transaction_object &sto) { + std::for_each(stos.cbegin(), stos.cend(), [&](const sidechain_transaction_object &sto) { if (sto.id == object_id_type(0, 0, 0)) { return; } diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp index 8faa5cdd..358c352c 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_ethereum.cpp @@ -76,7 +76,7 @@ std::string ethereum_rpc_client::get_network_id() { } std::string ethereum_rpc_client::get_nonce(const std::string &address) { - const std::string reply_str = eth_get_transaction_count("[\"" + address + "\", \"latest\"]"); + const std::string reply_str = eth_get_transaction_count("[\"" + address + "\", \"pending\"]"); const auto nonce_string = retrieve_value_from_reply(reply_str, ""); if (!nonce_string.empty()) { const auto nonce_val = ethereum::from_hex(nonce_string); From 578edc56d864a4637c9ef8dc2cb8efc3edcdae53 Mon Sep 17 00:00:00 2001 From: timur <12267899-timur.5@users.noreply.gitlab.com> Date: Fri, 16 Dec 2022 00:34:33 +0000 Subject: [PATCH 35/36] Fix Ubuntu 18 build --- Dockerfile | 65 +++++++++++++++++-- Dockerfile.18.04 | 44 +++++++++++-- .../wallet/include/graphene/wallet/wallet.hpp | 4 +- 3 files changed, 102 insertions(+), 11 deletions(-) diff --git a/Dockerfile b/Dockerfile index 50c51c3a..3f4c62b5 100644 --- a/Dockerfile +++ b/Dockerfile @@ -11,15 +11,14 @@ RUN \ apt-utils \ autoconf \ bash \ + bison \ build-essential \ ca-certificates \ - cmake \ dnsutils \ - doxygen \ expect \ + flex \ git \ graphviz \ - libboost-all-dev \ libbz2-dev \ libcurl4-openssl-dev \ libncurses-dev \ @@ -35,7 +34,6 @@ RUN \ ntp \ openssh-server \ pkg-config \ - perl \ python3 \ python3-jinja2 \ sudo \ @@ -53,6 +51,31 @@ RUN echo 'peerplays:peerplays' | chpasswd # SSH EXPOSE 22 +#=============================================================================== +# Boost setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + wget https://boostorg.jfrog.io/artifactory/main/release/1.72.0/source/boost_1_72_0.tar.gz && \ + tar -xzvf boost_1_72_0.tar.gz boost_1_72_0 && \ + cd boost_1_72_0/ && \ + ./bootstrap.sh && \ + ./b2 install + +#=============================================================================== +# cmake setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + wget -c 'https://cmake.org/files/v3.23/cmake-3.23.1-linux-x86_64.sh' -O cmake-3.23.1-linux-x86_64.sh && \ + chmod 755 ./cmake-3.23.1-linux-x86_64.sh && \ + ./cmake-3.23.1-linux-x86_64.sh --prefix=/usr/ --skip-license && \ + cmake --version + #=============================================================================== # libzmq setup #=============================================================================== @@ -85,6 +108,37 @@ RUN \ make -j$(nproc) install && \ ldconfig +#=============================================================================== +# Doxygen setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + sudo apt install -y bison flex && \ + wget https://github.com/doxygen/doxygen/archive/refs/tags/Release_1_8_17.tar.gz && \ + tar -xvf Release_1_8_17.tar.gz && \ + cd doxygen-Release_1_8_17 && \ + mkdir build && \ + cd build && \ + cmake .. && \ + make -j$(nproc) install && \ + ldconfig + +#=============================================================================== +# Perl setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + wget https://github.com/Perl/perl5/archive/refs/tags/v5.30.0.tar.gz && \ + tar -xvf v5.30.0.tar.gz && \ + cd perl5-5.30.0 && \ + ./Configure -des && \ + make -j$(nproc) install && \ + ldconfig + #=============================================================================== # Peerplays setup #=============================================================================== @@ -106,6 +160,9 @@ ADD . peerplays # Configure Peerplays RUN \ cd peerplays && \ + git submodule update --init --recursive && \ + git symbolic-ref --short HEAD && \ + git log --oneline -n 5 && \ mkdir build && \ cd build && \ cmake -DCMAKE_BUILD_TYPE=Release .. diff --git a/Dockerfile.18.04 b/Dockerfile.18.04 index 49a06fa1..2e153962 100644 --- a/Dockerfile.18.04 +++ b/Dockerfile.18.04 @@ -11,11 +11,12 @@ RUN \ apt-utils \ autoconf \ bash \ + bison \ build-essential \ ca-certificates \ dnsutils \ - doxygen \ expect \ + flex \ git \ graphviz \ libbz2-dev \ @@ -33,7 +34,6 @@ RUN \ ntp \ openssh-server \ pkg-config \ - perl \ python3 \ python3-jinja2 \ sudo \ @@ -58,9 +58,9 @@ EXPOSE 22 WORKDIR /home/peerplays/ RUN \ - wget -c 'https://boostorg.jfrog.io/artifactory/main/release/1.71.0/source/boost_1_71_0.tar.bz2' -O boost_1_71_0.tar.bz2 && \ - tar xjf boost_1_71_0.tar.bz2 && \ - cd boost_1_71_0/ && \ + wget https://boostorg.jfrog.io/artifactory/main/release/1.72.0/source/boost_1_72_0.tar.gz && \ + tar -xzvf boost_1_72_0.tar.gz boost_1_72_0 && \ + cd boost_1_72_0/ && \ ./bootstrap.sh && \ ./b2 install @@ -108,6 +108,37 @@ RUN \ make -j$(nproc) install && \ ldconfig +#=============================================================================== +# Doxygen setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + sudo apt install -y bison flex && \ + wget https://github.com/doxygen/doxygen/archive/refs/tags/Release_1_8_17.tar.gz && \ + tar -xvf Release_1_8_17.tar.gz && \ + cd doxygen-Release_1_8_17 && \ + mkdir build && \ + cd build && \ + cmake .. && \ + make -j$(nproc) install && \ + ldconfig + +#=============================================================================== +# Perl setup +#=============================================================================== + +WORKDIR /home/peerplays/ + +RUN \ + wget https://github.com/Perl/perl5/archive/refs/tags/v5.30.0.tar.gz && \ + tar -xvf v5.30.0.tar.gz && \ + cd perl5-5.30.0 && \ + ./Configure -des && \ + make -j$(nproc) install && \ + ldconfig + #=============================================================================== # Peerplays setup #=============================================================================== @@ -129,6 +160,9 @@ ADD . peerplays # Configure Peerplays RUN \ cd peerplays && \ + git submodule update --init --recursive && \ + git symbolic-ref --short HEAD && \ + git log --oneline -n 5 && \ mkdir build && \ cd build && \ cmake -DCMAKE_BUILD_TYPE=Release .. diff --git a/libraries/wallet/include/graphene/wallet/wallet.hpp b/libraries/wallet/include/graphene/wallet/wallet.hpp index 6a0b5ee5..a7807596 100644 --- a/libraries/wallet/include/graphene/wallet/wallet.hpp +++ b/libraries/wallet/include/graphene/wallet/wallet.hpp @@ -980,13 +980,13 @@ class wallet_api * * @return true if the label was set, otherwise false */ - bool set_key_label( public_key_type, string label ); + bool set_key_label( public_key_type key, string label ); /** Get label of a public key. * @param key a public key * @return the label if already set by \c set_key_label(), or an empty string if not set */ - string get_key_label( public_key_type )const; + string get_key_label( public_key_type key )const; /* Get the public key associated with a given label. * @param label a label From bb7c534b10b114cbf3571f54a20f5ca8cba6e255 Mon Sep 17 00:00:00 2001 From: serkixenos Date: Fri, 16 Dec 2022 04:27:31 +0100 Subject: [PATCH 36/36] Update Hive's son-account owner authority on primary wallet update --- .../sidechain_net_handler_hive.cpp | 35 ++++++++++++++----- 1 file changed, 26 insertions(+), 9 deletions(-) diff --git a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp index 63ae22c6..873fa08e 100644 --- a/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp +++ b/libraries/plugins/peerplays_sidechain/sidechain_net_handler_hive.cpp @@ -256,13 +256,14 @@ bool sidechain_net_handler_hive::process_proposal(const proposal_object &po) { const std::string memo_key = rpc_client->get_account_memo_key(wallet_account_name); - hive::authority active; - active.weight_threshold = total_weight * 2 / 3 + 1; - active.account_auths = account_auths; + hive::authority a; + a.weight_threshold = total_weight * 2 / 3 + 1; + a.account_auths = account_auths; hive::account_update_operation auo; auo.account = wallet_account_name; - auo.active = active; + auo.owner = a; + auo.active = a; auo.memo_key = op_trx.operations[0].get().memo_key; hive::signed_transaction htrx; @@ -505,13 +506,14 @@ void sidechain_net_handler_hive::process_primary_wallet() { return; } - hive::authority active; - active.weight_threshold = total_weight * 2 / 3 + 1; - active.account_auths = account_auths; + hive::authority a; + a.weight_threshold = total_weight * 2 / 3 + 1; + a.account_auths = account_auths; hive::account_update_operation auo; auo.account = wallet_account_name; - auo.active = active; + auo.owner = a; + auo.active = a; auo.memo_key = hive::public_key_type(memo_key); const std::string block_id_str = rpc_client->get_head_block_id(); @@ -546,12 +548,27 @@ void sidechain_net_handler_hive::process_primary_wallet() { proposal_op.proposed_ops.emplace_back(swu_op); + const auto signers = [this, &prev_sw, &active_sw, &swi] { + std::vector signers; + //! Check if we don't have any previous set of active SONs use the current one + if (prev_sw != swi.rend()) { + if (!prev_sw->sons.at(sidechain).empty()) + signers = prev_sw->sons.at(sidechain); + else + signers = active_sw->sons.at(sidechain); + } else { + signers = active_sw->sons.at(sidechain); + } + + return signers; + }(); + sidechain_transaction_create_operation stc_op; stc_op.payer = gpo.parameters.son_account(); stc_op.object_id = active_sw->id; stc_op.sidechain = sidechain; stc_op.transaction = tx_str; - stc_op.signers = gpo.active_sons.at(sidechain); + stc_op.signers = signers; proposal_op.proposed_ops.emplace_back(stc_op);