diff --git a/src/bench/ccoins_caching.cpp b/src/bench/ccoins_caching.cpp
--- a/src/bench/ccoins_caching.cpp
+++ b/src/bench/ccoins_caching.cpp
@@ -41,10 +41,10 @@
     dummyTransactions[1].vout.resize(2);
     dummyTransactions[1].vout[0].nValue = 21 * COIN;
     dummyTransactions[1].vout[0].scriptPubKey =
-        GetScriptForDestination(key[2].GetPubKey().GetID());
+        GetScriptForDestination(PKHash(key[2].GetPubKey()));
     dummyTransactions[1].vout[1].nValue = 22 * COIN;
     dummyTransactions[1].vout[1].scriptPubKey =
-        GetScriptForDestination(key[3].GetPubKey().GetID());
+        GetScriptForDestination(PKHash(key[3].GetPubKey()));
     AddCoins(coinsRet, CTransaction(dummyTransactions[1]), 0);
 
     return dummyTransactions;
diff --git a/src/bitcoin-tx.cpp b/src/bitcoin-tx.cpp
--- a/src/bitcoin-tx.cpp
+++ b/src/bitcoin-tx.cpp
@@ -349,7 +349,7 @@
     if (bScriptHash) {
         // Get the ID for the script, and then construct a P2SH destination for
         // it.
-        scriptPubKey = GetScriptForDestination(CScriptID(scriptPubKey));
+        scriptPubKey = GetScriptForDestination(ScriptHash(scriptPubKey));
     }
 
     // construct TxOut, append to transaction output list
@@ -420,7 +420,7 @@
         }
         // Get the ID for the script, and then construct a P2SH destination for
         // it.
-        scriptPubKey = GetScriptForDestination(CScriptID(scriptPubKey));
+        scriptPubKey = GetScriptForDestination(ScriptHash(scriptPubKey));
     }
 
     // construct TxOut, append to transaction output list
@@ -492,7 +492,7 @@
                 strprintf("redeemScript exceeds size limit: %d > %d",
                           scriptPubKey.size(), MAX_SCRIPT_ELEMENT_SIZE));
         }
-        scriptPubKey = GetScriptForDestination(CScriptID(scriptPubKey));
+        scriptPubKey = GetScriptForDestination(ScriptHash(scriptPubKey));
     }
 
     // construct TxOut, append to transaction output list
diff --git a/src/cashaddrenc.cpp b/src/cashaddrenc.cpp
--- a/src/cashaddrenc.cpp
+++ b/src/cashaddrenc.cpp
@@ -70,12 +70,12 @@
 public:
     CashAddrEncoder(const CChainParams &p) : params(p) {}
 
