Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve chainbase mapped and heap behavior #1691

Merged
merged 23 commits into from
Oct 5, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
a098946
Use Chainbase's branch with `mapped` mode updates.
greg7mdp Sep 28, 2023
121b0f7
Update chainbase to branch tip.
greg7mdp Sep 28, 2023
2914f46
Use `mapped_shared` mode for chainbase when loading snapshot.
greg7mdp Sep 28, 2023
63e6bef
Try making the new mode not the default one (renaming new mode `mappe…
greg7mdp Sep 29, 2023
73a6d22
Load snapshot in `mapped_shared` in leap-util, and revert to new mode…
greg7mdp Sep 29, 2023
7da7862
Merge branch 'main' of github.com:AntelopeIO/leap into gh_1650
greg7mdp Sep 29, 2023
8140958
Update to appbase branch tip.
greg7mdp Sep 29, 2023
418a570
Update chainbase to tip:
greg7mdp Sep 30, 2023
811192f
Update chainbase to tip.
greg7mdp Oct 2, 2023
797f045
Update appbase to branch tip.
greg7mdp Oct 2, 2023
ca9b6a9
If `mapped` mode was requested, revert to it after loading snapshot.
greg7mdp Oct 2, 2023
5618bd1
Update chainbase to branch tip.
greg7mdp Oct 3, 2023
bb86cf0
Call chainbase API to give the opportunity to flush some dirty pages.
greg7mdp Oct 3, 2023
fc421a9
Address PR comments (log info message in controller, naming)
greg7mdp Oct 3, 2023
43006e2
Make the new mode non-default; rename it `mapped_private`.
greg7mdp Oct 3, 2023
b02fa00
Call `check_memory_and_flush_if_needed()` only in write window as Mat…
greg7mdp Oct 3, 2023
6f0782d
Add snapshot load time to info log
greg7mdp Oct 4, 2023
958bc01
Merge branch 'main' of github.com:AntelopeIO/leap into gh_1650
greg7mdp Oct 4, 2023
5c9ebe7
Address PR comment (remove unneeded line)
greg7mdp Oct 4, 2023
eefda26
Add `mapped_private` description to `--help` and docs.
greg7mdp Oct 4, 2023
e023358
Merge branch 'main' of github.com:AntelopeIO/leap into gh_1650
greg7mdp Oct 4, 2023
f427935
Update to chainbase tip (`main` branch)
greg7mdp Oct 5, 2023
d8fb38c
Merge branch 'main' of github.com:AntelopeIO/leap into gh_1650
greg7mdp Oct 5, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 6 additions & 2 deletions docs/01_nodeos/03_plugins/chain_plugin/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -163,10 +163,14 @@ Config Options for eosio::chain_plugin:
headers signed by it will be fully
validated, but transactions in those
validated blocks will be trusted.
--database-map-mode arg (=mapped) Database map mode ("mapped", "heap", or
"locked").
--database-map-mode arg (=mapped) Database map mode ("mapped",
"mapped_private", "heap", or "locked").
In "mapped" mode database is memory
mapped as a file.
In "mapped_private" mode database is
memory mapped as a file using a private
mapping (no disk writeback until
program exit).
In "heap" mode database is preloaded in
to swappable memory and will use huge
pages if available.
Expand Down
26 changes: 19 additions & 7 deletions libraries/chain/controller.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@

#include <new>
#include <shared_mutex>
#include <utility>

namespace eosio { namespace chain {

Expand Down Expand Up @@ -591,6 +592,7 @@ struct controller_impl {
EOS_ASSERT( snapshot, snapshot_exception, "No snapshot reader provided" );
this->shutdown = shutdown;
try {
auto snapshot_load_start_time = fc::time_point::now();
snapshot->validate();
if( auto blog_head = blog.head() ) {
ilog( "Starting initialization from snapshot and block log ${b}-${e}, this may take a significant amount of time",
Expand All @@ -606,8 +608,11 @@ struct controller_impl {
}
ilog( "Snapshot loaded, lib: ${lib}", ("lib", head->block_num) );

init(check_shutdown);
ilog( "Finished initialization from snapshot" );
init(std::move(check_shutdown));
if (conf.revert_to_private_mode)
db.revert_to_private_mode();
auto snapshot_load_time = (fc::time_point::now() - snapshot_load_start_time).to_seconds();
ilog( "Finished initialization from snapshot (snapshot load time was ${t}s)", ("t", snapshot_load_time) );
} catch (boost::interprocess::bad_alloc& e) {
elog( "Failed initialization from snapshot - db storage not configured to have enough storage for the provided snapshot, please increase and retry snapshot" );
shutdown();
Expand All @@ -622,7 +627,7 @@ struct controller_impl {
("genesis_chain_id", genesis_chain_id)("controller_chain_id", chain_id)
);

this->shutdown = shutdown;
this->shutdown = std::move(shutdown);
if( fork_db.head() ) {
if( read_mode == db_read_mode::IRREVERSIBLE && fork_db.head()->id != fork_db.root()->id ) {
fork_db.rollback_head_to_root();
Expand All @@ -644,14 +649,14 @@ struct controller_impl {
} else {
blog.reset( genesis, head->block );
}
init(check_shutdown);
init(std::move(check_shutdown));
}

void startup(std::function<void()> shutdown, std::function<bool()> check_shutdown) {
EOS_ASSERT( db.revision() >= 1, database_exception, "This version of controller::startup does not work with a fresh state database." );
EOS_ASSERT( fork_db.head(), fork_database_exception, "No existing fork database despite existing chain state. Replay required." );

this->shutdown = shutdown;
this->shutdown = std::move(shutdown);
uint32_t lib_num = fork_db.root()->block_num;
auto first_block_num = blog.first_block_num();
if( auto blog_head = blog.head() ) {
Expand All @@ -674,7 +679,7 @@ struct controller_impl {
}
head = fork_db.head();

init(check_shutdown);
init(std::move(check_shutdown));
}


Expand Down Expand Up @@ -3475,9 +3480,16 @@ void controller::validate_tapos( const transaction& trx )const { try {
} FC_CAPTURE_AND_RETHROW() }

void controller::validate_db_available_size() const {
const auto free = db().get_segment_manager()->get_free_memory();
const auto free = db().get_free_memory();
const auto guard = my->conf.state_guard_size;
EOS_ASSERT(free >= guard, database_guard_exception, "database free: ${f}, guard size: ${g}", ("f", free)("g",guard));

// give a change to chainbase to write some pages to disk if memory becomes scarce.
if (is_write_window()) {
if (auto flushed_pages = mutable_db().check_memory_and_flush_if_needed()) {
ilog("CHAINBASE: flushed ${p} pages to disk to decrease memory pressure", ("p", flushed_pages));
}
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not really sure why to leave this in, since it's #if 0ed on the other side. Kind of deceptive.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It will do something on the next PR, so the deception will not be long lasting.

}
}

bool controller::is_protocol_feature_activated( const digest_type& feature_digest )const {
Expand Down
1 change: 1 addition & 0 deletions libraries/chain/include/eosio/chain/controller.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -79,6 +79,7 @@ namespace eosio { namespace chain {
bool disable_replay_opts = false;
bool contracts_console = false;
bool allow_ram_billing_in_notify = false;
bool revert_to_private_mode = false;
uint32_t maximum_variable_signature_length = chain::config::default_max_variable_signature_length;
bool disable_all_subjective_mitigations = false; //< for developer & testing purposes, can be configured using `disable-all-subjective-mitigations` when `EOSIO_DEVELOPER` build option is provided
uint32_t terminate_at_block = 0;
Expand Down
10 changes: 9 additions & 1 deletion plugins/chain_plugin/chain_plugin.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -345,8 +345,9 @@ void chain_plugin::set_program_options(options_description& cli, options_descrip
"Subjectively limit the maximum length of variable components in a variable legnth signature to this size in bytes")
("trusted-producer", bpo::value<vector<string>>()->composing(), "Indicate a producer whose blocks headers signed by it will be fully validated, but transactions in those validated blocks will be trusted.")
("database-map-mode", bpo::value<chainbase::pinnable_mapped_file::map_mode>()->default_value(chainbase::pinnable_mapped_file::map_mode::mapped),
"Database map mode (\"mapped\", \"heap\", or \"locked\").\n"
"Database map mode (\"mapped\", \"mapped_private\", \"heap\", or \"locked\").\n"
"In \"mapped\" mode database is memory mapped as a file.\n"
"In \"mapped_private\" mode database is memory mapped as a file using a private mapping (no disk writeback until program exit).\n"
#ifndef _WIN32
"In \"heap\" mode database is preloaded in to swappable memory and will use huge pages if available.\n"
"In \"locked\" mode database is preloaded, locked in to memory, and will use huge pages if available.\n"
Expand Down Expand Up @@ -934,6 +935,13 @@ void chain_plugin_impl::plugin_initialize(const variables_map& options) {

chain_config->db_map_mode = options.at("database-map-mode").as<pinnable_mapped_file::map_mode>();

// when loading a snapshot, all the state will be modified, so temporarily use the `mapped` mode instead
// of `mapped_private` to lower memory requirements.
if (snapshot_path && chain_config->db_map_mode == pinnable_mapped_file::mapped_private) {
chain_config->db_map_mode = pinnable_mapped_file::mapped;
chain_config->revert_to_private_mode = true; // revert to `mapped_private` mode after loading snapshot.
}

#ifdef EOSIO_EOS_VM_OC_RUNTIME_ENABLED
if( options.count("eos-vm-oc-cache-size-mb") )
chain_config->eosvmoc_config.cache_size = options.at( "eos-vm-oc-cache-size-mb" ).as<uint64_t>() * 1024u * 1024u;
Expand Down
2 changes: 1 addition & 1 deletion programs/leap-util/actions/snapshot.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -103,7 +103,7 @@ int snapshot_actions::run_subcommand() {
snap_out.flush();
snap_out.close();
} catch(const database_guard_exception& e) {
std::cerr << "Database is not configured to have enough storage to handle provided snapshot, please increase storage and try aagain" << std::endl;
std::cerr << "Database is not configured to have enough storage to handle provided snapshot, please increase storage and try again" << std::endl;
control.reset();
throw;
}
Expand Down