mirror of
https://github.com/monero-project/monero.git
synced 2025-05-02 12:26:06 -04:00
Improve cryptonote (block and tx) binary read performance
This commit is contained in:
parent
0a1ddc2eff
commit
08e4497c6e
29 changed files with 229 additions and 230 deletions
|
@ -152,10 +152,6 @@ namespace cryptonote
|
|||
|
||||
};
|
||||
|
||||
template<typename T> static inline unsigned int getpos(T &ar) { return 0; }
|
||||
template<> inline unsigned int getpos(binary_archive<true> &ar) { return ar.stream().tellp(); }
|
||||
template<> inline unsigned int getpos(binary_archive<false> &ar) { return ar.stream().tellg(); }
|
||||
|
||||
class transaction_prefix
|
||||
{
|
||||
|
||||
|
@ -236,17 +232,17 @@ namespace cryptonote
|
|||
set_blob_size_valid(false);
|
||||
}
|
||||
|
||||
const unsigned int start_pos = getpos(ar);
|
||||
const auto start_pos = ar.getpos();
|
||||
|
||||
FIELDS(*static_cast<transaction_prefix *>(this))
|
||||
|
||||
if (std::is_same<Archive<W>, binary_archive<W>>())
|
||||
prefix_size = getpos(ar) - start_pos;
|
||||
prefix_size = ar.getpos() - start_pos;
|
||||
|
||||
if (version == 1)
|
||||
{
|
||||
if (std::is_same<Archive<W>, binary_archive<W>>())
|
||||
unprunable_size = getpos(ar) - start_pos;
|
||||
unprunable_size = ar.getpos() - start_pos;
|
||||
|
||||
ar.tag("signatures");
|
||||
ar.begin_array();
|
||||
|
@ -284,11 +280,11 @@ namespace cryptonote
|
|||
{
|
||||
ar.begin_object();
|
||||
bool r = rct_signatures.serialize_rctsig_base(ar, vin.size(), vout.size());
|
||||
if (!r || !ar.stream().good()) return false;
|
||||
if (!r || !ar.good()) return false;
|
||||
ar.end_object();
|
||||
|
||||
if (std::is_same<Archive<W>, binary_archive<W>>())
|
||||
unprunable_size = getpos(ar) - start_pos;
|
||||
unprunable_size = ar.getpos() - start_pos;
|
||||
|
||||
if (!pruned && rct_signatures.type != rct::RCTTypeNull)
|
||||
{
|
||||
|
@ -296,7 +292,7 @@ namespace cryptonote
|
|||
ar.begin_object();
|
||||
r = rct_signatures.p.serialize_rctsig_prunable(ar, rct_signatures.type, vin.size(), vout.size(),
|
||||
vin.size() > 0 && vin[0].type() == typeid(txin_to_key) ? boost::get<txin_to_key>(vin[0]).key_offsets.size() - 1 : 0);
|
||||
if (!r || !ar.stream().good()) return false;
|
||||
if (!r || !ar.good()) return false;
|
||||
ar.end_object();
|
||||
}
|
||||
}
|
||||
|
@ -320,13 +316,13 @@ namespace cryptonote
|
|||
{
|
||||
ar.begin_object();
|
||||
bool r = rct_signatures.serialize_rctsig_base(ar, vin.size(), vout.size());
|
||||
if (!r || !ar.stream().good()) return false;
|
||||
if (!r || !ar.good()) return false;
|
||||
ar.end_object();
|
||||
}
|
||||
}
|
||||
if (!typename Archive<W>::is_saving())
|
||||
pruned = true;
|
||||
return ar.stream().good();
|
||||
return ar.good();
|
||||
}
|
||||
|
||||
private:
|
||||
|
|
|
@ -211,9 +211,7 @@ namespace cryptonote
|
|||
//---------------------------------------------------------------
|
||||
bool parse_and_validate_tx_from_blob(const blobdata_ref& tx_blob, transaction& tx)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << tx_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(tx_blob)};
|
||||
bool r = ::serialization::serialize(ba, tx);
|
||||
CHECK_AND_ASSERT_MES(r, false, "Failed to parse transaction from blob");
|
||||
CHECK_AND_ASSERT_MES(expand_transaction_1(tx, false), false, "Failed to expand transaction data");
|
||||
|
@ -224,9 +222,7 @@ namespace cryptonote
|
|||
//---------------------------------------------------------------
|
||||
bool parse_and_validate_tx_base_from_blob(const blobdata_ref& tx_blob, transaction& tx)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << tx_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(tx_blob)};
|
||||
bool r = tx.serialize_base(ba);
|
||||
CHECK_AND_ASSERT_MES(r, false, "Failed to parse transaction from blob");
|
||||
CHECK_AND_ASSERT_MES(expand_transaction_1(tx, true), false, "Failed to expand transaction data");
|
||||
|
@ -236,9 +232,7 @@ namespace cryptonote
|
|||
//---------------------------------------------------------------
|
||||
bool parse_and_validate_tx_prefix_from_blob(const blobdata_ref& tx_blob, transaction_prefix& tx)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << tx_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(tx_blob)};
|
||||
bool r = ::serialization::serialize_noeof(ba, tx);
|
||||
CHECK_AND_ASSERT_MES(r, false, "Failed to parse transaction prefix from blob");
|
||||
return true;
|
||||
|
@ -246,9 +240,7 @@ namespace cryptonote
|
|||
//---------------------------------------------------------------
|
||||
bool parse_and_validate_tx_from_blob(const blobdata_ref& tx_blob, transaction& tx, crypto::hash& tx_hash)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << tx_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(tx_blob)};
|
||||
bool r = ::serialization::serialize(ba, tx);
|
||||
CHECK_AND_ASSERT_MES(r, false, "Failed to parse transaction from blob");
|
||||
CHECK_AND_ASSERT_MES(expand_transaction_1(tx, false), false, "Failed to expand transaction data");
|
||||
|
@ -532,22 +524,15 @@ namespace cryptonote
|
|||
if(tx_extra.empty())
|
||||
return true;
|
||||
|
||||
std::string extra_str(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size());
|
||||
std::istringstream iss(extra_str);
|
||||
binary_archive<false> ar(iss);
|
||||
binary_archive<false> ar{epee::to_span(tx_extra)};
|
||||
|
||||
bool eof = false;
|
||||
while (!eof)
|
||||
do
|
||||
{
|
||||
tx_extra_field field;
|
||||
bool r = ::do_serialize(ar, field);
|
||||
CHECK_AND_NO_ASSERT_MES_L1(r, false, "failed to deserialize extra field. extra = " << string_tools::buff_to_hex_nodelimer(std::string(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size())));
|
||||
tx_extra_fields.push_back(field);
|
||||
|
||||
std::ios_base::iostate state = iss.rdstate();
|
||||
eof = (EOF == iss.peek());
|
||||
iss.clear(state);
|
||||
}
|
||||
} while (!ar.eof());
|
||||
CHECK_AND_NO_ASSERT_MES_L1(::serialization::check_stream_state(ar), false, "failed to deserialize extra field. extra = " << string_tools::buff_to_hex_nodelimer(std::string(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size())));
|
||||
|
||||
return true;
|
||||
|
@ -578,13 +563,10 @@ namespace cryptonote
|
|||
return true;
|
||||
}
|
||||
|
||||
std::string extra_str(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size());
|
||||
std::istringstream iss(extra_str);
|
||||
binary_archive<false> ar(iss);
|
||||
binary_archive<false> ar{epee::to_span(tx_extra)};
|
||||
|
||||
bool eof = false;
|
||||
size_t processed = 0;
|
||||
while (!eof)
|
||||
do
|
||||
{
|
||||
tx_extra_field field;
|
||||
bool r = ::do_serialize(ar, field);
|
||||
|
@ -596,12 +578,8 @@ namespace cryptonote
|
|||
break;
|
||||
}
|
||||
tx_extra_fields.push_back(field);
|
||||
processed = iss.tellg();
|
||||
|
||||
std::ios_base::iostate state = iss.rdstate();
|
||||
eof = (EOF == iss.peek());
|
||||
iss.clear(state);
|
||||
}
|
||||
processed = ar.getpos();
|
||||
} while (!ar.eof());
|
||||
if (!::serialization::check_stream_state(ar))
|
||||
{
|
||||
MWARNING("failed to deserialize extra field. extra = " << string_tools::buff_to_hex_nodelimer(std::string(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size())));
|
||||
|
@ -752,24 +730,18 @@ namespace cryptonote
|
|||
if (tx_extra.empty())
|
||||
return true;
|
||||
std::string extra_str(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size());
|
||||
std::istringstream iss(extra_str);
|
||||
binary_archive<false> ar(iss);
|
||||
binary_archive<false> ar{epee::strspan<std::uint8_t>(extra_str)};
|
||||
std::ostringstream oss;
|
||||
binary_archive<true> newar(oss);
|
||||
|
||||
bool eof = false;
|
||||
while (!eof)
|
||||
do
|
||||
{
|
||||
tx_extra_field field;
|
||||
bool r = ::do_serialize(ar, field);
|
||||
CHECK_AND_NO_ASSERT_MES_L1(r, false, "failed to deserialize extra field. extra = " << string_tools::buff_to_hex_nodelimer(std::string(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size())));
|
||||
if (field.type() != type)
|
||||
::do_serialize(newar, field);
|
||||
|
||||
std::ios_base::iostate state = iss.rdstate();
|
||||
eof = (EOF == iss.peek());
|
||||
iss.clear(state);
|
||||
}
|
||||
} while (!ar.eof());
|
||||
CHECK_AND_NO_ASSERT_MES_L1(::serialization::check_stream_state(ar), false, "failed to deserialize extra field. extra = " << string_tools::buff_to_hex_nodelimer(std::string(reinterpret_cast<const char*>(tx_extra.data()), tx_extra.size())));
|
||||
tx_extra.clear();
|
||||
std::string s = oss.str();
|
||||
|
@ -1357,9 +1329,7 @@ namespace cryptonote
|
|||
//---------------------------------------------------------------
|
||||
bool parse_and_validate_block_from_blob(const blobdata_ref& b_blob, block& b, crypto::hash *block_hash)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << b_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(b_blob)};
|
||||
bool r = ::serialization::serialize(ba, b);
|
||||
CHECK_AND_ASSERT_MES(r, false, "Failed to parse block from blob");
|
||||
b.invalidate_hashes();
|
||||
|
|
|
@ -148,9 +148,7 @@ namespace cryptonote
|
|||
template<class t_object>
|
||||
bool t_serializable_object_from_blob(t_object& to, const blobdata& b_blob)
|
||||
{
|
||||
std::stringstream ss;
|
||||
ss << b_blob;
|
||||
binary_archive<false> ba(ss);
|
||||
binary_archive<false> ba{epee::strspan<std::uint8_t>(b_blob)};
|
||||
bool r = ::serialization::serialize(ba, to);
|
||||
return r;
|
||||
}
|
||||
|
|
|
@ -57,11 +57,7 @@ namespace cryptonote
|
|||
// size - 1 - because of variant tag
|
||||
for (size = 1; size <= TX_EXTRA_PADDING_MAX_COUNT; ++size)
|
||||
{
|
||||
std::ios_base::iostate state = ar.stream().rdstate();
|
||||
bool eof = EOF == ar.stream().peek();
|
||||
ar.stream().clear(state);
|
||||
|
||||
if (eof)
|
||||
if (ar.eof())
|
||||
break;
|
||||
|
||||
uint8_t zero;
|
||||
|
@ -139,8 +135,7 @@ namespace cryptonote
|
|||
if(!::do_serialize(ar, field))
|
||||
return false;
|
||||
|
||||
std::istringstream iss(field);
|
||||
binary_archive<false> iar(iss);
|
||||
binary_archive<false> iar{epee::strspan<std::uint8_t>(field)};
|
||||
serialize_helper helper(*this);
|
||||
return ::serialization::serialize(iar, helper);
|
||||
}
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue