From 37f50f9b535f0258c3a1c6f7247a891b4c211ff3 Mon Sep 17 00:00:00 2001 From: M5M400 Date: Mon, 19 Dec 2016 18:39:52 +0100 Subject: [PATCH] Add files via upload --- .../cryptonote_format_utils.cpp | 57 ++++++++++++++++++- src/cryptonote_core/cryptonote_format_utils.h | 1 + 2 files changed, 57 insertions(+), 1 deletion(-) diff --git a/src/cryptonote_core/cryptonote_format_utils.cpp b/src/cryptonote_core/cryptonote_format_utils.cpp index b30c20cc..41eac6b4 100644 --- a/src/cryptonote_core/cryptonote_format_utils.cpp +++ b/src/cryptonote_core/cryptonote_format_utils.cpp @@ -613,10 +613,65 @@ namespace cryptonote return get_object_hash(static_cast(t), res, blob_size); } + //--------------------------------------------------------------- + bool get_transaction_hash(const transaction& t, crypto::hash& res, size_t* blob_size) + { + // v1 transactions hash the entire blob + if (t.version == 1) + { + size_t ignored_blob_size, &blob_size_ref = blob_size ? *blob_size : ignored_blob_size; + return get_object_hash(t, res, blob_size_ref); + } + + // v2 transactions hash different parts together, than hash the set of those hashes + crypto::hash hashes[3]; + + // prefix + get_transaction_prefix_hash(t, hashes[0]); + + transaction &tt = const_cast(t); + + // base rct + { + std::stringstream ss; + binary_archive ba(ss); + const size_t inputs = t.vin.size(); + const size_t outputs = t.vout.size(); + bool r = tt.rct_signatures.serialize_rctsig_base(ba, inputs, outputs); + CHECK_AND_ASSERT_MES(r, false, "Failed to serialize rct signatures base"); + cryptonote::get_blob_hash(ss.str(), hashes[1]); + } + + // prunable rct + if (t.rct_signatures.type == rct::RCTTypeNull) + { + hashes[2] = cryptonote::null_hash; + } + else + { + std::stringstream ss; + binary_archive ba(ss); + const size_t inputs = t.vin.size(); + const size_t outputs = t.vout.size(); + const size_t mixin = t.vin.empty() ? 0 : t.vin[0].type() == typeid(txin_to_key) ? boost::get(t.vin[0]).key_offsets.size() - 1 : 0; + bool r = tt.rct_signatures.p.serialize_rctsig_prunable(ba, t.rct_signatures.type, inputs, outputs, mixin); + CHECK_AND_ASSERT_MES(r, false, "Failed to serialize rct signatures prunable"); + cryptonote::get_blob_hash(ss.str(), hashes[2]); + } + + // the tx hash is the hash of the 3 hashes + res = cn_fast_hash(hashes, sizeof(hashes)); + + // we still need the size + if (blob_size) + *blob_size = get_object_blobsize(t); + + return true; + } //--------------------------------------------------------------- bool get_transaction_hash(const transaction& t, crypto::hash& res, size_t& blob_size) { - return get_object_hash(t, res, blob_size); + return get_transaction_hash(t, res, &blob_size); } //--------------------------------------------------------------- bool get_block_hashing_blob(const block& b, blobdata& blob) diff --git a/src/cryptonote_core/cryptonote_format_utils.h b/src/cryptonote_core/cryptonote_format_utils.h index a91349cf..b9e5dc59 100644 --- a/src/cryptonote_core/cryptonote_format_utils.h +++ b/src/cryptonote_core/cryptonote_format_utils.h @@ -77,6 +77,7 @@ namespace cryptonote crypto::hash get_transaction_hash(const transaction& t); bool get_transaction_hash(const transaction& t, crypto::hash& res); bool get_transaction_hash(const transaction& t, crypto::hash& res, size_t& blob_size); + bool get_transaction_hash(const transaction& t, crypto::hash& res, size_t* blob_size); bool get_block_hashing_blob(const block& b, blobdata& blob); bool get_bytecoin_block_hashing_blob(const block& b, blobdata& blob); blobdata get_block_hashing_blob(const bb_block& b);