From c51ca53daaefc432f17a9c73406ea7772f09aba6 Mon Sep 17 00:00:00 2001 From: tobtoht Date: Wed, 14 Aug 2024 16:13:35 +0200 Subject: [PATCH 1/5] epee: string_tools: remove dot from get_extension Fixes a regression introduced in #9254. Previously it did not include the dot. --- contrib/epee/src/string_tools.cpp | 7 ++++++- tests/unit_tests/epee_utils.cpp | 8 ++++++++ 2 files changed, 14 insertions(+), 1 deletion(-) diff --git a/contrib/epee/src/string_tools.cpp b/contrib/epee/src/string_tools.cpp index 525af1c46..aeb490d5d 100644 --- a/contrib/epee/src/string_tools.cpp +++ b/contrib/epee/src/string_tools.cpp @@ -178,7 +178,12 @@ namespace string_tools std::string get_extension(const std::string& str) { - return boost::filesystem::path(str).extension().string(); + std::string ext_with_dot = boost::filesystem::path(str).extension().string(); + + if (ext_with_dot.empty()) + return {}; + + return ext_with_dot.erase(0, 1); } //---------------------------------------------------------------------------- diff --git a/tests/unit_tests/epee_utils.cpp b/tests/unit_tests/epee_utils.cpp index 31bdc698d..46b27d85b 100644 --- a/tests/unit_tests/epee_utils.cpp +++ b/tests/unit_tests/epee_utils.cpp @@ -1443,6 +1443,14 @@ TEST(StringTools, GetIpInt32) EXPECT_EQ(htonl(0xff0aff00), ip); } +TEST(StringTools, GetExtension) +{ + EXPECT_EQ(std::string{}, epee::string_tools::get_extension("")); + EXPECT_EQ(std::string{}, epee::string_tools::get_extension(".")); + EXPECT_EQ(std::string{"keys"}, epee::string_tools::get_extension("wallet.keys")); + EXPECT_EQ(std::string{"3"}, epee::string_tools::get_extension("1.2.3")); +} + TEST(NetUtils, IPv4NetworkAddress) { static_assert(epee::net_utils::ipv4_network_address::get_type_id() == epee::net_utils::address_type::ipv4, "bad ipv4 type id"); From 89ad8ac8b1307788940966aa373526153f2191d8 Mon Sep 17 00:00:00 2001 From: tobtoht Date: Wed, 14 Aug 2024 19:45:55 +0200 Subject: [PATCH 2/5] epee: string_tools: keep full path in cut_off_extension --- contrib/epee/src/string_tools.cpp | 2 +- tests/unit_tests/epee_utils.cpp | 7 +++++++ 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/contrib/epee/src/string_tools.cpp b/contrib/epee/src/string_tools.cpp index aeb490d5d..36356d77e 100644 --- a/contrib/epee/src/string_tools.cpp +++ b/contrib/epee/src/string_tools.cpp @@ -189,7 +189,7 @@ namespace string_tools //---------------------------------------------------------------------------- std::string cut_off_extension(const std::string& str) { - return boost::filesystem::path(str).stem().string(); + return boost::filesystem::path(str).replace_extension("").string(); } #ifdef _WIN32 diff --git a/tests/unit_tests/epee_utils.cpp b/tests/unit_tests/epee_utils.cpp index 46b27d85b..64ed83694 100644 --- a/tests/unit_tests/epee_utils.cpp +++ b/tests/unit_tests/epee_utils.cpp @@ -1451,6 +1451,13 @@ TEST(StringTools, GetExtension) EXPECT_EQ(std::string{"3"}, epee::string_tools::get_extension("1.2.3")); } +TEST(StringTools, CutOffExtension) +{ + EXPECT_EQ(std::string{}, epee::string_tools::cut_off_extension("")); + EXPECT_EQ(std::string{"/home/user/Monero/wallets/wallet"}, epee::string_tools::cut_off_extension("/home/user/Monero/wallets/wallet")); + EXPECT_EQ(std::string{"/home/user/Monero/wallets/wallet"}, epee::string_tools::cut_off_extension("/home/user/Monero/wallets/wallet.keys")); +} + TEST(NetUtils, IPv4NetworkAddress) { static_assert(epee::net_utils::ipv4_network_address::get_type_id() == epee::net_utils::address_type::ipv4, "bad ipv4 type id"); From ed955bf751e304569cd4c04f558360154e19610e Mon Sep 17 00:00:00 2001 From: jeffro256 Date: Fri, 23 Aug 2024 12:15:17 -0500 Subject: [PATCH 3/5] build: fix build with Boost 1.85 and remove instances of viewkey logging 1. Use `std::is_standard_layout` and `std::is_trivially_copyable` instead of `std::is_pod` for KV byte-wise serialization, which fixes compile issue for Boost UUIDs 2. Use `std::has_unique_object_representations` instead of `alignof(T) == 1` for epee byte spans and epee hex functions 3. Removed reimplementation of `std::hash` for `boost::uuids::uuid 4. Removed `<<` operator overload for `crypto::secret_key` 5. Removed instances in code where private view key was dumped to the log in plaintext --- CMakeLists.txt | 1 + .../serialization/keyvalue_serialization.h | 18 ++++++++++-------- contrib/epee/include/span.h | 19 +++++++++---------- contrib/epee/include/string_tools.h | 2 ++ src/crypto/crypto.h | 14 +++++++++++--- .../cryptonote_format_utils.cpp | 4 ++-- src/cryptonote_core/cryptonote_tx_utils.cpp | 4 ++-- src/cryptonote_protocol/block_queue.cpp | 13 ++----------- src/device/device_default.cpp | 8 +++++--- src/lmdb/util.h | 4 ++-- src/simplewallet/simplewallet.cpp | 4 ++-- src/wallet/api/wallet.cpp | 8 ++++---- src/wallet/wallet2.cpp | 2 +- src/wallet/wallet_rpc_server.cpp | 4 ++-- tests/benchmark.cpp | 2 +- tests/core_tests/multisig.cpp | 10 +++++----- tests/functional_tests/make_test_signature.cc | 2 +- tests/unit_tests/crypto.cpp | 2 +- tests/unit_tests/multisig.cpp | 2 +- tests/unit_tests/serialization.cpp | 2 +- 20 files changed, 65 insertions(+), 60 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 97d6aee81..78350338d 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1091,6 +1091,7 @@ endif() find_package(Boost 1.58 QUIET REQUIRED COMPONENTS ${BOOST_COMPONENTS}) add_definitions(-DBOOST_ASIO_ENABLE_SEQUENTIAL_STRAND_ALLOCATION) add_definitions(-DBOOST_NO_AUTO_PTR) +add_definitions(-DBOOST_UUID_DISABLE_ALIGNMENT) # This restores UUID's std::has_unique_object_representations property set(CMAKE_FIND_LIBRARY_SUFFIXES ${OLD_LIB_SUFFIXES}) if(NOT Boost_FOUND) diff --git a/contrib/epee/include/serialization/keyvalue_serialization.h b/contrib/epee/include/serialization/keyvalue_serialization.h index ea767865c..ccfa2f15e 100644 --- a/contrib/epee/include/serialization/keyvalue_serialization.h +++ b/contrib/epee/include/serialization/keyvalue_serialization.h @@ -98,16 +98,18 @@ public: \ #define KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(varialble, val_name) \ epee::serialization::selector::serialize_t_val_as_blob(this_ref.varialble, stg, hparent_section, val_name); -#define KV_SERIALIZE_VAL_POD_AS_BLOB_N(varialble, val_name) \ - static_assert(std::is_pod::value, "t_type must be a POD type."); \ - KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(varialble, val_name) +#define KV_SERIALIZE_VAL_POD_AS_BLOB_N(variable, val_name) \ + static_assert(std::is_trivially_copyable_v, "t_type must be a trivially copyable type."); \ + static_assert(std::is_standard_layout_v, "t_type must be a standard layout type."); \ + KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(variable, val_name) -#define KV_SERIALIZE_VAL_POD_AS_BLOB_OPT_N(varialble, val_name, default_value) \ +#define KV_SERIALIZE_VAL_POD_AS_BLOB_OPT_N(variable, val_name, default_value) \ do { \ - static_assert(std::is_pod::value, "t_type must be a POD type."); \ - bool ret = KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(varialble, val_name) \ + static_assert(std::is_trivially_copyable_v, "t_type must be a trivially copyable type."); \ + static_assert(std::is_standard_layout_v, "t_type must be a standard layout type."); \ + bool ret = KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(variable, val_name) \ if (!ret) \ - epee::serialize_default(this_ref.varialble, default_value); \ + epee::serialize_default(this_ref.variable, default_value); \ } while(0); #define KV_SERIALIZE_CONTAINER_POD_AS_BLOB_N(varialble, val_name) \ @@ -118,7 +120,7 @@ public: \ #define KV_SERIALIZE(varialble) KV_SERIALIZE_N(varialble, #varialble) #define KV_SERIALIZE_VAL_POD_AS_BLOB(varialble) KV_SERIALIZE_VAL_POD_AS_BLOB_N(varialble, #varialble) #define KV_SERIALIZE_VAL_POD_AS_BLOB_OPT(varialble, def) KV_SERIALIZE_VAL_POD_AS_BLOB_OPT_N(varialble, #varialble, def) -#define KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE(varialble) KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(varialble, #varialble) //skip is_pod compile time check +#define KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE(varialble) KV_SERIALIZE_VAL_POD_AS_BLOB_FORCE_N(varialble, #varialble) //skip is_trivially_copyable and is_standard_layout compile time check #define KV_SERIALIZE_CONTAINER_POD_AS_BLOB(varialble) KV_SERIALIZE_CONTAINER_POD_AS_BLOB_N(varialble, #varialble) #define KV_SERIALIZE_OPT(variable,default_value) KV_SERIALIZE_OPT_N(variable, #variable, default_value) diff --git a/contrib/epee/include/span.h b/contrib/epee/include/span.h index c11e6dd2b..af02d4634 100644 --- a/contrib/epee/include/span.h +++ b/contrib/epee/include/span.h @@ -133,17 +133,13 @@ namespace epee return {src.data(), src.size()}; } - template - constexpr bool has_padding() noexcept - { - return !std::is_standard_layout() || alignof(T) != 1; - } - //! \return Cast data from `src` as `span`. template span to_byte_span(const span src) noexcept { - static_assert(!has_padding(), "source type may have padding"); + static_assert(!std::is_empty(), "empty value types will not work -> sizeof == 1"); + static_assert(std::is_standard_layout_v, "type must have standard layout"); + static_assert(std::has_unique_object_representations_v, "type must be trivially copyable with no padding"); return {reinterpret_cast(src.data()), src.size_bytes()}; } @@ -153,7 +149,8 @@ namespace epee { using value_type = typename T::value_type; static_assert(!std::is_empty(), "empty value types will not work -> sizeof == 1"); - static_assert(!has_padding(), "source value type may have padding"); + static_assert(std::is_standard_layout_v, "value type must have standard layout"); + static_assert(std::has_unique_object_representations_v, "value type must be trivially copyable with no padding"); return {reinterpret_cast(src.data()), src.size() * sizeof(value_type)}; } @@ -162,7 +159,8 @@ namespace epee span as_byte_span(const T& src) noexcept { static_assert(!std::is_empty(), "empty types will not work -> sizeof == 1"); - static_assert(!has_padding(), "source type may have padding"); + static_assert(std::is_standard_layout_v, "type must have standard layout"); + static_assert(std::has_unique_object_representations_v, "type must be trivially copyable with no padding"); return {reinterpret_cast(std::addressof(src)), sizeof(T)}; } @@ -171,7 +169,8 @@ namespace epee span as_mut_byte_span(T& src) noexcept { static_assert(!std::is_empty(), "empty types will not work -> sizeof == 1"); - static_assert(!has_padding(), "source type may have padding"); + static_assert(std::is_standard_layout_v, "type must have standard layout"); + static_assert(std::has_unique_object_representations_v, "type must be trivially copyable with no padding"); return {reinterpret_cast(std::addressof(src)), sizeof(T)}; } diff --git a/contrib/epee/include/string_tools.h b/contrib/epee/include/string_tools.h index 6f129908e..a8f50554d 100644 --- a/contrib/epee/include/string_tools.h +++ b/contrib/epee/include/string_tools.h @@ -89,6 +89,7 @@ namespace string_tools std::string pod_to_hex(const t_pod_type& s) { static_assert(std::is_standard_layout(), "expected standard layout type"); + static_assert(std::has_unique_object_representations_v, "type may have padding"); return to_hex::string(as_byte_span(s)); } //---------------------------------------------------------------------------- @@ -96,6 +97,7 @@ namespace string_tools bool hex_to_pod(const boost::string_ref hex_str, t_pod_type& s) { static_assert(std::is_standard_layout(), "expected standard layout type"); + static_assert(std::has_unique_object_representations_v, "type may have padding"); return from_hex::to_buffer(as_mut_byte_span(s), hex_str); } //---------------------------------------------------------------------------- diff --git a/src/crypto/crypto.h b/src/crypto/crypto.h index 6b4126246..925201782 100644 --- a/src/crypto/crypto.h +++ b/src/crypto/crypto.h @@ -171,7 +171,9 @@ namespace crypto { /* Generate a value filled with random bytes. */ template - typename std::enable_if::value, T>::type rand() { + T rand() { + static_assert(std::is_standard_layout_v, "cannot write random bytes into non-standard layout type"); + static_assert(std::is_trivially_copyable_v, "cannot write random bytes into non-trivially copyable type"); typename std::remove_cv::type res; generate_random_bytes_thread_safe(sizeof(T), (uint8_t*)&res); return res; @@ -314,8 +316,14 @@ namespace crypto { inline std::ostream &operator <<(std::ostream &o, const crypto::public_key &v) { epee::to_hex::formatted(o, epee::as_byte_span(v)); return o; } - inline std::ostream &operator <<(std::ostream &o, const crypto::secret_key &v) { - epee::to_hex::formatted(o, epee::as_byte_span(v)); return o; + /* Do NOT overload the << operator for crypto::secret_key here. Use secret_key_explicit_print_ref + * instead to prevent accidental implicit dumping of secret key material to the logs (which has + * happened before). For the same reason, do not overload it for crypto::ec_scalar either since + * crypto::secret_key is a subclass. I'm not sorry that it's obtuse; that's the point, bozo. + */ + struct secret_key_explicit_print_ref { const crypto::secret_key &sk; }; + inline std::ostream &operator <<(std::ostream &o, const secret_key_explicit_print_ref v) { + epee::to_hex::formatted(o, epee::as_byte_span(unwrap(unwrap(v.sk)))); return o; } inline std::ostream &operator <<(std::ostream &o, const crypto::key_derivation &v) { epee::to_hex::formatted(o, epee::as_byte_span(v)); return o; diff --git a/src/cryptonote_basic/cryptonote_format_utils.cpp b/src/cryptonote_basic/cryptonote_format_utils.cpp index ca56c2bc3..62ddd86fb 100644 --- a/src/cryptonote_basic/cryptonote_format_utils.cpp +++ b/src/cryptonote_basic/cryptonote_format_utils.cpp @@ -292,7 +292,7 @@ namespace cryptonote bool r = hwdev.generate_key_derivation(tx_public_key, ack.m_view_secret_key, recv_derivation); if (!r) { - MWARNING("key image helper: failed to generate_key_derivation(" << tx_public_key << ", " << ack.m_view_secret_key << ")"); + MWARNING("key image helper: failed to generate_key_derivation(" << tx_public_key << ", )"); memcpy(&recv_derivation, rct::identity().bytes, sizeof(recv_derivation)); } @@ -303,7 +303,7 @@ namespace cryptonote r = hwdev.generate_key_derivation(additional_tx_public_keys[i], ack.m_view_secret_key, additional_recv_derivation); if (!r) { - MWARNING("key image helper: failed to generate_key_derivation(" << additional_tx_public_keys[i] << ", " << ack.m_view_secret_key << ")"); + MWARNING("key image helper: failed to generate_key_derivation(" << additional_tx_public_keys[i] << ", )"); } else { diff --git a/src/cryptonote_core/cryptonote_tx_utils.cpp b/src/cryptonote_core/cryptonote_tx_utils.cpp index ed5b285e8..6935451b3 100644 --- a/src/cryptonote_core/cryptonote_tx_utils.cpp +++ b/src/cryptonote_core/cryptonote_tx_utils.cpp @@ -144,7 +144,7 @@ namespace cryptonote crypto::key_derivation derivation = AUTO_VAL_INIT(derivation); crypto::public_key out_eph_public_key = AUTO_VAL_INIT(out_eph_public_key); bool r = crypto::generate_key_derivation(miner_address.m_view_public_key, txkey.sec, derivation); - CHECK_AND_ASSERT_MES(r, false, "while creating outs: failed to generate_key_derivation(" << miner_address.m_view_public_key << ", " << txkey.sec << ")"); + CHECK_AND_ASSERT_MES(r, false, "while creating outs: failed to generate_key_derivation(" << miner_address.m_view_public_key << ", " << crypto::secret_key_explicit_print_ref{txkey.sec} << ")"); r = crypto::derive_public_key(derivation, no, miner_address.m_spend_public_key, out_eph_public_key); CHECK_AND_ASSERT_MES(r, false, "while creating outs: failed to derive_public_key(" << derivation << ", " << no << ", "<< miner_address.m_spend_public_key << ")"); @@ -484,7 +484,7 @@ namespace cryptonote crypto::generate_ring_signature(tx_prefix_hash, boost::get(tx.vin[i]).k_image, keys_ptrs, in_contexts[i].in_ephemeral.sec, src_entr.real_output, sigs.data()); ss_ring_s << "signatures:" << ENDL; std::for_each(sigs.begin(), sigs.end(), [&](const crypto::signature& s){ss_ring_s << s << ENDL;}); - ss_ring_s << "prefix_hash:" << tx_prefix_hash << ENDL << "in_ephemeral_key: " << in_contexts[i].in_ephemeral.sec << ENDL << "real_output: " << src_entr.real_output << ENDL; + ss_ring_s << "prefix_hash:" << tx_prefix_hash << ENDL << "in_ephemeral_key: " << crypto::secret_key_explicit_print_ref{in_contexts[i].in_ephemeral.sec} << ENDL << "real_output: " << src_entr.real_output << ENDL; i++; } diff --git a/src/cryptonote_protocol/block_queue.cpp b/src/cryptonote_protocol/block_queue.cpp index 9f4a93723..2c3e31f59 100644 --- a/src/cryptonote_protocol/block_queue.cpp +++ b/src/cryptonote_protocol/block_queue.cpp @@ -40,15 +40,6 @@ #undef MONERO_DEFAULT_LOG_CATEGORY #define MONERO_DEFAULT_LOG_CATEGORY "cn.block_queue" -namespace std { - static_assert(sizeof(size_t) <= sizeof(boost::uuids::uuid), "boost::uuids::uuid too small"); - template<> struct hash { - std::size_t operator()(const boost::uuids::uuid &_v) const { - return reinterpret_cast(_v); - } - }; -} - namespace cryptonote { @@ -472,7 +463,7 @@ bool block_queue::has_spans(const boost::uuids::uuid &connection_id) const float block_queue::get_speed(const boost::uuids::uuid &connection_id) const { boost::unique_lock lock(mutex); - std::unordered_map speeds; + std::unordered_map> speeds; for (const auto &span: blocks) { if (span.blocks.empty()) @@ -480,7 +471,7 @@ float block_queue::get_speed(const boost::uuids::uuid &connection_id) const // note that the average below does not average over the whole set, but over the // previous pseudo average and the latest rate: this gives much more importance // to the latest measurements, which is fine here - std::unordered_map::iterator i = speeds.find(span.connection_id); + const auto i = speeds.find(span.connection_id); if (i == speeds.end()) speeds.insert(std::make_pair(span.connection_id, span.rate)); else diff --git a/src/device/device_default.cpp b/src/device/device_default.cpp index 5bfdc2a87..30bb4a2e8 100644 --- a/src/device/device_default.cpp +++ b/src/device/device_default.cpp @@ -317,13 +317,15 @@ namespace hw { { // sending change to yourself; derivation = a*R r = generate_key_derivation(txkey_pub, sender_account_keys.m_view_secret_key, derivation); - CHECK_AND_ASSERT_MES(r, false, "at creation outs: failed to generate_key_derivation(" << txkey_pub << ", " << sender_account_keys.m_view_secret_key << ")"); + CHECK_AND_ASSERT_MES(r, false, "at creation outs: failed to generate_key_derivation(" << txkey_pub << ", )"); } else { // sending to the recipient; derivation = r*A (or s*C in the subaddress scheme) - r = generate_key_derivation(dst_entr.addr.m_view_public_key, dst_entr.is_subaddress && need_additional_txkeys ? additional_txkey.sec : tx_key, derivation); - CHECK_AND_ASSERT_MES(r, false, "at creation outs: failed to generate_key_derivation(" << dst_entr.addr.m_view_public_key << ", " << (dst_entr.is_subaddress && need_additional_txkeys ? additional_txkey.sec : tx_key) << ")"); + const crypto::secret_key &tx_privkey{dst_entr.is_subaddress && need_additional_txkeys ? additional_txkey.sec : tx_key}; + r = generate_key_derivation(dst_entr.addr.m_view_public_key, tx_privkey, derivation); + CHECK_AND_ASSERT_MES(r, false, "at creation outs: failed to generate_key_derivation(" + << dst_entr.addr.m_view_public_key << ", " << crypto::secret_key_explicit_print_ref{tx_privkey} << ")"); } if (need_additional_txkeys) diff --git a/src/lmdb/util.h b/src/lmdb/util.h index 64ad3752a..493fc0bd8 100644 --- a/src/lmdb/util.h +++ b/src/lmdb/util.h @@ -127,7 +127,7 @@ namespace lmdb /*! A LMDB comparison function that uses `std::memcmp`. - \toaram T is `!epee::has_padding` + \toaram T has standard layout and an alignment of 1 \tparam offset to `T` within the value. \return The result of `std::memcmp` over the value. @@ -135,7 +135,7 @@ namespace lmdb template inline int compare(MDB_val const* left, MDB_val const* right) noexcept { - static_assert(!epee::has_padding(), "memcmp will not work"); + static_assert(std::is_standard_layout_v && alignof(T) == 1, "memcmp will not work"); if (!left || !right || left->mv_size < sizeof(T) + offset || right->mv_size < sizeof(T) + offset) { assert("invalid use of custom comparison" == 0); diff --git a/src/simplewallet/simplewallet.cpp b/src/simplewallet/simplewallet.cpp index 153d5f2ac..1863d11b8 100644 --- a/src/simplewallet/simplewallet.cpp +++ b/src/simplewallet/simplewallet.cpp @@ -7872,9 +7872,9 @@ bool simple_wallet::submit_transfer(const std::vector &args_) std::string get_tx_key_stream(crypto::secret_key tx_key, std::vector additional_tx_keys) { ostringstream oss; - oss << epee::string_tools::pod_to_hex(tx_key); + oss << epee::string_tools::pod_to_hex(unwrap(unwrap(tx_key))); for (size_t i = 0; i < additional_tx_keys.size(); ++i) - oss << epee::string_tools::pod_to_hex(additional_tx_keys[i]); + oss << epee::string_tools::pod_to_hex(unwrap(unwrap(additional_tx_keys[i]))); return oss.str(); } diff --git a/src/wallet/api/wallet.cpp b/src/wallet/api/wallet.cpp index c8257919d..6c50002dd 100644 --- a/src/wallet/api/wallet.cpp +++ b/src/wallet/api/wallet.cpp @@ -895,7 +895,7 @@ std::string WalletImpl::integratedAddress(const std::string &payment_id) const std::string WalletImpl::secretViewKey() const { - return epee::string_tools::pod_to_hex(m_wallet->get_account().get_keys().m_view_secret_key); + return epee::string_tools::pod_to_hex(unwrap(unwrap(m_wallet->get_account().get_keys().m_view_secret_key))); } std::string WalletImpl::publicViewKey() const @@ -905,7 +905,7 @@ std::string WalletImpl::publicViewKey() const std::string WalletImpl::secretSpendKey() const { - return epee::string_tools::pod_to_hex(m_wallet->get_account().get_keys().m_spend_secret_key); + return epee::string_tools::pod_to_hex(unwrap(unwrap(m_wallet->get_account().get_keys().m_spend_secret_key))); } std::string WalletImpl::publicSpendKey() const @@ -1999,9 +1999,9 @@ std::string WalletImpl::getTxKey(const std::string &txid_str) const { clearStatus(); std::ostringstream oss; - oss << epee::string_tools::pod_to_hex(tx_key); + oss << epee::string_tools::pod_to_hex(unwrap(unwrap(tx_key))); for (size_t i = 0; i < additional_tx_keys.size(); ++i) - oss << epee::string_tools::pod_to_hex(additional_tx_keys[i]); + oss << epee::string_tools::pod_to_hex(unwrap(unwrap(additional_tx_keys[i]))); return oss.str(); } else diff --git a/src/wallet/wallet2.cpp b/src/wallet/wallet2.cpp index fa9c51bb2..3874ce850 100644 --- a/src/wallet/wallet2.cpp +++ b/src/wallet/wallet2.cpp @@ -4721,7 +4721,7 @@ boost::optional wallet2::get_keys_file_data(const crypt original_address = get_account_address_as_str(m_nettype, false, m_original_address); value.SetString(original_address.c_str(), original_address.length()); json.AddMember("original_address", value, json.GetAllocator()); - original_view_secret_key = epee::string_tools::pod_to_hex(m_original_view_secret_key); + original_view_secret_key = epee::string_tools::pod_to_hex(unwrap(unwrap(m_original_view_secret_key))); value.SetString(original_view_secret_key.c_str(), original_view_secret_key.length()); json.AddMember("original_view_secret_key", value, json.GetAllocator()); } diff --git a/src/wallet/wallet_rpc_server.cpp b/src/wallet/wallet_rpc_server.cpp index bb65304d4..478bf37d8 100644 --- a/src/wallet/wallet_rpc_server.cpp +++ b/src/wallet/wallet_rpc_server.cpp @@ -1311,9 +1311,9 @@ namespace tools res.tx_hash_list.push_back(epee::string_tools::pod_to_hex(cryptonote::get_transaction_hash(ptx.tx))); if (req.get_tx_keys) { - res.tx_key_list.push_back(epee::string_tools::pod_to_hex(ptx.tx_key)); + res.tx_key_list.push_back(epee::string_tools::pod_to_hex(unwrap(unwrap(ptx.tx_key)))); for (const crypto::secret_key& additional_tx_key : ptx.additional_tx_keys) - res.tx_key_list.back() += epee::string_tools::pod_to_hex(additional_tx_key); + res.tx_key_list.back() += epee::string_tools::pod_to_hex(unwrap(unwrap(additional_tx_key))); } } diff --git a/tests/benchmark.cpp b/tests/benchmark.cpp index 289368a62..5680a7089 100644 --- a/tests/benchmark.cpp +++ b/tests/benchmark.cpp @@ -109,7 +109,7 @@ namespace template bool compare(const T& lhs, const T& rhs) noexcept { - static_assert(!epee::has_padding(), "type might have padding"); + static_assert(std::is_standard_layout_v && alignof(T) == 1, "type might have padding"); return std::memcmp(std::addressof(lhs), std::addressof(rhs), sizeof(T)) == 0; } diff --git a/tests/core_tests/multisig.cpp b/tests/core_tests/multisig.cpp index 8c479ed50..9cec96ff1 100644 --- a/tests/core_tests/multisig.cpp +++ b/tests/core_tests/multisig.cpp @@ -227,13 +227,13 @@ bool gen_multisig_tx_validation_base::generate_with(std::vector()); EXPECT_TRUE(is_formatted()); EXPECT_TRUE(is_formatted()); - EXPECT_TRUE(is_formatted()); EXPECT_TRUE(is_formatted()); EXPECT_TRUE(is_formatted()); EXPECT_TRUE(is_formatted()); + EXPECT_TRUE(is_formatted()); } TEST(Crypto, null_keys) diff --git a/tests/unit_tests/multisig.cpp b/tests/unit_tests/multisig.cpp index 75dfaf20c..78d4bedfc 100644 --- a/tests/unit_tests/multisig.cpp +++ b/tests/unit_tests/multisig.cpp @@ -80,7 +80,7 @@ static void make_wallet(unsigned int idx, tools::wallet2 &wallet) wallet.generate("", "", spendkey, true, false); ASSERT_TRUE(test_addresses[idx].address == wallet.get_account().get_public_address_str(cryptonote::TESTNET)); wallet.decrypt_keys(""); - ASSERT_TRUE(test_addresses[idx].spendkey == epee::string_tools::pod_to_hex(wallet.get_account().get_keys().m_spend_secret_key)); + ASSERT_TRUE(test_addresses[idx].spendkey == epee::string_tools::pod_to_hex(unwrap(unwrap(wallet.get_account().get_keys().m_spend_secret_key)))); wallet.encrypt_keys(""); } catch (const std::exception &e) diff --git a/tests/unit_tests/serialization.cpp b/tests/unit_tests/serialization.cpp index 9daa44351..1ca9687a8 100644 --- a/tests/unit_tests/serialization.cpp +++ b/tests/unit_tests/serialization.cpp @@ -1113,7 +1113,7 @@ TEST(Serialization, portability_signed_tx) ASSERT_TRUE(ptx.selected_transfers.front() == 2); // ptx.{key_images, tx_key} ASSERT_TRUE(ptx.key_images == "<6c3cd6af97c4070a7aef9b1344e7463e29c7cd245076fdb65da447a34da3ca76> "); - ASSERT_TRUE(epee::string_tools::pod_to_hex(ptx.tx_key) == "0100000000000000000000000000000000000000000000000000000000000000"); + ASSERT_TRUE(epee::string_tools::pod_to_hex(unwrap(unwrap(ptx.tx_key))) == "0100000000000000000000000000000000000000000000000000000000000000"); // ptx.dests ASSERT_TRUE(ptx.dests.size() == 1); ASSERT_TRUE(ptx.dests[0].amount == 1400000000000); From 9c7e6ab04d4bf5b593785d59cb3952f6ab6eec9e Mon Sep 17 00:00:00 2001 From: tobtoht Date: Fri, 13 Sep 2024 15:42:20 +0200 Subject: [PATCH 4/5] ci: fix windows msys2 build --- .github/workflows/build.yml | 7 +--- cmake/CheckTrezor.cmake | 67 ++++++------------------------------- 2 files changed, 12 insertions(+), 62 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index 89c86af2e..0954bce45 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -68,12 +68,7 @@ jobs: - uses: msys2/setup-msys2@v2 with: update: true - install: mingw-w64-x86_64-toolchain make mingw-w64-x86_64-cmake mingw-w64-x86_64-ccache mingw-w64-x86_64-boost mingw-w64-x86_64-openssl mingw-w64-x86_64-zeromq mingw-w64-x86_64-libsodium mingw-w64-x86_64-hidapi mingw-w64-x86_64-libusb mingw-w64-x86_64-unbound git - - shell: msys2 {0} - run: | - curl -O https://repo.msys2.org/mingw/mingw64/mingw-w64-x86_64-protobuf-c-1.4.1-1-any.pkg.tar.zst - curl -O https://repo.msys2.org/mingw/mingw64/mingw-w64-x86_64-protobuf-21.9-1-any.pkg.tar.zst - pacman --noconfirm -U mingw-w64-x86_64-protobuf-c-1.4.1-1-any.pkg.tar.zst mingw-w64-x86_64-protobuf-21.9-1-any.pkg.tar.zst + install: mingw-w64-x86_64-toolchain make mingw-w64-x86_64-cmake mingw-w64-x86_64-ccache mingw-w64-x86_64-boost mingw-w64-x86_64-openssl mingw-w64-x86_64-zeromq mingw-w64-x86_64-libsodium mingw-w64-x86_64-hidapi mingw-w64-x86_64-protobuf mingw-w64-x86_64-libusb mingw-w64-x86_64-unbound git pkg-config - name: build run: | ${{env.CCACHE_SETTINGS}} diff --git a/cmake/CheckTrezor.cmake b/cmake/CheckTrezor.cmake index 87582a713..a6b0605dc 100644 --- a/cmake/CheckTrezor.cmake +++ b/cmake/CheckTrezor.cmake @@ -23,32 +23,6 @@ OPTION(USE_DEVICE_TREZOR_UDP_RELEASE "Trezor UdpTransport in release mode" $ENV{ OPTION(USE_DEVICE_TREZOR_DEBUG "Trezor Debugging enabled" $ENV{USE_DEVICE_TREZOR_DEBUG}) OPTION(TREZOR_DEBUG "Main Trezor debugging switch" $ENV{TREZOR_DEBUG}) -# Helper function to fix cmake < 3.6.0 FindProtobuf variables -function(_trezor_protobuf_fix_vars) - if(${CMAKE_VERSION} VERSION_LESS "3.6.0") - foreach(UPPER - PROTOBUF_SRC_ROOT_FOLDER - PROTOBUF_IMPORT_DIRS - PROTOBUF_DEBUG - PROTOBUF_LIBRARY - PROTOBUF_PROTOC_LIBRARY - PROTOBUF_INCLUDE_DIR - PROTOBUF_PROTOC_EXECUTABLE - PROTOBUF_LIBRARY_DEBUG - PROTOBUF_PROTOC_LIBRARY_DEBUG - PROTOBUF_LITE_LIBRARY - PROTOBUF_LITE_LIBRARY_DEBUG - ) - if (DEFINED ${UPPER}) - string(REPLACE "PROTOBUF_" "Protobuf_" Camel ${UPPER}) - if (NOT DEFINED ${Camel}) - set(${Camel} ${${UPPER}} PARENT_SCOPE) - endif() - endif() - endforeach() - endif() -endfunction() - macro(trezor_fatal_msg msg) if ($ENV{USE_DEVICE_TREZOR_MANDATORY}) message(FATAL_ERROR @@ -72,40 +46,21 @@ endmacro() # Use Trezor master switch if (USE_DEVICE_TREZOR) - # Protobuf is required to build protobuf messages for Trezor - include(FindProtobuf OPTIONAL) + # Look for protobuf-config.cmake, provided by Protobuf + find_package(Protobuf CONFIG) - # PkgConfig works better with new Protobuf - find_package(PkgConfig QUIET) - pkg_check_modules(PROTOBUF protobuf) - - if (NOT Protobuf_FOUND) - FIND_PACKAGE(Protobuf CONFIG) + if (Protobuf_FOUND) + # https://github.com/protocolbuffers/protobuf/issues/14576 + find_program(Protobuf_PROTOC_EXECUTABLE protoc REQUIRED) + set(Protobuf_LIBRARY protobuf::libprotobuf) # Compatibility with FindProtobuf.cmake + else() + # Look for FindProtobuf.cmake, provided by CMake + find_package(Protobuf) endif() - if (NOT Protobuf_FOUND) - FIND_PACKAGE(Protobuf) - endif() - - _trezor_protobuf_fix_vars() # Early fail for optional Trezor support - if(NOT Protobuf_FOUND AND NOT Protobuf_LIBRARY AND NOT Protobuf_PROTOC_EXECUTABLE AND NOT Protobuf_INCLUDE_DIR) - trezor_fatal_msg("Trezor: Could not find Protobuf") - elseif(${CMAKE_CXX_STANDARD} LESS 17 AND ${Protobuf_VERSION} GREATER 21) - trezor_fatal_msg("Trezor: Unsupported Protobuf version ${Protobuf_VERSION} with C++ ${CMAKE_CXX_STANDARD}. Please, use Protobuf v21.") - elseif(NOT Protobuf_LIBRARY) - trezor_fatal_msg("Trezor: Protobuf library not found: ${Protobuf_LIBRARY}") - unset(Protobuf_FOUND) - elseif(NOT Protobuf_PROTOC_EXECUTABLE OR NOT EXISTS "${Protobuf_PROTOC_EXECUTABLE}") - trezor_fatal_msg("Trezor: Protobuf executable not found: ${Protobuf_PROTOC_EXECUTABLE}") - unset(Protobuf_FOUND) - elseif(NOT Protobuf_INCLUDE_DIR OR NOT EXISTS "${Protobuf_INCLUDE_DIR}") - trezor_fatal_msg("Trezor: Protobuf include dir not found: ${Protobuf_INCLUDE_DIR}") - unset(Protobuf_FOUND) - else() - message(STATUS "Trezor: Protobuf lib: ${Protobuf_LIBRARY}, inc: ${Protobuf_INCLUDE_DIR}, protoc: ${Protobuf_PROTOC_EXECUTABLE}") - set(Protobuf_INCLUDE_DIRS ${Protobuf_INCLUDE_DIR}) - set(Protobuf_FOUND 1) # override found if all required info was provided by variables + if (NOT Protobuf_FOUND) + trezor_fatal_msg("Trezor: protobuf library not found") endif() if(TREZOR_DEBUG) From 170844bc5978f0b5c1126edbb0d10169d2489593 Mon Sep 17 00:00:00 2001 From: tobtoht Date: Wed, 2 Oct 2024 03:18:01 +0200 Subject: [PATCH 5/5] cmake: boost: fix header-only library search, bump minimum --- CMakeLists.txt | 52 +++++++++++++++++++++++++++++--------------------- README.md | 2 +- 2 files changed, 31 insertions(+), 23 deletions(-) diff --git a/CMakeLists.txt b/CMakeLists.txt index 78350338d..60cda040a 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -1084,33 +1084,41 @@ if(STATIC) set(Boost_USE_STATIC_RUNTIME ON) endif() -set(BOOST_COMPONENTS system filesystem thread date_time chrono regex serialization program_options) -if (WIN32) - list(APPEND BOOST_COMPONENTS locale) +# Find Boost headers +set(BOOST_MIN_VER 1.62) +find_package(Boost ${BOOST_MIN_VER} QUIET REQUIRED) + +if(NOT Boost_FOUND) + die("Could not find Boost libraries, please make sure you have installed Boost or libboost-all-dev (>=${BOOST_MIN_VER}) or the equivalent") +elseif(Boost_FOUND) + message(STATUS "Found Boost Version: ${Boost_VERSION_STRING}") + + set(BOOST_COMPONENTS filesystem thread date_time chrono serialization program_options) + if (WIN32) + list(APPEND BOOST_COMPONENTS locale) + endif() + + # Boost System is header-only since 1.69 + if (Boost_VERSION_STRING VERSION_LESS 1.69.0) + list(APPEND BOOST_COMPONENTS system) + endif() + + # Boost Regex is header-only since 1.77 + if (Boost_VERSION_STRING VERSION_LESS 1.77.0) + list(APPEND BOOST_COMPONENTS regex) + endif() + + message(STATUS "Boost components: ${BOOST_COMPONENTS}") + + # Find required Boost libraries + find_package(Boost ${BOOST_MIN_VER} QUIET REQUIRED COMPONENTS ${BOOST_COMPONENTS}) + set(CMAKE_FIND_LIBRARY_SUFFIXES ${OLD_LIB_SUFFIXES}) endif() -find_package(Boost 1.58 QUIET REQUIRED COMPONENTS ${BOOST_COMPONENTS}) + add_definitions(-DBOOST_ASIO_ENABLE_SEQUENTIAL_STRAND_ALLOCATION) add_definitions(-DBOOST_NO_AUTO_PTR) add_definitions(-DBOOST_UUID_DISABLE_ALIGNMENT) # This restores UUID's std::has_unique_object_representations property -set(CMAKE_FIND_LIBRARY_SUFFIXES ${OLD_LIB_SUFFIXES}) -if(NOT Boost_FOUND) - die("Could not find Boost libraries, please make sure you have installed Boost or libboost-all-dev (>=1.58) or the equivalent") -elseif(Boost_FOUND) - message(STATUS "Found Boost Version: ${Boost_VERSION}") - if (Boost_VERSION VERSION_LESS 10 AND Boost_VERSION VERSION_LESS 1.62.0 AND NOT (OPENSSL_VERSION VERSION_LESS 1.1)) - set(BOOST_BEFORE_1_62 true) - endif() - if (NOT Boost_VERSION VERSION_LESS 10 AND Boost_VERSION VERSION_LESS 106200 AND NOT (OPENSSL_VERSION VERSION_LESS 1.1)) - set(BOOST_BEFORE_1_62 true) - endif() - if (BOOST_BEFORE_1_62) - message(FATAL_ERROR "Boost ${Boost_VERSION} (older than 1.62) is too old to link with OpenSSL ${OPENSSL_VERSION} (1.1 or newer) found at ${OPENSSL_INCLUDE_DIR} and ${OPENSSL_LIBRARIES}. " - "Update Boost or install OpenSSL 1.0 and set path to it when running cmake: " - "cmake -DOPENSSL_ROOT_DIR='/usr/include/openssl-1.0'") - endif() -endif() - include_directories(SYSTEM ${Boost_INCLUDE_DIRS}) if(MINGW) set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -Wa,-mbig-obj") diff --git a/README.md b/README.md index 931207205..653a1a389 100644 --- a/README.md +++ b/README.md @@ -167,7 +167,7 @@ library archives (`.a`). | GCC | 7 | NO | `build-essential` | `base-devel` | `base-devel` | `gcc` | NO | | | CMake | 3.5 | NO | `cmake` | `cmake` | `cmake` | `cmake` | NO | | | pkg-config | any | NO | `pkg-config` | `base-devel` | `base-devel` | `pkgconf` | NO | | -| Boost | 1.58 | NO | `libboost-all-dev` | `boost` | `boost-devel` | `boost-devel` | NO | C++ libraries | +| Boost | 1.62 | NO | `libboost-all-dev` | `boost` | `boost-devel` | `boost-devel` | NO | C++ libraries | | OpenSSL | basically any | NO | `libssl-dev` | `openssl` | `openssl-devel` | `openssl-devel` | NO | sha256 sum | | libzmq | 4.2.0 | NO | `libzmq3-dev` | `zeromq` | `zeromq-devel` | `zeromq-devel` | NO | ZeroMQ library | | OpenPGM | ? | NO | `libpgm-dev` | `libpgm` | | `openpgm-devel` | NO | For ZeroMQ |