示例#1
0
        public ChainedBlock GetChainedBlock(ChainBase chain)
        {
            ChainedBlock chainedBlock;

            if (Special != null && Special.Value == SpecialFeature.Last)
            {
                chainedBlock = chain.Tip;
            }
            else if (Height != -1)
            {
                var h = chain.GetBlock(Height);
                if (h == null)
                {
                    return(null);
                }
                chainedBlock = h;
            }
            else
            {
                chainedBlock = chain.GetBlock(BlockId);
            }
            if (chainedBlock != null)
            {
                var height = chainedBlock.Height + Offset;
                height       = Math.Max(0, height);
                chainedBlock = chain.GetBlock(height);
            }
            return(chainedBlock);
        }
示例#2
0
        public BlockFetcher(Checkpoint checkpoint, IBlocksRepository blocksRepository, ChainBase chain, ChainedHeader lastProcessed, ILoggerFactory loggerFactory)
        {
            this.loggerFactory = loggerFactory;
            this.logger        = this.loggerFactory.CreateLogger(GetType().FullName);

            if (blocksRepository == null)
            {
                throw new ArgumentNullException("blocksRepository");
            }

            if (chain == null)
            {
                throw new ArgumentNullException("blockHeaders");
            }

            if (checkpoint == null)
            {
                throw new ArgumentNullException("checkpoint");
            }

            _BlockHeaders     = chain;
            _BlocksRepository = blocksRepository;
            _Checkpoint       = checkpoint;
            _LastProcessed    = lastProcessed;

            InitDefault();
        }
示例#3
0
 public void IndexOrderedBalances(ChainBase chain)
 {
     IndexBalances(chain, "balances", (txid, tx, blockid, header, height) =>
     {
         return(OrderedBalanceChange.ExtractScriptBalances(txid, tx, blockid, header, height));
     });
 }
示例#4
0
        private void EnqueueJobs(NodeBlocksRepository repo, ChainBase chain, CloudBlockBlob blobLock, string lease)
        {
            int          cumul      = 0;
            ChainedBlock from       = chain.Genesis;
            int          blockCount = 0;

            foreach (var block in repo.GetBlocks(new[] { chain.Genesis }.Concat(chain.EnumerateAfter(chain.Genesis)).Where(c => c.Height % BlockGranularity == 0).Select(c => c.HashBlock), default(CancellationToken)))
            {
                cumul      += block.Transactions.Count * BlockGranularity;
                blockCount += BlockGranularity;
                if (cumul > TransactionsPerWork)
                {
                    var nextFrom = chain.GetBlock(chain.GetBlock(block.GetHash()).Height + BlockGranularity);
                    if (nextFrom == null)
                    {
                        break;
                    }
                    EnqueueRange(chain, from, blockCount);
                    from       = nextFrom;
                    blockCount = 0;
                    cumul      = 0;
                }
            }

            blockCount = (chain.Tip.Height - from.Height) + 1;
            EnqueueRange(chain, from, blockCount);

            var bytes = chain.Tip.GetLocator().ToBytes();

            blobLock.UploadText(Encoders.Hex.EncodeData(bytes), null, new AccessCondition()
            {
                LeaseId = lease
            });
        }
        public BalanceSheet(IEnumerable<OrderedBalanceChange> changes, ChainBase chain)
        {
            if (chain == null)
                throw new ArgumentNullException("chain");
            _Chain = chain;

            var all = changes
                        .Where(c => c.SpentCoins != null) //Remove line whose previous coins have not been loadedcould not be deduced
                        .Where(c => c.MempoolEntry || chain.GetBlock(c.BlockId) != null) //Take only mempool entry, or confirmed one
                        .Where(c => !(c.IsCoinbase && c.MempoolEntry)) //There is no such thing as a Coinbase unconfirmed, by definition a coinbase appear in a block
                        .ToList(); 
            var confirmed = all.Where(o => o.BlockId != null).ToDictionary(o => o.TransactionId);
            Dictionary<uint256, OrderedBalanceChange> unconfirmed = new Dictionary<uint256, OrderedBalanceChange>();

            foreach(var item in all.Where(o => o.MempoolEntry && !confirmed.ContainsKey(o.TransactionId)))
            {
                unconfirmed.AddOrReplace(item.TransactionId, item);
            }

            _Prunable = all.Where(o => o.BlockId == null && confirmed.ContainsKey(o.TransactionId)).ToList();
            _All = all.Where(o => 
                (unconfirmed.ContainsKey(o.TransactionId) || confirmed.ContainsKey(o.TransactionId)) 
                    &&
                    !(o.BlockId == null && confirmed.ContainsKey(o.TransactionId))
                ).ToList();
            _Confirmed = _All.Where(o => o.BlockId != null && confirmed.ContainsKey(o.TransactionId)).ToList();
            _Unconfirmed = _All.Where(o => o.BlockId == null && unconfirmed.ContainsKey(o.TransactionId)).ToList();
        }
