Exemple #1
0
        public void ShouldTriggerBlockHandled()
        {
            using (DataGetFixture fixture = new DataGetFixture())
                using (DataGetSession session = fixture.Start())
                {
                    BlockReceived received = new BlockReceived
                    {
                        Payload = new DataGetBlock(),
                        Peer    = PeerHash.Random(),
                        Hash    = session.Service.Hash,
                        Block   = new BlockIndex(1, 0, 3616)
                    };

                    Trigger handler = Trigger.Bind(ref session.Service.Hooks.OnBlockHandled, data =>
                    {
                        data.Hash.Should().Be(session.Service.Hash);
                        data.Peer.Should().NotBeNull();
                        data.Block.Should().Be(received.Block);
                        data.Block.Size.Should().Be(3616);
                    });

                    session.Service.Start();
                    session.Service.Handle(received);

                    session.Pipeline.Process();
                    handler.Wait().Should().BeTrue();
                }
        }
Exemple #2
0
        private void OnBlockReceived(string block)
        {
            _log.Info($"Received: {block}");

            BlockReceived?.Invoke(this, new SerialPortBlockReceivedEventHandlerArgs
            {
                DataBlock = block
            });

            _lastReceivedBlockTime = DateTime.Now;
        }
Exemple #3
0
 public void Handle(BlockReceived data)
 {
     context.Queue.Add(() =>
     {
         if (context.Dependencies.DataMap.IsComplete(data.Block.Piece) == false)
         {
             context.Dependencies.DataStore.Write(data.Block, data.Payload);
             context.Hooks.CallBlockHandled(data.Hash, data.Peer, data.Block);
         }
         else
         {
             data.Payload.Release();
         }
     });
 }
Exemple #4
0
        public void ShouldWriteToRepositoryWhenBlockReceived()
        {
            using (DataGetFixture fixture = new DataGetFixture())
                using (DataGetSession session = fixture.Start())
                {
                    BlockReceived received = new BlockReceived
                    {
                        Payload = new DataGetBlock(),
                        Peer    = PeerHash.Random(),
                        Hash    = session.Service.Hash,
                        Block   = new BlockIndex(1, 0, 3616)
                    };

                    session.Service.Start();
                    session.Service.Handle(received);
                    session.Pipeline.Process();

                    A.CallTo(() => session.DataStore.Write(received.Block, received.Payload)).MustHaveHappened();
                }
        }
Exemple #5
0
 internal void RaiseBlockReceived(BlockEventArgs args)
 {
     BlockReceived?.InvokeAsync(args.TorrentManager, args);
 }
Exemple #6
0
        private async Task ProcessFillBlocks(
            TimeSpan timeout,
            CancellationToken cancellationToken
            )
        {
            var sessionRandom = new Random();
            IComparer <BlockPerception> canonComparer = BlockChain.Policy.CanonicalChainComparer;

            while (!cancellationToken.IsCancellationRequested)
            {
                int sessionId = sessionRandom.Next();

                if (!(BlockDemand is { } blockDemand))
                {
                    await Task.Delay(1, cancellationToken);

                    continue;
                }

                BoundPeer peer = blockDemand.Peer;

                try
                {
                    if (canonComparer.Compare(
                            BlockChain.PerceiveBlock(BlockDemand?.Header),
                            BlockChain.PerceiveBlock(BlockChain.Tip)
                            ) <= 0)
                    {
                        using (await _blockSyncMutex.LockAsync(cancellationToken))
                        {
                            BlockDemand = null;
                            continue;
                        }
                    }

                    var          hash        = new BlockHash(blockDemand.Header.Hash);
                    const string startLogMsg =
                        "{SessionId}: Got a new " + nameof(BlockDemand) + " from {Peer}; started " +
                        "to fetch the block #{BlockIndex} {BlockHash}...";
                    _logger.Debug(startLogMsg, sessionId, peer, blockDemand.Header.Index, hash);
                    await SyncPreviousBlocksAsync(
                        blockChain : BlockChain,
                        peer : peer,
                        stop : hash,
                        progress : null,
                        timeout : timeout,
                        totalBlockCount : 0,
                        logSessionId : sessionId,
                        cancellationToken : cancellationToken
                        );

                    _logger.Debug(
                        "{SessionId}: Synced block(s) from {Peer}; broadcast them to neighbors...",
                        sessionId,
                        peer
                        );

                    // FIXME: Clean up events
                    BlockReceived.Set();
                    BlockAppended.Set();
                    BroadcastBlock(peer.Address, BlockChain.Tip);

                    ProcessFillBlocksFinished.Set();
                }
                catch (TimeoutException)
                {
                    const string msg =
                        "{SessionId}: Timeout occurred during " + nameof(ProcessFillBlocks) +
                        "() from {Peer}.";
                    _logger.Debug(msg, sessionId, peer);
                }
                catch (InvalidBlockIndexException ibie)
                {
                    const string msg =
                        "{SessionId}: " + nameof(InvalidBlockIndexException) + " occurred during " +
                        nameof(ProcessFillBlocks) + "() from {Peer}: {Exception}";
                    _logger.Warning(ibie, msg, sessionId, peer, ibie);
                }
                catch (Exception e)
                {
                    const string msg =
                        "{SessionId}: Unexpected exception occurred during " +
                        nameof(ProcessFillBlocks) + "() from {Peer}: {Exception}";
                    _logger.Error(e, msg, sessionId, peer, e);
                }
                finally
                {
                    using (await _blockSyncMutex.LockAsync(cancellationToken))
                    {
                        const string msg =
                            "{SessionId}: " + nameof(ProcessFillBlocks) + "() finished.";
                        _logger.Debug(msg, sessionId);
                        if (BlockDemand.Equals(blockDemand))
                        {
                            const string resetMsg =
                                "{SessionId}: Reset " + nameof(BlockDemand) + "...";
                            _logger.Debug(resetMsg, sessionId);
                            BlockDemand = null;
                        }
                    }
                }
            }
        }