From 7e3dbdde0540d41905f9240540a792611ea1a25f Mon Sep 17 00:00:00 2001 From: wowario Date: Thu, 14 May 2020 17:44:48 +0300 Subject: [PATCH 1/5] build: prepare v0.8.0.0 release --- README.md | 3 ++- src/blocks/checkpoints.dat | Bin 25028 -> 26372 bytes src/checkpoints/checkpoints.cpp | 1 + src/cryptonote_core/blockchain.cpp | 2 +- 4 files changed, 4 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 03cee5b72..d8326791e 100644 --- a/README.md +++ b/README.md @@ -65,7 +65,8 @@ Dates are provided in the format YYYY-MM-DD. | 81769 | 2019-02-19 | Erotic EggplantEmoji | v0.5.0.0 | v0.5.0.2 | Cryptonight/wow, LWMA v1 with N=144, Updated Bulletproofs, Fee Per Byte, Auto-churn | 114969 | 2019-06-14 | F For Fappening | v0.6.1.0 | v0.6.1.2 | RandomWOW, new block weight algorithm, slightly more efficient RingCT format | 160777 | 2019-11-20 | Gaping Goatse | v0.7.0.0 | v0.7.1.0 | Only allow >= 2 outputs, change to the block median used to calculate penalty, rct sigs in coinbase forbidden, 4 unlock time as protocol rule -| XXXXX | 2020-04-XX | XXXX | v0.8.0.0 | v0.8.0.0 | Dandelion++ support +| - | - | Hallucinogenic Hypnotoad | v0.8.0.0 | v0.8.0.0 | Dandelion++ support +| XXXX | 2021-XX-XX | XXXX | v0.9.0.0 | v0.9.0.0 | SHA3-256 [FIPS 202] PoW X's indicate that these details have not been determined as of commit date. diff --git a/src/blocks/checkpoints.dat b/src/blocks/checkpoints.dat index 7e66b690affae5657bfb5a7c9482da09dd3c717c..4127ae48f84a88edbece811f1f5a2c832f48167b 100644 GIT binary patch delta 1367 zcmV-d1*rPO!vTcO0Rfz`0mET`4-b3$ma-~f7_vZj3QzE(eInuICDZ^AQ$EelkA|j) z1QZn{d7dsrMDr!}Ts@zrKZy~_Qsg*MX-buZh1xUiHubs=#b)wcv@%Cn=F)uYyE*WL z*gjpI{i&n{y^w(5D9zu?3P_9Z<|cy>oQM~Mf`XTjMUbHe$1>!9DqB2%w5>Q2FqVW@ z@J&@&r~Vp_Q(vH#UDgffzFvEmFP#K6CpKd`QpgGk<48m08`&^BU>;_UQbJb6)_!2M zN!0`03_g_vaKlw>C|?cyefjp_A$9C^Z!(@xt0Cis;?5(NT-$;As{u)o^xuMqlGN$$;WbecV*yGn*Qv z-*r~VS#l_G-r1>0WHIcReDn?*o405$cZW^)U4;@CC4O*}6Wi=V#V&%V;$Ywl#3AoK zvOkZLe!{S2)x{5Ui!8EN#S2O1kjXh3 z5;K0+UW}0XqyAsH#nf{B=L*=t!ZOZmVOO-+bC;`EqRt3kPp3d5%YP7Lm#uVh89aQb z2_nPzr*p`5(REKmRzz-!4R#ez)2YZ|5^QV7P*>c4e#c}kQ@ABHcpnbi5pI!yNa_o? z6$FcmqbuinCXtP^J$oe&hJ)Lw#L}N&s<6+`_r&cO@?_GR+8{GnnH%HXb4))Tb!rP3 zbvTgstY!RG14E?Y0aojseI$pc{1W*(9yb%(vQ)M`JZ=;9hMCuZ6lqTMkFbP7+L4i@ zvA`&QAsIl4ZFs|o+7^YTL&UZ?H`~yV*fi~R912>K;c3|6xLy|*9=i*#qD09V=!Idd zRNMf@mu^tzKp|C1FL{^h2-80-4K6lKI6_Tt3)K>R2S3>j70Xgkc^PLwI|I(h5?!sl z5Hx^l+fN~xkDZhzdv9o>^wuA1(nrZjHgoQO4C`uylN?3FJQC~p77o-IEoJ00(J=mo zz1}bIc8F`|X-5Xz_LdKU`q~3?52}g$!~ViE=}Sdrb)68}EHKy^R3S6hxhg#JR02z< zdI#C2wR3K;5vh%P{i!#?>1Xp8Ys+sIlw$gN Z@&V9_(Lm|HT9+2*t>`JS?TDr`2}w-Hle_=` delta 12 TcmZoU$9Uv0BV+qU#>0sKBYFio diff --git a/src/checkpoints/checkpoints.cpp b/src/checkpoints/checkpoints.cpp index 29961ae03..afad346ad 100644 --- a/src/checkpoints/checkpoints.cpp +++ b/src/checkpoints/checkpoints.cpp @@ -225,6 +225,7 @@ namespace cryptonote ADD_CHECKPOINT(160777, "9496690579af21f38f00e67e11c2e85a15912fe4f412aad33d1162be1579e755"); //Hard fork to v15 ADD_CHECKPOINT(194444, "0aa7ea6ade2ee8f5a525a079c53888fac415826ee8d1e8c92caa52629773db35"); ADD_CHECKPOINT(200500, "1e5c7af11e19a94f334576d79fe0179ff493ce378701f3f810b674db2760c228"); + ADD_CHECKPOINT(211300, "f712b6dc0dfe896d18c5ca9097144d05ef8810b11277663638c0963d96ea172c"); return true; } diff --git a/src/cryptonote_core/blockchain.cpp b/src/cryptonote_core/blockchain.cpp index d73313356..4b501045d 100644 --- a/src/cryptonote_core/blockchain.cpp +++ b/src/cryptonote_core/blockchain.cpp @@ -5098,7 +5098,7 @@ void Blockchain::cancel() } #if defined(PER_BLOCK_CHECKPOINT) -static const char expected_block_hashes_hash[] = "71ff39f29117b11ada338a4258cf5bf000f036495f6c34d0fd4d0ed9cb6a9d8b"; +static const char expected_block_hashes_hash[] = "a4717185cf3fc691aa7208e282d81c719f255eb630935deecdd4a6908f41ab75"; void Blockchain::load_compiled_in_block_hashes(const GetCheckpointsCallback& get_checkpoints) { if (get_checkpoints == nullptr || !m_fast_sync) -- 2.25.1 From e74aff06c28c8c30b6c44468b8132b38eb32cc21 Mon Sep 17 00:00:00 2001 From: moneromooo-monero Date: Wed, 13 May 2020 00:25:56 +0000 Subject: [PATCH 2/5] simplewallet: don't complain about incoming payment ids on change --- src/simplewallet/simplewallet.cpp | 4 ++-- src/simplewallet/simplewallet.h | 2 +- src/wallet/api/wallet.cpp | 2 +- src/wallet/wallet2.cpp | 18 ++++++++++++++++-- src/wallet/wallet2.h | 3 ++- 5 files changed, 22 insertions(+), 7 deletions(-) diff --git a/src/simplewallet/simplewallet.cpp b/src/simplewallet/simplewallet.cpp index c371b8fbc..69d4652bb 100644 --- a/src/simplewallet/simplewallet.cpp +++ b/src/simplewallet/simplewallet.cpp @@ -5466,7 +5466,7 @@ void simple_wallet::on_new_block(uint64_t height, const cryptonote::block& block m_refresh_progress_reporter.update(height, false); } //---------------------------------------------------------------------------------------------------- -void simple_wallet::on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, uint64_t unlock_time) +void simple_wallet::on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, bool is_change, uint64_t unlock_time) { if (m_locked) return; @@ -5477,7 +5477,7 @@ void simple_wallet::on_money_received(uint64_t height, const crypto::hash &txid, tr("idx ") << subaddr_index; const uint64_t warn_height = m_wallet->nettype() == TESTNET ? 1000000 : m_wallet->nettype() == STAGENET ? 50000 : 1650000; - if (height >= warn_height) + if (height >= warn_height && !is_change) { std::vector tx_extra_fields; parse_tx_extra(tx.extra, tx_extra_fields); // failure ok diff --git a/src/simplewallet/simplewallet.h b/src/simplewallet/simplewallet.h index 59818b303..bf459736f 100644 --- a/src/simplewallet/simplewallet.h +++ b/src/simplewallet/simplewallet.h @@ -342,7 +342,7 @@ namespace cryptonote //----------------- i_wallet2_callback --------------------- virtual void on_new_block(uint64_t height, const cryptonote::block& block); - virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, uint64_t unlock_time); + virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, bool is_change, uint64_t unlock_time); virtual void on_unconfirmed_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index); virtual void on_money_spent(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& in_tx, uint64_t amount, const cryptonote::transaction& spend_tx, const cryptonote::subaddress_index& subaddr_index); virtual void on_skip_transaction(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx); diff --git a/src/wallet/api/wallet.cpp b/src/wallet/api/wallet.cpp index db165db6d..13abf6273 100644 --- a/src/wallet/api/wallet.cpp +++ b/src/wallet/api/wallet.cpp @@ -157,7 +157,7 @@ struct Wallet2CallbackImpl : public tools::i_wallet2_callback } } - virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, uint64_t unlock_time) + virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, bool is_change, uint64_t unlock_time) { std::string tx_hash = epee::string_tools::pod_to_hex(txid); diff --git a/src/wallet/wallet2.cpp b/src/wallet/wallet2.cpp index 5e5b345dd..4779c3335 100644 --- a/src/wallet/wallet2.cpp +++ b/src/wallet/wallet2.cpp @@ -1869,6 +1869,20 @@ void wallet2::cache_tx_data(const cryptonote::transaction& tx, const crypto::has } } //---------------------------------------------------------------------------------------------------- +bool wallet2::spends_one_of_ours(const cryptonote::transaction &tx) const +{ + for (const auto &in: tx.vin) + { + if (in.type() != typeid(cryptonote::txin_to_key)) + continue; + const cryptonote::txin_to_key &in_to_key = boost::get(in); + auto it = m_key_images.find(in_to_key.k_image); + if (it != m_key_images.end()) + return true; + } + return false; +} +//---------------------------------------------------------------------------------------------------- void wallet2::process_new_transaction(const crypto::hash &txid, const cryptonote::transaction& tx, const std::vector &o_indices, uint64_t height, uint8_t block_version, uint64_t ts, bool miner_tx, bool pool, bool double_spend_seen, const tx_cache_data &tx_cache_data, std::map, size_t> *output_tracker_cache) { PERF_TIMER(process_new_transaction); @@ -2155,7 +2169,7 @@ void wallet2::process_new_transaction(const crypto::hash &txid, const cryptonote } LOG_PRINT_L0("Received money: " << print_money(td.amount()) << ", with tx: " << txid); if (0 != m_callback) - m_callback->on_money_received(height, txid, tx, td.m_amount, td.m_subaddr_index, td.m_tx.unlock_time); + m_callback->on_money_received(height, txid, tx, td.m_amount, td.m_subaddr_index, spends_one_of_ours(tx), td.m_tx.unlock_time); } total_received_1 += amount; notify = true; @@ -2232,7 +2246,7 @@ void wallet2::process_new_transaction(const crypto::hash &txid, const cryptonote LOG_PRINT_L0("Received money: " << print_money(td.amount()) << ", with tx: " << txid); if (0 != m_callback) - m_callback->on_money_received(height, txid, tx, td.m_amount, td.m_subaddr_index, td.m_tx.unlock_time); + m_callback->on_money_received(height, txid, tx, td.m_amount, td.m_subaddr_index, spends_one_of_ours(tx), td.m_tx.unlock_time); } total_received_1 += extra_amount; notify = true; diff --git a/src/wallet/wallet2.h b/src/wallet/wallet2.h index eb33713b5..3a14215b3 100644 --- a/src/wallet/wallet2.h +++ b/src/wallet/wallet2.h @@ -131,7 +131,7 @@ private: public: // Full wallet callbacks virtual void on_new_block(uint64_t height, const cryptonote::block& block) {} - virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, uint64_t unlock_time) {} + virtual void on_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index, bool is_change, uint64_t unlock_time) {} virtual void on_unconfirmed_money_received(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx, uint64_t amount, const cryptonote::subaddress_index& subaddr_index) {} virtual void on_money_spent(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& in_tx, uint64_t amount, const cryptonote::transaction& spend_tx, const cryptonote::subaddress_index& subaddr_index) {} virtual void on_skip_transaction(uint64_t height, const crypto::hash &txid, const cryptonote::transaction& tx) {} @@ -1517,6 +1517,7 @@ private: void check_rpc_cost(const char *call, uint64_t post_call_credits, uint64_t pre_credits, double expected_cost); bool should_expand(const cryptonote::subaddress_index &index) const; + bool spends_one_of_ours(const cryptonote::transaction &tx) const; cryptonote::account_base m_account; boost::optional m_daemon_login; -- 2.25.1 From febb8df4bbd60f8a7b2992d20b6d6d5f0a31759b Mon Sep 17 00:00:00 2001 From: moneromooo-monero Date: Wed, 13 May 2020 13:38:32 +0000 Subject: [PATCH 3/5] blockchain: fix theoretical race getting bulk timestamps --- src/cryptonote_core/blockchain.cpp | 1 + 1 file changed, 1 insertion(+) diff --git a/src/cryptonote_core/blockchain.cpp b/src/cryptonote_core/blockchain.cpp index d73313356..e8e6564ac 100644 --- a/src/cryptonote_core/blockchain.cpp +++ b/src/cryptonote_core/blockchain.cpp @@ -916,6 +916,7 @@ difficulty_type Blockchain::get_difficulty_for_next_block() //------------------------------------------------------------------ std::vector Blockchain::get_last_block_timestamps(unsigned int blocks) const { + CRITICAL_REGION_LOCAL(m_blockchain_lock); uint64_t height = m_db->height(); if (blocks > height) blocks = height; -- 2.25.1 From 4c757a7a2aa3cf2f0e77f9b11322641890dbc7d5 Mon Sep 17 00:00:00 2001 From: Lee Clagett Date: Tue, 12 May 2020 01:26:37 -0400 Subject: [PATCH 4/5] Fixed bugs for take_slice and byte_stream->byte_slice --- contrib/epee/src/byte_slice.cpp | 26 +++++++++++++++++--------- tests/unit_tests/epee_utils.cpp | 31 +++++++++++++++++++++++++++++++ 2 files changed, 48 insertions(+), 9 deletions(-) diff --git a/contrib/epee/src/byte_slice.cpp b/contrib/epee/src/byte_slice.cpp index 99c37fae3..12cc83e6c 100644 --- a/contrib/epee/src/byte_slice.cpp +++ b/contrib/epee/src/byte_slice.cpp @@ -173,9 +173,14 @@ namespace epee byte_slice::byte_slice(byte_stream&& stream) noexcept : storage_(nullptr), portion_(stream.data(), stream.size()) { - std::uint8_t* const data = stream.take_buffer().release() - sizeof(raw_byte_slice); - new (data) raw_byte_slice{}; - storage_.reset(reinterpret_cast(data)); + if (stream.size()) + { + std::uint8_t* const data = stream.take_buffer().release() - sizeof(raw_byte_slice); + new (data) raw_byte_slice{}; + storage_.reset(reinterpret_cast(data)); + } + else + portion_ = nullptr; } byte_slice::byte_slice(byte_slice&& source) noexcept @@ -205,14 +210,17 @@ namespace epee byte_slice byte_slice::take_slice(const std::size_t max_bytes) noexcept { byte_slice out{}; - std::uint8_t const* const ptr = data(); - out.portion_ = {ptr, portion_.remove_prefix(max_bytes)}; - if (portion_.empty()) - out.storage_ = std::move(storage_); // no atomic inc/dec - else - out = {storage_.get(), out.portion_}; + if (max_bytes) + { + std::uint8_t const* const ptr = data(); + out.portion_ = {ptr, portion_.remove_prefix(max_bytes)}; + if (portion_.empty()) + out.storage_ = std::move(storage_); // no atomic inc/dec + else + out = {storage_.get(), out.portion_}; + } return out; } diff --git a/tests/unit_tests/epee_utils.cpp b/tests/unit_tests/epee_utils.cpp index 2e93f9e67..a2cec965e 100644 --- a/tests/unit_tests/epee_utils.cpp +++ b/tests/unit_tests/epee_utils.cpp @@ -667,6 +667,23 @@ TEST(ByteSlice, TakeSlice) EXPECT_TRUE(boost::range::equal(base_string, slice)); const epee::span original = epee::to_span(slice); + const epee::byte_slice empty_slice = slice.take_slice(0); + EXPECT_EQ(original.begin(), slice.begin()); + EXPECT_EQ(slice.begin(), slice.cbegin()); + EXPECT_EQ(original.end(), slice.end()); + EXPECT_EQ(slice.end(), slice.cend()); + + EXPECT_EQ(nullptr, empty_slice.begin()); + EXPECT_EQ(nullptr, empty_slice.cbegin()); + EXPECT_EQ(nullptr, empty_slice.end()); + EXPECT_EQ(nullptr, empty_slice.cend()); + EXPECT_EQ(nullptr, empty_slice.data()); + EXPECT_TRUE(empty_slice.empty()); + EXPECT_EQ(0u, empty_slice.size()); + + EXPECT_FALSE(slice.empty()); + EXPECT_EQ(slice.cbegin(), slice.data()); + const epee::byte_slice slice2 = slice.take_slice(remove_size); EXPECT_EQ(original.begin() + remove_size, slice.begin()); @@ -1061,6 +1078,20 @@ TEST(ByteStream, ToByteSlice) EXPECT_EQ(nullptr, stream.data()); EXPECT_EQ(nullptr, stream.tellp()); EXPECT_TRUE(equal(source, slice)); + + stream = epee::byte_stream{}; + stream.reserve(1); + EXPECT_NE(nullptr, stream.data()); + EXPECT_NE(nullptr, stream.tellp()); + + const epee::byte_slice empty_slice{std::move(stream)}; + EXPECT_TRUE(empty_slice.empty()); + EXPECT_EQ(0u, empty_slice.size()); + EXPECT_EQ(nullptr, empty_slice.begin()); + EXPECT_EQ(nullptr, empty_slice.cbegin()); + EXPECT_EQ(nullptr, empty_slice.end()); + EXPECT_EQ(nullptr, empty_slice.cend()); + EXPECT_EQ(nullptr, empty_slice.data()); } TEST(ToHex, String) -- 2.25.1 From 87dcc37776bdaab2412912772fcee1e641a4ac33 Mon Sep 17 00:00:00 2001 From: wowario Date: Thu, 14 May 2020 12:37:05 +0300 Subject: [PATCH 5/5] switch to SHA-3 PoW Co-authored-by: fuwa --- src/crypto/CMakeLists.txt | 1 + src/crypto/hash-ops.h | 1 + src/crypto/hash.h | 4 +++ src/crypto/sha3.c | 29 +++++++++++++++++++++ src/cryptonote_basic/cryptonote_basic.h | 16 ++++++++++-- src/cryptonote_basic/miner.cpp | 8 +++--- src/cryptonote_basic/miner.h | 2 +- src/cryptonote_config.h | 1 + src/cryptonote_core/blockchain.cpp | 2 +- src/cryptonote_core/cryptonote_tx_utils.cpp | 6 ++++- src/hardforks/hardforks.cpp | 1 + src/rpc/core_rpc_server.cpp | 9 ++++--- src/rpc/core_rpc_server_commands_defs.h | 18 ++++++++++--- src/rpc/message_data_structs.h | 2 +- src/rpc/rpc_payment.cpp | 4 +-- src/rpc/rpc_payment.h | 2 +- src/wallet/wallet2.h | 2 +- src/wallet/wallet_rpc_payments.cpp | 4 +-- 18 files changed, 89 insertions(+), 23 deletions(-) create mode 100644 src/crypto/sha3.c diff --git a/src/crypto/CMakeLists.txt b/src/crypto/CMakeLists.txt index 80f1e5d7e..61de31cb2 100644 --- a/src/crypto/CMakeLists.txt +++ b/src/crypto/CMakeLists.txt @@ -42,6 +42,7 @@ set(crypto_sources hmac-keccak.c jh.c keccak.c + sha3.c oaes_lib.c random.c skein.c diff --git a/src/crypto/hash-ops.h b/src/crypto/hash-ops.h index 2fa558aee..79b176cc5 100644 --- a/src/crypto/hash-ops.h +++ b/src/crypto/hash-ops.h @@ -85,6 +85,7 @@ void hash_extra_blake(const void *data, size_t length, char *hash); void hash_extra_groestl(const void *data, size_t length, char *hash); void hash_extra_jh(const void *data, size_t length, char *hash); void hash_extra_skein(const void *data, size_t length, char *hash); +void sha3(const void *data, size_t length, char *hash); void tree_hash(const char (*hashes)[HASH_SIZE], size_t count, char *root_hash); diff --git a/src/crypto/hash.h b/src/crypto/hash.h index 27184fa53..93ffdc9ec 100644 --- a/src/crypto/hash.h +++ b/src/crypto/hash.h @@ -73,6 +73,10 @@ namespace crypto { inline void cn_slow_hash(const void *data, std::size_t length, hash &hash, int variant = 0, uint64_t height = 0) { cn_slow_hash(data, length, reinterpret_cast(&hash), variant, 0/*prehashed*/, height); } + + inline void sha3(const void *data, std::size_t length, hash &hash) { + sha3(data, length, reinterpret_cast(&hash)); + } inline void cn_slow_hash_prehashed(const void *data, std::size_t length, hash &hash, int variant = 0, uint64_t height = 0) { cn_slow_hash(data, length, reinterpret_cast(&hash), variant, 1/*prehashed*/, height); diff --git a/src/crypto/sha3.c b/src/crypto/sha3.c new file mode 100644 index 000000000..e5bb62ace --- /dev/null +++ b/src/crypto/sha3.c @@ -0,0 +1,29 @@ +#include +#include + +void handleErrors(void) { + printf("sha3 error, wow is ded\n"); + exit(1); +} + +void sha3(const void *data, size_t length, char *hash) +{ + EVP_MD_CTX *mdctx; + + if((mdctx = EVP_MD_CTX_new()) == NULL) { + handleErrors(); + } + + if(1 != EVP_DigestInit_ex(mdctx, EVP_sha3_256(), NULL)) { + handleErrors(); + } + + if(1 != EVP_DigestUpdate(mdctx, data, length)) { + handleErrors(); + } + + /* the digest context ctx is automatically cleaned up. */ + if(1 != EVP_DigestFinal(mdctx, (unsigned char*)hash, NULL)) { + handleErrors(); + } +} diff --git a/src/cryptonote_basic/cryptonote_basic.h b/src/cryptonote_basic/cryptonote_basic.h index e2286ae8c..feaa6610a 100644 --- a/src/cryptonote_basic/cryptonote_basic.h +++ b/src/cryptonote_basic/cryptonote_basic.h @@ -449,14 +449,26 @@ namespace cryptonote uint8_t minor_version; // now used as a voting mechanism, rather than how this particular block is built uint64_t timestamp; crypto::hash prev_id; - uint32_t nonce; + uint64_t nonce; BEGIN_SERIALIZE() VARINT_FIELD(major_version) VARINT_FIELD(minor_version) VARINT_FIELD(timestamp) FIELD(prev_id) - FIELD(nonce) + if (major_version >= HF_VERSION_SHA3_POW) + { + FIELD(nonce) + } + else + { + uint32_t nonce32; + if (typename Archive::is_saving()) + nonce32 = (uint32_t)nonce; + FIELD_N("nonce", nonce32); + if (!typename Archive::is_saving()) + nonce = nonce32; + } END_SERIALIZE() }; diff --git a/src/cryptonote_basic/miner.cpp b/src/cryptonote_basic/miner.cpp index c1e8365ac..c3c5cf0af 100644 --- a/src/cryptonote_basic/miner.cpp +++ b/src/cryptonote_basic/miner.cpp @@ -144,7 +144,7 @@ namespace cryptonote m_height = height; m_block_reward = block_reward; ++m_template_no; - m_starter_nonce = crypto::rand(); + m_starter_nonce = crypto::rand(); return true; } //----------------------------------------------------------------------------------------------------- @@ -375,7 +375,7 @@ namespace cryptonote m_threads_autodetect.push_back({epee::misc_utils::get_ns_count(), m_total_hashes}); m_threads_total = 1; } - m_starter_nonce = crypto::rand(); + m_starter_nonce = crypto::rand(); CRITICAL_REGION_LOCAL(m_threads_lock); if(is_mining()) { @@ -473,7 +473,7 @@ namespace cryptonote //----------------------------------------------------------------------------------------------------- bool miner::find_nonce_for_given_block(const get_block_hash_t &gbh, block& bl, const difficulty_type& diffic, uint64_t height) { - for(; bl.nonce != std::numeric_limits::max(); bl.nonce++) + for(; bl.nonce != std::numeric_limits::max(); bl.nonce++) { crypto::hash h; gbh(bl, height, diffic <= 100 ? 0 : tools::get_max_concurrency(), h); @@ -524,7 +524,7 @@ namespace cryptonote uint32_t th_local_index = boost::interprocess::ipcdetail::atomic_inc32(&m_thread_index); MLOG_SET_THREAD_NAME(std::string("[miner ") + std::to_string(th_local_index) + "]"); MGINFO("Miner thread was started ["<< th_local_index << "]"); - uint32_t nonce = m_starter_nonce + th_local_index; + uint64_t nonce = m_starter_nonce + th_local_index; uint64_t height = 0; difficulty_type local_diff = 0; uint32_t local_template_ver = 0; diff --git a/src/cryptonote_basic/miner.h b/src/cryptonote_basic/miner.h index ce50d674e..5ab865cea 100644 --- a/src/cryptonote_basic/miner.h +++ b/src/cryptonote_basic/miner.h @@ -123,7 +123,7 @@ namespace cryptonote epee::critical_section m_template_lock; block m_template; std::atomic m_template_no; - std::atomic m_starter_nonce; + std::atomic m_starter_nonce; difficulty_type m_diffic; uint64_t m_height; volatile uint32_t m_thread_index; diff --git a/src/cryptonote_config.h b/src/cryptonote_config.h index f97439ff6..50b5e1db0 100644 --- a/src/cryptonote_config.h +++ b/src/cryptonote_config.h @@ -178,6 +178,7 @@ #define HF_VERSION_REJECT_SIGS_IN_COINBASE 15 #define HF_VERSION_ENFORCE_MIN_AGE 15 #define HF_VERSION_EFFECTIVE_SHORT_TERM_MEDIAN_IN_PENALTY 15 +#define HF_VERSION_SHA3_POW 16 // Block 288,888 ~8 February 2021 #define PER_KB_FEE_QUANTIZATION_DECIMALS 8 diff --git a/src/cryptonote_core/blockchain.cpp b/src/cryptonote_core/blockchain.cpp index d73313356..dfb4e9098 100644 --- a/src/cryptonote_core/blockchain.cpp +++ b/src/cryptonote_core/blockchain.cpp @@ -1760,7 +1760,7 @@ bool Blockchain::handle_alternative_block(const block& b, const crypto::hash& id CHECK_AND_ASSERT_MES(current_diff, false, "!!!!!!! DIFFICULTY OVERHEAD !!!!!!!"); crypto::hash proof_of_work; memset(proof_of_work.data, 0xff, sizeof(proof_of_work.data)); - if (b.major_version >= RX_BLOCK_VERSION) + if (b.major_version >= RX_BLOCK_VERSION && b.major_version < HF_VERSION_SHA3_POW) { crypto::hash seedhash = null_hash; uint64_t seedheight = rx_seedheight(bei.height); diff --git a/src/cryptonote_core/cryptonote_tx_utils.cpp b/src/cryptonote_core/cryptonote_tx_utils.cpp index 5edfd76df..6c2baeb72 100644 --- a/src/cryptonote_core/cryptonote_tx_utils.cpp +++ b/src/cryptonote_core/cryptonote_tx_utils.cpp @@ -681,7 +681,11 @@ namespace cryptonote bool get_block_longhash(const Blockchain *pbc, const block& b, crypto::hash& res, const uint64_t height, const int miners) { blobdata bd = get_block_hashing_blob(b); - if (b.major_version >= RX_BLOCK_VERSION) + if (b.major_version >= HF_VERSION_SHA3_POW) + { + crypto::sha3(bd.data(), bd.size(), res); + } + else if (b.major_version >= RX_BLOCK_VERSION && b.major_version < HF_VERSION_SHA3_POW) { uint64_t seed_height, main_height; crypto::hash hash; diff --git a/src/hardforks/hardforks.cpp b/src/hardforks/hardforks.cpp index 861a0c377..fd30a37e7 100644 --- a/src/hardforks/hardforks.cpp +++ b/src/hardforks/hardforks.cpp @@ -41,6 +41,7 @@ const hardfork_t mainnet_hard_forks[] = { { 13, 114969, 0, 1559292691 }, { 14, 115257, 0, 1559292774 }, { 15, 160777, 0, 1573280497 }, + { 16, 288888, 0, 1589210508 }, }; const size_t num_mainnet_hard_forks = sizeof(mainnet_hard_forks) / sizeof(mainnet_hard_forks[0]); diff --git a/src/rpc/core_rpc_server.cpp b/src/rpc/core_rpc_server.cpp index 4c709b115..abb0e37c0 100644 --- a/src/rpc/core_rpc_server.cpp +++ b/src/rpc/core_rpc_server.cpp @@ -1261,7 +1261,7 @@ namespace cryptonote if (lMiner.is_mining() || lMiner.get_is_background_mining_enabled()) res.address = get_account_address_as_str(nettype(), false, lMiningAdr); const uint8_t major_version = m_core.get_blockchain_storage().get_current_hard_fork_version(); - const unsigned variant = major_version >= 13 ? 6 : major_version >= 11 && major_version <= 12 ? 4 : 2; + const unsigned variant = major_version >= HF_VERSION_SHA3_POW ? 7 : major_version >= 13 && major_version < HF_VERSION_SHA3_POW ? 6 : major_version >= 11 && major_version <= 12 ? 4 : 2; switch (variant) { case 0: res.pow_algorithm = "Cryptonight"; break; @@ -1269,6 +1269,7 @@ namespace cryptonote case 2: case 3: res.pow_algorithm = "CNv2 (Cryptonight variant 2)"; break; case 4: case 5: res.pow_algorithm = "CN/WOW"; break; case 6: res.pow_algorithm = "RandomWOW"; break; + case 7: res.pow_algorithm = "SHA-3"; break; default: res.pow_algorithm = "I'm not sure actually"; break; } if (res.is_background_mining_enabled) @@ -1621,7 +1622,7 @@ namespace cryptonote return false; } - if (b.major_version >= RX_BLOCK_VERSION) + if (b.major_version >= RX_BLOCK_VERSION && b.major_version < HF_VERSION_SHA3_POW) { uint64_t next_height; crypto::rx_seedheights(height, &seed_height, &next_height); @@ -1736,7 +1737,7 @@ namespace cryptonote crypto::hash seed_hash, next_seed_hash; if (!get_block_template(info.address, req.prev_block.empty() ? NULL : &prev_block, blob_reserve, reserved_offset, wdiff, res.height, res.expected_reward, b, res.seed_height, seed_hash, next_seed_hash, error_resp)) return false; - if (b.major_version >= RX_BLOCK_VERSION) + if (b.major_version >= RX_BLOCK_VERSION && b.major_version < HF_VERSION_SHA3_POW) { res.seed_hash = string_tools::pod_to_hex(seed_hash); if (seed_hash != next_seed_hash) @@ -3017,7 +3018,7 @@ namespace cryptonote } res.hashing_blob = epee::string_tools::buff_to_hex_nodelimer(hashing_blob); res.top_hash = epee::string_tools::pod_to_hex(top_hash); - if (hashing_blob[0] >= RX_BLOCK_VERSION) + if (hashing_blob[0] >= RX_BLOCK_VERSION && hashing_blob[0] < HF_VERSION_SHA3_POW) { res.seed_hash = string_tools::pod_to_hex(seed_hash); if (seed_hash != next_seed_hash) diff --git a/src/rpc/core_rpc_server_commands_defs.h b/src/rpc/core_rpc_server_commands_defs.h index 8552807f7..7e7858b95 100644 --- a/src/rpc/core_rpc_server_commands_defs.h +++ b/src/rpc/core_rpc_server_commands_defs.h @@ -984,7 +984,7 @@ namespace cryptonote uint8_t minor_version; uint64_t timestamp; std::string prev_hash; - uint32_t nonce; + uint64_t nonce; bool orphan_status; uint64_t height; uint64_t depth; @@ -1008,7 +1008,19 @@ namespace cryptonote KV_SERIALIZE(minor_version) KV_SERIALIZE(timestamp) KV_SERIALIZE(prev_hash) - KV_SERIALIZE(nonce) + if (this_ref.major_version >= HF_VERSION_SHA3_POW) + { + KV_SERIALIZE(nonce) + } + else + { + uint32_t nonce32; + if (is_store) + nonce32 = (uint32_t)this_ref.nonce; + epee::serialization::selector::serialize(nonce32, stg, hparent_section, "nonce"); + if (!is_store) + const_cast(this_ref.nonce) = nonce32; + } KV_SERIALIZE(orphan_status) KV_SERIALIZE(height) KV_SERIALIZE(depth) @@ -2350,7 +2362,7 @@ namespace cryptonote { struct request_t: public rpc_access_request_base { - uint32_t nonce; + uint64_t nonce; uint32_t cookie; BEGIN_KV_SERIALIZE_MAP() diff --git a/src/rpc/message_data_structs.h b/src/rpc/message_data_structs.h index e64f5f163..d4b018dbe 100644 --- a/src/rpc/message_data_structs.h +++ b/src/rpc/message_data_structs.h @@ -163,7 +163,7 @@ namespace rpc uint64_t minor_version; uint64_t timestamp; crypto::hash prev_id; - uint32_t nonce; + uint64_t nonce; uint64_t height; uint64_t depth; crypto::hash hash; diff --git a/src/rpc/rpc_payment.cpp b/src/rpc/rpc_payment.cpp index 2b9c19f57..741d92812 100644 --- a/src/rpc/rpc_payment.cpp +++ b/src/rpc/rpc_payment.cpp @@ -178,7 +178,7 @@ namespace cryptonote return true; } - bool rpc_payment::submit_nonce(const crypto::public_key &client, uint32_t nonce, const crypto::hash &top, int64_t &error_code, std::string &error_message, uint64_t &credits, crypto::hash &hash, cryptonote::block &block, uint32_t cookie, bool &stale) + bool rpc_payment::submit_nonce(const crypto::public_key &client, uint64_t nonce, const crypto::hash &top, int64_t &error_code, std::string &error_message, uint64_t &credits, crypto::hash &hash, cryptonote::block &block, uint32_t cookie, bool &stale) { client_info &info = m_client_info[client]; // creates if not found if (cookie != info.cookie && cookie != info.cookie - 1) @@ -231,7 +231,7 @@ namespace cryptonote block = is_current ? info.block : info.previous_block; *(uint32_t*)(hashing_blob.data() + 39) = SWAP32LE(nonce); - if (block.major_version >= RX_BLOCK_VERSION) + if (block.major_version >= RX_BLOCK_VERSION && block.major_version < HF_VERSION_SHA3_POW) { const uint64_t seed_height = is_current ? info.seed_height : info.previous_seed_height; const crypto::hash &seed_hash = is_current ? info.seed_hash : info.previous_seed_hash; diff --git a/src/rpc/rpc_payment.h b/src/rpc/rpc_payment.h index f6832fd34..559736cf6 100644 --- a/src/rpc/rpc_payment.h +++ b/src/rpc/rpc_payment.h @@ -102,7 +102,7 @@ namespace cryptonote uint64_t balance(const crypto::public_key &client, int64_t delta = 0); bool pay(const crypto::public_key &client, uint64_t ts, uint64_t payment, const std::string &rpc, bool same_ts, uint64_t &credits); bool get_info(const crypto::public_key &client, const std::function &get_block_template, cryptonote::blobdata &hashing_blob, uint64_t &seed_height, crypto::hash &seed_hash, const crypto::hash &top, uint64_t &diff, uint64_t &credits_per_hash_found, uint64_t &credits, uint32_t &cookie); - bool submit_nonce(const crypto::public_key &client, uint32_t nonce, const crypto::hash &top, int64_t &error_code, std::string &error_message, uint64_t &credits, crypto::hash &hash, cryptonote::block &block, uint32_t cookie, bool &stale); + bool submit_nonce(const crypto::public_key &client, uint64_t nonce, const crypto::hash &top, int64_t &error_code, std::string &error_message, uint64_t &credits, crypto::hash &hash, cryptonote::block &block, uint32_t cookie, bool &stale); const cryptonote::account_public_address &get_payment_address() const { return m_address; } bool foreach(const std::function &f) const; unsigned int flush_by_age(time_t seconds = 0); diff --git a/src/wallet/wallet2.h b/src/wallet/wallet2.h index eb33713b5..358e18e8e 100644 --- a/src/wallet/wallet2.h +++ b/src/wallet/wallet2.h @@ -1276,7 +1276,7 @@ private: bool get_rpc_payment_info(bool mining, bool &payment_required, uint64_t &credits, uint64_t &diff, uint64_t &credits_per_hash_found, cryptonote::blobdata &hashing_blob, uint64_t &height, uint64_t &seed_height, crypto::hash &seed_hash, crypto::hash &next_seed_hash, uint32_t &cookie); bool daemon_requires_payment(); - bool make_rpc_payment(uint32_t nonce, uint32_t cookie, uint64_t &credits, uint64_t &balance); + bool make_rpc_payment(uint64_t nonce, uint32_t cookie, uint64_t &credits, uint64_t &balance); bool search_for_rpc_payment(uint64_t credits_target, const std::function &startfunc, const std::function &contfunc, const std::function &foundfunc = NULL, const std::function &errorfunc = NULL); template void handle_payment_changes(const T &res, std::true_type) { if (res.status == CORE_RPC_STATUS_OK || res.status == CORE_RPC_STATUS_PAYMENT_REQUIRED) diff --git a/src/wallet/wallet_rpc_payments.cpp b/src/wallet/wallet_rpc_payments.cpp index 4f5364269..5e79e5e46 100644 --- a/src/wallet/wallet_rpc_payments.cpp +++ b/src/wallet/wallet_rpc_payments.cpp @@ -75,7 +75,7 @@ bool wallet2::daemon_requires_payment() return get_rpc_payment_info(false, payment_required, credits, diff, credits_per_hash_found, blob, height, seed_height, seed_hash, next_seed_hash, cookie) && payment_required; } //---------------------------------------------------------------------------------------------------- -bool wallet2::make_rpc_payment(uint32_t nonce, uint32_t cookie, uint64_t &credits, uint64_t &balance) +bool wallet2::make_rpc_payment(uint64_t nonce, uint32_t cookie, uint64_t &credits, uint64_t &balance) { cryptonote::COMMAND_RPC_ACCESS_SUBMIT_NONCE::request req = AUTO_VAL_INIT(req); cryptonote::COMMAND_RPC_ACCESS_SUBMIT_NONCE::response res = AUTO_VAL_INIT(res); @@ -143,7 +143,7 @@ bool wallet2::search_for_rpc_payment(uint64_t credits_target, const std::functio const uint32_t local_nonce = nonce++; // wrapping's OK *(uint32_t*)(hashing_blob.data() + 39) = SWAP32LE(local_nonce); const uint8_t major_version = hashing_blob[0]; - if (major_version >= RX_BLOCK_VERSION) + if (major_version >= RX_BLOCK_VERSION && major_version < HF_VERSION_SHA3_POW) { const int miners = 1; crypto::rx_slow_hash(height, seed_height, seed_hash.data, hashing_blob.data(), hashing_blob.size(), hash.data, miners, 0); -- 2.25.1