示例#6
0
        public long IndexBlocks(ChainBase chain = null)
        {
            long blkCount = 0;

            SetThrottling();
            BlockingCollection <Block> blocks = new BlockingCollection <Block>(20);
            var tasks = CreateTaskPool(blocks, Index, 15);

            using (IndexerTrace.NewCorrelation("Import blocks to azure started").Open())
            {
                Configuration.GetBlocksContainer().CreateIfNotExists();
                using (var storedBlocks = Enumerate("blocks", chain))
                {
                    foreach (var block in storedBlocks)
                    {
                        blkCount++;
                        blocks.Add(block.Block);
                        if (storedBlocks.NeedSave)
                        {
                            tasks.Stop();
                            storedBlocks.SaveCheckpoint();
                            tasks.Start();
                        }
                    }
                    tasks.Stop();
                    storedBlocks.SaveCheckpoint();
                }
            }
            return(blkCount);
        }
示例#7
0
        public void SynchronizeChain(ChainBase chain)
        {
            Dictionary <uint256, BlockHeader> headers = new Dictionary <uint256, BlockHeader>();
            HashSet <uint256> inChain = new HashSet <uint256>();

            inChain.Add(chain.GetBlock(0).HashBlock);
            foreach (var header in Enumerate(true).Select(b => b.Item.Header))
            {
                var hash = header.GetHash();
                headers.Add(hash, header);
            }
            List <uint256> toRemove = new List <uint256>();

            while (headers.Count != 0)
            {
                foreach (var header in headers)
                {
                    if (inChain.Contains(header.Value.HashPrevBlock))
                    {
                        toRemove.Add(header.Key);
                        chain.SetTip(header.Value);
                        inChain.Add(header.Key);
                    }
                }
                foreach (var item in toRemove)
                {
                    headers.Remove(item);
                }
                if (toRemove.Count == 0)
                {
                    break;
                }
                toRemove.Clear();
            }
        }
示例#8
0
        public BalanceSheet(IEnumerable <OrderedBalanceChange> changes, ChainBase chain, bool colored)
        {
            if (chain == null)
            {
                throw new ArgumentNullException("chain");
            }
            _Chain = chain;

            var all = changes
                      .Where(c => c.SpentCoins != null)                                //Remove line whose previous coins have not been loaded
                      .Where(c => !colored || c.ColoredBalanceChangeEntry != null)     //Remove live whose color could not be deduced
                      .Where(c => c.MempoolEntry || chain.GetBlock(c.BlockId) != null) //Take only mempool entry, or confirmed one
                      .Where(c => !(c.IsCoinbase && c.MempoolEntry))                   //There is no such thing as a Coinbase unconfirmed, by definition a coinbase appear in a block
                      .ToList();
            var confirmed   = all.Where(o => o.BlockId != null).ToDictionary(o => o.TransactionId);
            var unconfirmed = all.Where(o => o.MempoolEntry && !confirmed.ContainsKey(o.TransactionId)).ToDictionary(o => o.TransactionId);

            _Prunable = all.Where(o => o.BlockId == null && confirmed.ContainsKey(o.TransactionId)).ToList();
            _All      = all.Where(o =>
                                  (unconfirmed.ContainsKey(o.TransactionId) || confirmed.ContainsKey(o.TransactionId))
                                  &&
                                  !(o.BlockId == null && confirmed.ContainsKey(o.TransactionId))
                                  ).ToList();
            _Confirmed   = _All.Where(o => o.BlockId != null && confirmed.ContainsKey(o.TransactionId)).ToList();
            _Unconfirmed = _All.Where(o => o.BlockId == null && unconfirmed.ContainsKey(o.TransactionId)).ToList();
        }
        public static void UpdateChain(this IEnumerable <ChainBlockHeader> entries, ChainBase chain)
        {
            Stack <ChainBlockHeader> toApply = new Stack <ChainBlockHeader>();

            foreach (var entry in entries)
            {
                var prev = chain.GetBlock(entry.Header.HashPrevBlock);
                if (prev == null)
                {
                    toApply.Push(entry);
                }
                else
                {
                    toApply.Push(entry);
                    break;
                }
            }
            while (toApply.Count > 0)
            {
                var newTip = toApply.Pop();

                var chained = new ChainedBlock(newTip.Header, newTip.BlockId, chain.GetBlock(newTip.Header.HashPrevBlock));
                chain.SetTip(chained);
            }
        }
