BlockchainLMDB seems to be working*!

* - Well, mostly.  Haven't let it sync too far just yet.  Currently
trying to figure out the best way to deal with LMDB/mmap virtual memory
pages.
This commit is contained in:
Thomas Winget 2014-10-30 00:58:14 -04:00 committed by warptangent
parent 1a546e3222
commit 0915913111
3 changed files with 155 additions and 141 deletions

View file

@ -119,7 +119,7 @@ void BlockchainLMDB::add_block( const block& blk
, const uint64_t& coins_generated
)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
crypto::hash h = get_block_hash(blk);
@ -228,7 +228,7 @@ void BlockchainLMDB::add_block( const block& blk
void BlockchainLMDB::remove_block()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
MDB_val k;
@ -282,7 +282,7 @@ void BlockchainLMDB::remove_block()
void BlockchainLMDB::add_transaction_data(const crypto::hash& blk_hash, const transaction& tx)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
crypto::hash h = get_transaction_hash(tx);
@ -333,7 +333,7 @@ void BlockchainLMDB::add_transaction_data(const crypto::hash& blk_hash, const tr
void BlockchainLMDB::remove_transaction_data(const crypto::hash& tx_hash)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
crypto::hash h = tx_hash;
@ -373,7 +373,7 @@ void BlockchainLMDB::remove_transaction_data(const crypto::hash& tx_hash)
void BlockchainLMDB::add_output(const crypto::hash& tx_hash, const tx_out& tx_output, const uint64_t& local_index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
MDB_val k;
@ -407,9 +407,10 @@ void BlockchainLMDB::add_output(const crypto::hash& tx_hash, const tx_out& tx_ou
uint64_t amount = tx_output.amount;
v.mv_size = sizeof(uint64_t);
v.mv_data = &amount;
if (mdb_put(*m_write_txn, m_output_amounts, &v, &k, 0))
if (auto result = mdb_put(*m_write_txn, m_output_amounts, &v, &k, 0))
{
LOG_PRINT_L0("Failed to add output amount to db transaction");
LOG_PRINT_L0("E: " << mdb_strerror(result));
throw DB_ERROR("Failed to add output amount to db transaction");
}
@ -428,14 +429,12 @@ void BlockchainLMDB::add_output(const crypto::hash& tx_hash, const tx_out& tx_ou
throw DB_ERROR("Failed to add output global index to db transaction");
}
LOG_PRINT_L0(__func__ << ": amount == " << amount << ", tx_index == " << local_index << "amount_index == " << get_num_outputs(amount) << ", tx_hash == " << pod_to_hex(tx_hash));
m_num_outputs++;
}
void BlockchainLMDB::remove_output(const tx_out& tx_output)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
MDB_val k;
@ -493,7 +492,7 @@ void BlockchainLMDB::remove_output(const tx_out& tx_output)
void BlockchainLMDB::add_spent_key(const crypto::key_image& k_image)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
crypto::key_image key = k_image;
@ -520,7 +519,7 @@ void BlockchainLMDB::add_spent_key(const crypto::key_image& k_image)
void BlockchainLMDB::remove_spent_key(const crypto::key_image& k_image)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
crypto::key_image key_cpy = k_image;
@ -537,7 +536,7 @@ void BlockchainLMDB::remove_spent_key(const crypto::key_image& k_image)
blobdata BlockchainLMDB::output_to_blob(const tx_out& output)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
blobdata b;
if (!t_serializable_object_to_blob(output, b))
{
@ -549,7 +548,7 @@ blobdata BlockchainLMDB::output_to_blob(const tx_out& output)
tx_out BlockchainLMDB::output_from_blob(const blobdata& blob)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
std::stringstream ss;
ss << blob;
binary_archive<false> ba(ss);
@ -566,13 +565,13 @@ tx_out BlockchainLMDB::output_from_blob(const blobdata& blob)
uint64_t BlockchainLMDB::get_output_global_index(const uint64_t& amount, const uint64_t& index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
return 0;
}
void BlockchainLMDB::check_open()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
if (!m_open)
{
LOG_PRINT_L0("DB operation attempted on a not-open DB instance");
@ -582,12 +581,12 @@ void BlockchainLMDB::check_open()
BlockchainLMDB::~BlockchainLMDB()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
}
BlockchainLMDB::BlockchainLMDB()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
// initialize folder to something "safe" just in case
// someone accidentally misuses this class...
m_folder = "thishsouldnotexistbecauseitisgibberish";
@ -597,7 +596,7 @@ BlockchainLMDB::BlockchainLMDB()
void BlockchainLMDB::open(const std::string& filename)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
if (m_open)
{
@ -636,9 +635,16 @@ void BlockchainLMDB::open(const std::string& filename)
LOG_PRINT_L0("Failed to set max number of dbs");
throw DB_ERROR("Failed to set max number of dbs");
}
if (mdb_env_open(m_env, filename.c_str(), 0, 0664))
if (auto result = mdb_env_set_mapsize(m_env, 1 << 29))
{
LOG_PRINT_L0("Failed to set max memory map size");
LOG_PRINT_L0("E: " << mdb_strerror(result));
throw DB_ERROR("Failed to set max memory map size");
}
if (auto result = mdb_env_open(m_env, filename.c_str(), 0, 0664))
{
LOG_PRINT_L0("Failed to open lmdb environment");
LOG_PRINT_L0("E: " << mdb_strerror(result));
throw DB_ERROR("Failed to open lmdb environment");
}
@ -705,32 +711,32 @@ void BlockchainLMDB::open(const std::string& filename)
// unused for now, create will happen on open if doesn't exist
void BlockchainLMDB::create(const std::string& filename)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
throw DB_CREATE_FAILURE("create() is not implemented for this BlockchainDB, open() will create files if needed.");
}
void BlockchainLMDB::close()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
// FIXME: not yet thread safe!!! Use with care.
mdb_env_close(m_env);
}
void BlockchainLMDB::sync()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
// LMDB documentation leads me to believe this is unnecessary
}
void BlockchainLMDB::reset()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
// TODO: this
}
std::vector<std::string> BlockchainLMDB::get_filenames()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
std::vector<std::string> filenames;
boost::filesystem::path datafile(m_folder);
@ -747,7 +753,7 @@ std::vector<std::string> BlockchainLMDB::get_filenames()
// TODO: this?
bool BlockchainLMDB::lock()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
return false;
}
@ -755,14 +761,14 @@ bool BlockchainLMDB::lock()
// TODO: this?
void BlockchainLMDB::unlock()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
}
bool BlockchainLMDB::block_exists(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -797,7 +803,7 @@ bool BlockchainLMDB::block_exists(const crypto::hash& h)
block BlockchainLMDB::get_block(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
return get_block_from_height(get_block_height(h));
@ -805,7 +811,7 @@ block BlockchainLMDB::get_block(const crypto::hash& h)
uint64_t BlockchainLMDB::get_block_height(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -839,7 +845,7 @@ uint64_t BlockchainLMDB::get_block_height(const crypto::hash& h)
block_header BlockchainLMDB::get_block_header(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
// block_header object is automatically cast from block object
@ -848,7 +854,7 @@ block_header BlockchainLMDB::get_block_header(const crypto::hash& h)
block BlockchainLMDB::get_block_from_height(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -892,7 +898,7 @@ block BlockchainLMDB::get_block_from_height(const uint64_t& height)
uint64_t BlockchainLMDB::get_block_timestamp(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -925,7 +931,7 @@ uint64_t BlockchainLMDB::get_block_timestamp(const uint64_t& height)
uint64_t BlockchainLMDB::get_top_block_timestamp()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
// if no blocks, return 0
@ -939,7 +945,7 @@ uint64_t BlockchainLMDB::get_top_block_timestamp()
size_t BlockchainLMDB::get_block_size(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -972,7 +978,7 @@ size_t BlockchainLMDB::get_block_size(const uint64_t& height)
difficulty_type BlockchainLMDB::get_block_cumulative_difficulty(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1005,7 +1011,7 @@ difficulty_type BlockchainLMDB::get_block_cumulative_difficulty(const uint64_t&
difficulty_type BlockchainLMDB::get_block_difficulty(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
difficulty_type diff1 = 0;
@ -1022,7 +1028,7 @@ difficulty_type BlockchainLMDB::get_block_difficulty(const uint64_t& height)
uint64_t BlockchainLMDB::get_block_already_generated_coins(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1055,7 +1061,7 @@ uint64_t BlockchainLMDB::get_block_already_generated_coins(const uint64_t& heigh
crypto::hash BlockchainLMDB::get_block_hash_from_height(const uint64_t& height)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1088,7 +1094,7 @@ crypto::hash BlockchainLMDB::get_block_hash_from_height(const uint64_t& height)
std::vector<block> BlockchainLMDB::get_blocks_range(const uint64_t& h1, const uint64_t& h2)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
std::vector<block> v;
@ -1102,7 +1108,7 @@ std::vector<block> BlockchainLMDB::get_blocks_range(const uint64_t& h1, const ui
std::vector<crypto::hash> BlockchainLMDB::get_hashes_range(const uint64_t& h1, const uint64_t& h2)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
std::vector<crypto::hash> v;
@ -1116,7 +1122,7 @@ std::vector<crypto::hash> BlockchainLMDB::get_hashes_range(const uint64_t& h1, c
crypto::hash BlockchainLMDB::top_block_hash()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
if (m_height != 0)
{
@ -1128,7 +1134,7 @@ crypto::hash BlockchainLMDB::top_block_hash()
block BlockchainLMDB::get_top_block()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
if (m_height != 0)
@ -1142,7 +1148,7 @@ block BlockchainLMDB::get_top_block()
uint64_t BlockchainLMDB::height()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
return m_height;
@ -1151,7 +1157,7 @@ uint64_t BlockchainLMDB::height()
bool BlockchainLMDB::tx_exists(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1185,7 +1191,7 @@ bool BlockchainLMDB::tx_exists(const crypto::hash& h)
uint64_t BlockchainLMDB::get_tx_unlock_time(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1218,7 +1224,7 @@ uint64_t BlockchainLMDB::get_tx_unlock_time(const crypto::hash& h)
transaction BlockchainLMDB::get_tx(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1261,7 +1267,7 @@ transaction BlockchainLMDB::get_tx(const crypto::hash& h)
uint64_t BlockchainLMDB::get_tx_count()
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1285,7 +1291,7 @@ uint64_t BlockchainLMDB::get_tx_count()
std::vector<transaction> BlockchainLMDB::get_tx_list(const std::vector<crypto::hash>& hlist)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
std::vector<transaction> v;
@ -1299,7 +1305,7 @@ std::vector<transaction> BlockchainLMDB::get_tx_list(const std::vector<crypto::h
uint64_t BlockchainLMDB::get_tx_block_height(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1333,7 +1339,7 @@ uint64_t BlockchainLMDB::get_tx_block_height(const crypto::hash& h)
//FIXME: make sure the random method used here is appropriate
uint64_t BlockchainLMDB::get_random_output(const uint64_t& amount)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
uint64_t num_outputs = get_num_outputs(amount);
@ -1348,7 +1354,7 @@ uint64_t BlockchainLMDB::get_random_output(const uint64_t& amount)
uint64_t BlockchainLMDB::get_num_outputs(const uint64_t& amount)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1387,7 +1393,7 @@ uint64_t BlockchainLMDB::get_num_outputs(const uint64_t& amount)
crypto::public_key BlockchainLMDB::get_output_key(const uint64_t& amount, const uint64_t& index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
uint64_t global = get_output_global_index(amount, index);
@ -1405,7 +1411,7 @@ crypto::public_key BlockchainLMDB::get_output_key(const uint64_t& amount, const
tx_out BlockchainLMDB::get_output(const crypto::hash& h, const uint64_t& index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1467,7 +1473,7 @@ tx_out BlockchainLMDB::get_output(const crypto::hash& h, const uint64_t& index)
tx_out BlockchainLMDB::get_output(const uint64_t& index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1502,7 +1508,7 @@ tx_out BlockchainLMDB::get_output(const uint64_t& index)
tx_out_index BlockchainLMDB::get_output_tx_and_index(const uint64_t& amount, const uint64_t& index)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1595,7 +1601,7 @@ tx_out_index BlockchainLMDB::get_output_tx_and_index(const uint64_t& amount, con
std::vector<uint64_t> BlockchainLMDB::get_tx_output_indices(const crypto::hash& h)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
std::vector<uint64_t> index_vec;
@ -1647,7 +1653,7 @@ std::vector<uint64_t> BlockchainLMDB::get_tx_output_indices(const crypto::hash&
bool BlockchainLMDB::has_key_image(const crypto::key_image& img)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
@ -1680,7 +1686,7 @@ uint64_t BlockchainLMDB::add_block( const block& blk
, const std::vector<transaction>& txs
)
{
LOG_PRINT_L2("BlockchainLMDB::" << __func__);
LOG_PRINT_L3("BlockchainLMDB::" << __func__);
check_open();
txn_safe txn;
if (mdb_txn_begin(m_env, NULL, 0, txn))