peerplays_migrated/programs/light_client/Wallet.hpp

159 lines
5.2 KiB
C++
Raw Normal View History

2015-07-22 20:23:42 +00:00
#pragma once
#pragma GCC diagnostic ignored "-Wunknown-pragmas"
#include <graphene/chain/protocol/types.hpp>
2015-07-22 20:23:42 +00:00
#include <QObject>
2015-07-23 13:32:29 +00:00
#include <QList>
#include <QPair>
#include <QtQml>
2015-07-22 20:23:42 +00:00
using std::string;
using std::vector;
using std::set;
using fc::flat_set;
using std::map;
using graphene::chain::public_key_type;
using graphene::chain::digest_type;
using graphene::chain::signature_type;
using fc::optional;
class Transaction;
QString toQString(public_key_type k);
2015-07-22 20:23:42 +00:00
struct key_data
{
string label; /** unique label assigned to this key */
2015-07-23 13:32:29 +00:00
/** encrypted as a packed std::string containing a wif private key */
vector<char> encrypted_private_key;
int32_t brain_sequence = -1;
optional<public_key_type> owner; /// if this key was derived from an owner key + sequence
2015-07-22 20:23:42 +00:00
};
struct wallet_file
{
2015-07-22 20:59:22 +00:00
vector<char> encrypted_brain_key;
fc::sha512 brain_key_digest;
vector<char> encrypted_master_key;
fc::sha512 master_key_digest;
2015-07-22 20:23:42 +00:00
map<public_key_type, key_data> encrypted_private_keys;
};
/**
* @class Wallet
* @brief Securely maintains a set of labeled public and private keys
2015-07-23 13:32:29 +00:00
*
* @note this API is designed for use with QML which does not support exceptions so
* all errors are passed via return values.
2015-07-22 20:23:42 +00:00
*/
class Wallet : public QObject
{
Q_OBJECT
Q_PROPERTY(bool isOpen READ isOpen NOTIFY isOpenChanged)
Q_PROPERTY(bool isLocked READ isLocked NOTIFY isLockedChanged)
2015-07-22 20:23:42 +00:00
public:
Wallet( QObject* parent = nullptr );
2015-07-22 20:23:42 +00:00
~Wallet();
Q_INVOKABLE bool open(QString file_path);
2015-07-22 20:23:42 +00:00
Q_INVOKABLE bool close();
bool isOpen()const;
2015-07-22 20:23:42 +00:00
Q_INVOKABLE bool save();
Q_INVOKABLE bool saveAs(QString file_path);
Q_INVOKABLE bool create(QString file_path, QString password, QString brain_key = QString());
2015-07-22 20:23:42 +00:00
/** required to generate new owner keys */
Q_INVOKABLE bool loadBrainKey(QString brain_key);
2015-07-22 20:23:42 +00:00
/** removes brain key to secure owner keys */
Q_INVOKABLE bool purgeBrainKey();
Q_INVOKABLE bool hasBrainKey()const;
/** @pre hasBrainKey() */
2015-07-22 20:59:22 +00:00
Q_INVOKABLE QString getBrainKey();
2015-07-22 20:23:42 +00:00
bool isLocked()const;
Q_INVOKABLE bool unlock(QString password);
2015-07-22 22:37:00 +00:00
Q_INVOKABLE bool lock();
Q_INVOKABLE bool changePassword(QString new_password);
2015-07-22 20:23:42 +00:00
/**
* @pre !isLocked();
* @post save()
2015-07-24 17:57:47 +00:00
* @return WIF private key
2015-07-22 20:23:42 +00:00
*/
Q_INVOKABLE QString getActivePrivateKey(QString owner_public_key, uint32_t sequence);
Q_INVOKABLE QString getActivePublicKey(QString owner_public_key, uint32_t sequence);
2015-07-22 20:23:42 +00:00
/**
* @pre !isLocked();
* @pre hasBrainKey();
* @post save()
2015-07-24 17:57:47 +00:00
* @return WIF private key
2015-07-22 20:23:42 +00:00
*/
Q_INVOKABLE QString getOwnerPrivateKey(uint32_t sequence);
Q_INVOKABLE QString getOwnerPublicKey(uint32_t sequence);
Q_INVOKABLE QString getPublicKey(QString wif_private_key)const;
2015-07-22 20:23:42 +00:00
Q_INVOKABLE QString getKeyLabel(QString pubkey);
Q_INVOKABLE bool setKeyLabel(QString pubkey, QString label);
Q_INVOKABLE QString getPublicKey(QString label);
Q_INVOKABLE QString getPrivateKey(QString pubkey);
Q_INVOKABLE bool hasPrivateKey(QString pubkey, bool include_with_brain_key = false);
2015-07-22 20:23:42 +00:00
/** imports a public key and assigns it a label */
Q_INVOKABLE bool importPublicKey(QString pubkey, QString label = QString());
2015-07-22 20:23:42 +00:00
2015-07-24 17:57:47 +00:00
/**
2015-07-22 20:23:42 +00:00
* @param wifkey a private key in (WIF) Wallet Import Format
2015-07-24 17:57:47 +00:00
* @pre !isLocked()
2015-07-22 20:23:42 +00:00
**/
Q_INVOKABLE bool importPrivateKey(QString wifkey, QString label = QString());
2015-07-22 20:23:42 +00:00
/** removes the key, its lablel and its private key */
Q_INVOKABLE bool removePublicKey(QString pubkey);
2015-07-22 20:23:42 +00:00
/** removes only the private key, keeping the public key and label */
Q_INVOKABLE bool removePrivateKey(QString pubkey);
2015-07-22 20:23:42 +00:00
2015-07-23 13:32:29 +00:00
/**
* @param only_if_private filter any public keys for which the wallet lacks a private key
* @return a list of PUBLICKEY, LABEL for all known public keys
*/
Q_INVOKABLE QList<QPair<QString,QString>> getAllPublicKeys(bool only_if_private)const;
2015-07-22 20:23:42 +00:00
/**
* @pre !isLocked()
*/
Q_INVOKABLE void sign(Transaction* transaction) const;
vector<signature_type> signDigest(const digest_type& d,
const set<public_key_type>& keys)const;
2015-07-22 20:23:42 +00:00
const flat_set<public_key_type>& getAvailablePrivateKeys()const;
Q_SIGNALS:
void isLockedChanged(bool state);
void isOpenChanged(bool state);
2015-07-22 20:23:42 +00:00
private:
fc::path _wallet_file_path;
wallet_file _data;
2015-07-22 20:59:22 +00:00
/** used to decrypt all of the encrypted private keys */
2015-07-22 20:23:42 +00:00
fc::sha512 _decrypted_master_key;
flat_set<public_key_type> _available_private_keys;
map<QString,QString> _label_to_key;
2015-07-22 20:59:22 +00:00
QString _brain_key;
2015-07-22 20:23:42 +00:00
};
QML_DECLARE_TYPE(Wallet)
FC_REFLECT( key_data, (label)(encrypted_private_key)(brain_sequence)(owner) )
FC_REFLECT( wallet_file,
(encrypted_brain_key)
(brain_key_digest)
(encrypted_master_key)
(master_key_digest)
(encrypted_private_keys)
)