示例#10
0
        internal void Index(ChainBase chain, int startHeight, CancellationToken cancellationToken = default(CancellationToken))
        {
            List <ChainPartEntry> entries = new List <ChainPartEntry>(((chain.Height - startHeight) / BlockHeaderPerRow) + 5);

            startHeight = startHeight - (startHeight % BlockHeaderPerRow);
            ChainPartEntry chainPart = null;

            for (int i = startHeight; i <= chain.Tip.Height; i++)
            {
                if (chainPart == null)
                {
                    chainPart = new ChainPartEntry()
                    {
                        ChainOffset = i
                    }
                }
                ;

                var block = chain.GetBlock(i);
                chainPart.BlockHeaders.Add(block.Header);
                if (chainPart.BlockHeaders.Count == BlockHeaderPerRow)
                {
                    entries.Add(chainPart);
                    chainPart = null;
                }
            }
            if (chainPart != null)
            {
                entries.Add(chainPart);
            }
            this.Index(entries, cancellationToken);
        }
示例#11
0
        private void EnqueueRange(ChainBase chain, ChainedBlock startCumul, int blockCount)
        {
            ListenerTrace.Info("Enqueing from " + startCumul.Height + " " + blockCount + " blocks");
            if (blockCount == 0)
            {
                return;
            }
            var tasks = _IndexTasks
                        .Where(t => chain.FindFork(t.Value.Item1.BlockLocator).Height <= startCumul.Height + blockCount)
                        .Select(t => new BlockRange()
            {
                From   = startCumul.Height,
                Count  = blockCount,
                Target = t.Key
            })
                        .Select(t => _Conf.Topics.InitialIndexing.AddAsync(t))
                        .ToArray();

            try
            {
                Task.WaitAll(tasks);
            }
            catch (AggregateException aex)
            {
                ExceptionDispatchInfo.Capture(aex.InnerException).Throw();
                throw;
            }
        }
示例#12
0
文件: Tracker.cs 项目: zzms/NBitcoin
            public WalletTransaction ToWalletTransaction(ChainBase chain, string wallet)
            {
                var chainHeight = chain.Height;
                var tx          = new WalletTransaction()
                {
                    Proof           = Proof,
                    Transaction     = Transaction,
                    UnconfirmedSeen = UnconfirmedSeen,
                    AddedDate       = AddedDate
                };

                tx.ReceivedCoins = GetCoins(ReceivedCoins, _TrackedScripts, wallet);
                tx.SpentCoins    = GetCoins(SpentCoins, _TrackedScripts, wallet);

                if (BlockId != null)
                {
                    var header = chain.GetBlock(BlockId);
                    if (header != null)
                    {
                        tx.BlockInformation = new BlockInformation()
                        {
                            Confirmations = chainHeight - header.Height + 1,
                            Height        = header.Height,
                            Header        = header.Header
                        };
                    }
                }
                return(tx);
            }
示例#13
0
        /// <summary>
        /// Synchronize a given Chain to the tip of the given node if its height is higher. (Thread safe).
        /// </summary>
        /// <param name="peer">Node to synchronize the chain for.</param>
        /// <param name="chain">The chain to synchronize.</param>
        /// <param name="hashStop">The location until which it synchronize.</param>
        /// <param name="cancellationToken"></param>
        /// <returns></returns>
        private IEnumerable <ChainedHeader> SynchronizeChain(INetworkPeer peer, ChainBase chain, uint256 hashStop = null, CancellationToken cancellationToken = default(CancellationToken))
        {
            ChainedHeader        oldTip  = chain.Tip;
            List <ChainedHeader> headers = this.GetHeadersFromFork(peer, oldTip, hashStop, cancellationToken).ToList();

            if (headers.Count == 0)
            {
                return(new ChainedHeader[0]);
            }

            ChainedHeader newTip = headers[headers.Count - 1];

            if (newTip.Height <= oldTip.Height)
            {
                throw new ProtocolException("No tip should have been recieved older than the local one");
            }

            foreach (ChainedHeader header in headers)
            {
                if (!header.Validate(peer.Network))
                {
                    throw new ProtocolException("A header which does not pass proof of work verification has been received");
                }
            }

            chain.SetTip(newTip);

            return(headers);
        }
