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

add command pop_blocks monerod #4903

Merged
merged 1 commit into from
Dec 12, 2018
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
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
32 changes: 32 additions & 0 deletions src/cryptonote_core/blockchain.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -576,6 +576,38 @@ bool Blockchain::deinit()
return true;
}
//------------------------------------------------------------------
// This function removes blocks from the top of blockchain.
// It starts a batch and calls private method pop_block_from_blockchain().
void Blockchain::pop_blocks(uint64_t nblocks)
{
uint64_t i;
CRITICAL_REGION_LOCAL(m_tx_pool);
CRITICAL_REGION_LOCAL1(m_blockchain_lock);

while (!m_db->batch_start())
{
m_blockchain_lock.unlock();
m_tx_pool.unlock();
epee::misc_utils::sleep_no_w(1000);
Jasonhcwong marked this conversation as resolved.
Show resolved Hide resolved
m_tx_pool.lock();
m_blockchain_lock.lock();
}

try
{
for (i=0; i < nblocks; ++i)
{
pop_block_from_blockchain();
}
}
catch (const std::exception& e)
{
LOG_ERROR("Error when popping blocks, only " << i << " blocks are popped: " << e.what());
}
Jasonhcwong marked this conversation as resolved.
Show resolved Hide resolved

m_db->batch_stop();
}
//------------------------------------------------------------------
// This function tells BlockchainDB to remove the top block from the
// blockchain and then returns all transactions (except the miner tx, of course)
// from it to the tx_pool
Expand Down
7 changes: 7 additions & 0 deletions src/cryptonote_core/blockchain.h
Original file line number Diff line number Diff line change
Expand Up @@ -967,6 +967,13 @@ namespace cryptonote
*/
std::vector<time_t> get_last_block_timestamps(unsigned int blocks) const;

/**
* @brief removes blocks from the top of the blockchain
*
* @param nblocks number of blocks to be removed
*/
void pop_blocks(uint64_t nblocks);

private:

// TODO: evaluate whether or not each of these typedefs are left over from blockchain_storage
Expand Down
25 changes: 25 additions & 0 deletions src/daemon/command_parser_executor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -674,6 +674,31 @@ bool t_command_parser_executor::sync_info(const std::vector<std::string>& args)
return m_executor.sync_info();
}

bool t_command_parser_executor::pop_blocks(const std::vector<std::string>& args)
{
if (args.size() != 1)
{
std::cout << "Exactly one parameter is needed" << std::endl;
return false;
}

try
{
uint64_t nblocks = boost::lexical_cast<uint64_t>(args[0]);
if (nblocks < 1)
{
std::cout << "number of blocks must be greater than 0" << std::endl;
return false;
}
return m_executor.pop_blocks(nblocks);
}
catch (const boost::bad_lexical_cast&)
{
std::cout << "number of blocks must be a number greater than 0" << std::endl;
Jasonhcwong marked this conversation as resolved.
Show resolved Hide resolved
}
return false;
}

bool t_command_parser_executor::version(const std::vector<std::string>& args)
{
std::cout << "Monero '" << MONERO_RELEASE_NAME << "' (v" << MONERO_VERSION_FULL << ")" << std::endl;
Expand Down
2 changes: 2 additions & 0 deletions src/daemon/command_parser_executor.h
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,8 @@ class t_command_parser_executor final

bool sync_info(const std::vector<std::string>& args);

bool pop_blocks(const std::vector<std::string>& args);

bool version(const std::vector<std::string>& args);
};

Expand Down
6 changes: 6 additions & 0 deletions src/daemon/command_server.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -281,6 +281,12 @@ t_command_server::t_command_server(
, std::bind(&t_command_parser_executor::sync_info, &m_parser, p::_1)
, "Print information about the blockchain sync state."
);
m_command_lookup.set_handler(
"pop_blocks"
, std::bind(&t_command_parser_executor::pop_blocks, &m_parser, p::_1)
, "pop_blocks <nblocks>"
, "Remove blocks from end of blockchain"
);
m_command_lookup.set_handler(
"version"
, std::bind(&t_command_parser_executor::version, &m_parser, p::_1)
Expand Down
27 changes: 27 additions & 0 deletions src/daemon/rpc_command_executor.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1967,4 +1967,31 @@ bool t_rpc_command_executor::sync_info()
return true;
}

