* Created unit test for #325
* remove needless find()
* issue - 154: Don't allow to vote when vesting balance is 0
* Increase block creation timeout to 2500ms
* increase delay for node connection
* remove cache from cli get_account
* add cli tests framework
* Adjust newly merged code to new API
* Merged changes from Bitshares PR 1036
* GRPH-76 - Short-cut long sequences of missed blocks
Fixes database::update_global_dynamic_data to speed up counting missed blocks.
(This also fixes a minor issue with counting - the previous algorithm would skip missed blocks for the witness who signed the first block after the gap.)
* Improved resilience of block database against corruption
* Moved reindex logic into database / chain_database, make use of additional blocks in block_database
Fixed tests wrt db.open
* Enable undo + fork database for final blocks in a replay
Dont remove blocks from block db when popping blocks, handle edge case in replay wrt fork_db, adapted unit tests
* Log starting block number of replay
* Prevent unsigned integer underflow
* Fixed lock detection
* Dont leave _data_dir empty if db is locked
* Writing the object_database is now almost atomic
* Improved consistency check for block_log
* Cut back block_log index file if inconsistent
* Fixed undo_database
* Added test case for broken merge on empty undo_db
* exclude second undo_db.enable() call in some cases
* Add missing change
* change bitshares to core in message
* Merge pull request #938 from bitshares/fix-block-storing
Store correct block ID when switching forks
* Fixed integer overflow issue
* Fix for for history ID mismatch ( Bitshares PR #875 )
* Update the FC submodule with the changes for GRPH-4
* Merged Bitshares PR #1462 and compilation fixes
* Support/gitlab (#123)
* Updated gitlab process
* Fix undefined references in cli test
* Updated GitLab CI
* Fix #436 object_database created outside of witness data directory
* supplement more comments on database::_opened variable
* prevent segfault when destructing application obj
* Fixed test failures and compilation issue
* minor performance improvement
* Added comment
* Fix compilation in debug mode
* Fixed duplicate ops returned from get_account_history
* Fixed account_history_pagination test
* Removed unrelated comment
* Update to fixed version of fc
* Skip auth check when pushing self-generated blocks
* Extract public keys before pushing a transaction
* Dereference chain_database shared_ptr
* Updated transaction::signees to mutable
and
* updated get_signature_keys() to return a const reference,
* get_signature_keys() will update signees on first call,
* modified test cases and wallet.cpp accordingly,
* no longer construct a new signed_transaction object before pushing
* Added get_asset_count API
* No longer extract public keys before pushing a trx
and removed unused new added constructor and _get_signature_keys() function from signed_transaction struct
* changes to withdraw_vesting feature(for both cdd and GPOS)
* Comments update
* update to GPOS hardfork ref
* Remove leftover comment from merge
* fix for get_vesting_balance API call
* braces update
* Allow sufficient space for new undo_session
* Throw for deep nesting
* node.cpp: Check the attacker/buggy client before updating items ids
The peer is an attacker or buggy, which means the item_hashes_received is
not correct.
Move the check before updating items ids to save some time in this case.
* Create .gitlab-ci.yml
* Added cli_test to CI
* fixing build errors (#150)
* fixing build errors
vest type correction
* fixing build errors
vest type correction
* fixes
new Dockerfile
* vesting_balance_type correction
vesting_balance_type changed to normal
* gcc5 support to Dockerfile
gcc5 support to Dockerfile
* use random port numbers in app_test (#154)
* Changes to compiple with GCC 7(Ubuntu 18.04)
* proposal fail_reason bug fixed (#157)
* Added Sonarcloud code_quality to CI (#159)
* Added sonarcloud analysis (#158)
* changes to have separate methods and single withdrawl fee for multiple vest objects
* 163-fix, Return only non-zero vesting balances
* Support/gitlab develop (#168)
* Added code_quality to CI
* Update .gitlab-ci.yml
* Point to PBSA/peerplays-fc commit f13d063 (#167)
* [GRPH-3] Additional cli tests (#155)
* Additional cli tests
* Compatible with latest fc changes
* Fixed Spacing issues
* [GRPH-106] Added voting tests (#136)
* Added more voting tests
* Added additional option
* Adjust p2p log level (#180)
* merge gpos to develop (#186)
* issue - 154: Don't allow to vote when vesting balance is 0
* changes to withdraw_vesting feature(for both cdd and GPOS)
* Comments update
* update to GPOS hardfork ref
* fix for get_vesting_balance API call
* braces update
* Create .gitlab-ci.yml
* fixing build errors (#150)
* fixing build errors
vest type correction
* fixing build errors
vest type correction
* fixes
new Dockerfile
* vesting_balance_type correction
vesting_balance_type changed to normal
* gcc5 support to Dockerfile
gcc5 support to Dockerfile
* Changes to compiple with GCC 7(Ubuntu 18.04)
* changes to have separate methods and single withdrawl fee for multiple vest objects
* 163-fix, Return only non-zero vesting balances
* Revert "Revert "GPOS protocol""
This reverts commit 67616417b7.
* add new line needed to gpos hardfork file
* comment temporally cli_vote_for_2_witnesses until refactor or delete
* fix gpos tests
* fix gitlab-ci conflict
* Fixed few error messages
* error message corrections at other places
* Updated FC repository to peerplays-network/peerplays-fc (#189)
Point to fc commit hash 6096e94 [latest-fc branch]
* Project name update in Doxyfile (#146)
* changes to allow user to vote in each sub-period
* Fixed GPOS vesting factor issue when proxy is set
* Added unit test for proxy voting
* Review changes
* changes to update last voting time
* resolve merge conflict
* unit test changes and also separated GPOS test suite
* delete unused variables
* removed witness check
* eliminate time gap between two consecutive vesting periods
* deleted GPOS specific test suite and updated gpos tests
* updated GPOS hf
* Fixed dividend distribution issue and added test case
* fix flag
* clean newlines gpos_tests
* adapt gpos_tests to changed flag
* Fix to roll in GPOS rules, carry votes from 6th sub-period
* check was already modified
* comments updated
* updated comments to the benefit of reviewer
* Added token symbol name in error messages
* Added token symbol name in error messages (#204)
* case 1: Fixed last voting time issue
* get_account bug fixed
* Fixed flag issue
* Fixed spelling issue
* remove non needed gcc5 changes to dockerfile
* GRPH134- High CPU Issue, websocket changes (#213)
* update submodule branch to refer to the latest commit on latest-fc branch (#214)
* Improve account maintenance performance (#130)
* Improve account maintenance performance
* merge fixes
* Fixed merge issue
* Fixed indentations and extra ';'
* Update CI for syncing gitmodules (#216)
* Added logging for the old update_expired_feeds bug
The old bug is https://github.com/cryptonomex/graphene/issues/615 .
Due to the bug, `update_median_feeds()` and `check_call_orders()`
will be called when a feed is not actually expired, normally this
should not affect consensus since calling them should not change
any data in the state.
However, the logging indicates that `check_call_orders()` did
change some data under certain circumstances, specifically, when
multiple limit order matching issue (#453) occurred at same block.
* https://github.com/bitshares/bitshares-core/issues/453
* Minor performance improvement for price::is_null()
* Use static refs in db_getter for immutable objects
* Minor performance improvement for db_maint
* Minor code updates for asset_evaluator.cpp
* changed an `assert()` to `FC_ASSERT()`
* replaced one `db.get(asset_id_type())` with `db.get_core_asset()`
* capture only required variables for lambda
* Improve update_expired_feeds performance #1093
* Change static refs to member pointers of db class
* Added getter for witness schedule object
* Added getter for core dynamic data object
* Use getters
* Removed unused variable
* Add comments for update_expired_feeds in db_block
* Minor refactory asset_create_evaluator::do_apply()
* Added FC_ASSERT for dynamic data id of core asset
* Added header inclusions in db_management.cpp
* fix global objects usage during replay
* Logging config parsing issue
* added new files
* compilation fix
* Simplified code in database::pay_workers()
* issue with withdrawl
* Added unit test for empty account history
* set extensions default values
* Update GPOS hardfork date and don't allow GPOS features before hardfork time
* refer to latest commit of latest-fc branch (#224)
* account name or id support in all database api
* asset id or name support in all asset APIs
* Fixed compilation issues
* Fixed alignment issues
* Externalized some API templates
* Externalize serialization of blocks, tx, ops
* Externalized db objects
* Externalized genesis serialization
* Externalized serialization in protocol library
* Undo superfluous change
* remove default value for extension parameter
* fix compilation issues
* GRPH-46-Quit_command_cliwallet
* removed multiple function definition
* Fixed chainparameter update proposal issue
* Move GPOS withdraw logic to have single transaction(also single fee) and update API
* Added log for authorization failure of proposal operations
* Votes consideration on GPOS activation
* bump fc version
* fix gpos tests
* Bump fc version
* Updated gpos/voting_tests
* Fixed withdraw vesting bug
* Added unit test
* Update hardfork date for TESTNET, sync fc module and update logs
* avoid wlog as it filling up space
* Beatrice hot fix(sync issue fix)
* gpos tests fix
* Set hardfork date to Jan5th on TESTNET
Co-authored-by: Peter Conrad <github.com@quisquis.de>
Co-authored-by: John M. Jones <jmjatlanta@gmail.com>
Co-authored-by: obucinac <obucinac@users.noreply.github.com>
Co-authored-by: Bobinson K B <bobinson@gmail.com>
Co-authored-by: Alfredo Garcia <oxarbitrage@gmail.com>
Co-authored-by: Miha Čančula <miha@noughmad.eu>
Co-authored-by: Abit <abitmore@users.noreply.github.com>
Co-authored-by: Roshan Syed <r.syed@pbsa.info>
Co-authored-by: Sandip Patel <sandip@knackroot.com>
Co-authored-by: RichardWeiYang <richard.weiyang@gmail.com>
Co-authored-by: gladcow <jahr@yandex.ru>
Co-authored-by: satyakoneru <satyakoneru.iiith@gmail.com>
581 lines
26 KiB
C++
581 lines
26 KiB
C++
/*
|
|
* Copyright (c) 2015 Cryptonomex, Inc., and contributors.
|
|
*
|
|
* The MIT License
|
|
*
|
|
* Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
* of this software and associated documentation files (the "Software"), to deal
|
|
* in the Software without restriction, including without limitation the rights
|
|
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
* copies of the Software, and to permit persons to whom the Software is
|
|
* furnished to do so, subject to the following conditions:
|
|
*
|
|
* The above copyright notice and this permission notice shall be included in
|
|
* all copies or substantial portions of the Software.
|
|
*
|
|
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
|
|
* THE SOFTWARE.
|
|
*/
|
|
#pragma once
|
|
#include <graphene/chain/protocol/types.hpp>
|
|
#include <graphene/db/generic_index.hpp>
|
|
#include <graphene/chain/protocol/account.hpp>
|
|
#include <boost/multi_index/composite_key.hpp>
|
|
|
|
namespace graphene { namespace chain {
|
|
class database;
|
|
|
|
/**
|
|
* @class account_statistics_object
|
|
* @ingroup object
|
|
* @ingroup implementation
|
|
*
|
|
* This object contains regularly updated statistical data about an account. It is provided for the purpose of
|
|
* separating the account data that changes frequently from the account data that is mostly static, which will
|
|
* minimize the amount of data that must be backed up as part of the undo history everytime a transfer is made.
|
|
*/
|
|
class account_statistics_object : public graphene::db::abstract_object<account_statistics_object>
|
|
{
|
|
public:
|
|
static const uint8_t space_id = implementation_ids;
|
|
static const uint8_t type_id = impl_account_statistics_object_type;
|
|
|
|
account_id_type owner;
|
|
|
|
string name; ///< redundantly store account name here for better maintenance performance
|
|
|
|
/**
|
|
* Keep the most recent operation as a root pointer to a linked list of the transaction history.
|
|
*/
|
|
account_transaction_history_id_type most_recent_op;
|
|
/** Total operations related to this account. */
|
|
uint32_t total_ops = 0;
|
|
/** Total operations related to this account that has been removed from the database. */
|
|
uint32_t removed_ops = 0;
|
|
|
|
/**
|
|
* When calculating votes it is necessary to know how much is stored in orders (and thus unavailable for
|
|
* transfers). Rather than maintaining an index of [asset,owner,order_id] we will simply maintain the running
|
|
* total here and update it every time an order is created or modified.
|
|
*/
|
|
share_type total_core_in_orders;
|
|
|
|
share_type core_in_balance = 0; ///< redundantly store core balance here for better maintenance performance
|
|
|
|
bool has_cashback_vb = false; ///< redundantly store this for better maintenance performance
|
|
|
|
bool is_voting = false; ///< redundately store whether this account is voting for better maintenance performance
|
|
|
|
|
|
/// Whether this account owns some CORE asset and is voting
|
|
inline bool has_some_core_voting() const
|
|
{
|
|
return is_voting && ( total_core_in_orders > 0 || core_in_balance > 0 || has_cashback_vb );
|
|
}
|
|
|
|
/**
|
|
* Tracks the total fees paid by this account for the purpose of calculating bulk discounts.
|
|
*/
|
|
share_type lifetime_fees_paid;
|
|
|
|
/**
|
|
* Tracks the fees paid by this account which have not been disseminated to the various parties that receive
|
|
* them yet (registrar, referrer, lifetime referrer, network, etc). This is used as an optimization to avoid
|
|
* doing massive amounts of uint128 arithmetic on each and every operation.
|
|
*
|
|
* These fees will be paid out as vesting cash-back, and this counter will reset during the maintenance
|
|
* interval.
|
|
*/
|
|
share_type pending_fees;
|
|
/**
|
|
* Same as @ref pending_fees, except these fees will be paid out as pre-vested cash-back (immediately
|
|
* available for withdrawal) rather than requiring the normal vesting period.
|
|
*/
|
|
share_type pending_vested_fees;
|
|
|
|
/**
|
|
* Keep the date of the last voting activity for this account.
|
|
*/
|
|
time_point_sec last_vote_time;
|
|
|
|
/// Whether this account has pending fees, no matter vested or not
|
|
inline bool has_pending_fees() const { return pending_fees > 0 || pending_vested_fees > 0; }
|
|
|
|
/// Whether need to process this account during the maintenance interval
|
|
inline bool need_maintenance() const { return has_some_core_voting() || has_pending_fees(); }
|
|
|
|
/// @brief Split up and pay out @ref pending_fees and @ref pending_vested_fees
|
|
void process_fees(const account_object& a, database& d) const;
|
|
|
|
/**
|
|
* Core fees are paid into the account_statistics_object by this method
|
|
*/
|
|
void pay_fee( share_type core_fee, share_type cashback_vesting_threshold );
|
|
};
|
|
|
|
/**
|
|
* @brief Tracks the balance of a single account/asset pair
|
|
* @ingroup object
|
|
*
|
|
* This object is indexed on owner and asset_type so that black swan
|
|
* events in asset_type can be processed quickly.
|
|
*/
|
|
class account_balance_object : public abstract_object<account_balance_object>
|
|
{
|
|
public:
|
|
static const uint8_t space_id = implementation_ids;
|
|
static const uint8_t type_id = impl_account_balance_object_type;
|
|
|
|
account_id_type owner;
|
|
asset_id_type asset_type;
|
|
share_type balance;
|
|
bool maintenance_flag = false; ///< Whether need to process this balance object in maintenance interval
|
|
|
|
asset get_balance()const { return asset(balance, asset_type); }
|
|
void adjust_balance(const asset& delta);
|
|
};
|
|
|
|
|
|
/**
|
|
* @brief This class represents an account on the object graph
|
|
* @ingroup object
|
|
* @ingroup protocol
|
|
*
|
|
* Accounts are the primary unit of authority on the graphene system. Users must have an account in order to use
|
|
* assets, trade in the markets, vote for committee_members, etc.
|
|
*/
|
|
class account_object : public graphene::db::abstract_object<account_object>
|
|
{
|
|
public:
|
|
static const uint8_t space_id = protocol_ids;
|
|
static const uint8_t type_id = account_object_type;
|
|
|
|
/**
|
|
* The time at which this account's membership expires.
|
|
* If set to any time in the past, the account is a basic account.
|
|
* If set to time_point_sec::maximum(), the account is a lifetime member.
|
|
* If set to any time not in the past less than time_point_sec::maximum(), the account is an annual member.
|
|
*
|
|
* See @ref is_lifetime_member, @ref is_basic_account, @ref is_annual_member, and @ref is_member
|
|
*/
|
|
time_point_sec membership_expiration_date;
|
|
|
|
///The account that paid the fee to register this account. Receives a percentage of referral rewards.
|
|
account_id_type registrar;
|
|
/// The account credited as referring this account. Receives a percentage of referral rewards.
|
|
account_id_type referrer;
|
|
/// The lifetime member at the top of the referral tree. Receives a percentage of referral rewards.
|
|
account_id_type lifetime_referrer;
|
|
|
|
/// Percentage of fee which should go to network.
|
|
uint16_t network_fee_percentage = GRAPHENE_DEFAULT_NETWORK_PERCENT_OF_FEE;
|
|
/// Percentage of fee which should go to lifetime referrer.
|
|
uint16_t lifetime_referrer_fee_percentage = 0;
|
|
/// Percentage of referral rewards (leftover fee after paying network and lifetime referrer) which should go
|
|
/// to referrer. The remainder of referral rewards goes to the registrar.
|
|
uint16_t referrer_rewards_percentage = 0;
|
|
|
|
/// The account's name. This name must be unique among all account names on the graph. May not be empty.
|
|
string name;
|
|
|
|
/**
|
|
* The owner authority represents absolute control over the account. Usually the keys in this authority will
|
|
* be kept in cold storage, as they should not be needed very often and compromise of these keys constitutes
|
|
* complete and irrevocable loss of the account. Generally the only time the owner authority is required is to
|
|
* update the active authority.
|
|
*/
|
|
authority owner;
|
|
/// The owner authority contains the hot keys of the account. This authority has control over nearly all
|
|
/// operations the account may perform.
|
|
authority active;
|
|
|
|
typedef account_options options_type;
|
|
account_options options;
|
|
|
|
/// The reference implementation records the account's statistics in a separate object. This field contains the
|
|
/// ID of that object.
|
|
account_statistics_id_type statistics;
|
|
|
|
/**
|
|
* This is a set of all accounts which have 'whitelisted' this account. Whitelisting is only used in core
|
|
* validation for the purpose of authorizing accounts to hold and transact in whitelisted assets. This
|
|
* account cannot update this set, except by transferring ownership of the account, which will clear it. Other
|
|
* accounts may add or remove their IDs from this set.
|
|
*/
|
|
flat_set<account_id_type> whitelisting_accounts;
|
|
|
|
/**
|
|
* Optionally track all of the accounts this account has whitelisted or blacklisted, these should
|
|
* be made Immutable so that when the account object is cloned no deep copy is required. This state is
|
|
* tracked for GUI display purposes.
|
|
*
|
|
* TODO: move white list tracking to its own multi-index container rather than having 4 fields on an
|
|
* account. This will scale better because under the current design if you whitelist 2000 accounts,
|
|
* then every time someone fetches this account object they will get the full list of 2000 accounts.
|
|
*/
|
|
///@{
|
|
set<account_id_type> whitelisted_accounts;
|
|
set<account_id_type> blacklisted_accounts;
|
|
///@}
|
|
|
|
|
|
/**
|
|
* This is a set of all accounts which have 'blacklisted' this account. Blacklisting is only used in core
|
|
* validation for the purpose of forbidding accounts from holding and transacting in whitelisted assets. This
|
|
* account cannot update this set, and it will be preserved even if the account is transferred. Other accounts
|
|
* may add or remove their IDs from this set.
|
|
*/
|
|
flat_set<account_id_type> blacklisting_accounts;
|
|
|
|
/**
|
|
* Vesting balance which receives cashback_reward deposits.
|
|
*/
|
|
optional<vesting_balance_id_type> cashback_vb;
|
|
|
|
special_authority owner_special_authority = no_special_authority();
|
|
special_authority active_special_authority = no_special_authority();
|
|
|
|
/**
|
|
* This flag is set when the top_n logic sets both authorities,
|
|
* and gets reset when authority or special_authority is set.
|
|
*/
|
|
uint8_t top_n_control_flags = 0;
|
|
static const uint8_t top_n_control_owner = 1;
|
|
static const uint8_t top_n_control_active = 2;
|
|
|
|
/**
|
|
* This is a set of assets which the account is allowed to have.
|
|
* This is utilized to restrict buyback accounts to the assets that trade in their markets.
|
|
* In the future we may expand this to allow accounts to e.g. voluntarily restrict incoming transfers.
|
|
*/
|
|
optional< flat_set<asset_id_type> > allowed_assets;
|
|
|
|
optional< affiliate_reward_distributions > affiliate_distributions;
|
|
|
|
bool has_special_authority()const
|
|
{
|
|
return (owner_special_authority.which() != special_authority::tag< no_special_authority >::value)
|
|
|| (active_special_authority.which() != special_authority::tag< no_special_authority >::value);
|
|
}
|
|
|
|
template<typename DB>
|
|
const vesting_balance_object& cashback_balance(const DB& db)const
|
|
{
|
|
FC_ASSERT(cashback_vb);
|
|
return db.get(*cashback_vb);
|
|
}
|
|
|
|
/// @return true if this is a lifetime member account; false otherwise.
|
|
bool is_lifetime_member()const
|
|
{
|
|
return membership_expiration_date == time_point_sec::maximum();
|
|
}
|
|
/// @return true if this is a basic account; false otherwise.
|
|
bool is_basic_account(time_point_sec now)const
|
|
{
|
|
return now > membership_expiration_date;
|
|
}
|
|
/// @return true if the account is an unexpired annual member; false otherwise.
|
|
/// @note This method will return false for lifetime members.
|
|
bool is_annual_member(time_point_sec now)const
|
|
{
|
|
return !is_lifetime_member() && !is_basic_account(now);
|
|
}
|
|
/// @return true if the account is an annual or lifetime member; false otherwise.
|
|
bool is_member(time_point_sec now)const
|
|
{
|
|
return !is_basic_account(now);
|
|
}
|
|
|
|
account_id_type get_id()const { return id; }
|
|
};
|
|
|
|
/**
|
|
* @brief This secondary index will allow a reverse lookup of all accounts that a particular key or account
|
|
* is an potential signing authority.
|
|
*/
|
|
class account_member_index : public secondary_index
|
|
{
|
|
/* std::less::operator() is less efficient so using key_compare here.
|
|
* Let assume that it has two keys key1 and key2 and we want to insert key3.
|
|
* the insert function needs to first call std::less::operator() with key1 and key3.
|
|
* Assume std::less::operator()(key1, key3) returns false.
|
|
* It has to call std::less::operator() again with the keys switched,
|
|
* std::less::operator()(key3, key1), to decide whether key1 is equal to key3 or
|
|
* key3 is greater than key1. There are two calls to std::less::operator() to make
|
|
* a decision if the first call returns false.
|
|
* std::map::insert and std::set used key_compare,
|
|
* there would be sufficient information to make the right decision using just one call.
|
|
*/
|
|
class key_compare {
|
|
public:
|
|
inline bool operator()( const public_key_type& a, const public_key_type& b )const
|
|
{
|
|
return a.key_data < b.key_data;
|
|
}
|
|
};
|
|
|
|
public:
|
|
virtual void object_inserted( const object& obj ) override;
|
|
virtual void object_removed( const object& obj ) override;
|
|
virtual void about_to_modify( const object& before ) override;
|
|
virtual void object_modified( const object& after ) override;
|
|
|
|
|
|
/** given an account or key, map it to the set of accounts that reference it in an active or owner authority */
|
|
map< account_id_type, set<account_id_type> > account_to_account_memberships;
|
|
map< public_key_type, set<account_id_type>, key_compare > account_to_key_memberships;
|
|
/** some accounts use address authorities in the genesis block */
|
|
map< address, set<account_id_type> > account_to_address_memberships;
|
|
|
|
|
|
protected:
|
|
set<account_id_type> get_account_members( const account_object& a )const;
|
|
set<public_key_type, key_compare> get_key_members( const account_object& a )const;
|
|
set<address> get_address_members( const account_object& a )const;
|
|
|
|
set<account_id_type> before_account_members;
|
|
set<public_key_type, key_compare> before_key_members;
|
|
set<address> before_address_members;
|
|
};
|
|
|
|
|
|
/**
|
|
* @brief This secondary index will allow a reverse lookup of all accounts that have been referred by
|
|
* a particular account.
|
|
*/
|
|
class account_referrer_index : public secondary_index
|
|
{
|
|
public:
|
|
virtual void object_inserted( const object& obj ) override;
|
|
virtual void object_removed( const object& obj ) override;
|
|
virtual void about_to_modify( const object& before ) override;
|
|
virtual void object_modified( const object& after ) override;
|
|
|
|
/** maps the referrer to the set of accounts that they have referred */
|
|
map< account_id_type, set<account_id_type> > referred_by;
|
|
};
|
|
|
|
/**
|
|
* @brief Tracks a pending payout of a single dividend payout asset
|
|
* from a single dividend holder asset to a holder's account.
|
|
*
|
|
* Each maintenance interval, this will be adjusted to account for
|
|
* any new transfers to the dividend distribution account.
|
|
* @ingroup object
|
|
*
|
|
*/
|
|
class pending_dividend_payout_balance_for_holder_object : public abstract_object<pending_dividend_payout_balance_for_holder_object>
|
|
{
|
|
public:
|
|
static const uint8_t space_id = implementation_ids;
|
|
static const uint8_t type_id = impl_pending_dividend_payout_balance_for_holder_object_type;
|
|
|
|
account_id_type owner;
|
|
asset_id_type dividend_holder_asset_type;
|
|
asset_id_type dividend_payout_asset_type;
|
|
share_type pending_balance;
|
|
|
|
asset get_pending_balance()const { return asset(pending_balance, dividend_payout_asset_type); }
|
|
void adjust_balance(const asset& delta);
|
|
};
|
|
|
|
|
|
/**
|
|
* @brief This secondary index will allow fast access to the balance objects
|
|
* that belonging to an account.
|
|
*/
|
|
class balances_by_account_index : public secondary_index
|
|
{
|
|
public:
|
|
virtual void object_inserted( const object& obj ) override;
|
|
virtual void object_removed( const object& obj ) override;
|
|
virtual void about_to_modify( const object& before ) override;
|
|
virtual void object_modified( const object& after ) override;
|
|
|
|
const map< asset_id_type, const account_balance_object* >& get_account_balances( const account_id_type& acct )const;
|
|
const account_balance_object* get_account_balance( const account_id_type& acct, const asset_id_type& asset )const;
|
|
|
|
private:
|
|
static const uint8_t bits;
|
|
static const uint64_t mask;
|
|
|
|
/** Maps each account to its balance objects */
|
|
vector< vector< map< asset_id_type, const account_balance_object* > > > balances;
|
|
std::stack< object_id_type > ids_being_modified;
|
|
};
|
|
|
|
struct by_asset_balance;
|
|
struct by_maintenance_flag;
|
|
struct by_account_asset;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef multi_index_container<
|
|
account_balance_object,
|
|
indexed_by<
|
|
ordered_unique< tag<by_id>, member< object, object_id_type, &object::id > >,
|
|
ordered_non_unique< tag<by_maintenance_flag>,
|
|
member< account_balance_object, bool, &account_balance_object::maintenance_flag > >,
|
|
ordered_unique< tag<by_account_asset>,
|
|
composite_key<
|
|
account_balance_object,
|
|
member<account_balance_object, account_id_type, &account_balance_object::owner>,
|
|
member<account_balance_object, asset_id_type, &account_balance_object::asset_type>
|
|
>
|
|
>,
|
|
ordered_unique< tag<by_asset_balance>,
|
|
composite_key<
|
|
account_balance_object,
|
|
member<account_balance_object, asset_id_type, &account_balance_object::asset_type>,
|
|
member<account_balance_object, share_type, &account_balance_object::balance>,
|
|
member<account_balance_object, account_id_type, &account_balance_object::owner>
|
|
>,
|
|
composite_key_compare<
|
|
std::less< asset_id_type >,
|
|
std::greater< share_type >,
|
|
std::less< account_id_type >
|
|
>
|
|
>
|
|
>
|
|
> account_balance_object_multi_index_type;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef generic_index<account_balance_object, account_balance_object_multi_index_type> account_balance_index;
|
|
|
|
struct by_name{};
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef multi_index_container<
|
|
account_object,
|
|
indexed_by<
|
|
ordered_unique< tag<by_id>, member< object, object_id_type, &object::id > >,
|
|
ordered_unique< tag<by_name>, member<account_object, string, &account_object::name> >
|
|
>
|
|
> account_multi_index_type;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef generic_index<account_object, account_multi_index_type> account_index;
|
|
|
|
struct by_dividend_payout_account{}; // use when calculating pending payouts
|
|
struct by_dividend_account_payout{}; // use when doing actual payouts
|
|
struct by_account_dividend_payout{}; // use in get_full_accounts()
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef multi_index_container<
|
|
pending_dividend_payout_balance_for_holder_object,
|
|
indexed_by<
|
|
ordered_unique< tag<by_id>, member< object, object_id_type, &object::id > >,
|
|
ordered_unique< tag<by_dividend_payout_account>,
|
|
composite_key<
|
|
pending_dividend_payout_balance_for_holder_object,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_holder_asset_type>,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_payout_asset_type>,
|
|
member<pending_dividend_payout_balance_for_holder_object, account_id_type, &pending_dividend_payout_balance_for_holder_object::owner>
|
|
>
|
|
>,
|
|
ordered_unique< tag<by_dividend_account_payout>,
|
|
composite_key<
|
|
pending_dividend_payout_balance_for_holder_object,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_holder_asset_type>,
|
|
member<pending_dividend_payout_balance_for_holder_object, account_id_type, &pending_dividend_payout_balance_for_holder_object::owner>,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_payout_asset_type>
|
|
>
|
|
>,
|
|
ordered_unique< tag<by_account_dividend_payout>,
|
|
composite_key<
|
|
pending_dividend_payout_balance_for_holder_object,
|
|
member<pending_dividend_payout_balance_for_holder_object, account_id_type, &pending_dividend_payout_balance_for_holder_object::owner>,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_holder_asset_type>,
|
|
member<pending_dividend_payout_balance_for_holder_object, asset_id_type, &pending_dividend_payout_balance_for_holder_object::dividend_payout_asset_type>
|
|
>
|
|
>
|
|
>
|
|
> pending_dividend_payout_balance_for_holder_object_multi_index_type;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef generic_index<pending_dividend_payout_balance_for_holder_object, pending_dividend_payout_balance_for_holder_object_multi_index_type> pending_dividend_payout_balance_for_holder_object_index;
|
|
|
|
struct by_owner;
|
|
struct by_maintenance_seq;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef multi_index_container<
|
|
account_statistics_object,
|
|
indexed_by<
|
|
ordered_unique< tag<by_id>, member< object, object_id_type, &object::id > >,
|
|
ordered_unique< tag<by_owner>,
|
|
member< account_statistics_object, account_id_type, &account_statistics_object::owner > >,
|
|
ordered_unique< tag<by_maintenance_seq>,
|
|
composite_key<
|
|
account_statistics_object,
|
|
const_mem_fun<account_statistics_object, bool, &account_statistics_object::need_maintenance>,
|
|
member<account_statistics_object, string, &account_statistics_object::name>
|
|
>
|
|
>
|
|
>
|
|
> account_stats_multi_index_type;
|
|
|
|
/**
|
|
* @ingroup object_index
|
|
*/
|
|
typedef generic_index<account_statistics_object, account_stats_multi_index_type> account_stats_index;
|
|
|
|
}}
|
|
|
|
FC_REFLECT_DERIVED( graphene::chain::account_object,
|
|
(graphene::db::object),
|
|
(membership_expiration_date)(registrar)(referrer)(lifetime_referrer)
|
|
(network_fee_percentage)(lifetime_referrer_fee_percentage)(referrer_rewards_percentage)
|
|
(name)(owner)(active)(options)(statistics)(whitelisting_accounts)(blacklisting_accounts)
|
|
(whitelisted_accounts)(blacklisted_accounts)
|
|
(cashback_vb)
|
|
(owner_special_authority)(active_special_authority)
|
|
(top_n_control_flags)
|
|
(allowed_assets)(affiliate_distributions)
|
|
)
|
|
|
|
FC_REFLECT_DERIVED( graphene::chain::account_balance_object,
|
|
(graphene::db::object),
|
|
(owner)(asset_type)(balance)(maintenance_flag) )
|
|
|
|
FC_REFLECT_DERIVED( graphene::chain::account_statistics_object,
|
|
(graphene::chain::object),
|
|
(owner)(name)
|
|
(most_recent_op)
|
|
(total_ops)(removed_ops)
|
|
(total_core_in_orders)
|
|
(core_in_balance)
|
|
(has_cashback_vb)
|
|
(is_voting)
|
|
(lifetime_fees_paid)
|
|
(pending_fees)(pending_vested_fees)
|
|
(last_vote_time)
|
|
)
|
|
|
|
FC_REFLECT_DERIVED( graphene::chain::pending_dividend_payout_balance_for_holder_object,
|
|
(graphene::db::object),
|
|
(owner)(dividend_holder_asset_type)(dividend_payout_asset_type)(pending_balance) )
|
|
|
|
GRAPHENE_EXTERNAL_SERIALIZATION( extern, graphene::chain::account_object )
|
|
GRAPHENE_EXTERNAL_SERIALIZATION( extern, graphene::chain::account_balance_object )
|
|
GRAPHENE_EXTERNAL_SERIALIZATION( extern, graphene::chain::account_statistics_object )
|
|
GRAPHENE_EXTERNAL_SERIALIZATION( extern, graphene::chain::pending_dividend_payout_balance_for_holder_object )
|