示例#14
0
 /// <summary>
 /// Get a block fetcher of the specified chain from the specified checkpoint
 /// </summary>
 /// <param name="checkpoint">The checkpoint name to load from</param>
 /// <param name="chain">The chain to fetcher (default: the Node's main chain)</param>
 /// <returns>A BlockFetcher for enumerating blocks and saving progression</returns>
 public BlockFetcher GetBlockFetcher(string checkpointName, Node node, ChainBase chain = null)
 {
     if (checkpointName == null)
     {
         throw new ArgumentNullException("checkpointName");
     }
     return(this.GetBlockFetcher(this.GetCheckpointRepository().GetCheckpoint(checkpointName), node, chain));
 }
示例#15
0
        /// <summary>
        /// Returns the first common chained block header between two chains.
        /// </summary>
        /// <param name="chainSrc">The source chain.</param>
        /// <param name="otherChain">The other chain.</param>
        /// <returns>First common chained block header or <c>null</c>.</returns>
        private ChainedBlock FindFork(ChainBase chainSrc, ChainBase otherChain)
        {
            if (otherChain == null)
            {
                throw new ArgumentNullException("otherChain");
            }

            return(chainSrc.FindFork(otherChain.Tip.EnumerateToGenesis().Select(o => o.HashBlock)));
        }
示例#16
0
        public void SynchronizeChain(ChainBase chain)
        {
            Dictionary <uint256, Block>        blocks        = new Dictionary <uint256, Block>();
            Dictionary <uint256, ChainedBlock> chainedBlocks = new Dictionary <uint256, ChainedBlock>();
            HashSet <uint256> inChain = new HashSet <uint256>();

            inChain.Add(chain.GetBlock(0).HashBlock);
            chainedBlocks.Add(chain.GetBlock(0).HashBlock, chain.GetBlock(0));

            foreach (var block in this.Enumerate(false).Select(b => b.Item))
            {
                var hash = block.GetHash();
                blocks.Add(hash, block);
            }
            List <uint256> toRemove = new List <uint256>();

            while (blocks.Count != 0)
            {
                // to optimize keep a track of the last block
                ChainedBlock last = chain.GetBlock(0);
                foreach (var block in blocks)
                {
                    if (inChain.Contains(block.Value.Header.HashPrevBlock))
                    {
                        toRemove.Add(block.Key);
                        ChainedBlock chainedBlock;
                        if (last.HashBlock == block.Value.Header.HashPrevBlock)
                        {
                            chainedBlock = last;
                        }
                        else
                        {
                            if (!chainedBlocks.TryGetValue(block.Value.Header.HashPrevBlock, out chainedBlock))
                            {
                                break;
                            }
                        }
                        var chainedHeader = new ChainedBlock(block.Value.Header, block.Value.GetHash(), chainedBlock);
                        chain.SetTip(chainedHeader);
                        chainedBlocks.TryAdd(chainedHeader.HashBlock, chainedHeader);
                        inChain.Add(block.Key);
                        last = chainedHeader;
                    }
                }
                foreach (var item in toRemove)
                {
                    blocks.Remove(item);
                }
                if (toRemove.Count == 0)
                {
                    break;
                }
                toRemove.Clear();
            }
        }
示例#17
0
文件: Node.cs 项目: jannickj/NBitcoin
        public IEnumerable <ChainedBlock> SynchronizeChain(ChainBase chain, uint256 hashStop = null, CancellationToken cancellationToken = default(CancellationToken))
        {
            List <ChainedBlock> headers = new List <ChainedBlock>();

            foreach (var header in GetHeadersFromFork(chain.Tip, hashStop, cancellationToken))
            {
                chain.SetTip(header);
                headers.Add(header);
            }
            return(headers);
        }
示例#18
0
        public void IndexWalletBalances(ChainBase chain)
        {
            Configuration.GetWalletBalanceTable().CreateIfNotExists();
            Configuration.GetWalletRulesTable().CreateIfNotExists();
            var walletRules = Configuration.CreateIndexerClient().GetAllWalletRules();

            IndexBalances(chain, "wallets", (txid, tx, blockid, header, height) =>
            {
                return(OrderedBalanceChange.ExtractWalletBalances(txid, tx, blockid, header, height, walletRules));
            });
        }
示例#19
0
        public static bool TryGetHeight(this ChainBase chain, uint256 blockId, out int height)
        {
            height = 0;
            var block = chain.GetBlock(blockId);

            if (block == null)
            {
                return(false);
            }
            height = block.Height;
            return(true);
        }
