1 // Copyright (c) 2009-2010 Satoshi Nakamoto
2 // Copyright (c) 2009-2018 The Bitcoin Core developers
3 // Distributed under the MIT software license, see the accompanying
4 // file COPYING or http://www.opensource.org/licenses/mit-license.php.
5 
6 #ifndef BITCOIN_KEYSTORE_H
7 #define BITCOIN_KEYSTORE_H
8 
9 #include <key.h>
10 #include <pubkey.h>
11 #include <script/script.h>
12 #include <script/sign.h>
13 #include <script/standard.h>
14 #include <sync.h>
15 
16 #include <boost/signals2/signal.hpp>
17 
18 /** A virtual base class for key stores */
19 class CKeyStore : public SigningProvider
20 {
21 public:
22     //! Add a key to the store.
23     virtual bool AddKeyPubKey(const CKey &key, const CPubKey &pubkey) =0;
24 
25     //! Check whether a key corresponding to a given address is present in the store.
26     virtual bool HaveKey(const CKeyID &address) const =0;
27     virtual std::set<CKeyID> GetKeys() const =0;
28 
29     //! Support for BIP 0013 : see https://github.com/bitcoin/bips/blob/master/bip-0013.mediawiki
30     virtual bool AddCScript(const CScript& redeemScript) =0;
31     virtual bool HaveCScript(const CScriptID &hash) const =0;
32     virtual std::set<CScriptID> GetCScripts() const =0;
33 
34     //! Support for Watch-only addresses
35     virtual bool AddWatchOnly(const CScript &dest) =0;
36     virtual bool RemoveWatchOnly(const CScript &dest) =0;
37     virtual bool HaveWatchOnly(const CScript &dest) const =0;
38     virtual bool HaveWatchOnly() const =0;
39 };
40 
41 /** Basic key store, that keeps keys in an address->secret map */
42 class CBasicKeyStore : public CKeyStore
43 {
44 protected:
45     mutable CCriticalSection cs_KeyStore;
46 
47     using KeyMap = std::map<CKeyID, CKey>;
48     using WatchKeyMap = std::map<CKeyID, CPubKey>;
49     using ScriptMap = std::map<CScriptID, CScript>;
50     using WatchOnlySet = std::set<CScript>;
51 
52     KeyMap mapKeys GUARDED_BY(cs_KeyStore);
53     WatchKeyMap mapWatchKeys GUARDED_BY(cs_KeyStore);
54     ScriptMap mapScripts GUARDED_BY(cs_KeyStore);
55     WatchOnlySet setWatchOnly GUARDED_BY(cs_KeyStore);
56 
57     void ImplicitlyLearnRelatedKeyScripts(const CPubKey& pubkey) EXCLUSIVE_LOCKS_REQUIRED(cs_KeyStore);
58 
59 public:
60     bool AddKeyPubKey(const CKey& key, const CPubKey &pubkey) override;
AddKey(const CKey & key)61     bool AddKey(const CKey &key) { return AddKeyPubKey(key, key.GetPubKey()); }
62     bool GetPubKey(const CKeyID &address, CPubKey& vchPubKeyOut) const override;
63     bool HaveKey(const CKeyID &address) const override;
64     std::set<CKeyID> GetKeys() const override;
65     bool GetKey(const CKeyID &address, CKey &keyOut) const override;
66     bool AddCScript(const CScript& redeemScript) override;
67     bool HaveCScript(const CScriptID &hash) const override;
68     std::set<CScriptID> GetCScripts() const override;
69     bool GetCScript(const CScriptID &hash, CScript& redeemScriptOut) const override;
70 
71     bool AddWatchOnly(const CScript &dest) override;
72     bool RemoveWatchOnly(const CScript &dest) override;
73     bool HaveWatchOnly(const CScript &dest) const override;
74     bool HaveWatchOnly() const override;
75 };
76 
77 /** Return the CKeyID of the key involved in a script (if there is a unique one). */
78 CKeyID GetKeyForDestination(const CKeyStore& store, const CTxDestination& dest);
79 
80 /** Checks if a CKey is in the given CKeyStore compressed or otherwise*/
81 bool HaveKey(const CKeyStore& store, const CKey& key);
82 
83 #endif // BITCOIN_KEYSTORE_H
84