From 1131292908f7d7c4ddfe4d228f356c4224cdf368 Mon Sep 17 00:00:00 2001 From: cryptozoidberg Date: Sat, 13 Aug 2022 23:23:16 +0200 Subject: [PATCH] Multiple fixes of bugs exposed by basic zarcanum coretest --- src/currency_core/blockchain_storage.cpp | 19 ++--- src/currency_core/core_runtime_config.h | 12 ++++ src/currency_core/currency_config.h | 3 +- src/currency_core/currency_format_utils.cpp | 77 ++++++++++++++------- tests/core_tests/chaingen.cpp | 9 +-- 5 files changed, 78 insertions(+), 42 deletions(-) diff --git a/src/currency_core/blockchain_storage.cpp b/src/currency_core/blockchain_storage.cpp index 3c2e6f15..7c808b28 100644 --- a/src/currency_core/blockchain_storage.cpp +++ b/src/currency_core/blockchain_storage.cpp @@ -1305,7 +1305,15 @@ bool blockchain_storage::prevalidate_miner_transaction(const block& b, uint64_t return false; } - CHECK_AND_ASSERT_MES(b.miner_tx.attachment.empty(), false, "coinbase transaction has attachments; attachments are not allowed for coinbase transactions."); + if (is_hardfork_active(ZANO_HARDFORK_04_ZARCANUM)) + { + CHECK_AND_ASSERT_MES(b.miner_tx.attachment.size() == 1, false, "coinbase transaction wrong attachments number(expeted 1 - rangeproofs)"); + CHECK_AND_ASSERT_MES(b.miner_tx.attachment[0].type() == typeid(zarcanum_outs_range_proof), false, "coinbase transaction wrong attachmenttype (expeted - zarcanum_outs_range_proof)"); + } + else + { + CHECK_AND_ASSERT_MES(b.miner_tx.attachment.empty(), false, "coinbase transaction has attachments; attachments are not allowed for coinbase transactions."); + } return true; } @@ -1445,12 +1453,7 @@ bool blockchain_storage::create_block_template(const create_block_template_param boost::multiprecision::uint128_t already_generated_coins; CRITICAL_REGION_BEGIN(m_read_lock); height = m_db_blocks.size(); - if(!m_core_runtime_config.is_hardfork_active_for_height(1, height)) - b.major_version = BLOCK_MAJOR_VERSION_INITIAL; - else if(!m_core_runtime_config.is_hardfork_active_for_height(3, height)) - b.major_version = HF1_BLOCK_MAJOR_VERSION; - else - b.major_version = CURRENT_BLOCK_MAJOR_VERSION; + b.major_version = m_core_runtime_config.hard_forks.get_block_major_version_by_height(height); b.minor_version = CURRENT_BLOCK_MINOR_VERSION; b.prev_id = get_top_block_id(); @@ -5564,7 +5567,7 @@ bool blockchain_storage::collect_rangeproofs_data_from_tx(std::vector commitments_1div8; + for (size_t out_index = out_index_start, i = 0; i < outs_count; ++out_index, ++i) + { + const tx_out_zarcanum& toz = boost::get(vouts[out_index]); // may throw an exception, only zarcanum outputs are exprected + const crypto::public_key* p = &toz.amount_commitment; + commitments_1div8.push_back(p); + } + + result.outputs_count = outs_count; + uint8_t err = 0; + bool r = crypto::bpp_gen<>(amounts, blinding_masks, commitments_1div8, result.bpp, &err); + CHECK_AND_ASSERT_MES(r, false, "bpp_gen failed with error " << err); + + return true; + } + //--------------------------------------------------------------- wide_difficulty_type correct_difficulty_with_sequence_factor(size_t sequence_factor, wide_difficulty_type diff) { @@ -168,7 +195,7 @@ namespace currency const pos_entry& pe) { CHECK_AND_ASSERT_MES(destinations.size() <= CURRENCY_TX_MAX_ALLOWED_OUTS || height == 0, false, "Too many outs (" << destinations.size() << ")! Miner tx can't be constructed."); - + tx.version = tx_version; tx.vin.clear(); tx.vout.clear(); tx.extra.clear(); @@ -204,15 +231,36 @@ namespace currency uint64_t no = 0; std::set deriv_cache; + uint64_t summary_outs_money = 0; + //fill outputs + finalized_tx result = AUTO_VAL_INIT(result); + uint8_t tx_outs_attr = 0; + + size_t output_index = tx.vout.size(); // in case of append mode we need to start output indexing from the last one + 1 + uint64_t range_proof_start_index = output_index; + crypto::scalar_vec_t blinding_masks(tx.vout.size() + destinations.size()); // vector of secret blinging masks for each output. For range proof generation + crypto::scalar_vec_t amounts(tx.vout.size() + destinations.size()); // vector of amounts, converted to scalars. For ranage proof generation + crypto::scalar_t blinding_masks_sum = 0; for (auto& d : destinations) { - bool r = construct_tx_out(d, txkey.sec, no, tx, deriv_cache, account_keys()); + + bool r = construct_tx_out(d, txkey.sec, no, tx, deriv_cache, account_keys(), blinding_masks[no], result, tx_outs_attr); CHECK_AND_ASSERT_MES(r, false, "Failed to contruct miner tx out"); + amounts[output_index - range_proof_start_index] = d.amount; + summary_outs_money += d.amount; + blinding_masks_sum += blinding_masks[output_index]; no++; } + if (tx.version > TRANSACTION_VERSION_PRE_HF4) + { + //add range proofs + currency::zarcanum_outs_range_proof range_proofs = AUTO_VAL_INIT(range_proofs); + bool r = generate_zarcanum_outs_range_proof(range_proof_start_index, amounts.size(), amounts, blinding_masks, tx.vout, range_proofs); + CHECK_AND_ASSERT_MES(r, false, "Failed to generate zarcanum_outs_range_proof()"); + tx.attachment.push_back(range_proofs); + } - tx.version = tx_version; if (!have_type_in_variant_container(tx.extra)) { //if stake unlock time was not set, then we can use simple "whole transaction" lock scheme @@ -1432,29 +1480,6 @@ namespace currency return true; } - //-------------------------------------------------------------------------------- - bool generate_zarcanum_outs_range_proof(size_t out_index_start, size_t outs_count, const crypto::scalar_vec_t& amounts, const crypto::scalar_vec_t& blinding_masks, - const std::vector& vouts, zarcanum_outs_range_proof& result) - { - //TODO: review for Andre - CHECK_AND_ASSERT_MES(amounts.size() == outs_count, false, ""); - CHECK_AND_ASSERT_MES(blinding_masks.size() == outs_count, false, ""); - CHECK_AND_ASSERT_MES(out_index_start + outs_count == vouts.size(), false, ""); - - std::vector commitments_1div8; - for (size_t out_index = out_index_start, i = 0; i < outs_count; ++out_index, ++i) - { - const tx_out_zarcanum& toz = boost::get(vouts[out_index]); // may throw an exception, only zarcanum outputs are exprected - const crypto::public_key* p = &toz.amount_commitment; - commitments_1div8.push_back(p); - } - - uint8_t err = 0; - bool r = crypto::bpp_gen<>(amounts, blinding_masks, commitments_1div8, result.bpp, &err); - CHECK_AND_ASSERT_MES(r, false, "bpp_gen failed with error " << err); - - return true; - } bool construct_tx(const account_keys& sender_account_keys, const finalize_tx_param& ftp, finalized_tx& result) { diff --git a/tests/core_tests/chaingen.cpp b/tests/core_tests/chaingen.cpp index 704045a5..3ebed4a9 100644 --- a/tests/core_tests/chaingen.cpp +++ b/tests/core_tests/chaingen.cpp @@ -222,13 +222,8 @@ bool test_generator::construct_block(currency::block& blk, // else // blk.major_version = BLOCK_MAJOR_VERSION_INITIAL; - if (!m_hardforks.is_hardfork_active_for_height(1, height)) - blk.major_version = BLOCK_MAJOR_VERSION_INITIAL; - else if (!m_hardforks.is_hardfork_active_for_height(3, height)) - blk.major_version = HF1_BLOCK_MAJOR_VERSION; - else - blk.major_version = CURRENT_BLOCK_MAJOR_VERSION; - + blk.major_version = m_hardforks.get_block_major_version_by_height(height); + blk.minor_version = CURRENT_BLOCK_MINOR_VERSION; blk.timestamp = timestamp; blk.prev_id = prev_id;