/// <summary> /// Creates test chain with a consensus loop. /// </summary> public static async Task <TestChainContext> CreateAsync(Network network, string dataDir) { var testChainContext = new TestChainContext() { Network = network }; testChainContext.NodeSettings = new NodeSettings(network).LoadArguments(new string[] { $"-datadir={dataDir}" }); if (dataDir != null) { testChainContext.NodeSettings.DataDir = dataDir; } testChainContext.ConnectionSettings = new ConnectionManagerSettings(); testChainContext.ConnectionSettings.Load(testChainContext.NodeSettings); testChainContext.LoggerFactory = new ExtendedLoggerFactory(); testChainContext.LoggerFactory.AddConsoleWithFilters(); testChainContext.DateTimeProvider = DateTimeProvider.Default; network.Consensus.Options = new PowConsensusOptions(); ConsensusSettings consensusSettings = new ConsensusSettings(testChainContext.NodeSettings, testChainContext.LoggerFactory); testChainContext.Checkpoints = new Checkpoints(); PowConsensusValidator consensusValidator = new PowConsensusValidator(network, testChainContext.Checkpoints, testChainContext.DateTimeProvider, testChainContext.LoggerFactory); testChainContext.Chain = new ConcurrentChain(network); CachedCoinView cachedCoinView = new CachedCoinView(new InMemoryCoinView(testChainContext.Chain.Tip.HashBlock), DateTimeProvider.Default, testChainContext.LoggerFactory); testChainContext.MockConnectionManager = new Moq.Mock <IConnectionManager>(); testChainContext.MockReadOnlyNodesCollection = new Moq.Mock <IReadOnlyNetworkPeerCollection>(); testChainContext.MockConnectionManager.Setup(s => s.ConnectedPeers).Returns(testChainContext.MockReadOnlyNodesCollection.Object); testChainContext.MockConnectionManager.Setup(s => s.NodeSettings).Returns(testChainContext.NodeSettings); testChainContext.MockConnectionManager.Setup(s => s.ConnectionSettings).Returns(testChainContext.ConnectionSettings); testChainContext.ConnectionManager = testChainContext.MockConnectionManager.Object; LookaheadBlockPuller blockPuller = new LookaheadBlockPuller(testChainContext.Chain, testChainContext.ConnectionManager, testChainContext.LoggerFactory); testChainContext.PeerBanning = new PeerBanning(testChainContext.ConnectionManager, testChainContext.LoggerFactory, testChainContext.DateTimeProvider, testChainContext.NodeSettings); NodeDeployments deployments = new NodeDeployments(testChainContext.Network, testChainContext.Chain); ConsensusRules consensusRules = new ConsensusRules(testChainContext.Network, testChainContext.LoggerFactory, testChainContext.DateTimeProvider, testChainContext.Chain, deployments, consensusSettings, testChainContext.Checkpoints).Register(new FullNodeBuilderConsensusExtension.CoreConsensusRules()); testChainContext.Consensus = new ConsensusLoop(new AsyncLoopFactory(testChainContext.LoggerFactory), consensusValidator, new NodeLifetime(), testChainContext.Chain, cachedCoinView, blockPuller, new NodeDeployments(network, testChainContext.Chain), testChainContext.LoggerFactory, new ChainState(new InvalidBlockHashStore(testChainContext.DateTimeProvider)), testChainContext.ConnectionManager, testChainContext.DateTimeProvider, new Signals.Signals(), consensusSettings, testChainContext.NodeSettings, testChainContext.PeerBanning, consensusRules); await testChainContext.Consensus.StartAsync(); return(testChainContext); }
/// <summary> /// Creates the test chain with some default blocks and txs. /// </summary> /// <param name="network">Network to create the chain on.</param> /// <param name="scriptPubKey">Public key to create blocks/txs with.</param> /// <returns>Context object representing the test chain.</returns> public static async Task <ITestChainContext> CreateAsync(Network network, Script scriptPubKey, string dataDir) { NodeSettings nodeSettings = new NodeSettings(network.Name, network).LoadArguments(new string[] { $"-datadir={dataDir}" }); if (dataDir != null) { nodeSettings.DataDir = dataDir; } var loggerFactory = new ExtendedLoggerFactory(); IDateTimeProvider dateTimeProvider = DateTimeProvider.Default; network.Consensus.Options = new PowConsensusOptions(); ConsensusSettings consensusSettings = new ConsensusSettings(nodeSettings, loggerFactory); PowConsensusValidator consensusValidator = new PowConsensusValidator(network, new Checkpoints(), dateTimeProvider, loggerFactory); ConcurrentChain chain = new ConcurrentChain(network); CachedCoinView cachedCoinView = new CachedCoinView(new InMemoryCoinView(chain.Tip.HashBlock), DateTimeProvider.Default, loggerFactory); NetworkPeerFactory networkPeerFactory = new NetworkPeerFactory(network, dateTimeProvider, loggerFactory); var peerAddressManager = new PeerAddressManager(nodeSettings.DataFolder, loggerFactory); var peerDiscovery = new PeerDiscovery(new AsyncLoopFactory(loggerFactory), loggerFactory, Network.PurpleMain, networkPeerFactory, new NodeLifetime(), nodeSettings, peerAddressManager); var connectionManager = new ConnectionManager(dateTimeProvider, loggerFactory, network, networkPeerFactory, nodeSettings, new NodeLifetime(), new NetworkPeerConnectionParameters(), peerAddressManager, new IPeerConnector[] { }, peerDiscovery); LookaheadBlockPuller blockPuller = new LookaheadBlockPuller(chain, connectionManager, new LoggerFactory()); PeerBanning peerBanning = new PeerBanning(connectionManager, loggerFactory, dateTimeProvider, nodeSettings); NodeDeployments deployments = new NodeDeployments(network, chain); ConsensusRules consensusRules = new ConsensusRules(network, loggerFactory, dateTimeProvider, chain, deployments, consensusSettings, new Checkpoints()).Register(new FullNodeBuilderConsensusExtension.CoreConsensusRules()); ConsensusLoop consensus = new ConsensusLoop(new AsyncLoopFactory(loggerFactory), consensusValidator, new NodeLifetime(), chain, cachedCoinView, blockPuller, deployments, loggerFactory, new ChainState(new InvalidBlockHashStore(dateTimeProvider)), connectionManager, dateTimeProvider, new Signals.Signals(), consensusSettings, nodeSettings, peerBanning, consensusRules); await consensus.StartAsync(); BlockPolicyEstimator blockPolicyEstimator = new BlockPolicyEstimator(new MempoolSettings(nodeSettings), loggerFactory, nodeSettings); TxMempool mempool = new TxMempool(dateTimeProvider, blockPolicyEstimator, loggerFactory, nodeSettings); MempoolSchedulerLock mempoolLock = new MempoolSchedulerLock(); // Simple block creation, nothing special yet: PowBlockAssembler blockAssembler = CreatePowBlockAssembler(network, consensus, chain, mempoolLock, mempool, dateTimeProvider, loggerFactory); BlockTemplate newBlock = blockAssembler.CreateNewBlock(scriptPubKey); chain.SetTip(newBlock.Block.Header); await consensus.ValidateAndExecuteBlockAsync(new RuleContext(new BlockValidationContext { Block = newBlock.Block }, network.Consensus, consensus.Tip) { CheckPow = false, CheckMerkleRoot = false }); List <BlockInfo> blockinfo = CreateBlockInfoList(); // We can't make transactions until we have inputs // Therefore, load 100 blocks :) int baseheight = 0; List <Block> blocks = new List <Block>(); List <Transaction> srcTxs = new List <Transaction>(); for (int i = 0; i < blockinfo.Count; ++i) { Block currentBlock = newBlock.Block.Clone(); // pointer for convenience currentBlock.Header.HashPrevBlock = chain.Tip.HashBlock; currentBlock.Header.Version = 1; currentBlock.Header.Time = Utils.DateTimeToUnixTime(chain.Tip.GetMedianTimePast()) + 1; Transaction txCoinbase = currentBlock.Transactions[0].Clone(); txCoinbase.Inputs.Clear(); txCoinbase.Version = 1; txCoinbase.AddInput(new TxIn(new Script(new[] { Op.GetPushOp(blockinfo[i].extraNonce), Op.GetPushOp(chain.Height) }))); // Ignore the (optional) segwit commitment added by CreateNewBlock (as the hardcoded nonces don't account for this) txCoinbase.AddOutput(new TxOut(Money.Zero, new Script())); currentBlock.Transactions[0] = txCoinbase; if (srcTxs.Count == 0) { baseheight = chain.Height; } if (srcTxs.Count < 4) { srcTxs.Add(currentBlock.Transactions[0]); } currentBlock.UpdateMerkleRoot(); currentBlock.Header.Nonce = blockinfo[i].nonce; chain.SetTip(currentBlock.Header); await consensus.ValidateAndExecuteBlockAsync(new RuleContext(new BlockValidationContext { Block = currentBlock }, network.Consensus, consensus.Tip) { CheckPow = false, CheckMerkleRoot = false }); blocks.Add(currentBlock); } // Just to make sure we can still make simple blocks blockAssembler = CreatePowBlockAssembler(network, consensus, chain, mempoolLock, mempool, dateTimeProvider, loggerFactory); newBlock = blockAssembler.CreateNewBlock(scriptPubKey); MempoolValidator mempoolValidator = new MempoolValidator(mempool, mempoolLock, consensusValidator, dateTimeProvider, new MempoolSettings(nodeSettings), chain, cachedCoinView, loggerFactory, nodeSettings); return(new TestChainContext { MempoolValidator = mempoolValidator, SrcTxs = srcTxs }); }
public async Task InitializeAsync() { this.blockinfo = new List <Blockinfo>(); var lst = blockinfoarr.Cast <long>().ToList(); for (int i = 0; i < lst.Count; i += 2) { this.blockinfo.Add(new Blockinfo { extranonce = (int)lst[i], nonce = (uint)lst[i + 1] }); } // Note that by default, these tests run with size accounting enabled. this.network = Network.Main; var hex = Encoders.Hex.DecodeData("04678afdb0fe5548271967f1a67130b7105cd6a828e03909a67962e0ea1f61deb649f6bc3f4cef38c4f35504e51ec112de5c384df7ba0b8d578a4c702b6bf11d5f"); this.scriptPubKey = new Script(new[] { Op.GetPushOp(hex), OpcodeType.OP_CHECKSIG }); this.newBlock = new BlockTemplate(); this.entry = new TestMemPoolEntryHelper(); this.chain = new ConcurrentChain(this.network); this.network.Consensus.Options = new PowConsensusOptions(); IDateTimeProvider dateTimeProvider = DateTimeProvider.Default; this.cachedCoinView = new CachedCoinView(new InMemoryCoinView(this.chain.Tip.HashBlock), dateTimeProvider, new LoggerFactory()); LoggerFactory loggerFactory = new LoggerFactory(); var nodeSettings = NodeSettings.Default(); var consensusSettings = new ConsensusSettings(nodeSettings, loggerFactory) { UseCheckpoints = this.useCheckpoints }; PowConsensusValidator consensusValidator = new PowConsensusValidator(this.network, new Checkpoints(this.network, consensusSettings), dateTimeProvider, loggerFactory); NetworkPeerFactory networkPeerFactory = new NetworkPeerFactory(dateTimeProvider, loggerFactory); var connectionManager = new ConnectionManager(this.network, new NetworkPeerConnectionParameters(), nodeSettings, loggerFactory, new NodeLifetime(), new AsyncLoopFactory(loggerFactory), new PeerAddressManager(), dateTimeProvider, networkPeerFactory, new IPeerConnector[] { }); LookaheadBlockPuller blockPuller = new LookaheadBlockPuller(this.chain, connectionManager, new LoggerFactory()); PeerBanning peerBanning = new PeerBanning(connectionManager, loggerFactory, dateTimeProvider, nodeSettings); NodeDeployments deployments = new NodeDeployments(this.network, this.chain); ConsensusRules consensusRules = new ConsensusRules(this.network, loggerFactory, dateTimeProvider, chain, deployments).Register(new FullNodeBuilderConsensusExtension.BaseConsensusRules()); this.consensus = new ConsensusLoop(new AsyncLoopFactory(loggerFactory), consensusValidator, new NodeLifetime(), this.chain, this.cachedCoinView, blockPuller, new NodeDeployments(this.network, this.chain), loggerFactory, new ChainState(new FullNode(), new InvalidBlockHashStore(dateTimeProvider)), connectionManager, dateTimeProvider, new Signals.Signals(), new Checkpoints(this.network, consensusSettings), consensusSettings, nodeSettings, peerBanning, consensusRules); await this.consensus.StartAsync(); this.entry.Fee(11); this.entry.Height(11); var date1 = new MemoryPoolTests.DateTimeProviderSet(); date1.time = dateTimeProvider.GetTime(); date1.timeutc = dateTimeProvider.GetUtcNow(); this.date = date1; this.mempool = new TxMempool(dateTimeProvider, new BlockPolicyEstimator(new MempoolSettings(nodeSettings), new LoggerFactory(), nodeSettings), new LoggerFactory(), nodeSettings);; this.mempoolLock = new MempoolSchedulerLock(); // Simple block creation, nothing special yet: this.newBlock = AssemblerForTest(this).CreateNewBlock(this.scriptPubKey); this.chain.SetTip(this.newBlock.Block.Header); await this.consensus.ValidateAndExecuteBlockAsync(new ContextInformation(new BlockValidationContext { Block = this.newBlock.Block }, this.network.Consensus) { CheckPow = false, CheckMerkleRoot = false }); // We can't make transactions until we have inputs // Therefore, load 100 blocks :) this.baseheight = 0; List <Block> blocks = new List <Block>(); this.txFirst = new List <Transaction>(); for (int i = 0; i < this.blockinfo.Count; ++i) { var pblock = this.newBlock.Block.Clone(); // pointer for convenience pblock.Header.HashPrevBlock = this.chain.Tip.HashBlock; pblock.Header.Version = 1; pblock.Header.Time = Utils.DateTimeToUnixTime(this.chain.Tip.GetMedianTimePast()) + 1; Transaction txCoinbase = pblock.Transactions[0].Clone(); txCoinbase.Inputs.Clear(); txCoinbase.Version = 1; txCoinbase.AddInput(new TxIn(new Script(new[] { Op.GetPushOp(this.blockinfo[i].extranonce), Op.GetPushOp(this.chain.Height) }))); // Ignore the (optional) segwit commitment added by CreateNewBlock (as the hardcoded nonces don't account for this) txCoinbase.AddOutput(new TxOut(Money.Zero, new Script())); pblock.Transactions[0] = txCoinbase; if (this.txFirst.Count == 0) { this.baseheight = this.chain.Height; } if (this.txFirst.Count < 4) { this.txFirst.Add(pblock.Transactions[0]); } pblock.UpdateMerkleRoot(); pblock.Header.Nonce = this.blockinfo[i].nonce; this.chain.SetTip(pblock.Header); await this.consensus.ValidateAndExecuteBlockAsync(new ContextInformation(new BlockValidationContext { Block = pblock }, this.network.Consensus) { CheckPow = false, CheckMerkleRoot = false }); blocks.Add(pblock); } // Just to make sure we can still make simple blocks this.newBlock = AssemblerForTest(this).CreateNewBlock(this.scriptPubKey); Assert.NotNull(this.newBlock); }