示例#20
0
 public WalletTransactionsCollection GetWalletTransactions(ChainBase chain, string wallet = "default")
 {
     lock (cs)
     {
         return(new WalletTransactionsCollection(_Operations
                                                 .Select(op => op.Value)
                                                 .Where(op => op.CheckProof())
                                                 .Select(o => o.ToWalletTransaction(chain, _TrackedScripts, wallet))
                                                 .Where(o => o.ReceivedCoins.Length != 0 || o.SpentCoins.Length != 0)
                                                 .ToArray()));
     }
 }
示例#21
0
文件: Tracker.cs 项目: zzms/NBitcoin
 public WalletTransactionsCollection GetWalletTransactions(ChainBase chain, string wallet = "default")
 {
     lock (cs)
     {
         return(new WalletTransactionsCollection(_Operations
                                                 .Select(op => op.Value)
                                                 .Where(op => op.CheckProof())
                                                 .Where(op => op.ContainsWallet(wallet))
                                                 .Select(o => o.ToWalletTransaction(chain, wallet))
                                                 .ToArray()));
     }
 }
示例#22
0
        public IEnumerable <T> Query(ChainBase chain, BalanceQuery query = null)
        {
            if (query == null)
            {
                query = new BalanceQuery();
            }
            var tableQuery = query.CreateTableQuery(Escape(Scope), "");

            return(ExecuteBalanceQuery(Table, tableQuery, query.PageSizes)
                   .Where(_ => chain.Contains(((ConfirmedBalanceLocator)UnEscapeLocator(_.RowKey)).BlockHash))
                   .Select(_ => Serializer.ToObject <T>(ParseData(_))));
        }
示例#23
0
        public static void UpdateChain(this IEnumerable <ChainBlockHeader> entries, ChainBase chain)
        {
            var entriesAsync = new AsyncEnumerable <ChainBlockHeader>(async yield =>
            {
                foreach (var entry in entries)
                {
                    await yield.ReturnAsync(entry);
                }
            });

            UpdateChain(entriesAsync, chain, default(CancellationToken)).GetAwaiter().GetResult();
        }
示例#24
0
        static void Main(string[] args)
        {
            try
            {
                var options = new IndexerOptions();
                if (args.Length == 0)
                {
                    System.Console.WriteLine(options.GetUsage());
                }
                if (Parser.Default.ParseArguments(args, options))
                {
                    System.Console.WriteLine("NBitcoin.Indexer " + typeof(AzureIndexer).Assembly.GetName().Version);
                    var indexer = AzureIndexer.CreateIndexer();
                    indexer.CheckpointInterval = TimeSpan.Parse(options.CheckpointInterval);
                    indexer.NoSave             = options.NoSave;
                    indexer.FromHeight         = options.From;
                    indexer.ToHeight           = options.To;
                    indexer.TaskCount          = options.ThreadCount;

                    ChainBase chain = null;
                    if (options.IndexBlocks)
                    {
                        chain = chain ?? indexer.GetNodeChain();
                        indexer.IndexBlocks(chain);
                    }
                    if (options.IndexChain)
                    {
                        chain = chain ?? indexer.GetNodeChain();
                        indexer.IndexChain(chain);
                    }
                    if (options.IndexTransactions)
                    {
                        chain = chain ?? indexer.GetNodeChain();
                        indexer.IndexTransactions(chain);
                    }
                    if (options.IndexAddresses)
                    {
                        chain = chain ?? indexer.GetNodeChain();
                        indexer.IndexOrderedBalances(chain);
                    }
                    if (options.IndexWallets)
                    {
                        chain = chain ?? indexer.GetNodeChain();
                        indexer.IndexWalletBalances(chain);
                    }
                }
            }
            catch (ConfigurationErrorsException ex)
            {
                System.Console.WriteLine("LocalSettings.config missing settings : " + ex.Message);
            }
        }
示例#25
0
 public void SynchronizeChain(ChainBase chain)
 {
     if (chain.Tip != null && chain.Genesis.HashBlock != Configuration.Network.GetGenesis().GetHash())
     {
         throw new ArgumentException("Incompatible Network between the indexer and the chain", "chain");
     }
     if (chain.Tip == null)
     {
         chain.SetTip(new ChainedBlock(Configuration.Network.GetGenesis().Header, 0));
     }
     GetChainChangesUntilFork(chain.Tip, false)
     .UpdateChain(chain);
 }