bool t_rpc_command_executor::pop_blocks(uint64_t num_blocks)
{
cryptonote::COMMAND_RPC_POP_BLOCKS::request req;
cryptonote::COMMAND_RPC_POP_BLOCKS::response res;
std::string fail_message = "pop_blocks failed";

req.nblocks = num_blocks;
if (m_is_rpc)
{
if (!m_rpc_client->rpc_request(req, res, "/pop_blocks", fail_message.c_str()))
{
return true;
}
}
else
{
if (!m_rpc_server->on_pop_blocks(req, res) || res.status != CORE_RPC_STATUS_OK)
{
tools::fail_msg_writer() << make_error(fail_message, res.status);
return true;
}
}
tools::success_msg_writer() << "new height: " << res.height;

return true;
}

}// namespace daemonize
2 changes: 2 additions & 0 deletions src/daemon/rpc_command_executor.h
Original file line number Diff line number Diff line change
Expand Up @@ -152,6 +152,8 @@ class t_rpc_command_executor final {
bool relay_tx(const std::string &txid);

bool sync_info();

bool pop_blocks(uint64_t num_blocks);
};

} // namespace daemonize
12 changes: 12 additions & 0 deletions src/rpc/core_rpc_server.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -2021,6 +2021,18 @@ namespace cryptonote
return true;
}
//------------------------------------------------------------------------------------------------------------------------------
bool core_rpc_server::on_pop_blocks(const COMMAND_RPC_POP_BLOCKS::request& req, COMMAND_RPC_POP_BLOCKS::response& res)
{
PERF_TIMER(on_pop_blocks);

m_core.get_blockchain_storage().pop_blocks(req.nblocks);

res.height = m_core.get_current_blockchain_height();
res.status = CORE_RPC_STATUS_OK;

return true;
}
//------------------------------------------------------------------------------------------------------------------------------
bool core_rpc_server::on_relay_tx(const COMMAND_RPC_RELAY_TX::request& req, COMMAND_RPC_RELAY_TX::response& res, epee::json_rpc::error& error_resp)
{
PERF_TIMER(on_relay_tx);
Expand Down
2 changes: 2 additions & 0 deletions src/rpc/core_rpc_server.h
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,7 @@ namespace cryptonote
MAP_URI_AUTO_JON2("/get_outs", on_get_outs, COMMAND_RPC_GET_OUTPUTS)
MAP_URI_AUTO_JON2_IF("/update", on_update, COMMAND_RPC_UPDATE, !m_restricted)
MAP_URI_AUTO_BIN2("/get_output_distribution.bin", on_get_output_distribution_bin, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION)
MAP_URI_AUTO_JON2_IF("/pop_blocks", on_pop_blocks, COMMAND_RPC_POP_BLOCKS, !m_restricted)
BEGIN_JSON_RPC_MAP("/json_rpc")
MAP_JON_RPC("get_block_count", on_getblockcount, COMMAND_RPC_GETBLOCKCOUNT)
MAP_JON_RPC("getblockcount", on_getblockcount, COMMAND_RPC_GETBLOCKCOUNT)
Expand Down Expand Up @@ -189,6 +190,7 @@ namespace cryptonote
bool on_stop_save_graph(const COMMAND_RPC_STOP_SAVE_GRAPH::request& req, COMMAND_RPC_STOP_SAVE_GRAPH::response& res);
bool on_update(const COMMAND_RPC_UPDATE::request& req, COMMAND_RPC_UPDATE::response& res);
bool on_get_output_distribution_bin(const COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::request& req, COMMAND_RPC_GET_OUTPUT_DISTRIBUTION::response& res);
bool on_pop_blocks(const COMMAND_RPC_POP_BLOCKS::request& req, COMMAND_RPC_POP_BLOCKS::response& res);

//json_rpc
bool on_getblockcount(const COMMAND_RPC_GETBLOCKCOUNT::request& req, COMMAND_RPC_GETBLOCKCOUNT::response& res);
Expand Down
23 changes: 23 additions & 0 deletions src/rpc/core_rpc_server_commands_defs.h
Original file line number Diff line number Diff line change
Expand Up @@ -2326,4 +2326,27 @@ namespace cryptonote
};
};

struct COMMAND_RPC_POP_BLOCKS
{
struct request
{
uint64_t nblocks;

BEGIN_KV_SERIALIZE_MAP()
KV_SERIALIZE(nblocks);
END_KV_SERIALIZE_MAP()
};

struct response
{
std::string status;
uint64_t height;

BEGIN_KV_SERIALIZE_MAP()
KV_SERIALIZE(status)
KV_SERIALIZE(height)
END_KV_SERIALIZE_MAP()
};
};

}