From 325c21d4da665835bf39999c83a46bc7c48e2d8c Mon Sep 17 00:00:00 2001 From: woodser Date: Sun, 18 Aug 2019 09:51:25 -0400 Subject: [PATCH] define multisig functions, models, and impl placeholders --- src/wallet/monero_wallet.cpp | 36 ++++++++++++++ src/wallet/monero_wallet.h | 78 ++++++++++++++++++++++++++++++ src/wallet/monero_wallet_model.cpp | 25 ++++++++++ src/wallet/monero_wallet_model.h | 35 ++++++++++++++ 4 files changed, 174 insertions(+) diff --git a/src/wallet/monero_wallet.cpp b/src/wallet/monero_wallet.cpp index 558c818..59c5ebe 100644 --- a/src/wallet/monero_wallet.cpp +++ b/src/wallet/monero_wallet.cpp @@ -2542,6 +2542,42 @@ namespace monero { m_w2->deinit(); } + monero_multisig_info monero_wallet::get_multisig_info() { + throw runtime_error("get_multisig_info not implemented"); + } + + string monero_wallet::prepare_multisig() { + throw runtime_error("prepare_multisig not implemented"); + } + + monero_multisig_init_result monero_wallet::make_multisig(const vector& multisig_hexes, int threshold, const string& password) { + throw runtime_error("make_multisig not implemented"); + } + + string monero_wallet::finalize_multisig(const vector& multisig_hexes, const string& password) { + throw runtime_error("finalize_multisig not implemented"); + } + + monero_multisig_init_result monero_wallet::exchange_multisig_keys(const vector& multisig_hexes, const string& password) { + throw runtime_error("exchange_multisig_keys not implemented"); + } + + string monero_wallet::get_multisig_hex() { + throw runtime_error("get_multisig_hex not implemented"); + } + + int monero_wallet::import_multisig_hex(const vector& multisig_hexes) { + throw runtime_error("import_multisig_hex not implemented"); + } + + monero_multisig_sign_result monero_wallet::sign_multisig_tx_hex(const string& multisig_tx_hex) { + throw runtime_error("sign_multisig_tx_hex not implemented"); + } + + vector monero_wallet::submit_multisig_tx_hex(const string& signed_multisig_tx_hex) { + throw runtime_error("submit_multisig_tx_hex not implemented"); + } + // ------------------------------- PRIVATE HELPERS ---------------------------- void monero_wallet::init_common() { diff --git a/src/wallet/monero_wallet.h b/src/wallet/monero_wallet.h index 34dde9e..7ca0348 100644 --- a/src/wallet/monero_wallet.h +++ b/src/wallet/monero_wallet.h @@ -1301,6 +1301,84 @@ namespace monero { */ void close(); + /** + * Get multisig info about this wallet. + * + * @return multisig info about this wallet + */ + monero_multisig_info get_multisig_info(); + + /** + * Get multisig info as hex to share with participants to begin creating a + * multisig wallet. + * + * @return this wallet's multisig hex to share with participants + */ + string prepare_multisig(); + + /** + * Make this wallet multisig by importing multisig hex from participants. + * + * @param multisig_hexes are multisig hex from each participant + * @param threshold is the number of signatures needed to sign transfers + * @password is the wallet password + * @return the result which has the multisig's address xor this wallet's multisig hex to share with participants iff not N/N + */ + monero_multisig_init_result make_multisig(const vector& multisig_hexes, int threshold, const string& password); + + /** + * Finalize a N-1/N multisig wallet. + * + * TODO monero core: this is a special case of exchangeMultisigKeys() for N-1/N multisig. use that as the last step instead and remove this? that would further generalize the process + * + * @param multisig_hexes are multisig hex from each participant + * @param password is the wallet's password // TODO monero core: redundant? wallet is created with password + * @return the multisig wallet's address + */ + string finalize_multisig(const vector& multisig_hexes, const string& password); + + /** + * Exchange multisig hex with participants in a M/N multisig wallet. + * + * This process must be repeated with participants exactly N-M times. + * + * @param multisig_hexes are multisig hex from each participant + * @param password is the wallet's password // TODO monero core: redundant? wallet is created with password + * @return the result which has the multisig's address xor this wallet's multisig hex to share with participants iff not done + */ + monero_multisig_init_result exchange_multisig_keys(const vector& mutisig_hexes, const string& password); + + /** + * Export this wallet's multisig info as hex for other participants. + * + * @return this wallet's multisig info as hex for other participants + */ + string get_multisig_hex(); + + /** + * Import multisig info as hex from other participants. + * + * @param multisig_hexes are multisig hex from each participant + * @return the number of outputs signed with the given multisig hex + */ + int import_multisig_hex(const vector& multisig_hexes); + + /** + * Sign previously created multisig transactions as represented by hex. + * + * @param multisig_tx_hex is the hex shared among the multisig transactions when they were created + * @return the result of signing the multisig transactions + */ + monero_multisig_sign_result sign_multisig_tx_hex(const string& multisig_tx_hex); + + /** + * Submit signed multisig transactions as represented by a hex string. + * + * @param signed_multisig_tx_hex is the signed multisig hex returned from signMultisigTxs() + * @return the resulting transaction ids + */ + vector submit_multisig_tx_hex(const string& signed_multisig_tx_hex); + // --------------------------------- PRIVATE -------------------------------- private: diff --git a/src/wallet/monero_wallet_model.cpp b/src/wallet/monero_wallet_model.cpp index 5c926e2..95e22d7 100644 --- a/src/wallet/monero_wallet_model.cpp +++ b/src/wallet/monero_wallet_model.cpp @@ -683,4 +683,29 @@ namespace monero { if (m_unconfirmed_spent_amount != boost::none) node.put("unconfirmedSpentAmount", *m_unconfirmed_spent_amount); return node; } + + // --------------------------- MONERO MULTISIG ------------------------------ + + boost::property_tree::ptree monero_multisig_init_result::to_property_tree() const { + boost::property_tree::ptree node; + node.put("address", m_address); + node.put("multisigHex", m_multisig_hex); + return node; + } + + boost::property_tree::ptree monero_multisig_info::to_property_tree() const { + boost::property_tree::ptree node; + node.put("isMultisig", m_is_multisig); + node.put("isReady", m_is_ready); + node.put("threshold", m_threshold); + node.put("numParticipants", m_num_participants); + return node; + } + + boost::property_tree::ptree monero_multisig_sign_result::to_property_tree() const { + boost::property_tree::ptree node; + node.put("signedMultisigTxHex", m_signed_multisig_tx_hex); + if (!m_tx_ids.empty()) node.add_child("txIds", monero_utils::to_property_tree(m_tx_ids)); + return node; + } } diff --git a/src/wallet/monero_wallet_model.h b/src/wallet/monero_wallet_model.h index 541df9b..c59c037 100644 --- a/src/wallet/monero_wallet_model.h +++ b/src/wallet/monero_wallet_model.h @@ -376,4 +376,39 @@ namespace monero { boost::property_tree::ptree to_property_tree() const; }; + + /** + * Models the result of initializing a multisig wallet which results in the + * multisig wallet's address xor another multisig hex to share with + * participants to create the wallet. + */ + struct monero_multisig_init_result : serializable_struct { + boost::optional m_address; + boost::optional m_multisig_hex; + + boost::property_tree::ptree to_property_tree() const; + }; + + /** + * Models information about a multisig wallet. + */ + struct monero_multisig_info : serializable_struct { + bool m_is_multisig; + bool m_is_ready; + uint32_t m_threshold; + uint32_t m_num_participants; + + boost::property_tree::ptree to_property_tree() const; + }; + + /** + * Models the result of signing multisig tx hex. + */ + struct monero_multisig_sign_result : serializable_struct { + boost::optional m_signed_multisig_tx_hex; + vector m_tx_ids; + + boost::property_tree::ptree to_property_tree() const; + }; + }