示例#26
0
        public long IndexTransactions(ChainBase chain = null)
        {
            long txCount = 0;

            SetThrottling();

            BlockingCollection <TransactionEntry.Entity[]> transactions = new BlockingCollection <TransactionEntry.Entity[]>(20);

            var tasks = CreateTaskPool(transactions, (txs) => Index(txs), 30);

            using (IndexerTrace.NewCorrelation("Import transactions to azure started").Open())
            {
                Configuration.GetTransactionTable().CreateIfNotExists();
                var buckets = new MultiValueDictionary <string, TransactionEntry.Entity>();
                using (var storedBlocks = Enumerate("transactions", chain))
                {
                    foreach (var block in storedBlocks)
                    {
                        foreach (var transaction in block.Block.Transactions)
                        {
                            txCount++;
                            var indexed = new TransactionEntry.Entity(null, transaction, block.BlockId);
                            buckets.Add(indexed.PartitionKey, indexed);
                            var collection = buckets[indexed.PartitionKey];
                            if (collection.Count == 100)
                            {
                                PushTransactions(buckets, collection, transactions);
                            }
                            if (storedBlocks.NeedSave)
                            {
                                foreach (var kv in buckets.AsLookup().ToArray())
                                {
                                    PushTransactions(buckets, kv, transactions);
                                }
                                tasks.Stop();
                                storedBlocks.SaveCheckpoint();
                                tasks.Start();
                            }
                        }
                    }

                    foreach (var kv in buckets.AsLookup().ToArray())
                    {
                        PushTransactions(buckets, kv, transactions);
                    }
                    tasks.Stop();
                    storedBlocks.SaveCheckpoint();
                }
            }
            return(txCount);
        }
示例#27
0
        public void IndexChain(ChainBase chain, CancellationToken cancellationToken = default(CancellationToken))
        {
            this.logger.LogTrace("()");

            if (chain == null)
            {
                throw new ArgumentNullException("chain");
            }
            this.SetThrottling();

            using (IndexerTrace.NewCorrelation("Index main chain to azure started"))
            {
                this.Configuration.GetChainTable().CreateIfNotExistsAsync().GetAwaiter().GetResult();
                IndexerTrace.InputChainTip(chain.Tip);
                var client  = this.Configuration.CreateIndexerClient();
                var changes = client.GetChainChangesUntilFork(chain.Tip, true, cancellationToken).ToList();

                var height = 0;
                if (changes.Count != 0)
                {
                    this.logger.LogTrace("Changes count: {0}", changes.Count);

                    IndexerTrace.IndexedChainTip(changes[0].BlockId, changes[0].Height);
                    if (changes[0].Height > chain.Tip.Height)
                    {
                        IndexerTrace.InputChainIsLate();

                        this.logger.LogTrace("(-):LATE");
                        return;
                    }
                    height = changes[changes.Count - 1].Height + 1;
                    if (height > chain.Height)
                    {
                        IndexerTrace.IndexedChainIsUpToDate(chain.Tip);

                        this.logger.LogTrace("(-):UP_TO_DATE");
                        return;
                    }
                }
                else
                {
                    this.logger.LogTrace("No work found");
                    IndexerTrace.NoForkFoundWithStored();
                }

                IndexerTrace.IndexingChain(chain.GetBlock(height), chain.Tip);
                this.Index(chain, height, cancellationToken);
            }

            this.logger.LogTrace("(-)");
        }
        public void ComputeStakeModifier(ChainBase chainIndex, ChainedBlock pindex, BlockStake blockStake)
        {
            var pindexPrev     = pindex.Previous;
            var blockStakePrev = pindexPrev == null ? null : this.stakeChain.Get(pindexPrev.HashBlock);

            // compute stake modifier
            var stakeContext = new StakeModifierContext();

            this.ComputeNextStakeModifier(chainIndex, pindexPrev, stakeContext);

            blockStake.SetStakeModifier(stakeContext.StakeModifier, stakeContext.GeneratedStakeModifier);
            blockStake.StakeModifierV2 = this.ComputeStakeModifierV2(
                pindexPrev, blockStakePrev, blockStake.IsProofOfWork() ? pindex.HashBlock : blockStake.PrevoutStake.Hash);
        }
示例#29
0
		private ChainedBlock CreateBlock(DateTimeOffset now, int offset, ChainBase chain = null)
		{
			Block b = new Block(new BlockHeader()
			{
				BlockTime = now + TimeSpan.FromMinutes(offset)
			});
			if(chain != null)
			{
				b.Header.HashPrevBlock = chain.Tip.HashBlock;
				return new ChainedBlock(b.Header, null, chain.Tip);
			}
			else
				return new ChainedBlock(b.Header, 0);
		}
