Use the default UA-based Sapling address for the saplingmigration tool.

This commit is contained in:
Kris Nuttycombe 2021-09-24 15:20:13 -06:00
parent f6ad523ccb
commit 290b2e4e39
5 changed files with 37 additions and 14 deletions

View File

@ -564,4 +564,12 @@ BOOST_AUTO_TEST_CASE( getmaxcoverage ) // some more tests just to get 100% cover
CHECKBITWISEOPERATOR(R1,~R2,&)
}
BOOST_AUTO_TEST_CASE( blob88_increment )
{
blob88 bzero(0);
blob88 bone(1);
BOOST_CHECK(bzero.increment());
BOOST_CHECK(bzero == bone);
}
BOOST_AUTO_TEST_SUITE_END()

View File

@ -120,18 +120,15 @@ public:
}
explicit blob88(const std::vector<unsigned char>& vch) : base_blob<88>(vch) {}
std::optional<blob88> increment() const {
blob88 result = *this;
bool increment() {
for (int i = 0; i < 11; i++) {
result.data[i] += 1;
if (result.data[i] != 0) {
// no overflow
return result;
this->data[i] += 1;
if (this->data[i] != 0) {
return true; // no overflow
}
}
return std::nullopt;
return false; //overflow
}
// treat as little-endian for numeric comparison

View File

@ -192,6 +192,7 @@ CAmount AsyncRPCOperation_saplingmigration::chooseAmount(const CAmount& availabl
}
// Unless otherwise specified, the migration destination address is the address for Sapling account 0
// at the smallest diversifier index which produces a valid diversified address.
libzcash::SaplingPaymentAddress AsyncRPCOperation_saplingmigration::getMigrationDestAddress(const HDSeed& seed) {
KeyIO keyIO(Params());
if (mapArgs.count("-migrationdestaddress")) {
@ -202,12 +203,12 @@ libzcash::SaplingPaymentAddress AsyncRPCOperation_saplingmigration::getMigration
return *saplingAddress;
}
// TODO: use UVK-based derivation here instead.
auto usk = pwalletMain->GetUnifiedSpendingKeyForAccount(0);
assert(usk.has_value()); // mnemonic seeds are currently always generated to have valid USKs at account 0
auto xsk = usk.value().GetSaplingExtendedSpendingKey();
if (xsk.has_value()) {
return xsk.value().ToXFVK().DefaultAddress();
auto ua = usk.value().ToFullViewingKey().FindAddress(libzcash::diversifier_index_t(0));
auto addr = ua.first.GetSaplingPaymentAddress();
if (addr.has_value()) {
return addr.value();
} else {
// This error will only occur if Sapling address generation has been disbled for USKs from this
// wallet.

View File

@ -394,8 +394,15 @@ UnifiedSpendingKey CWallet::GenerateNewUnifiedSpendingKey() {
}
std::optional<libzcash::UnifiedSpendingKey> CWallet::GetUnifiedSpendingKeyForAccount(uint32_t accountId) {
//TODO
return std::nullopt;
auto seed = GetMnemonicSeed();
assert(seed.has_value());
// TODO: is there any reason to cache and not re-derive this every time?
auto usk = UnifiedSpendingKey::Derive(seed.value(), BIP44CoinType(), accountId);
if (usk.has_value()) {
return usk.value().first;
} else {
return std::nullopt;
}
}
void CWallet::LoadKeyMetadata(const CPubKey &pubkey, const CKeyMetadata &meta)

View File

@ -321,6 +321,16 @@ public:
}
std::optional<ZcashdUnifiedAddress> Address(diversifier_index_t j) const;
std::pair<ZcashdUnifiedAddress, diversifier_index_t> FindAddress(diversifier_index_t j) const {
auto addr = Address(j);
while (!addr.has_value()) {
if (!j.increment())
throw std::runtime_error(std::string(__func__) + ": diversifier index overflow.");;
addr = Address(j);
}
return std::make_pair(addr.value(), j);
}
};
class UnifiedSpendingKey {