-    std::string operator()(const CKeyID &id) const {
+    std::string operator()(const PKHash &id) const {
         std::vector<uint8_t> data = PackAddrData(id, PUBKEY_TYPE);
         return cashaddr::Encode(params.CashAddrPrefix(), data);
     }
 
-    std::string operator()(const CScriptID &id) const {
+    std::string operator()(const ScriptHash &id) const {
         std::vector<uint8_t> data = PackAddrData(id, SCRIPT_TYPE);
         return cashaddr::Encode(params.CashAddrPrefix(), data);
     }
@@ -165,9 +165,9 @@
 
     switch (content.type) {
         case PUBKEY_TYPE:
-            return CKeyID(hash);
+            return PKHash(hash);
         case SCRIPT_TYPE:
-            return CScriptID(hash);
+            return ScriptHash(hash);
         default:
             return CNoDestination{};
     }
diff --git a/src/key_io.cpp b/src/key_io.cpp
--- a/src/key_io.cpp
+++ b/src/key_io.cpp
@@ -27,14 +27,14 @@
     explicit DestinationEncoder(const CChainParams &params)
         : m_params(params) {}
 
-    std::string operator()(const CKeyID &id) const {
+    std::string operator()(const PKHash &id) const {
         std::vector<uint8_t> data =
             m_params.Base58Prefix(CChainParams::PUBKEY_ADDRESS);
         data.insert(data.end(), id.begin(), id.end());
         return EncodeBase58Check(data);
     }
 
-    std::string operator()(const CScriptID &id) const {
+    std::string operator()(const ScriptHash &id) const {
         std::vector<uint8_t> data =
             m_params.Base58Prefix(CChainParams::SCRIPT_ADDRESS);
         data.insert(data.end(), id.begin(), id.end());
@@ -61,7 +61,7 @@
         std::equal(pubkey_prefix.begin(), pubkey_prefix.end(), data.begin())) {
         std::copy(data.begin() + pubkey_prefix.size(), data.end(),
                   hash.begin());
-        return CKeyID(hash);
+        return PKHash(hash);
     }
     // Script-hash-addresses have version 5 (or 196 testnet).
     // The data vector contains RIPEMD160(SHA256(cscript)), where cscript is
@@ -72,7 +72,7 @@
         std::equal(script_prefix.begin(), script_prefix.end(), data.begin())) {
         std::copy(data.begin() + script_prefix.size(), data.end(),
                   hash.begin());
-        return CScriptID(hash);
+        return ScriptHash(hash);
     }
     return CNoDestination();
 }
diff --git a/src/keystore.cpp b/src/keystore.cpp
--- a/src/keystore.cpp
+++ b/src/keystore.cpp
@@ -164,8 +164,8 @@
 CKeyID GetKeyForDestination(const CKeyStore &store,
                             const CTxDestination &dest) {
     // Only supports destinations which map to single public keys, i.e. P2PKH.
-    if (auto id = boost::get<CKeyID>(&dest)) {
-        return *id;
+    if (auto id = boost::get<PKHash>(&dest)) {
+        return CKeyID(*id);
     }
     return CKeyID();
 }
diff --git a/src/outputtype.cpp b/src/outputtype.cpp
--- a/src/outputtype.cpp
+++ b/src/outputtype.cpp
@@ -35,14 +35,15 @@
 CTxDestination GetDestinationForKey(const CPubKey &key, OutputType type) {
     switch (type) {
         case OutputType::LEGACY:
-            return key.GetID();
+            return PKHash(key);
         default:
             assert(false);
     }
 }
 
 std::vector<CTxDestination> GetAllDestinationsForKey(const CPubKey &key) {
-    return std::vector<CTxDestination>{key.GetID()};
+    PKHash keyid(key);
+    return std::vector<CTxDestination>{std::move(keyid)};
 }
 
 CTxDestination AddAndGetDestinationForScript(CKeyStore &keystore,
@@ -53,7 +54,7 @@
     // Note that scripts over 520 bytes are not yet supported.
     switch (type) {
         case OutputType::LEGACY:
-            return CScriptID(script);
+            return ScriptHash(script);
         default:
             assert(false);
     }
diff --git a/src/qt/coincontroldialog.cpp b/src/qt/coincontroldialog.cpp
--- a/src/qt/coincontroldialog.cpp
+++ b/src/qt/coincontroldialog.cpp
@@ -508,8 +508,8 @@
         CTxDestination address;
         if (ExtractDestination(out.txout.scriptPubKey, address)) {
             CPubKey pubkey;
-            CKeyID *keyid = boost::get<CKeyID>(&address);
-            if (keyid && model->wallet().getPubKey(*keyid, pubkey)) {
+            PKHash *pkhash = boost::get<PKHash>(&address);
+            if (pkhash && model->wallet().getPubKey(CKeyID(*pkhash), pubkey)) {
                 nBytesInputs += (pubkey.IsCompressed() ? 148 : 180);
             } else {
                 // in all error cases, simply assume 148 here
diff --git a/src/qt/guiutil.cpp b/src/qt/guiutil.cpp
--- a/src/qt/guiutil.cpp
+++ b/src/qt/guiutil.cpp
@@ -111,7 +111,7 @@
         0xeb, 0x15, 0x23, 0x1d, 0xfc, 0xeb, 0x60, 0x92, 0x58, 0x86,
         0xb6, 0x7d, 0x06, 0x52, 0x99, 0x92, 0x59, 0x15, 0xae, 0xb1};
 
-    const CTxDestination dstKey = CKeyID(uint160(dummydata));
+    const CTxDestination dstKey = PKHash(uint160(dummydata));
     return MakeAddrInvalid(EncodeCashAddr(dstKey, params), params);
 }
 
diff --git a/src/qt/signverifymessagedialog.cpp b/src/qt/signverifymessagedialog.cpp
--- a/src/qt/signverifymessagedialog.cpp
+++ b/src/qt/signverifymessagedialog.cpp
@@ -123,8 +123,8 @@
             tr("Please check the address and try again."));
         return;
     }
-    const CKeyID *keyID = boost::get<CKeyID>(&destination);
-    if (!keyID) {
+    const PKHash *pkhash = boost::get<PKHash>(&destination);
+    if (!pkhash) {
         ui->addressIn_SM->setValid(false);
         ui->statusLabel_SM->setStyleSheet("QLabel { color: red; }");
         ui->statusLabel_SM->setText(
@@ -141,7 +141,7 @@
     }
 
     CKey key;
-    if (!model->wallet().getPrivKey(*keyID, key)) {
+    if (!model->wallet().getPrivKey(CKeyID(*pkhash), key)) {
         ui->statusLabel_SM->setStyleSheet("QLabel { color: red; }");
         ui->statusLabel_SM->setText(
             tr("Private key for the entered address is not available."));
@@ -203,7 +203,7 @@
             tr("Please check the address and try again."));
         return;
     }
-    if (!boost::get<CKeyID>(&destination)) {
+    if (!boost::get<PKHash>(&destination)) {
         ui->addressIn_VM->setValid(false);
         ui->statusLabel_VM->setStyleSheet("QLabel { color: red; }");
         ui->statusLabel_VM->setText(
@@ -239,7 +239,7 @@
         return;
     }
 
-    if (!(CTxDestination(pubkey.GetID()) == destination)) {
+    if (!(CTxDestination(PKHash(pubkey)) == destination)) {
         ui->statusLabel_VM->setStyleSheet("QLabel { color: red; }");
         ui->statusLabel_VM->setText(QString("<nobr>") +
                                     tr("Message verification failed.") +
diff --git a/src/qt/test/wallettests.cpp b/src/qt/test/wallettests.cpp
--- a/src/qt/test/wallettests.cpp
+++ b/src/qt/test/wallettests.cpp
@@ -159,9 +159,9 @@
         walletModel.getTransactionTableModel();
     QCOMPARE(transactionTableModel->rowCount({}), 105);
     TxId txid1 = SendCoins(*wallet.get(), sendCoinsDialog,
-                           CTxDestination(CKeyID()), 5 * COIN);
+                           CTxDestination(PKHash()), 5 * COIN);
     TxId txid2 = SendCoins(*wallet.get(), sendCoinsDialog,
-                           CTxDestination(CKeyID()), 10 * COIN);
+                           CTxDestination(PKHash()), 10 * COIN);
     QCOMPARE(transactionTableModel->rowCount({}), 107);
     QVERIFY(FindTx(*transactionTableModel, txid1).isValid());
     QVERIFY(FindTx(*transactionTableModel, txid2).isValid());
diff --git a/src/rpc/misc.cpp b/src/rpc/misc.cpp
--- a/src/rpc/misc.cpp
+++ b/src/rpc/misc.cpp
@@ -332,8 +332,8 @@
         throw JSONRPCError(RPC_TYPE_ERROR, "Invalid address");
     }
 
-    const CKeyID *keyID = boost::get<CKeyID>(&destination);
-    if (!keyID) {
+    const PKHash *pkhash = boost::get<PKHash>(&destination);
+    if (!pkhash) {
         throw JSONRPCError(RPC_TYPE_ERROR, "Address does not refer to key");
     }
 
@@ -354,7 +354,7 @@
         return false;
     }
 
-    return (pubkey.GetID() == *keyID);
+    return (pubkey.GetID() == *pkhash);
 }
 
 static UniValue signmessagewithprivkey(const Config &config,
diff --git a/src/rpc/rawtransaction.cpp b/src/rpc/rawtransaction.cpp
--- a/src/rpc/rawtransaction.cpp
+++ b/src/rpc/rawtransaction.cpp
@@ -674,7 +674,7 @@
     if (type.isStr() && type.get_str() != "scripthash") {
         // P2SH cannot be wrapped in a P2SH. If this script is already a P2SH,
         // don't return the address for a P2SH of the P2SH.
-        r.pushKV("p2sh", EncodeDestination(CScriptID(script), config));
+        r.pushKV("p2sh", EncodeDestination(ScriptHash(script), config));
     }
 
     return r;
diff --git a/src/rpc/util.cpp b/src/rpc/util.cpp
--- a/src/rpc/util.cpp
+++ b/src/rpc/util.cpp
@@ -225,13 +225,13 @@
         return UniValue(UniValue::VOBJ);
     }
 
-    UniValue operator()(const CKeyID &keyID) const {
+    UniValue operator()(const PKHash &keyID) const {
         UniValue obj(UniValue::VOBJ);
         obj.pushKV("isscript", false);
         return obj;
     }
 
-    UniValue operator()(const CScriptID &scriptID) const {
+    UniValue operator()(const ScriptHash &scriptID) const {
         UniValue obj(UniValue::VOBJ);
         obj.pushKV("isscript", true);
         return obj;
diff --git a/src/script/descriptor.cpp b/src/script/descriptor.cpp
--- a/src/script/descriptor.cpp
+++ b/src/script/descriptor.cpp
@@ -510,7 +510,7 @@
                                      FlatSigningProvider &out) const override {
         CKeyID id = keys[0].GetID();
         out.pubkeys.emplace(id, keys[0]);
-        return Singleton(GetScriptForDestination(id));
+        return Singleton(GetScriptForDestination(PKHash(id)));
     }
 
 public:
@@ -530,7 +530,7 @@
         // P2PK
         ret.emplace_back(GetScriptForRawPubKey(keys[0]));
         // P2PKH
-        ret.emplace_back(GetScriptForDestination(id));
+        ret.emplace_back(GetScriptForDestination(PKHash(id)));
         return ret;
     }
 
@@ -566,7 +566,7 @@
     std::vector<CScript> MakeScripts(const std::vector<CPubKey> &,
                                      const CScript *script,
                                      FlatSigningProvider &) const override {
-        return Singleton(GetScriptForDestination(CScriptID(*script)));
+        return Singleton(GetScriptForDestination(ScriptHash(*script)));
     }
 
 public:
diff --git a/src/script/standard.h b/src/script/standard.h
--- a/src/script/standard.h
+++ b/src/script/standard.h
@@ -61,14 +61,28 @@
     }
 };
 
+struct PKHash : public uint160 {
+    PKHash() : uint160() {}
+    explicit PKHash(const uint160 &hash) : uint160(hash) {}
+    explicit PKHash(const CPubKey &pubkey);
+    using uint160::uint160;
+};
+
+struct ScriptHash : public uint160 {
+    ScriptHash() : uint160() {}
+    explicit ScriptHash(const uint160 &hash) : uint160(hash) {}
+    explicit ScriptHash(const CScript &script);
+    using uint160::uint160;
+};
+
 /**
  * A txout script template with a specific destination. It is either:
  *  * CNoDestination: no destination set
- *  * CKeyID: TX_PUBKEYHASH destination
- *  * CScriptID: TX_SCRIPTHASH destination
+ *  * PKHash: TX_PUBKEYHASH destination (P2PKH)
+ *  * ScriptHash: TX_SCRIPTHASH destination (P2SH)
  *  A CTxDestination is the internal data type encoded in a bitcoin address
  */
-typedef boost::variant<CNoDestination, CKeyID, CScriptID> CTxDestination;
+typedef boost::variant<CNoDestination, PKHash, ScriptHash> CTxDestination;
 
 /** Check whether a CTxDestination is a CNoDestination. */
 bool IsValidDestination(const CTxDestination &dest);
diff --git a/src/script/standard.cpp b/src/script/standard.cpp
--- a/src/script/standard.cpp
+++ b/src/script/standard.cpp
@@ -16,6 +16,11 @@
 CScriptID::CScriptID(const CScript &in)
     : uint160(Hash160(in.begin(), in.end())) {}
 
+ScriptHash::ScriptHash(const CScript &in)
+    : uint160(Hash160(in.begin(), in.end())) {}
+
+PKHash::PKHash(const CPubKey &pubkey) : uint160(pubkey.GetID()) {}
+
 const char *GetTxnOutputType(txnouttype t) {
     switch (t) {
         case TX_NONSTANDARD:
@@ -158,15 +163,15 @@
             return false;
         }
 
-        addressRet = pubKey.GetID();
+        addressRet = PKHash(pubKey);
         return true;
     }
     if (whichType == TX_PUBKEYHASH) {
-        addressRet = CKeyID(uint160(vSolutions[0]));
+        addressRet = PKHash(uint160(vSolutions[0]));
         return true;
     }
     if (whichType == TX_SCRIPTHASH) {
-        addressRet = CScriptID(uint160(vSolutions[0]));
+        addressRet = ScriptHash(uint160(vSolutions[0]));
         return true;
     }
     // Multisig txns have more than one address...
@@ -194,7 +199,7 @@
                 continue;
             }
 
-            CTxDestination address = pubKey.GetID();
+            CTxDestination address = PKHash(pubKey);
             addressRet.push_back(address);
         }
 
@@ -226,14 +231,14 @@
         return false;
     }
 
-    bool operator()(const CKeyID &keyID) const {
+    bool operator()(const PKHash &keyID) const {
         script->clear();
         *script << OP_DUP << OP_HASH160 << ToByteVector(keyID) << OP_EQUALVERIFY
                 << OP_CHECKSIG;
         return true;
     }
 
-    bool operator()(const CScriptID &scriptID) const {
+    bool operator()(const ScriptHash &scriptID) const {
         script->clear();
         *script << OP_HASH160 << ToByteVector(scriptID) << OP_EQUAL;
         return true;
diff --git a/src/test/blockfilter_index_tests.cpp b/src/test/blockfilter_index_tests.cpp
--- a/src/test/blockfilter_index_tests.cpp
+++ b/src/test/blockfilter_index_tests.cpp
@@ -162,7 +162,7 @@
         tip = ::ChainActive().Tip();
     }
     CScript coinbase_script_pub_key =
-        GetScriptForDestination(coinbaseKey.GetPubKey().GetID());
+        GetScriptForDestination(PKHash(coinbaseKey.GetPubKey()));
     std::vector<std::shared_ptr<CBlock>> chainA, chainB;
     BOOST_REQUIRE(BuildChain(tip, coinbase_script_pub_key, 10, chainA));
     BOOST_REQUIRE(BuildChain(tip, coinbase_script_pub_key, 10, chainB));
diff --git a/src/test/cashaddrenc_tests.cpp b/src/test/cashaddrenc_tests.cpp
--- a/src/test/cashaddrenc_tests.cpp
+++ b/src/test/cashaddrenc_tests.cpp
@@ -10,6 +10,8 @@
 #include <uint256.h>
 #include <util/strencodings.h>
 
+#include <key_io.h>
+
 #include <test/util/setup_common.h>
 
 #include <boost/test/unit_test.hpp>
@@ -42,8 +44,8 @@
 
 class DstTypeChecker : public boost::static_visitor<void> {
 public:
-    void operator()(const CKeyID &id) { isKey = true; }
-    void operator()(const CScriptID &id) { isScript = true; }
+    void operator()(const PKHash &id) { isKey = true; }
+    void operator()(const ScriptHash &id) { isScript = true; }
     void operator()(const CNoDestination &) {}
 
     static bool IsScriptDst(const CTxDestination &d) {
@@ -108,8 +110,8 @@
 
 BOOST_AUTO_TEST_CASE(encode_decode) {
     std::vector<CTxDestination> toTest = {CNoDestination{},
-                                          CKeyID(uint160S("badf00d")),
-                                          CScriptID(uint160S("f00dbad"))};
+                                          PKHash(uint160S("badf00d")),
+                                          ScriptHash(uint160S("f00dbad"))};
 
     for (auto dst : toTest) {
         for (auto net : GetNetworks()) {
@@ -123,7 +125,7 @@
 
 // Check that an encoded cash address is not valid on another network.
 BOOST_AUTO_TEST_CASE(invalid_on_wrong_network) {
-    const CTxDestination dst = CKeyID(uint160S("c0ffee"));
+    const CTxDestination dst = PKHash(uint160S("c0ffee"));
     const CTxDestination invalidDst = CNoDestination{};
 
     for (auto net : GetNetworks()) {
@@ -151,8 +153,8 @@
 
     for (size_t i = 0; i < NUM_TESTS; ++i) {
         uint160 hash = insecure_GetRandUInt160(rand);
-        const CTxDestination dst_key = CKeyID(hash);
-        const CTxDestination dst_scr = CScriptID(hash);
+        const CTxDestination dst_key = PKHash(hash);
+        const CTxDestination dst_scr = ScriptHash(hash);
 
         const std::string encoded_key = EncodeCashAddr(dst_key, *params);
         const CTxDestination decoded_key = DecodeCashAddr(encoded_key, *params);
@@ -290,13 +292,13 @@
         "bitcoincash:pqq3728yw0y47sqn6l2na30mcw6zm78dzq5ucqzc37"};
 
     for (size_t i = 0; i < hash.size(); ++i) {
-        const CTxDestination dstKey = CKeyID(uint160(hash[i]));
+        const CTxDestination dstKey = PKHash(uint160(hash[i]));
         BOOST_CHECK_EQUAL(pubkey[i], EncodeCashAddr(dstKey, *params));
 
         CashAddrContent keyContent{PUBKEY_TYPE, hash[i]};
         BOOST_CHECK_EQUAL(pubkey[i], EncodeCashAddr("bitcoincash", keyContent));
 
-        const CTxDestination dstScript = CScriptID(uint160(hash[i]));
+        const CTxDestination dstScript = ScriptHash(uint160(hash[i]));
         BOOST_CHECK_EQUAL(script[i], EncodeCashAddr(dstScript, *params));
 
         CashAddrContent scriptContent{SCRIPT_TYPE, hash[i]};
diff --git a/src/test/coins_tests.cpp b/src/test/coins_tests.cpp
--- a/src/test/coins_tests.cpp
+++ b/src/test/coins_tests.cpp
@@ -516,7 +516,7 @@
     BOOST_CHECK_EQUAL(c1.GetHeight(), 203998U);
     BOOST_CHECK_EQUAL(c1.GetTxOut().nValue, int64_t(60000000000) * SATOSHI);
     BOOST_CHECK_EQUAL(HexStr(c1.GetTxOut().scriptPubKey),
-                      HexStr(GetScriptForDestination(CKeyID(uint160(ParseHex(
+                      HexStr(GetScriptForDestination(PKHash(uint160(ParseHex(
                           "816115944e077fe7c803cfa57f29b36bf87c1d35"))))));
 
     // Good example
@@ -529,7 +529,7 @@
     BOOST_CHECK_EQUAL(c2.GetHeight(), 120891U);
     BOOST_CHECK_EQUAL(c2.GetTxOut().nValue, 110397 * SATOSHI);
     BOOST_CHECK_EQUAL(HexStr(c2.GetTxOut().scriptPubKey),
-                      HexStr(GetScriptForDestination(CKeyID(uint160(ParseHex(
+                      HexStr(GetScriptForDestination(PKHash(uint160(ParseHex(
                           "8c988f1a4a4de2161e0f50aac7f17e7f9555caa4"))))));
 
     // Smallest possible example
diff --git a/src/test/denialofservice_tests.cpp b/src/test/denialofservice_tests.cpp
--- a/src/test/denialofservice_tests.cpp
+++ b/src/test/denialofservice_tests.cpp
@@ -417,7 +417,7 @@
         tx.vout.resize(1);
         tx.vout[0].nValue = 1 * CENT;
         tx.vout[0].scriptPubKey =
-            GetScriptForDestination(key.GetPubKey().GetID());
+            GetScriptForDestination(PKHash(key.GetPubKey()));
 
         AddOrphanTx(MakeTransactionRef(tx), i);
     }
@@ -432,7 +432,7 @@
         tx.vout.resize(1);
         tx.vout[0].nValue = 1 * CENT;
         tx.vout[0].scriptPubKey =
-            GetScriptForDestination(key.GetPubKey().GetID());
+            GetScriptForDestination(PKHash(key.GetPubKey()));
         SignSignature(keystore, *txPrev, tx, 0, SigHashType());
 
         AddOrphanTx(MakeTransactionRef(tx), i);
@@ -446,7 +446,7 @@
         tx.vout.resize(1);
         tx.vout[0].nValue = 1 * CENT;
         tx.vout[0].scriptPubKey =
-            GetScriptForDestination(key.GetPubKey().GetID());
+            GetScriptForDestination(PKHash(key.GetPubKey()));
         tx.vin.resize(2777);
         for (size_t j = 0; j < tx.vin.size(); j++) {
             tx.vin[j].prevout = COutPoint(txPrev->GetId(), j);
diff --git a/src/test/dstencode_tests.cpp b/src/test/dstencode_tests.cpp
--- a/src/test/dstencode_tests.cpp
+++ b/src/test/dstencode_tests.cpp
@@ -33,8 +33,8 @@
                                  139, 218, 81,  119, 184, 106, 21,
                                  195, 178, 159, 85,  152, 115};
 
-    const CTxDestination dstKey = CKeyID(uint160(hash));
-    const CTxDestination dstScript = CScriptID(uint160(hash));
+    const CTxDestination dstKey = PKHash(uint160(hash));
+    const CTxDestination dstScript = ScriptHash(uint160(hash));
 
     std::string cashaddr_pubkey =
         "bitcoincash:qpm2qsznhks23z7629mms6s4cwef74vcwvy22gdx6a";
diff --git a/src/test/key_tests.cpp b/src/test/key_tests.cpp
--- a/src/test/key_tests.cpp
+++ b/src/test/key_tests.cpp
@@ -120,13 +120,13 @@
 
     const CChainParams &chainParams = Params();
     BOOST_CHECK(DecodeDestination(addr1, chainParams) ==
-                CTxDestination(pubkey1.GetID()));
+                CTxDestination(PKHash(pubkey1)));
     BOOST_CHECK(DecodeDestination(addr2, chainParams) ==
-                CTxDestination(pubkey2.GetID()));
+                CTxDestination(PKHash(pubkey2)));
     BOOST_CHECK(DecodeDestination(addr1C, chainParams) ==
-                CTxDestination(pubkey1C.GetID()));
+                CTxDestination(PKHash(pubkey1C)));
     BOOST_CHECK(DecodeDestination(addr2C, chainParams) ==
-                CTxDestination(pubkey2C.GetID()));
+                CTxDestination(PKHash(pubkey2C)));
 
     for (int n = 0; n < 16; n++) {
         std::string strMsg = strprintf("Very secret message %i: 11", n);
diff --git a/src/test/miner_tests.cpp b/src/test/miner_tests.cpp
--- a/src/test/miner_tests.cpp
+++ b/src/test/miner_tests.cpp
@@ -455,7 +455,7 @@
     tx.vin[0].scriptSig = CScript() << OP_1;
     tx.vout[0].nValue = BLOCKSUBSIDY - LOWFEE;
     script = CScript() << OP_0;
-    tx.vout[0].scriptPubKey = GetScriptForDestination(CScriptID(script));
+    tx.vout[0].scriptPubKey = GetScriptForDestination(ScriptHash(script));
     txid = tx.GetId();
     g_mempool.addUnchecked(
         entry.Fee(LOWFEE).Time(GetTime()).SpendsCoinbase(true).FromTx(tx));
diff --git a/src/test/script_p2sh_tests.cpp b/src/test/script_p2sh_tests.cpp
--- a/src/test/script_p2sh_tests.cpp
+++ b/src/test/script_p2sh_tests.cpp
@@ -69,13 +69,14 @@
     // different keys, straight/P2SH, pubkey/pubkeyhash
     CScript standardScripts[4];
     standardScripts[0] << ToByteVector(key[0].GetPubKey()) << OP_CHECKSIG;
-    standardScripts[1] = GetScriptForDestination(key[1].GetPubKey().GetID());
+    standardScripts[1] = GetScriptForDestination(PKHash(key[1].GetPubKey()));
     standardScripts[2] << ToByteVector(key[1].GetPubKey()) << OP_CHECKSIG;
-    standardScripts[3] = GetScriptForDestination(key[2].GetPubKey().GetID());
+    standardScripts[3] = GetScriptForDestination(PKHash(key[2].GetPubKey()));
     CScript evalScripts[4];
     for (int i = 0; i < 4; i++) {
         keystore.AddCScript(standardScripts[i]);
-        evalScripts[i] = GetScriptForDestination(CScriptID(standardScripts[i]));
+        evalScripts[i] =
+            GetScriptForDestination(ScriptHash(standardScripts[i]));
     }
 
     // Funding transaction:
@@ -142,7 +143,7 @@
     CScript invalidAsScript;
     invalidAsScript << OP_INVALIDOPCODE << OP_INVALIDOPCODE;
 
-    CScript p2sh = GetScriptForDestination(CScriptID(invalidAsScript));
+    CScript p2sh = GetScriptForDestination(ScriptHash(invalidAsScript));
 
     CScript scriptSig;
     scriptSig << Serialize(invalidAsScript);
@@ -153,7 +154,7 @@
 
     // Try to recur, and verification should succeed because
     // the inner HASH160 <> EQUAL should only check the hash:
-    CScript p2sh2 = GetScriptForDestination(CScriptID(p2sh));
+    CScript p2sh2 = GetScriptForDestination(ScriptHash(p2sh));
     CScript scriptSig2;
     scriptSig2 << Serialize(invalidAsScript) << Serialize(p2sh);
 
@@ -174,7 +175,7 @@
     }
 
     CScript inner[4];
-    inner[0] = GetScriptForDestination(key[0].GetPubKey().GetID());
+    inner[0] = GetScriptForDestination(PKHash(key[0].GetPubKey()));
     inner[1] = GetScriptForMultisig(
         2, std::vector<CPubKey>(keys.begin(), keys.begin() + 2));
     inner[2] = GetScriptForMultisig(
@@ -184,7 +185,7 @@
 
     CScript outer[4];
     for (int i = 0; i < 4; i++) {
-        outer[i] = GetScriptForDestination(CScriptID(inner[i]));
+        outer[i] = GetScriptForDestination(ScriptHash(inner[i]));
         keystore.AddCScript(inner[i]);
     }
 
@@ -303,7 +304,7 @@
     CScript scriptSig;
     scriptSig << Serialize(notValid);
 
-    CScript fund = GetScriptForDestination(CScriptID(notValid));
+    CScript fund = GetScriptForDestination(ScriptHash(notValid));
 
     // Validation should succeed under old rules (hash is correct):
     BOOST_CHECK(Verify(scriptSig, fund, false, err));
@@ -333,12 +334,12 @@
     txFrom.vout.resize(4);
 
     // First three are standard:
-    CScript pay1 = GetScriptForDestination(key[0].GetPubKey().GetID());
+    CScript pay1 = GetScriptForDestination(PKHash(key[0].GetPubKey()));
     keystore.AddCScript(pay1);
     CScript pay1of3 = GetScriptForMultisig(1, keys);
 
     // P2SH (OP_CHECKSIG)
-    txFrom.vout[0].scriptPubKey = GetScriptForDestination(CScriptID(pay1));
+    txFrom.vout[0].scriptPubKey = GetScriptForDestination(ScriptHash(pay1));
     txFrom.vout[0].nValue = 1000 * SATOSHI;
     // ordinary OP_CHECKSIG
     txFrom.vout[1].scriptPubKey = pay1;
@@ -359,7 +360,8 @@
               << ToByteVector(key[5].GetPubKey());
     oneAndTwo << OP_3 << OP_CHECKMULTISIG;
     keystore.AddCScript(oneAndTwo);
-    txFrom.vout[3].scriptPubKey = GetScriptForDestination(CScriptID(oneAndTwo));
+    txFrom.vout[3].scriptPubKey =
+        GetScriptForDestination(ScriptHash(oneAndTwo));
     txFrom.vout[3].nValue = 4000 * SATOSHI;
 
     AddCoins(coins, CTransaction(txFrom), 0);
@@ -367,7 +369,7 @@
     CMutableTransaction txTo;
     txTo.vout.resize(1);
     txTo.vout[0].scriptPubKey =
-        GetScriptForDestination(key[1].GetPubKey().GetID());
+        GetScriptForDestination(PKHash(key[1].GetPubKey()));
 
     txTo.vin.resize(5);
     for (int i = 0; i < 5; i++) {
diff --git a/src/test/script_standard_tests.cpp b/src/test/script_standard_tests.cpp
--- a/src/test/script_standard_tests.cpp
+++ b/src/test/script_standard_tests.cpp
@@ -271,24 +271,24 @@
     s.clear();
     s << ToByteVector(pubkey) << OP_CHECKSIG;
     BOOST_CHECK(ExtractDestination(s, address));
-    BOOST_CHECK(boost::get<CKeyID>(&address) &&
-                *boost::get<CKeyID>(&address) == pubkey.GetID());
+    BOOST_CHECK(boost::get<PKHash>(&address) &&
+                *boost::get<PKHash>(&address) == PKHash(pubkey));
 
     // TX_PUBKEYHASH
     s.clear();
     s << OP_DUP << OP_HASH160 << ToByteVector(pubkey.GetID()) << OP_EQUALVERIFY
       << OP_CHECKSIG;
     BOOST_CHECK(ExtractDestination(s, address));
-    BOOST_CHECK(boost::get<CKeyID>(&address) &&
-                *boost::get<CKeyID>(&address) == pubkey.GetID());
+    BOOST_CHECK(boost::get<PKHash>(&address) &&
+                *boost::get<PKHash>(&address) == PKHash(pubkey));
 
     // TX_SCRIPTHASH
     CScript redeemScript(s); // initialize with leftover P2PKH script
     s.clear();
     s << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
     BOOST_CHECK(ExtractDestination(s, address));
-    BOOST_CHECK(boost::get<CScriptID>(&address) &&
-                *boost::get<CScriptID>(&address) == CScriptID(redeemScript));
+    BOOST_CHECK(boost::get<ScriptHash>(&address) &&
+                *boost::get<ScriptHash>(&address) == ScriptHash(redeemScript));
 
     // TX_MULTISIG
     s.clear();
@@ -331,8 +331,8 @@
     BOOST_CHECK_EQUAL(whichType, TX_PUBKEY);
     BOOST_CHECK_EQUAL(addresses.size(), 1U);
     BOOST_CHECK_EQUAL(nRequired, 1);
-    BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
-                *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
+    BOOST_CHECK(boost::get<PKHash>(&addresses[0]) &&
+                *boost::get<PKHash>(&addresses[0]) == PKHash(pubkeys[0]));
 
     // TX_PUBKEYHASH
     s.clear();
@@ -342,8 +342,8 @@
     BOOST_CHECK_EQUAL(whichType, TX_PUBKEYHASH);
     BOOST_CHECK_EQUAL(addresses.size(), 1U);
     BOOST_CHECK_EQUAL(nRequired, 1);
-    BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
-                *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
+    BOOST_CHECK(boost::get<PKHash>(&addresses[0]) &&
+                *boost::get<PKHash>(&addresses[0]) == PKHash(pubkeys[0]));
 
     // TX_SCRIPTHASH
     // initialize with leftover P2PKH script
@@ -354,9 +354,9 @@
     BOOST_CHECK_EQUAL(whichType, TX_SCRIPTHASH);
     BOOST_CHECK_EQUAL(addresses.size(), 1U);
     BOOST_CHECK_EQUAL(nRequired, 1);
-    BOOST_CHECK(boost::get<CScriptID>(&addresses[0]) &&
-                *boost::get<CScriptID>(&addresses[0]) ==
-                    CScriptID(redeemScript));
+    BOOST_CHECK(boost::get<ScriptHash>(&addresses[0]) &&
+                *boost::get<ScriptHash>(&addresses[0]) ==
+                    ScriptHash(redeemScript));
 
     // TX_MULTISIG
     s.clear();
@@ -366,10 +366,10 @@
     BOOST_CHECK_EQUAL(whichType, TX_MULTISIG);
     BOOST_CHECK_EQUAL(addresses.size(), 2U);
     BOOST_CHECK_EQUAL(nRequired, 2);
-    BOOST_CHECK(boost::get<CKeyID>(&addresses[0]) &&
-                *boost::get<CKeyID>(&addresses[0]) == pubkeys[0].GetID());
-    BOOST_CHECK(boost::get<CKeyID>(&addresses[1]) &&
-                *boost::get<CKeyID>(&addresses[1]) == pubkeys[1].GetID());
+    BOOST_CHECK(boost::get<PKHash>(&addresses[0]) &&
+                *boost::get<PKHash>(&addresses[0]) == PKHash(pubkeys[0]));
+    BOOST_CHECK(boost::get<PKHash>(&addresses[1]) &&
+                *boost::get<PKHash>(&addresses[1]) == PKHash(pubkeys[1]));
 
     // TX_NULL_DATA
     s.clear();
@@ -397,18 +397,18 @@
 
     CScript expected, result;
 
-    // CKeyID
+    // PKHash
     expected.clear();
     expected << OP_DUP << OP_HASH160 << ToByteVector(pubkeys[0].GetID())
              << OP_EQUALVERIFY << OP_CHECKSIG;
-    result = GetScriptForDestination(pubkeys[0].GetID());
+    result = GetScriptForDestination(PKHash(pubkeys[0]));
     BOOST_CHECK(result == expected);
 
     // CScriptID
     CScript redeemScript(result);
     expected.clear();
     expected << OP_HASH160 << ToByteVector(CScriptID(redeemScript)) << OP_EQUAL;
-    result = GetScriptForDestination(CScriptID(redeemScript));
+    result = GetScriptForDestination(ScriptHash(redeemScript));
     BOOST_CHECK(result == expected);
 
     // CNoDestination
@@ -479,7 +479,7 @@
     // P2PKH compressed
     {
         CBasicKeyStore keystore;
-        scriptPubKey = GetScriptForDestination(pubkeys[0].GetID());
+        scriptPubKey = GetScriptForDestination(PKHash(pubkeys[0]));
 
         // Keystore does not have key
         result = IsMine(keystore, scriptPubKey);
@@ -494,7 +494,7 @@
     // P2PKH uncompressed
     {
         CBasicKeyStore keystore;
-        scriptPubKey = GetScriptForDestination(uncompressedPubkey.GetID());
+        scriptPubKey = GetScriptForDestination(PKHash(uncompressedPubkey));
 
         // Keystore does not have key
         result = IsMine(keystore, scriptPubKey);
@@ -510,8 +510,8 @@
     {
         CBasicKeyStore keystore;
 
-        CScript redeemScript = GetScriptForDestination(pubkeys[0].GetID());
-        scriptPubKey = GetScriptForDestination(CScriptID(redeemScript));
+        CScript redeemScript = GetScriptForDestination(PKHash(pubkeys[0]));
+        scriptPubKey = GetScriptForDestination(ScriptHash(redeemScript));
 
         // Keystore does not have redeemScript or key
         result = IsMine(keystore, scriptPubKey);
@@ -533,10 +533,10 @@
         CBasicKeyStore keystore;
 
         CScript redeemscript_inner =
-            GetScriptForDestination(pubkeys[0].GetID());
+            GetScriptForDestination(PKHash(pubkeys[0]));
         CScript redeemscript =
-            GetScriptForDestination(CScriptID(redeemscript_inner));
-        scriptPubKey = GetScriptForDestination(CScriptID(redeemscript));
+            GetScriptForDestination(ScriptHash(redeemscript_inner));
+        scriptPubKey = GetScriptForDestination(ScriptHash(redeemscript));
 
         keystore.AddCScript(redeemscript);
         keystore.AddCScript(redeemscript_inner);
@@ -584,7 +584,7 @@
 
         CScript redeemScript =
             GetScriptForMultisig(2, {uncompressedPubkey, pubkeys[1]});
-        scriptPubKey = GetScriptForDestination(CScriptID(redeemScript));
+        scriptPubKey = GetScriptForDestination(ScriptHash(redeemScript));
 
         // Keystore has no redeemScript
         result = IsMine(keystore, scriptPubKey);
diff --git a/src/test/script_tests.cpp b/src/test/script_tests.cpp
--- a/src/test/script_tests.cpp
+++ b/src/test/script_tests.cpp
@@ -2730,7 +2730,7 @@
     }
 
     CMutableTransaction txFrom = BuildCreditingTransaction(
-        GetScriptForDestination(keys[0].GetPubKey().GetID()), Amount::zero());
+        GetScriptForDestination(PKHash(keys[0].GetPubKey())), Amount::zero());
     CMutableTransaction txTo =
         BuildSpendingTransaction(CScript(), CTransaction(txFrom));
     CScript &scriptPubKey = txFrom.vout[0].scriptPubKey;
@@ -2763,7 +2763,7 @@
     CScript pkSingle;
     pkSingle << ToByteVector(keys[0].GetPubKey()) << OP_CHECKSIG;
     keystore.AddCScript(pkSingle);
-    scriptPubKey = GetScriptForDestination(CScriptID(pkSingle));
+    scriptPubKey = GetScriptForDestination(ScriptHash(pkSingle));
     SignSignature(keystore, CTransaction(txFrom), txTo, 0,
                   SigHashType().withForkId());
     scriptSig = DataFromTransaction(txTo, 0, txFrom.vout[0]);
diff --git a/src/test/transaction_tests.cpp b/src/test/transaction_tests.cpp
--- a/src/test/transaction_tests.cpp
+++ b/src/test/transaction_tests.cpp
@@ -306,10 +306,10 @@
     dummyTransactions[1].vout.resize(2);
     dummyTransactions[1].vout[0].nValue = 21 * CENT;
     dummyTransactions[1].vout[0].scriptPubKey =
-        GetScriptForDestination(key[2].GetPubKey().GetID());
+        GetScriptForDestination(PKHash(key[2].GetPubKey()));
     dummyTransactions[1].vout[1].nValue = 22 * CENT;
     dummyTransactions[1].vout[1].scriptPubKey =
-        GetScriptForDestination(key[3].GetPubKey().GetID());
+        GetScriptForDestination(PKHash(key[3].GetPubKey()));
     AddCoins(coinsRet, CTransaction(dummyTransactions[1]), 0);
 
     return dummyTransactions;
@@ -566,10 +566,10 @@
 
     // P2SH pay-to-compressed-pubkey.
     CreateCreditAndSpend(keystore,
-                         GetScriptForDestination(CScriptID(scriptPubkey1)),
+                         GetScriptForDestination(ScriptHash(scriptPubkey1)),
                          output1, input1);
     CreateCreditAndSpend(keystore,
-                         GetScriptForDestination(CScriptID(scriptPubkey2)),
+                         GetScriptForDestination(ScriptHash(scriptPubkey2)),
                          output2, input2);
     ReplaceRedeemScript(input2.vin[0].scriptSig, scriptPubkey1);
     CheckWithFlag(output1, input1, 0, true);
@@ -591,10 +591,10 @@
 
     // P2SH pay-to-uncompressed-pubkey.
     CreateCreditAndSpend(keystore,
-                         GetScriptForDestination(CScriptID(scriptPubkey1L)),
+                         GetScriptForDestination(ScriptHash(scriptPubkey1L)),
                          output1, input1);
     CreateCreditAndSpend(keystore,
-                         GetScriptForDestination(CScriptID(scriptPubkey2L)),
+                         GetScriptForDestination(ScriptHash(scriptPubkey2L)),
                          output2, input2);
     ReplaceRedeemScript(input2.vin[0].scriptSig, scriptPubkey1L);
     CheckWithFlag(output1, input1, 0, true);
@@ -615,12 +615,12 @@
 
     // P2SH 2-of-2 multisig
     CreateCreditAndSpend(keystore,
-                         GetScriptForDestination(CScriptID(scriptMulti)),
+                         GetScriptForDestination(ScriptHash(scriptMulti)),
                          output1, input1, false);
     CheckWithFlag(output1, input1, 0, true);
     CheckWithFlag(output1, input1, SCRIPT_VERIFY_P2SH, false);
     CreateCreditAndSpend(keystore2,
-                         GetScriptForDestination(CScriptID(scriptMulti)),
+                         GetScriptForDestination(ScriptHash(scriptMulti)),
                          output2, input2, false);
     CheckWithFlag(output2, input2, 0, true);
     CheckWithFlag(output2, input2, SCRIPT_VERIFY_P2SH, false);
@@ -646,7 +646,7 @@
     t.vout[0].nValue = 90 * CENT;
     CKey key;
     key.MakeNewKey(true);
-    t.vout[0].scriptPubKey = GetScriptForDestination(key.GetPubKey().GetID());
+    t.vout[0].scriptPubKey = GetScriptForDestination(PKHash(key.GetPubKey()));
 
     std::string reason;
     BOOST_CHECK(IsStandardTx(CTransaction(t), reason));
diff --git a/src/test/txindex_tests.cpp b/src/test/txindex_tests.cpp
--- a/src/test/txindex_tests.cpp
+++ b/src/test/txindex_tests.cpp
@@ -58,7 +58,7 @@
     // Check that new transactions in new blocks make it into the index.
     for (int i = 0; i < 10; i++) {
         CScript coinbase_script_pub_key =
-            GetScriptForDestination(coinbaseKey.GetPubKey().GetID());
+            GetScriptForDestination(PKHash(coinbaseKey.GetPubKey()));
         std::vector<CMutableTransaction> no_txns;
         const CBlock &block =
             CreateAndProcessBlock(no_txns, coinbase_script_pub_key);
diff --git a/src/test/txvalidationcache_tests.cpp b/src/test/txvalidationcache_tests.cpp
--- a/src/test/txvalidationcache_tests.cpp
+++ b/src/test/txvalidationcache_tests.cpp
@@ -200,9 +200,9 @@
     CScript p2pk_scriptPubKey =
         CScript() << ToByteVector(coinbaseKey.GetPubKey()) << OP_CHECKSIG;
     CScript p2sh_scriptPubKey =
-        GetScriptForDestination(CScriptID(p2pk_scriptPubKey));
+        GetScriptForDestination(ScriptHash(p2pk_scriptPubKey));
     CScript p2pkh_scriptPubKey =
-        GetScriptForDestination(coinbaseKey.GetPubKey().GetID());
+        GetScriptForDestination(PKHash(coinbaseKey.GetPubKey()));
 
     CBasicKeyStore keystore;
     keystore.AddKey(coinbaseKey);
diff --git a/src/wallet/rpcdump.cpp b/src/wallet/rpcdump.cpp
--- a/src/wallet/rpcdump.cpp
+++ b/src/wallet/rpcdump.cpp
@@ -277,7 +277,7 @@
             throw JSONRPCError(RPC_WALLET_ERROR,
                                "Error adding p2sh redeemScript to wallet");
         }
-        ImportAddress(pwallet, id, strLabel);
+        ImportAddress(pwallet, ScriptHash(id), strLabel);
     } else {
         CTxDestination destination;
         if (ExtractDestination(script, destination)) {
@@ -791,18 +791,18 @@
             if (pwallet->HaveKey(keyid)) {
                 pwallet->WalletLogPrintf(
                     "Skipping import of %s (key already present)\n",
-                    EncodeDestination(keyid, config));
+                    EncodeDestination(PKHash(keyid), config));
                 continue;
             }
             pwallet->WalletLogPrintf("Importing %s...\n",
-                                     EncodeDestination(keyid, config));
+                                     EncodeDestination(PKHash(keyid), config));
             if (!pwallet->AddKeyPubKey(key, pubkey)) {
                 fGood = false;
                 continue;
             }
             pwallet->mapKeyMetadata[keyid].nCreateTime = time;
             if (has_label) {
-                pwallet->SetAddressBook(keyid, label, "receive");
+                pwallet->SetAddressBook(PKHash(keyid), label, "receive");
             }
             nTimeBegin = std::min(nTimeBegin, time);
             progress++;
@@ -973,9 +973,9 @@
     // sort time/key pairs
     std::vector<std::pair<int64_t, CKeyID>> vKeyBirth;
     for (const auto &entry : mapKeyBirth) {
-        if (const CKeyID *keyID = boost::get<CKeyID>(&entry.first)) {
+        if (const PKHash *keyID = boost::get<PKHash>(&entry.first)) {
             // set and test
-            vKeyBirth.push_back(std::make_pair(entry.second, *keyID));
+            vKeyBirth.push_back(std::make_pair(entry.second, CKeyID(*keyID)));
         }
     }
     mapKeyBirth.clear();
@@ -1043,7 +1043,7 @@
     for (const CScriptID &scriptid : scripts) {
         CScript script;
         std::string create_time = "0";
-        std::string address = EncodeDestination(scriptid, config);
+        std::string address = EncodeDestination(ScriptHash(scriptid), config);
         // get birth times for scripts with metadata
         auto it = pwallet->m_script_metadata.find(scriptid);
         if (it != pwallet->m_script_metadata.end()) {
diff --git a/src/wallet/rpcwallet.cpp b/src/wallet/rpcwallet.cpp
--- a/src/wallet/rpcwallet.cpp
+++ b/src/wallet/rpcwallet.cpp
@@ -628,13 +628,14 @@
         throw JSONRPCError(RPC_TYPE_ERROR, "Invalid address");
     }
 
-    const CKeyID *keyID = boost::get<CKeyID>(&dest);
-    if (!keyID) {
+    const PKHash *pkhash = boost::get<PKHash>(&dest);
+    if (!pkhash) {
         throw JSONRPCError(RPC_TYPE_ERROR, "Address does not refer to key");
     }
 
     CKey key;
-    if (!pwallet->GetKey(*keyID, key)) {
+    CKeyID keyID(*pkhash);
+    if (!pwallet->GetKey(keyID, key)) {
         throw JSONRPCError(RPC_WALLET_ERROR, "Private key not available");
     }
 
@@ -3447,7 +3448,8 @@
             }
 
             if (scriptPubKey.IsPayToScriptHash()) {
-                const CScriptID &hash = boost::get<CScriptID>(address);
+                const CScriptID &hash =
+                    CScriptID(boost::get<ScriptHash>(address));
                 CScript redeemScript;
                 if (pwallet->GetCScript(hash, redeemScript)) {
                     entry.pushKV("redeemScript", HexStr(redeemScript.begin(),
@@ -4042,7 +4044,8 @@
         return UniValue(UniValue::VOBJ);
     }
 
-    UniValue operator()(const CKeyID &keyID) const {
+    UniValue operator()(const PKHash &pkhash) const {
+        CKeyID keyID(pkhash);
         UniValue obj(UniValue::VOBJ);
         CPubKey vchPubKey;
         if (pwallet && pwallet->GetPubKey(keyID, vchPubKey)) {
@@ -4052,7 +4055,8 @@
         return obj;
     }
 
-    UniValue operator()(const CScriptID &scriptID) const {
+    UniValue operator()(const ScriptHash &scripthash) const {
+        CScriptID scriptID(scripthash);
         UniValue obj(UniValue::VOBJ);
         CScript subscript;
         if (pwallet && pwallet->GetCScript(scriptID, subscript)) {
diff --git a/src/wallet/test/wallet_tests.cpp b/src/wallet/test/wallet_tests.cpp
--- a/src/wallet/test/wallet_tests.cpp
+++ b/src/wallet/test/wallet_tests.cpp
@@ -347,7 +347,7 @@
 }
 
 BOOST_AUTO_TEST_CASE(LoadReceiveRequests) {
-    CTxDestination dest = CKeyID();
+    CTxDestination dest = PKHash();
     LOCK(m_wallet.cs_wallet);
     m_wallet.AddDestData(dest, "misc", "val_misc");
     m_wallet.AddDestData(dest, "rr0", "val_rr0");
@@ -433,7 +433,7 @@
         list = wallet->ListCoins(*locked_chain);
     }
     BOOST_CHECK_EQUAL(list.size(), 1U);
-    BOOST_CHECK_EQUAL(boost::get<CKeyID>(list.begin()->first).ToString(),
+    BOOST_CHECK_EQUAL(boost::get<PKHash>(list.begin()->first).ToString(),
                       coinbaseAddress);
     BOOST_CHECK_EQUAL(list.begin()->second.size(), 1U);
 
@@ -452,7 +452,7 @@
         list = wallet->ListCoins(*locked_chain);
     }
     BOOST_CHECK_EQUAL(list.size(), 1U);
-    BOOST_CHECK_EQUAL(boost::get<CKeyID>(list.begin()->first).ToString(),
+    BOOST_CHECK_EQUAL(boost::get<PKHash>(list.begin()->first).ToString(),
                       coinbaseAddress);
     BOOST_CHECK_EQUAL(list.begin()->second.size(), 2U);
 
@@ -485,7 +485,7 @@
         list = wallet->ListCoins(*locked_chain);
     }
     BOOST_CHECK_EQUAL(list.size(), 1U);
-    BOOST_CHECK_EQUAL(boost::get<CKeyID>(list.begin()->first).ToString(),
+    BOOST_CHECK_EQUAL(boost::get<PKHash>(list.begin()->first).ToString(),
                       coinbaseAddress);
     BOOST_CHECK_EQUAL(list.begin()->second.size(), 2U);
 }
diff --git a/src/wallet/test/walletdb_tests.cpp b/src/wallet/test/walletdb_tests.cpp
--- a/src/wallet/test/walletdb_tests.cpp
+++ b/src/wallet/test/walletdb_tests.cpp
@@ -31,8 +31,8 @@
 BOOST_AUTO_TEST_CASE(write_erase_name) {
     WalletBatch batch(m_wallet.GetDBHandle(), "cr+");
 
-    CTxDestination dst1 = CKeyID(uint160S("c0ffee"));
-    CTxDestination dst2 = CKeyID(uint160S("f00d"));
+    CTxDestination dst1 = PKHash(uint160S("c0ffee"));
+    CTxDestination dst2 = PKHash(uint160S("f00d"));
 
     BOOST_CHECK(batch.WriteName(dst1, "name1"));
     BOOST_CHECK(batch.WriteName(dst2, "name2"));
@@ -57,8 +57,8 @@
 BOOST_AUTO_TEST_CASE(write_erase_purpose) {
     WalletBatch batch(m_wallet.GetDBHandle(), "cr+");
 
-    CTxDestination dst1 = CKeyID(uint160S("c0ffee"));
-    CTxDestination dst2 = CKeyID(uint160S("f00d"));
+    CTxDestination dst1 = PKHash(uint160S("c0ffee"));
+    CTxDestination dst2 = PKHash(uint160S("f00d"));
 
     BOOST_CHECK(batch.WritePurpose(dst1, "purpose1"));
     BOOST_CHECK(batch.WritePurpose(dst2, "purpose2"));
@@ -83,8 +83,8 @@
 BOOST_AUTO_TEST_CASE(write_erase_destdata) {
     WalletBatch batch(m_wallet.GetDBHandle(), "cr+");
 
-    CTxDestination dst1 = CKeyID(uint160S("c0ffee"));
-    CTxDestination dst2 = CKeyID(uint160S("f00d"));
+    CTxDestination dst1 = PKHash(uint160S("c0ffee"));
+    CTxDestination dst2 = PKHash(uint160S("f00d"));
 
     BOOST_CHECK(batch.WriteDestData(dst1, "key1", "value1"));
     BOOST_CHECK(batch.WriteDestData(dst1, "key2", "value2"));
diff --git a/src/wallet/wallet.cpp b/src/wallet/wallet.cpp
--- a/src/wallet/wallet.cpp
+++ b/src/wallet/wallet.cpp
@@ -358,7 +358,7 @@
 
     // Check if we need to remove from watch-only.
     CScript script;
-    script = GetScriptForDestination(pubkey.GetID());
+    script = GetScriptForDestination(PKHash(pubkey));
     if (HaveWatchOnly(script)) {
         RemoveWatchOnly(script);
     }
@@ -501,7 +501,7 @@
      */
     if (redeemScript.size() > MAX_SCRIPT_ELEMENT_SIZE) {
         std::string strAddr =
-            EncodeDestination(CScriptID(redeemScript), GetConfig());
+            EncodeDestination(ScriptHash(redeemScript), GetConfig());
         WalletLogPrintf("%s: Warning: This wallet contains a redeemScript "
                         "of size %i which exceeds maximum size %i thus can "
                         "never be redeemed. Do not use address %s.\n",
@@ -4247,7 +4247,7 @@
     // Get birth times for keys with metadata.
     for (const auto &entry : mapKeyMetadata) {
         if (entry.second.nCreateTime) {
-            mapKeyBirth[entry.first] = entry.second.nCreateTime;
+            mapKeyBirth[PKHash(entry.first)] = entry.second.nCreateTime;
         }
     }
 
@@ -4258,7 +4258,7 @@
         tip_height && *tip_height > 144 ? *tip_height - 144 : 0;
     std::map<CKeyID, int> mapKeyFirstBlock;
     for (const CKeyID &keyid : GetKeys()) {
-        if (mapKeyBirth.count(keyid) == 0) {
+        if (mapKeyBirth.count(PKHash(keyid)) == 0) {
             mapKeyFirstBlock[keyid] = max_height;
         }
     }
@@ -4293,7 +4293,7 @@
     // Extract block timestamps for those keys.
     for (const auto &entry : mapKeyFirstBlock) {
         // block times can be 2h off
-        mapKeyBirth[entry.first] =
+        mapKeyBirth[PKHash(entry.first)] =
             locked_chain.getBlockTime(entry.second) - TIMESTAMP_WINDOW;
     }
 }