示例#30
0
 public int IndexWalletBalances(ChainBase chain)
 {
     using (IndexerTrace.NewCorrelation("Import wallet balances to azure started"))
     {
         using (var node = this.Configuration.ConnectToNode(false))
         {
             node.VersionHandshake();
             var task = new IndexBalanceTask(this.Configuration, this.Configuration.CreateIndexerClient().GetAllWalletRules());
             task.SaveProgression = !this.IgnoreCheckpoints;
             task.Index(this.GetBlockFetcher(this.GetCheckpointInternal(IndexerCheckpoints.Wallets), node, chain), this.TaskScheduler);
             return(task.IndexedEntities);
         }
     }
 }
示例#31
0
 public long IndexBlocks(ChainBase chain = null)
 {
     using (IndexerTrace.NewCorrelation("Import blocks to azure started"))
     {
         using (var node = this.Configuration.ConnectToNode(false))
         {
             node.VersionHandshake();
             var task = new IndexBlocksTask(this.Configuration);
             task.SaveProgression = !this.IgnoreCheckpoints;
             task.Index(this.GetBlockFetcher(this.GetCheckpointInternal(IndexerCheckpoints.Blocks), node, chain), this.TaskScheduler);
             return(task.IndexedBlocks);
         }
     }
 }
示例#32
0
 public int IndexOrderedBalances(ChainBase chain)
 {
     using (IndexerTrace.NewCorrelation("Import balances to azure started"))
     {
         using (var node = Configuration.ConnectToNode(false))
         {
             node.VersionHandshake();
             var task = new IndexBalanceTask(Configuration, null);
             task.SaveProgression = !IgnoreCheckpoints;
             task.Index(GetBlockFetcher(GetCheckpointInternal(IndexerCheckpoints.Balances), node, chain), TaskScheduler);
             return(task.IndexedEntities);
         }
     }
 }
        public long IndexTransactions(ChainBase chain = null)
        {
            using(IndexerTrace.NewCorrelation("Import transactions to azure started").Open())
            {
                using(var node = Configuration.ConnectToNode(false))
                {

                    node.VersionHandshake();

                    var task = new IndexTransactionsTask(Configuration);
                    task.SaveProgression = !IgnoreCheckpoints;
                    task.Index(GetBlockFetcher(GetCheckpointInternal(IndexerCheckpoints.Transactions), node, chain), TaskScheduler);
                    return task.IndexedEntities;
                }
            }
        }
		public static void UpdateChain(this IEnumerable<ChainBlockHeader> entries, ChainBase chain)
		{
			Stack<ChainBlockHeader> toApply = new Stack<ChainBlockHeader>();
			foreach(var entry in entries)
			{
				var prev = chain.GetBlock(entry.Header.HashPrevBlock);
				if(prev == null)
					toApply.Push(entry);
				else
				{
					toApply.Push(entry);
					break;
				}
			}
			while(toApply.Count > 0)
			{
				var newTip = toApply.Pop();

				var chained = new ChainedBlock(newTip.Header, newTip.BlockId, chain.GetBlock(newTip.Header.HashPrevBlock));
				chain.SetTip(chained);
			}
		}
        internal void Index(ChainBase chain, int startHeight)
        {
            List<ChainPartEntry> entries = new List<ChainPartEntry>(((chain.Height - startHeight) / BlockHeaderPerRow) + 5);
            startHeight = startHeight - (startHeight % BlockHeaderPerRow);
            ChainPartEntry chainPart = null;
            for(int i = startHeight; i <= chain.Tip.Height; i++)
            {
                if(chainPart == null)
                    chainPart = new ChainPartEntry()
                    {
                        ChainOffset = i
                    };

                var block = chain.GetBlock(i);
                chainPart.BlockHeaders.Add(block.Header);
                if(chainPart.BlockHeaders.Count == BlockHeaderPerRow)
                {
                    entries.Add(chainPart);
                    chainPart = null;
                }
            }
            if(chainPart != null)
                entries.Add(chainPart);
            Index(entries);
        }
 /// <summary>
 /// Get a block fetcher of the specified chain from the specified checkpoint
 /// </summary>
 /// <param name="checkpoint">The checkpoint to load from</param>
 /// <param name="chain">The chain to fetcher (default: the Node's main chain)</param>
 /// <returns>A BlockFetcher for enumerating blocks and saving progression</returns>
 public BlockFetcher GetBlockFetcher(Checkpoint checkpoint, Node node, ChainBase chain = null)
 {
     if(checkpoint == null)
         throw new ArgumentNullException("checkpoint");
     if(node == null)
         throw new ArgumentNullException("node");
     chain = chain ?? GetNodeChain(node);
     IndexerTrace.CheckpointLoaded(chain.FindFork(checkpoint.BlockLocator), checkpoint.CheckpointName);
     return new BlockFetcher(checkpoint, new NodeBlocksRepository(node), chain)
     {
         NeedSaveInterval = CheckpointInterval,
         FromHeight = FromHeight,
         ToHeight = ToHeight
     };
 }
 /// <summary>
 /// Get a block fetcher of the specified chain from the specified checkpoint
 /// </summary>
 /// <param name="checkpoint">The checkpoint name to load from</param>
 /// <param name="chain">The chain to fetcher (default: the Node's main chain)</param>
 /// <returns>A BlockFetcher for enumerating blocks and saving progression</returns>
 public BlockFetcher GetBlockFetcher(string checkpointName, Node node, ChainBase chain = null)
 {
     if(checkpointName == null)
         throw new ArgumentNullException("checkpointName");
     return GetBlockFetcher(GetCheckpointRepository().GetCheckpoint(checkpointName), node, chain);
 }
 public int IndexWalletBalances(ChainBase chain)
 {
     using(IndexerTrace.NewCorrelation("Import wallet balances to azure started").Open())
     {
         using(var node = Configuration.ConnectToNode(false))
         {
             node.VersionHandshake();
             var task = new IndexBalanceTask(Configuration, Configuration.CreateIndexerClient().GetAllWalletRules());
             task.SaveProgression = !IgnoreCheckpoints;
             task.Index(GetBlockFetcher(GetCheckpointInternal(IndexerCheckpoints.Wallets), node, chain), TaskScheduler);
             return task.IndexedEntities;
         }
     }
 }
