diff --git a/contracts/eosio.system/eosio.system.abi b/contracts/eosio.system/eosio.system.abi index a3e957327e884c3787b00a067b808375ae11b2ea..7c4b223035529229a0bfb89565f57d9c6a9bd1b0 100644 --- a/contracts/eosio.system/eosio.system.abi +++ b/contracts/eosio.system/eosio.system.abi @@ -322,6 +322,14 @@ {"name":"deposit_votes", "type":"int64"}, {"name":"unpaid_base_cnt", "type":"uint32"} ] + },{ + "name": "master_sn_info", + "base": "", + "fields": [ + {"name":"seq_num", "type":"uint16"}, + {"name":"owner", "type":"account_name"}, + {"name":"url", "type":"string"} + ] },{ "name": "producers_seq", "base": "", @@ -648,6 +656,12 @@ "index_type": "i64", "key_names" : ["owner"], "key_types" : ["uint64"] + },{ + "name": "mastersnlist", + "type": "master_sn_info", + "index_type": "i64", + "key_names" : ["seq_num"], + "key_types" : ["uint64"] },{ "name": "producerseq", "type": "producers_seq", diff --git a/contracts/eosio.system/eosio.system.hpp b/contracts/eosio.system/eosio.system.hpp index e12da15cce1a927af1f0f8600c74a80ee2e3255d..3f7267d887bf9dc74d9b61a9bad4405fca92f8c0 100644 --- a/contracts/eosio.system/eosio.system.hpp +++ b/contracts/eosio.system/eosio.system.hpp @@ -133,6 +133,17 @@ namespace eosiosystem { EOSLIB_SERIALIZE( producers_seq, (seq_num)(master)(voter_list)(prods_all) ) }; + + struct master_sn_info { + uint16_t seq_num = 1; // from 1 to 21 + account_name owner; + std::string url; + + uint64_t primary_key()const { return seq_num; } + + EOSLIB_SERIALIZE( master_sn_info, (seq_num)(owner)(url)) + }; + typedef eosio::multi_index< N(mastersnlist), master_sn_info> master_sn_list; //##YTA-Change end: //##YTA-Change start: @@ -335,6 +346,10 @@ namespace eosiosystem { void change_producer_seq_info( const account_name producer, const eosio::public_key& producer_key, bool isactive, bool seturl, const std::string& url); void update_producers_seq_totalvotes( uint16_t seq_num, account_name owner, double total_votes); + + void delproducer( const account_name producer ); + + void elect_new_sn_master( uint16_t seq_num ); //##YTA-Change end: // Implementation details: diff --git a/contracts/eosio.system/producer_pay.cpp b/contracts/eosio.system/producer_pay.cpp index 18ed144d8cff043c99458445405b7085f508e4e6..e2022306f2c9dc0b6b376fe165098e8a5a462477 100644 --- a/contracts/eosio.system/producer_pay.cpp +++ b/contracts/eosio.system/producer_pay.cpp @@ -272,6 +272,28 @@ namespace eosiosystem { uint32_t total_unpaid_blocks = _gstate.total_unpaid_blocks; uint32_t total_unpaid_base_cnt = _gstateex.total_unpaid_base_cnt; + + /* + //double total_producer_vote_weight = _gstate.total_producer_vote_weight; + + uint32_t total_unpaid_blocks = 0; + uint32_t total_unpaid_base_cnt = 0; + double total_producer_vote_weight = 0; + + for( auto it = _producers.begin(); it != _producers.end(); it++ ) { + total_unpaid_blocks += it->unpaid_blocks; + total_producer_vote_weight += it->total_votes; + } + + for( auto it = _producersext.begin(); it != _producersext.end(); it++ ) { + total_unpaid_base_cnt += it->unpaid_base_cnt; + } + + _gstate.total_unpaid_blocks = total_unpaid_blocks; + _gstateex.total_unpaid_base_cnt = total_unpaid_base_cnt; + _gstate.total_producer_vote_weight = total_producer_vote_weight; + */ + for( auto it = _producers.begin(); it != _producers.end(); it++ ) { if(!(it->active())) diff --git a/contracts/eosio.system/voting.cpp b/contracts/eosio.system/voting.cpp index 54f09ee4de14807942c581faa9bd1e5b0cc1ed90..3b367cdf4861c5978d8c2548e7019097ea56f1ef 100644 --- a/contracts/eosio.system/voting.cpp +++ b/contracts/eosio.system/voting.cpp @@ -18,6 +18,8 @@ #include #include +const uint64_t useconds_per_day_v = 24 * 3600 * uint64_t(1000000); + namespace eosiosystem { using eosio::indexed_by; using eosio::const_mem_fun; @@ -118,23 +120,93 @@ namespace eosiosystem { _producersext.erase(_producersext.begin()); } - for( uint16_t seq = 1; seq <= 21; seq++ ) { - producers_seq_table _prod_seq( _self, seq ); - if( _prod_seq.begin() != _prod_seq.end() ) - _prod_seq.erase(_prod_seq.begin()); - } + producers_seq_table _prod_seq( _self, _self ); + while (_prod_seq.begin() != _prod_seq.end()) { + _prod_seq.erase(_prod_seq.begin()); + } _gstateex.total_unpaid_base_cnt = 0; all_prods_singleton _all_prods(_self, _self); all_prods_level _all_prods_state; - if (_all_prods.exists()) + if (_all_prods.exists()) { _all_prods_state = _all_prods.get(); _all_prods_state.prods_l1.clear(); _all_prods_state.prods_l2.clear(); _all_prods_state.prods_l3.clear(); _all_prods.set(_all_prods_state,_self); + } + + master_sn_list _snlist( _self, _self ); + while (_snlist.begin() != _snlist.end()) { + _snlist.erase(_snlist.begin()); + } + } + + void system_contract::delproducer( const account_name producer ) { + auto itp = _producers.find(producer); + if( itp != _producers.end() ) { + _gstate.total_unpaid_blocks -= itp->unpaid_blocks; + _gstate.total_producer_vote_weight -= itp->total_votes; + _producers.erase(itp); + } + + auto itpex = _producersext.find(producer); + uint16_t seq_num = 0; + if( itpex != _producersext.end() ) { + _gstateex.total_unpaid_base_cnt -= itpex->unpaid_base_cnt; + seq_num = itpex->seq_num; + _producersext.erase(itpex); + } else { + return; + } + + bool needNewSnMaster = false; + master_sn_list _snlist(_self, _self); + auto sn_itr = _snlist.find (seq_num); + if( sn_itr != _snlist.end() ) { + if(sn_itr->owner == producer) { + needNewSnMaster = true; + } + } + rm_producer_seq(producer, seq_num); + + if( needNewSnMaster ) { + elect_new_sn_master( seq_num ); + } + } + + void system_contract::elect_new_sn_master( uint16_t seq_num ) { + producers_seq_table _prodseq(_self, _self); + auto ps_itr = _prodseq.find (seq_num); + if( ps_itr == _prodseq.end() ) + return; + + //account_name newMaster = 0; + _prodseq.modify( ps_itr, _self, [&]( producers_seq& info ){ + std::sort(info.prods_all.begin(), info.prods_all.end(), [&](prod_meta lhs, prod_meta rhs){return lhs.total_votes > rhs.total_votes;}); + for( auto it =info.prods_all.begin(); it != info.prods_all.end(); it++ ) { + if( it->is_active && (current_time()-it->last_crash_time) > useconds_per_day_v ) { + //newMaster = it->owner; + info.master = it->owner; + master_sn_list _snlist(_self, _self); + auto sn_itr = _snlist.find (seq_num); + if( sn_itr == _snlist.end() ) { + _snlist.emplace(_self, [&](auto &row) { + row.seq_num = seq_num; + row.owner = it->owner; + row.url = it->url; + }); + } else { + _snlist.modify(sn_itr, _self, [&](auto &row) { + row.owner = it->owner; + row.url = it->url; + }); + } + } + } + }); } void system_contract::seqproducer( const account_name producer, uint16_t seq , uint8_t level ) { @@ -194,22 +266,37 @@ namespace eosiosystem { } - producers_seq_table _prodseq(_self, seq); + producers_seq_table _prodseq(_self, _self); auto ps_itr = _prodseq.find (seq); - if( ps_itr == _prodseq.end() ) - return; - _prodseq.modify( ps_itr, _self, [&]( producers_seq& info ){ - if(info.master == producer) { - info.master = 0; - } + if( ps_itr != _prodseq.end() ) { + _prodseq.modify( ps_itr, _self, [&]( producers_seq& info ){ + if(info.master == producer) { + info.master = 0; + } - for( auto itall = info.prods_all.begin(); itall != info.prods_all.end(); itall++ ) { - if(itall->owner == producer) { - info.prods_all.erase(itall); - break; - } - } - }); + for( auto itall = info.prods_all.begin(); itall != info.prods_all.end(); itall++ ) { + if(itall->owner == producer) { + info.prods_all.erase(itall); + break; + } + } + + for( auto itvoter = info.voter_list.begin(); itvoter != info.voter_list.end(); itvoter++ ) { + if( *itvoter == producer ) { + info.voter_list.erase(itvoter); + break; + } + } + }); + } + + master_sn_list _snlist(_self, _self); + auto sn_itr = _snlist.find (seq); + if( sn_itr != _snlist.end() ) { + if(sn_itr->owner == producer) { + _snlist.erase(sn_itr); + } + } } void system_contract::add_producer_seq( const account_name producer, uint16_t seq , uint8_t level ) { @@ -244,7 +331,7 @@ namespace eosiosystem { _all_prods.set(_all_prods_state,_self); - producers_seq_table _prodseq(_self, seq); + producers_seq_table _prodseq(_self, _self); prod_meta prodm; prodm.owner = producer; prodm.total_votes = prod.total_votes; @@ -268,7 +355,24 @@ namespace eosiosystem { row.master = producer; } }); - } + } + + if(level == 1) { + master_sn_list _snlist(_self, _self); + auto sn_itr = _snlist.find (seq); + if( sn_itr == _snlist.end() ) { + _snlist.emplace(_self, [&](auto &row) { + row.seq_num = seq; + row.owner = producer; + row.url = prod.url; + }); + } else { + _snlist.modify(sn_itr, _self, [&](auto &row) { + row.owner = producer; + row.url = prod.url; + }); + } + } } void system_contract::change_producer_seq_info( const account_name producer, const eosio::public_key& producer_key, bool isactive, bool seturl, const std::string& url) { @@ -311,7 +415,7 @@ namespace eosiosystem { if (it == _producersext.end()) return; uint16_t seq = it->seq_num; - producers_seq_table _prodseq(_self, seq); + producers_seq_table _prodseq(_self, _self); auto ps_itr = _prodseq.find (seq); if( ps_itr == _prodseq.end() ) return; @@ -325,7 +429,18 @@ namespace eosiosystem { } } }); - + + master_sn_list _snlist(_self, _self); + auto sn_itr = _snlist.find (seq); + if( sn_itr != _snlist.end() ) { + if(sn_itr->owner == producer) { + if(seturl) { + _snlist.modify(sn_itr, _self, [&](auto &row) { + row.url = url; + }); + } + } + } } void system_contract::update_producers_seq_totalvotes( uint16_t seq_num, account_name owner, double total_votes) { @@ -358,8 +473,7 @@ namespace eosiosystem { _all_prods.set(_all_prods_state,_self); } - - producers_seq_table _prodseq(_self, seq_num); + producers_seq_table _prodseq(_self, _self); auto ps_itr = _prodseq.find (seq_num); if( ps_itr == _prodseq.end() ) return; @@ -405,8 +519,6 @@ namespace eosiosystem { } - const uint64_t useconds_per_day_v = 24 * 3600 * uint64_t(1000000); - void system_contract::update_elected_producers_yta( block_timestamp block_time ) { all_prods_singleton _all_prods(_self, _self); @@ -819,6 +931,8 @@ namespace eosiosystem { } } + account_name producer_not_fount = 0; + for( const auto& pd : producer_deltas ) { double total_votes = 0; auto pitr = _producers.find( pd.first ); @@ -834,7 +948,10 @@ namespace eosiosystem { total_votes = p.total_votes; }); } else { - eosio_assert( !pd.second.second /* not from new set */, "producer is not registered" ); //data corruption + if(voting) { + eosio_assert( !pd.second.second /* not from new set */, "producer is not registered" ); //data corruption + } + producer_not_fount = pd.first; } //##YTA-Change start: auto pitr2 = _producersext.find( pd.first ); @@ -842,16 +959,25 @@ namespace eosiosystem { //pitr2->seq_num update_producers_seq_totalvotes(pitr2->seq_num, pd.first, total_votes); } else { - eosio_assert( !pd.second.second /* not from new set */, "producer is not registered" ); //data corruption + if(voting) { + eosio_assert( !pd.second.second /* not from new set */, "producer is not registered" ); //data corruption + } } //##YTA-Change end: - - } + //delete the last missing producer _voters.modify( voter, 0, [&]( auto& av ) { av.last_vote_weight = new_vote_weight; av.producers = producers; + if(producer_not_fount) { + for( auto it= av.producers.begin(); it != av.producers.end(); it++ ) { + if(*it == producer_not_fount) { + av.producers.erase(it); + break; + } + } + } av.proxy = proxy; }); } @@ -866,6 +992,9 @@ namespace eosiosystem { * @pre new state must be different than current state */ void system_contract::regproxy( const account_name proxy, bool isproxy ) { + + eosio_assert(1 == 2, "proxy not supported."); + require_auth( proxy ); auto pitr = _voters.find(proxy); diff --git a/contracts/eosio.token/eosio.token.cpp b/contracts/eosio.token/eosio.token.cpp index cf533c5cd9ca976d24aa80c517b0f4d72271564a..3da0163683730aa86a44169a1e1316aed3588df1 100644 --- a/contracts/eosio.token/eosio.token.cpp +++ b/contracts/eosio.token/eosio.token.cpp @@ -116,7 +116,9 @@ void token::sub_balance_yta( account_name owner, asset value , account_name to) const auto& from = from_acnts.get( value.symbol.name(), "no balance object found" ); //todo : need consider lock_token situation - if( to == N(eosio.stake) || to == hdd_deposit_account ) { + if( to == hdd_deposit_account) { + eosio_assert( from.balance.amount >= value.amount, "overdrawn balance" ); + } else if( to == N(eosio.stake) ) { //forfeit can not use to delegatebw and vote auto deposit_and_forfeit = hdddeposit(hdd_deposit_account).get_deposit_and_forfeit(owner); eosio_assert( deposit_and_forfeit.symbol == value.symbol, "symbol precision mismatch" ); diff --git a/contracts/hddpool/hddpool.hpp b/contracts/hddpool/hddpool.hpp index 30e8449e7f70015ba5db82ca756a7fec41bb0128..2eaf1eb6f44926deea468b1a890cfd1459d1833e 100644 --- a/contracts/hddpool/hddpool.hpp +++ b/contracts/hddpool/hddpool.hpp @@ -129,8 +129,8 @@ private: struct minerinfo { uint64_t minerid; - name owner; - name admin; + name owner; //收益账号 + name admin; //管理员账号 name pool_id; uint64_t max_space; uint64_t space_left;