diff --git a/src/wallet/test/wallet_tests.cpp b/src/wallet/test/wallet_tests.cpp --- a/src/wallet/test/wallet_tests.cpp +++ b/src/wallet/test/wallet_tests.cpp @@ -649,4 +649,24 @@ !wallet->GetNewDestination(OutputType::LEGACY, "", dest, error)); } +bool malformed_descriptor(std::ios_base::failure e) { + std::string s(e.what()); + return s.find("Missing checksum") != std::string::npos; +} + +BOOST_FIXTURE_TEST_CASE(wallet_descriptor_test, BasicTestingSetup) { + std::vector<uint8_t> malformed_record; + CVectorWriter vw(0, 0, malformed_record, 0); + vw << std::string("notadescriptor"); + vw << (uint64_t)0; + vw << (int32_t)0; + vw << (int32_t)0; + vw << (int32_t)1; + + VectorReader vr(0, 0, malformed_record, 0); + WalletDescriptor w_desc; + BOOST_CHECK_EXCEPTION(vr >> w_desc, std::ios_base::failure, + malformed_descriptor); +} + BOOST_AUTO_TEST_SUITE_END() diff --git a/src/wallet/walletutil.h b/src/wallet/walletutil.h --- a/src/wallet/walletutil.h +++ b/src/wallet/walletutil.h @@ -6,6 +6,7 @@ #define BITCOIN_WALLET_WALLETUTIL_H #include <fs.h> +#include <script/descriptor.h> #include <vector> @@ -91,4 +92,48 @@ bool Exists() const; }; +/** Descriptor with some wallet metadata */ +class WalletDescriptor { +public: + std::shared_ptr<Descriptor> descriptor; + uint64_t creation_time; + int32_t range_start; // First item in range; start of range, inclusive, i.e. + // [range_start, range_end). This never changes. + int32_t range_end; // Item after the last; end of range, exclusive, i.e. + // [range_start, range_end). This will increment with + // each TopUp() + int32_t next_index; // Position of the next item to generate + DescriptorCache cache; + + ADD_SERIALIZE_METHODS; + + template <typename Stream, typename Operation> + inline void SerializationOp(Stream &s, Operation ser_action) { + if (ser_action.ForRead()) { + std::string desc; + std::string error; + READWRITE(desc); + FlatSigningProvider keys; + descriptor = Parse(desc, keys, error, true); + if (!descriptor) { + throw std::ios_base::failure("Invalid descriptor: " + error); + } + } else { + READWRITE(descriptor->ToString()); + } + READWRITE(creation_time); + READWRITE(next_index); + READWRITE(range_start); + READWRITE(range_end); + } + + WalletDescriptor() {} + WalletDescriptor(std::shared_ptr<Descriptor> descriptor_, + uint64_t creation_time_, int32_t range_start_, + int32_t range_end_, int32_t next_index_) + : descriptor(descriptor_), creation_time(creation_time_), + range_start(range_start_), range_end(range_end_), + next_index(next_index_) {} +}; + #endif // BITCOIN_WALLET_WALLETUTIL_H