示例#39
0
			public WalletTransaction ToWalletTransaction(ChainBase chain, ConcurrentDictionary<string, TrackedScript> trackedScripts, string wallet)
			{
				var chainHeight = chain.Height;
				var tx = new WalletTransaction()
				{
					Proof = Proof,
					Transaction = Transaction,
					UnconfirmedSeen = UnconfirmedSeen,
					AddedDate = AddedDate
				};

				tx.ReceivedCoins = GetCoins(ReceivedCoins, trackedScripts, wallet);
				tx.SpentCoins = GetCoins(SpentCoins, trackedScripts, wallet);

				if(BlockId != null)
				{
					var header = chain.GetBlock(BlockId);
					if(header != null)
					{
						tx.BlockInformation = new BlockInformation()
						{
							Confirmations = chainHeight - header.Height + 1,
							Height = header.Height,
							Header = header.Header
						};
					}
				}
				return tx;
			}
        public void IndexChain(ChainBase chain)
        {
            if(chain == null)
                throw new ArgumentNullException("chain");
            SetThrottling();

            using(IndexerTrace.NewCorrelation("Index main chain to azure started").Open())
            {
                Configuration.GetChainTable().CreateIfNotExists();
                IndexerTrace.InputChainTip(chain.Tip);
                var client = Configuration.CreateIndexerClient();
                var changes = client.GetChainChangesUntilFork(chain.Tip, true).ToList();

                var height = 0;
                if(changes.Count != 0)
                {
                    IndexerTrace.IndexedChainTip(changes[0].BlockId, changes[0].Height);
                    if(changes[0].Height > chain.Tip.Height)
                    {
                        IndexerTrace.InputChainIsLate();
                        return;
                    }
                    height = changes[changes.Count - 1].Height + 1;
                    if(height > chain.Height)
                    {
                        IndexerTrace.IndexedChainIsUpToDate(chain.Tip);
                        return;
                    }
                }
                else
                {
                    IndexerTrace.NoForkFoundWithStored();
                }

                IndexerTrace.IndexingChain(chain.GetBlock(height), chain.Tip);
                Index(chain, height);

            }
        }
示例#41
0
		public WalletTransactionsCollection GetWalletTransactions(ChainBase chain, string wallet = "default")
		{
			lock(cs)
			{
				return new WalletTransactionsCollection(_Operations
					.Select(op => op.Value)
					.Where(op => op.CheckProof())
					.Where(op => op.ContainsWallet(wallet))
					.Select(o => o.ToWalletTransaction(chain, wallet))
					.ToArray());
			}
		}
示例#42
0
		public WalletTransactionsCollection GetWalletTransactions(ChainBase chain, string wallet = "default")
		{
			lock(cs)
			{
				return new WalletTransactionsCollection(_Operations
					.Select(op => op.Value)
					.Where(op => op.CheckProof())
					.Select(o => o.ToWalletTransaction(chain, _TrackedScripts, wallet))
					.Where(o => o.ReceivedCoins.Length != 0 || o.SpentCoins.Length != 0)
					.ToArray());
			}
		}