Track net value entering and exiting the Sprout circuit
Delta values will be stored for new blocks; old blocks can be filled in by re-indexing. The net value currently in the Sprout circuit is only calculated when delta values for all previous blocks are present.
This commit is contained in:
@@ -2,6 +2,18 @@
|
||||
|
||||
#include "consensus/validation.h"
|
||||
#include "main.h"
|
||||
#include "utiltest.h"
|
||||
|
||||
extern ZCJoinSplit* params;
|
||||
|
||||
extern bool ReceivedBlockTransactions(const CBlock &block, CValidationState& state, CBlockIndex *pindexNew, const CDiskBlockPos& pos);
|
||||
|
||||
void ExpectOptionalAmount(CAmount expected, boost::optional<CAmount> actual) {
|
||||
EXPECT_TRUE((bool)actual);
|
||||
if (actual) {
|
||||
EXPECT_EQ(expected, *actual);
|
||||
}
|
||||
}
|
||||
|
||||
// Fake an empty view
|
||||
class FakeCoinsViewDB : public CCoinsView {
|
||||
@@ -61,3 +73,77 @@ TEST(Validation, ContextualCheckInputsPassesWithCoinbase) {
|
||||
CValidationState state;
|
||||
EXPECT_TRUE(ContextualCheckInputs(tx, state, view, false, 0, false, Params(CBaseChainParams::MAIN).GetConsensus()));
|
||||
}
|
||||
|
||||
TEST(Validation, ReceivedBlockTransactions) {
|
||||
auto sk = libzcash::SpendingKey::random();
|
||||
|
||||
// Create a fake genesis block
|
||||
CBlock block1;
|
||||
block1.vtx.push_back(GetValidReceive(*params, sk, 5, true));
|
||||
block1.hashMerkleRoot = block1.BuildMerkleTree();
|
||||
CBlockIndex fakeIndex1 {block1};
|
||||
|
||||
// Create a fake child block
|
||||
CBlock block2;
|
||||
block2.hashPrevBlock = block1.GetHash();
|
||||
block2.vtx.push_back(GetValidReceive(*params, sk, 10, true));
|
||||
block2.hashMerkleRoot = block2.BuildMerkleTree();
|
||||
CBlockIndex fakeIndex2 {block2};
|
||||
fakeIndex2.pprev = &fakeIndex1;
|
||||
|
||||
CDiskBlockPos pos1;
|
||||
CDiskBlockPos pos2;
|
||||
|
||||
// Set initial state of indices
|
||||
ASSERT_TRUE(fakeIndex1.RaiseValidity(BLOCK_VALID_TREE));
|
||||
ASSERT_TRUE(fakeIndex2.RaiseValidity(BLOCK_VALID_TREE));
|
||||
EXPECT_TRUE(fakeIndex1.IsValid(BLOCK_VALID_TREE));
|
||||
EXPECT_TRUE(fakeIndex2.IsValid(BLOCK_VALID_TREE));
|
||||
EXPECT_FALSE(fakeIndex1.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
EXPECT_FALSE(fakeIndex2.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
|
||||
// Sprout pool values should not be set
|
||||
EXPECT_FALSE((bool)fakeIndex1.nSproutValue);
|
||||
EXPECT_FALSE((bool)fakeIndex1.nChainSproutValue);
|
||||
EXPECT_FALSE((bool)fakeIndex2.nSproutValue);
|
||||
EXPECT_FALSE((bool)fakeIndex2.nChainSproutValue);
|
||||
|
||||
// Mark the second block's transactions as received first
|
||||
CValidationState state;
|
||||
EXPECT_TRUE(ReceivedBlockTransactions(block2, state, &fakeIndex2, pos2));
|
||||
EXPECT_FALSE(fakeIndex1.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
EXPECT_TRUE(fakeIndex2.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
|
||||
// Sprout pool value delta should now be set for the second block,
|
||||
// but not any chain totals
|
||||
EXPECT_FALSE((bool)fakeIndex1.nSproutValue);
|
||||
EXPECT_FALSE((bool)fakeIndex1.nChainSproutValue);
|
||||
{
|
||||
SCOPED_TRACE("ExpectOptionalAmount call");
|
||||
ExpectOptionalAmount(20, fakeIndex2.nSproutValue);
|
||||
}
|
||||
EXPECT_FALSE((bool)fakeIndex2.nChainSproutValue);
|
||||
|
||||
// Now mark the first block's transactions as received
|
||||
EXPECT_TRUE(ReceivedBlockTransactions(block1, state, &fakeIndex1, pos1));
|
||||
EXPECT_TRUE(fakeIndex1.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
EXPECT_TRUE(fakeIndex2.IsValid(BLOCK_VALID_TRANSACTIONS));
|
||||
|
||||
// Sprout pool values should now be set for both blocks
|
||||
{
|
||||
SCOPED_TRACE("ExpectOptionalAmount call");
|
||||
ExpectOptionalAmount(10, fakeIndex1.nSproutValue);
|
||||
}
|
||||
{
|
||||
SCOPED_TRACE("ExpectOptionalAmount call");
|
||||
ExpectOptionalAmount(10, fakeIndex1.nChainSproutValue);
|
||||
}
|
||||
{
|
||||
SCOPED_TRACE("ExpectOptionalAmount call");
|
||||
ExpectOptionalAmount(20, fakeIndex2.nSproutValue);
|
||||
}
|
||||
{
|
||||
SCOPED_TRACE("ExpectOptionalAmount call");
|
||||
ExpectOptionalAmount(30, fakeIndex2.nChainSproutValue);
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user