@@ -70,38 +70,45 @@ bool HasAnyRecordOfType(WalletDatabase& db, const std::string& key)
70
70
return false ;
71
71
}
72
72
73
- BOOST_FIXTURE_TEST_CASE (wallet_load_verif_crypted_key_checksum, TestingSetup)
73
+ template <typename ... Args>
74
+ SerializeData MakeSerializeData (const Args&... args)
74
75
{
75
- // The test duplicates the db so each case has its own db instance.
76
- int NUMBER_OF_TESTS = 4 ;
77
- std::vector<std::unique_ptr<WalletDatabase>> dbs;
78
- CKey first_key;
79
- auto get_db = [](std::vector<std::unique_ptr<WalletDatabase>>& dbs) {
80
- std::unique_ptr<WalletDatabase> db = std::move (dbs.back ());
81
- dbs.pop_back ();
82
- return db;
83
- };
84
-
85
- { // Context setup.
76
+ CDataStream s (0 , 0 );
77
+ SerializeMany (s, args...);
78
+ return {s.begin (), s.end ()};
79
+ }
80
+
81
+
82
+ BOOST_FIXTURE_TEST_CASE (wallet_load_ckey, TestingSetup)
83
+ {
84
+ SerializeData ckey_record_key;
85
+ SerializeData ckey_record_value;
86
+ std::map<SerializeData, SerializeData> records;
87
+
88
+ {
89
+ // Context setup.
86
90
// Create and encrypt legacy wallet
87
91
std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , CreateMockableWalletDatabase ()));
88
92
LOCK (wallet->cs_wallet );
89
93
auto legacy_spkm = wallet->GetOrCreateLegacyScriptPubKeyMan ();
90
94
BOOST_CHECK (legacy_spkm->SetupGeneration (true ));
91
95
92
- // Get the first key in the wallet
96
+ // Retrieve a key
93
97
CTxDestination dest = *Assert (legacy_spkm->GetNewDestination (OutputType::LEGACY));
94
98
CKeyID key_id = GetKeyForDestination (*legacy_spkm, dest);
99
+ CKey first_key;
95
100
BOOST_CHECK (legacy_spkm->GetKey (key_id, first_key));
96
101
97
- // Encrypt the wallet and duplicate database
102
+ // Encrypt the wallet
98
103
BOOST_CHECK (wallet->EncryptWallet (" encrypt" ));
99
104
wallet->Flush ();
100
105
101
- DatabaseOptions options;
102
- for (int i=0 ; i < NUMBER_OF_TESTS; i++) {
103
- dbs.emplace_back (DuplicateMockDatabase (wallet->GetDatabase ()));
104
- }
106
+ // Store a copy of all the records
107
+ records = GetMockableDatabase (*wallet).m_records ;
108
+
109
+ // Get the record for the retrieved key
110
+ ckey_record_key = MakeSerializeData (DBKeys::CRYPTED_KEY, first_key.GetPubKey ());
111
+ ckey_record_value = records.at (ckey_record_key);
105
112
}
106
113
107
114
{
@@ -112,7 +119,7 @@ BOOST_FIXTURE_TEST_CASE(wallet_load_verif_crypted_key_checksum, TestingSetup)
112
119
// the records every time that 'CWallet::Unlock' gets called, which is not good.
113
120
114
121
// Load the wallet and check that is encrypted
115
- std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , get_db (dbs )));
122
+ std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , CreateMockableWalletDatabase (records )));
116
123
BOOST_CHECK_EQUAL (wallet->LoadWallet (), DBErrors::LOAD_OK);
117
124
BOOST_CHECK (wallet->IsCrypted ());
118
125
BOOST_CHECK (HasAnyRecordOfType (wallet->GetDatabase (), DBKeys::CRYPTED_KEY));
@@ -127,18 +134,12 @@ BOOST_FIXTURE_TEST_CASE(wallet_load_verif_crypted_key_checksum, TestingSetup)
127
134
{
128
135
// Second test case:
129
136
// Verify that loading up a 'ckey' with no checksum triggers a complete re-write of the crypted keys.
130
- std::unique_ptr<WalletDatabase> db = get_db (dbs);
131
- {
132
- std::unique_ptr<DatabaseBatch> batch = db->MakeBatch (false );
133
- std::pair<std::vector<unsigned char >, uint256> value;
134
- BOOST_CHECK (batch->Read (std::make_pair (DBKeys::CRYPTED_KEY, first_key.GetPubKey ()), value));
135
137
136
- const auto key = std::make_pair (DBKeys::CRYPTED_KEY, first_key.GetPubKey ());
137
- BOOST_CHECK (batch->Write (key, value.first , /* fOverwrite=*/ true ));
138
- }
138
+ // Cut off the 32 byte checksum from a ckey record
139
+ records[ckey_record_key].resize (ckey_record_value.size () - 32 );
139
140
140
141
// Load the wallet and check that is encrypted
141
- std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , std::move (db )));
142
+ std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , CreateMockableWalletDatabase (records )));
142
143
BOOST_CHECK_EQUAL (wallet->LoadWallet (), DBErrors::LOAD_OK);
143
144
BOOST_CHECK (wallet->IsCrypted ());
144
145
BOOST_CHECK (HasAnyRecordOfType (wallet->GetDatabase (), DBKeys::CRYPTED_KEY));
@@ -154,35 +155,25 @@ BOOST_FIXTURE_TEST_CASE(wallet_load_verif_crypted_key_checksum, TestingSetup)
154
155
{
155
156
// Third test case:
156
157
// Verify that loading up a 'ckey' with an invalid checksum throws an error.
157
- std::unique_ptr<WalletDatabase> db = get_db (dbs);
158
- {
159
- std::unique_ptr<DatabaseBatch> batch = db->MakeBatch (false );
160
- std::vector<unsigned char > crypted_data;
161
- BOOST_CHECK (batch->Read (std::make_pair (DBKeys::CRYPTED_KEY, first_key.GetPubKey ()), crypted_data));
162
-
163
- // Write an invalid checksum
164
- std::pair<std::vector<unsigned char >, uint256> value = std::make_pair (crypted_data, uint256::ONE);
165
- const auto key = std::make_pair (DBKeys::CRYPTED_KEY, first_key.GetPubKey ());
166
- BOOST_CHECK (batch->Write (key, value, /* fOverwrite=*/ true ));
167
- }
168
-
169
- std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , std::move (db)));
158
+
159
+ // Cut off the 32 byte checksum from a ckey record
160
+ records[ckey_record_key].resize (ckey_record_value.size () - 32 );
161
+ // Fill in the checksum space with 0s
162
+ records[ckey_record_key].resize (ckey_record_value.size ());
163
+
164
+ std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , CreateMockableWalletDatabase (records)));
170
165
BOOST_CHECK_EQUAL (wallet->LoadWallet (), DBErrors::CORRUPT);
171
166
}
172
167
173
168
{
174
169
// Fourth test case:
175
170
// Verify that loading up a 'ckey' with an invalid pubkey throws an error
176
- std::unique_ptr<WalletDatabase> db = get_db (dbs);
177
- {
178
- CPubKey invalid_key;
179
- BOOST_ASSERT (!invalid_key.IsValid ());
180
- const auto key = std::make_pair (DBKeys::CRYPTED_KEY, invalid_key);
181
- std::pair<std::vector<unsigned char >, uint256> value;
182
- BOOST_CHECK (db->MakeBatch (false )->Write (key, value, /* fOverwrite=*/ true ));
183
- }
184
-
185
- std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , std::move (db)));
171
+ CPubKey invalid_key;
172
+ BOOST_ASSERT (!invalid_key.IsValid ());
173
+ SerializeData key = MakeSerializeData (DBKeys::CRYPTED_KEY, invalid_key);
174
+ records[key] = ckey_record_value;
175
+
176
+ std::shared_ptr<CWallet> wallet (new CWallet (m_node.chain .get (), " " , CreateMockableWalletDatabase (records)));
186
177
BOOST_CHECK_EQUAL (wallet->LoadWallet (), DBErrors::CORRUPT);
187
178
}
188
179
}
0 commit comments