diff --git a/src/Makefile.gtest.include b/src/Makefile.gtest.include index fa730acc..b4cfd3c2 100644 --- a/src/Makefile.gtest.include +++ b/src/Makefile.gtest.include @@ -5,6 +5,7 @@ bin_PROGRAMS += zcash-gtest zcash_gtest_SOURCES = \ gtest/main.cpp \ gtest/json_test_vectors.cpp \ + gtest/test_foundersreward.cpp \ gtest/test_jsonspirit.cpp \ gtest/test_tautology.cpp \ gtest/test_checktransaction.cpp \ diff --git a/src/chainparams.cpp b/src/chainparams.cpp index 04497b6b..0c7e91e1 100644 --- a/src/chainparams.cpp +++ b/src/chainparams.cpp @@ -13,6 +13,8 @@ #include +#include "base58.h" + using namespace std; #include "chainparamsseeds.h" @@ -138,6 +140,23 @@ public: // (the tx=... number in the SetBestChain debug.log lines) 0 // * estimated number of transactions per day after checkpoint }; + + // Founders reward script expects a vector of 2-of-3 multisig addresses + vFoundersRewardAddress = { + "37dSC2gL2SftgVJBHemBfWtSsNwuNfeTkz", "3KENXyYPCx4SZPGqE2Qp64Vrt49JNxvCbH", "3B2t3k6oQBACSmZArbYiseYsbsxBFFsHXG", "3QuE4MQXQwuzynXJwLPuWaciKjmRqkj9Yg", + "3FGDxAMPbjgq2ZTSFdoeWTHUu8i3nZcENb", "3HMUFCvai1KtyJ3woLXyY5dGTWjBwmD3M2", "3Mqskxz8RexngVRBkZnGVCLp1Z7wyqFjVE", "359NbXKBNezXEUqvU1cqJkfdZTHbzfsQfV", + "3KGJQmUe7zjMFkTGskiBH6JBNuymJRzU3a", "36PjhjMcMkU9kjgvCocAke5VSF6JzKXuqZ", "35fucu9Bh1AKad9zMvDgDhc3kmoj6ZcFNV", "35EnKe4u16128G6j1efUT27Vwqha6MgWDH", + "3FWa1GEjWWY3eFuFK8ht2HBhH8ZT1zXJcR", "3ByiCPMp3vNYjq1fQrQx2LXbMJ3uyiUfH6", "3DNWVawdGNJJ3sp9aMgyjtFv74rPivPUcM", "3HKAkRbUbUTV2vs1qSoEbhpoUAjNAmGxrm", + "3CV41uQT2B6FU8H57rAh22d4wyDG8FrK37", "361jTn1yhDRHji9qMrwq8p2qbSxrEfcf58", "3A4hTEi36fQdvTczkiNESqdtoADRFEUGdr", "36LBGQ4CNWRtEVxdRk8Lym52rFqRx5aAy9", + "34Hvy7rqUToVzQKu6v6gN69Qo1M37ktKpZ", "3Qii1z7vD5EFpGx3yFAqDBLQ9kCdfpxwpC", "3HNSu7ibS7yu4FW3Sf2D36Ms8BKDhBTPQo", "36djsWiivpZwPC4eZqMAFoS87VgxkjDHen", + "3E7dsoe6eJavv6HEwADC7eV2JjHXZE8wx4", "3Ks5EBz94K2TgAx19vxvwX6A2cUf1AWNfJ", "3GuGkVkqD1k9wYJNikNhMxK8ci8HGnJ3HN", "3QPjeeX5FFwEbDk8RHDXCPunsgHp9YLXsV", + "3MY2DeyRPJaUKZwpKTGsT31vZMLtVk66FP", "36f92vZ3jo3TYBXVGv55BptKmL2MDL47ZF", "3DDUDXN3aSgXckFnTdFTV1t8HjkifNKbJM", "3ArUZmHERS6CDyNYb1DhnCZ7XCCoWEURAb", + "3QnJ98YuZcVZhxs49kwwDmf5BUYPbjvKRQ", "3DNdji6oCCTVbLF4iuzamAv73MGQ9LsKNb", "3Q5cGqEzkBLMac8DNSdVesZPUcucFP3jqU", "3JuQnoHp6Qm9N39ETD4yRHhj1CCKXo3deG", + "3EQftBB2MsZ4wNgGxKfhMREU3hNk29VZeW", "38baEewZky2kRaMSvjxh2x3eDdHt1ovVnu", "32kq15rjjtjaj1Z5dW8N6DikKxBeEbCZ5B", "34tta8VkpCZFNZyM9oWf656QcNwDB2qoRV", + "33nGWUV4nKjAM7XWYNTf5Fe6aBahCe22RN", "36tt5b1MDeYks6N7Zhk5gDs3sNZjkh4mG7", "32eS4cHrpJv7MkGQzkA7KwYZuNCvbpCzm4", "39Wqmd6f23mFWsMurx9d9YbaHxyEmXpw4G", + "32x1txo29hfy6fm5kMryX2175qz7ocU8iz", "3KR3wPnecQgpndUGAdwWCfehbEES4DES3C", "3HBPRij6s8Thv2AnRytLEZ9pW6Wqoztcr6", "3N3BPLx8rHfEdqPnEWuguYfAXtDXc8sK53", + }; + assert(vFoundersRewardAddress.size() <= consensus.GetLastFoundersRewardBlockHeight()); } }; static CMainParams mainParams; @@ -202,6 +221,22 @@ public: 0 }; + // Founders reward script expects a vector of 2-of-3 multisig addresses + vFoundersRewardAddress = { + "2NF5QVDMtYBHaUzPLTxirybjwPjm9wVwacv", "2N8qoHsvVvdrDc89dXjpBWZHMbWdaHVc3rg", "2N8xpkGmATvu1GjgpjSjmt5L5V5fnEhW89v", "2MtTJnZRWNKJtmr5NN5jnjL9hTqP6tFBuLE", + "2N3Jbuca4yhcqMCa36w5Jy9NdLf7Te2BBZr", "2NAkLyEyxv1y1tvE3LawvaFXZ12GKDyXc9K", "2NEA5WxHJfpFWijWuJLwyjNmNYAKSdBFrFt", "2N68WRnm7HJYZRBL7XtqRJVQD7dCJtQx4Vg", + "2NAieMb6ZfC2RJ6c19Ch4JER6yqgRAd1CeG", "2Mvw6JtXth8cYPHxD2DGwF2fzL6C5g66w6w", "2N3treWEan8WhpKurCNTdsgh6JtTD8hLMEY", "2N46cPyaEBFb1MxHJWdtXKhfRjKWhoAF2VY", + "2N2hFwZYHvKCjqVJHCYwpy6FaBycyjcKaHB", "2N3wQ8GyAbtb4FXgymzK99ZUDdrdDVQBGNx", "2N2tq2AcVroDciF5H3WpkHraUiK6eZZgJqR", "2N6g8Q9Z6mZwQzTw1s5KoSaVTKYxBVDMeqc", + "2NFfPnK3jj85sn9mWe5EivUdnUPykMRXGp6", "2MwC4NhXRQSZzN9cfeg88Cdsp6DiXn2Axt9", "2MsTXMg8TBfKQvj7UJfMXKp3naKYv9ty3jv", "2MzPMV6sPt45J2qU1Uvft2U1ES1q9Cnw74J", + "2NEo5vX2Gvg83FbSUTfndQqkZbFHd1zJnZz", "2Mtkiihqt6wTV5uwvdmf9nTZKgEzZx6BMXB", "2MvM6urpNbfS2QFPFeUEoM14VKgBKoV8Qws", "2Mv3FDtDtyiHQA6u6kDWoiBKDkL5JFuA4Se", + "2MtyHB5chweTMBXXVPqSLAWHF6fgajGisi6", "2N3BU59PLVRWmPvffumGNWJdorY8ex5NKHq", "2NEiq16k9nQzYxWL1mvJVN32ticcL3b65vW", "2NB1groo8MTEAvPDbgcmzHsr56rSpbmXj48", + "2MwMr9dW3hrkgsmpWivobrwScfXC8hFsg4N", "2My9qRCuUBJ9aZohh8f4VQoXvBgmP9pBE11", "2MyHm9yFdm3aou91PLWzEVDeWrcrC5re4GS", "2N73XvH7vdzKr7UGHFkAeAUJFz4o8zTFeZY", + "2MwPLTmV6469VBcDxcsnotq4Qbf8CRX7DWz", "2MtmeB8wEGepSRodY7sq7myZVmFsBWAXYpW", "2N1WmRvcqMomQGePwvkd5QrKXQuYePDZh9Z", "2MwuBXGGBAPK2TupdoQK2Fw63vitJb7RUJZ", + "2Mz4XXqLy2TC5bmBczjakVeqajFo5D3jma2", "2NB19923xi5D9MPqZZvkvH5VbQ2MNRfW9e2", "2NBKhC9RJPPxA8B8bdPvvYvGGjkSoTfdrKh", "2Mzn2q4ZmReBsSQFHRscXav4Xt44wXWeo9a", + "2N1BqHdQV1r6NBeF3bbj3rE1by3MPrwgbbb", "2N6VpEUSwCvh1FCuVKb9eZCxcFnZuzcxB6f", "2N2Uq4i7DYaq2ngJZi4eXf9DAXuDYCDKMzc", "2MwsKBtaZeVKzD51otkAyBDoeuaDDK8wgqe", + "2NCajs4c2PeW8pWZxyMUiV3rDkEYyYnRAhQ", "2MuGtcBJQLfJD6GFbXy7iTtG8QasgZ8qd3Y", "2NFZ3yjeBSS3FKMy1N1zTeSEyqiRgnH35v4", "2Mvv8o9U4dbJjgWPvLDy3L6Sh74Wmynf36q", + }; + assert(vFoundersRewardAddress.size() <= consensus.GetLastFoundersRewardBlockHeight()); } }; static CTestNetParams testNetParams; @@ -259,6 +294,10 @@ public: 0, 0 }; + + // Founders reward script expects a vector of 2-of-3 multisig addresses + vFoundersRewardAddress = { "2N2e2FRfP9D1dRN1oRWkH7pbFM69eGNAuQ4" }; + assert(vFoundersRewardAddress.size() <= consensus.GetLastFoundersRewardBlockHeight()); } }; static CRegTestParams regTestParams; @@ -298,3 +337,41 @@ bool SelectParamsFromCommandLine() SelectParams(network); return true; } + + +// Block height must be >0 and <=last founders reward block height +// Index variable i ranges from 0 - (vFoundersRewardAddress.size()-1) +std::string CChainParams::GetFoundersRewardAddressAtHeight(int nHeight) const { + int maxHeight = consensus.GetLastFoundersRewardBlockHeight(); + assert(nHeight > 0 && nHeight <= maxHeight); + + size_t addressChangeInterval = (maxHeight + vFoundersRewardAddress.size()) / vFoundersRewardAddress.size(); + size_t i = nHeight / addressChangeInterval; + return vFoundersRewardAddress[i]; +} + +// Block height must be >0 and <=last founders reward block height +// The founders reward address is expected to be a multisig (P2SH) address +CScript CChainParams::GetFoundersRewardScriptAtHeight(int nHeight) const { + assert(nHeight > 0 && nHeight <= consensus.GetLastFoundersRewardBlockHeight()); + + // #1398 START + // We can remove this code when miner_tests no longer expect this script + if (fMinerTestModeForFoundersRewardScript) { + auto rewardScript = ParseHex("a9146708e6670db0b950dac68031025cc5b63213a49187"); + return CScript(rewardScript.begin(), rewardScript.end()); + } + // #1398 END + + CBitcoinAddress address(GetFoundersRewardAddressAtHeight(nHeight).c_str()); + assert(address.IsValid()); + assert(address.IsScript()); + CScriptID scriptID = get(address.Get()); // Get() returns a boost variant + CScript script = CScript() << OP_HASH160 << ToByteVector(scriptID) << OP_EQUAL; + return script; +} + +std::string CChainParams::GetFoundersRewardAddressAtIndex(int i) const { + assert(i >= 0 && i < vFoundersRewardAddress.size()); + return vFoundersRewardAddress[i]; +} diff --git a/src/chainparams.h b/src/chainparams.h index de89fa0e..ac9d099e 100644 --- a/src/chainparams.h +++ b/src/chainparams.h @@ -77,6 +77,12 @@ public: const std::vector& Base58Prefix(Base58Type type) const { return base58Prefixes[type]; } const std::vector& FixedSeeds() const { return vFixedSeeds; } const Checkpoints::CCheckpointData& Checkpoints() const { return checkpointData; } + /** Return the founder's reward address and script for a given block height */ + std::string GetFoundersRewardAddressAtHeight(int height) const; + CScript GetFoundersRewardScriptAtHeight(int height) const; + std::string GetFoundersRewardAddressAtIndex(int i) const; + /** #1398 to return a fixed founders reward script for miner_tests */ + bool fMinerTestModeForFoundersRewardScript = false; protected: CChainParams() {} @@ -102,6 +108,7 @@ protected: bool fMineBlocksOnDemand; bool fTestnetToBeDeprecatedFieldRPC; Checkpoints::CCheckpointData checkpointData; + std::vector vFoundersRewardAddress; }; /** diff --git a/src/consensus/params.h b/src/consensus/params.h index 5d951eef..d3e6462b 100644 --- a/src/consensus/params.h +++ b/src/consensus/params.h @@ -32,6 +32,9 @@ struct Params { */ int SubsidySlowStartShift() const { return nSubsidySlowStartInterval / 2; } int nSubsidyHalvingInterval; + int GetLastFoundersRewardBlockHeight() const { + return nSubsidyHalvingInterval + SubsidySlowStartShift() - 1; + } /** Used to check majorities for block version upgrade */ int nMajorityEnforceBlockUpgrade; int nMajorityRejectBlockOutdated; diff --git a/src/gtest/test_foundersreward.cpp b/src/gtest/test_foundersreward.cpp new file mode 100644 index 00000000..66e3081d --- /dev/null +++ b/src/gtest/test_foundersreward.cpp @@ -0,0 +1,178 @@ +#include + +#include "main.h" +#include "utilmoneystr.h" +#include "chainparams.h" +#include "utilstrencodings.h" +#include "zcash/Address.hpp" +#include "wallet/wallet.h" +#include "amount.h" +#include +#include +#include +#include +#include + +// To run tests: +// ./zcash-gtest --gtest_filter="founders_reward_test.*" + +// +// Enable this test to generate and print 48 testnet 2-of-3 multisig addresses. +// The output can be copied into chainparams.cpp. +// The temporary wallet file can be renamed as wallet.dat and used for testing with zcashd. +// +#if 0 +TEST(founders_reward_test, create_testnet_2of3multisig) { + ECC_Start(); + SelectParams(CBaseChainParams::TESTNET); + boost::filesystem::path temp = boost::filesystem::temp_directory_path() / boost::filesystem::unique_path(); + const std::string path = temp.native() + "-wallet.dat"; + bool fFirstRun; + auto pWallet = std::make_shared(path); + ASSERT_EQ(DB_LOAD_OK, pWallet->LoadWallet(fFirstRun)); + pWallet->TopUpKeyPool(); + std::cout << "Test wallet file path: " << path << std::endl; + + int numKeys = 48; + std::vector pubkeys; + pubkeys.resize(3); + CPubKey newKey; + std::vector addresses; + for (int i = 0; i < numKeys; i++) { + ASSERT_TRUE(pWallet->GetKeyFromPool(newKey)); + pubkeys[0] = newKey; + ASSERT_TRUE(pWallet->GetKeyFromPool(newKey)); + pubkeys[1] = newKey; + ASSERT_TRUE(pWallet->GetKeyFromPool(newKey)); + pubkeys[2] = newKey; + CScript result = GetScriptForMultisig(2, pubkeys); + ASSERT_FALSE(result.size() > MAX_SCRIPT_ELEMENT_SIZE); + CScriptID innerID(result); + std::string address = CBitcoinAddress(innerID).ToString(); + addresses.push_back(address); + } + + // Print out the addresses, 4 on each line. + std::string s = "vFoundersRewardAddress = {\n"; + int i=0; + int colsPerRow = 4; + ASSERT_TRUE(numKeys % colsPerRow == 0); + int numRows = numKeys/colsPerRow; + for (int row=0; rowFlush(true); +} +#endif + + +// Utility method to check the number of unique addresses from height 1 to maxHeight +void checkNumberOfUniqueAddresses(int nUnique) { + int maxHeight = Params().GetConsensus().GetLastFoundersRewardBlockHeight(); + std::set addresses; + for (int i = 1; i <= maxHeight; i++) { + addresses.insert(Params().GetFoundersRewardAddressAtHeight(i)); + } + ASSERT_TRUE(addresses.size() == nUnique); +} + + +TEST(founders_reward_test, general) { + SelectParams(CBaseChainParams::TESTNET); + + CChainParams params = Params(); + + // First testnet reward: + // address = 2NF5QVDMtYBHaUzPLTxirybjwPjm9wVwacv + // script = OP_HASH160 ef775f1f997f122a062fff1a2d7443abd1f9c642 OP_EQUAL + // raw script = a914ef775f1f997f122a062fff1a2d7443abd1f9c64287 + EXPECT_EQ(params.GetFoundersRewardScriptAtHeight(1), ParseHex("a914ef775f1f997f122a062fff1a2d7443abd1f9c64287")); + EXPECT_EQ(params.GetFoundersRewardAddressAtHeight(1), "2NF5QVDMtYBHaUzPLTxirybjwPjm9wVwacv"); + + int maxHeight = params.GetConsensus().GetLastFoundersRewardBlockHeight(); + + // If the block height parameter is out of bounds, there is an assert. + EXPECT_DEATH(params.GetFoundersRewardScriptAtHeight(0), "nHeight"); + EXPECT_DEATH(params.GetFoundersRewardScriptAtHeight(maxHeight+1), "nHeight"); + EXPECT_DEATH(params.GetFoundersRewardAddressAtHeight(0), "nHeight"); + EXPECT_DEATH(params.GetFoundersRewardAddressAtHeight(maxHeight+1), "nHeight"); +} + + +#define NUM_MAINNET_FOUNDER_ADDRESSES 48 + +TEST(founders_reward_test, mainnet) { + SelectParams(CBaseChainParams::MAIN); + checkNumberOfUniqueAddresses(NUM_MAINNET_FOUNDER_ADDRESSES); +} + + +#define NUM_TESTNET_FOUNDER_ADDRESSES 48 + +TEST(founders_reward_test, testnet) { + SelectParams(CBaseChainParams::TESTNET); + checkNumberOfUniqueAddresses(NUM_TESTNET_FOUNDER_ADDRESSES); +} + + +#define NUM_REGTEST_FOUNDER_ADDRESSES 1 + +TEST(founders_reward_test, regtest) { + SelectParams(CBaseChainParams::REGTEST); + checkNumberOfUniqueAddresses(NUM_REGTEST_FOUNDER_ADDRESSES); +} + + + +// Test that 10% founders reward is fully rewarded after the first halving and slow start shift. +// On Mainnet, this would be 2,100,000 ZEC after 850,000 blocks (840,000 + 10,000). +TEST(founders_reward_test, slow_start_subsidy) { + SelectParams(CBaseChainParams::MAIN); + CChainParams params = Params(); + + int maxHeight = params.GetConsensus().GetLastFoundersRewardBlockHeight(); + CAmount totalSubsidy = 0; + for (int nHeight = 1; nHeight <= maxHeight; nHeight++) { + CAmount nSubsidy = GetBlockSubsidy(nHeight, params.GetConsensus()) / 5; + totalSubsidy += nSubsidy; + } + + ASSERT_TRUE(totalSubsidy == MAX_MONEY/10.0); +} + + +// For use with mainnet and testnet which each have 48 addresses. +// Verify the number of rewards each individual address receives. +void verifyNumberOfRewards() { + CChainParams params = Params(); + int maxHeight = params.GetConsensus().GetLastFoundersRewardBlockHeight(); + std::multiset ms; + for (int nHeight = 1; nHeight <= maxHeight; nHeight++) { + ms.insert(params.GetFoundersRewardAddressAtHeight(nHeight)); + } + + ASSERT_TRUE(ms.count(params.GetFoundersRewardAddressAtIndex(0)) == 17708); + for (int i = 1; i <= 46; i++) { + ASSERT_TRUE(ms.count(params.GetFoundersRewardAddressAtIndex(i)) == 17709); + } + ASSERT_TRUE(ms.count(params.GetFoundersRewardAddressAtIndex(47)) == 17677); +} + +// Verify the number of rewards going to each mainnet address +TEST(founders_reward_test, per_address_reward_mainnet) { + SelectParams(CBaseChainParams::MAIN); + verifyNumberOfRewards(); +} + +// Verify the number of rewards going to each testnet address +TEST(founders_reward_test, per_address_reward_testnet) { + SelectParams(CBaseChainParams::TESTNET); + verifyNumberOfRewards(); +} \ No newline at end of file diff --git a/src/main.cpp b/src/main.cpp index d0321ff6..55a4c36a 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -3084,13 +3084,15 @@ bool ContextualCheckBlock(const CBlock& block, CValidationState& state, CBlockIn } // Coinbase transaction must include an output sending 20% of - // the block reward to `FOUNDERS_REWARD_SCRIPT` until the first - // subsidy halving block, with exception to the genesis block. - if ((nHeight > 0) && (nHeight < consensusParams.nSubsidyHalvingInterval)) { + // the block reward to a founders reward script, until the last founders + // reward block is reached, with exception of the genesis block. + // The last founders reward block is defined as the block just before the + // first subsidy halving block, which occurs at halving_interval + slow_start_shift + if ((nHeight > 0) && (nHeight <= consensusParams.GetLastFoundersRewardBlockHeight())) { bool found = false; BOOST_FOREACH(const CTxOut& output, block.vtx[0].vout) { - if (output.scriptPubKey == ParseHex(FOUNDERS_REWARD_SCRIPT)) { + if (output.scriptPubKey == Params().GetFoundersRewardScriptAtHeight(nHeight)) { if (output.nValue == (GetBlockSubsidy(nHeight, consensusParams) / 5)) { found = true; break; diff --git a/src/main.h b/src/main.h index 9c875d8c..0cb71407 100644 --- a/src/main.h +++ b/src/main.h @@ -47,9 +47,6 @@ class CValidationState; struct CNodeStateStats; -// This is a 2-of-3 multisig P2SH -static const char *FOUNDERS_REWARD_SCRIPT = "a9146708e6670db0b950dac68031025cc5b63213a49187"; - /** Default for -blockmaxsize and -blockminsize, which control the range of sizes the mining code will create **/ static const unsigned int DEFAULT_BLOCK_MAX_SIZE = 750000; static const unsigned int DEFAULT_BLOCK_MIN_SIZE = 0; diff --git a/src/miner.cpp b/src/miner.cpp index a27210b6..3c3a69e7 100644 --- a/src/miner.cpp +++ b/src/miner.cpp @@ -335,17 +335,14 @@ CBlockTemplate* CreateNewBlock(const CScript& scriptPubKeyIn) txNew.vout[0].scriptPubKey = scriptPubKeyIn; txNew.vout[0].nValue = GetBlockSubsidy(nHeight, chainparams.GetConsensus()); - if ((nHeight > 0) && (nHeight < chainparams.GetConsensus().nSubsidyHalvingInterval)) { + if ((nHeight > 0) && (nHeight <= chainparams.GetConsensus().GetLastFoundersRewardBlockHeight())) { // Founders reward is 20% of the block subsidy auto vFoundersReward = txNew.vout[0].nValue / 5; // Take some reward away from us txNew.vout[0].nValue -= vFoundersReward; - auto rewardScript = ParseHex(FOUNDERS_REWARD_SCRIPT); - // And give it to the founders - txNew.vout.push_back(CTxOut(vFoundersReward, CScript(rewardScript.begin(), - rewardScript.end()))); + txNew.vout.push_back(CTxOut(vFoundersReward, chainparams.GetFoundersRewardScriptAtHeight(nHeight))); } // Add fees diff --git a/src/rpcmining.cpp b/src/rpcmining.cpp index fb6b0a56..11230acd 100644 --- a/src/rpcmining.cpp +++ b/src/rpcmining.cpp @@ -786,7 +786,7 @@ Value getblocksubsidy(const Array& params, bool fHelp) CAmount nReward = GetBlockSubsidy(nHeight, Params().GetConsensus()); CAmount nFoundersReward = 0; - if ((nHeight > 0) && (nHeight < Params().GetConsensus().nSubsidyHalvingInterval)) { + if ((nHeight > 0) && (nHeight <= Params().GetConsensus().GetLastFoundersRewardBlockHeight())) { nFoundersReward = nReward/5; nReward -= nFoundersReward; } diff --git a/src/test/miner_tests.cpp b/src/test/miner_tests.cpp index a93a13fd..7b145c83 100644 --- a/src/test/miner_tests.cpp +++ b/src/test/miner_tests.cpp @@ -137,6 +137,14 @@ struct { // NOTE: These tests rely on CreateNewBlock doing its own self-validation! BOOST_AUTO_TEST_CASE(CreateNewBlock_validity) { + // #1398 START + // Current test data expects to receive a reward script for the address + // 2N2e2FRfP9D1dRN1oRWkH7pbFM69eGNAuQ4 even though the test is run on mainnet + // and not testnet, and there are many founders reward addresses not just one. + // When test data is re-generated, we will no longer need to do this. + Params(CBaseChainParams::MAIN).fMinerTestModeForFoundersRewardScript = true; + // #1398 END + CScript scriptPubKey = CScript() << ParseHex("04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f") << OP_CHECKSIG; CBlockTemplate *pblocktemplate; CMutableTransaction tx,tx2;