Example #1
0
        protected override void ChannelRead0(IChannelHandlerContext ctx, DatagramPacket packet)
        {
            var content = packet.Content;
            var address = packet.Sender;

            byte[] msg = new byte[content.ReadableBytes];
            content.ReadBytes(msg);

            if (msg.Length < 98)
            {
                _logger.Error($"Incorrect message, length: {msg.Length}, sender: {address}");
                ctx.DisconnectAsync();
                return;
            }

            var typeRaw = msg[97];

            if (!Enum.IsDefined(typeof(MessageType), (int)typeRaw))
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Unsupported message type: {typeRaw}, sender: {address}, message {msg.ToHexString()}");
                }
                ctx.DisconnectAsync();
                return;
            }

            var type = (MessageType)typeRaw;

            if (_logger.IsTrace)
            {
                _logger.Trace($"Received message: {type}");
            }

            DiscoveryMessage message;

            try
            {
                message            = Deserialize(type, msg);
                message.FarAddress = (IPEndPoint)address;
            }
            catch (Exception e)
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Error during deserialization of the message, type: {type}, sender: {address}, msg: {msg.ToHexString()}, {e.Message}");
                }
                return;
            }

            try
            {
                _discoveryManager.OnIncomingMessage(message);
            }
            catch (Exception e)
            {
                _logger.Error($"Error while processing message, type: {type}, sender: {address}, message: {message}", e);
            }
        }
Example #2
0
        public async Task OnPingMessageTest()
        {
            //receiving ping
            var address = new IPEndPoint(IPAddress.Parse(_host), _port);

            _discoveryManager.OnIncomingMessage(new PingMessage {
                FarAddress = address, FarPublicKey = _publicKey, DestinationAddress = _nodeTable.MasterNode.Address, SourceAddress = address
            });
            await Task.Delay(500);

            // expecting to send pong
            _messageSender.Received(1).SendMessage(Arg.Is <PongMessage>(m => m.FarAddress.Address.ToString() == _host && m.FarAddress.Port == _port));

            // send pings to  new node
            _messageSender.Received().SendMessage(Arg.Is <PingMessage>(m => m.FarAddress.Address.ToString() == _host && m.FarAddress.Port == _port));
        }
        public void OnPingMessageTest()
        {
            //receiving ping
            var address = new IPEndPoint(IPAddress.Parse(_host), _port);

            _discoveryManager.OnIncomingMessage(new PingMessage {
                FarAddress = address, FarPublicKey = _publicKey, DestinationAddress = _nodeTable.MasterNode.Address, SourceAddress = address
            });
            Thread.Sleep(400);

            //expecting to send pong
            _messageSender.Received(1).SendMessage(Arg.Is <PongMessage>(m => m.FarAddress.Address.ToString() == _host && m.FarAddress.Port == _port));

            //expecting to send 3 pings for every new node
            _messageSender.Received(3).SendMessage(Arg.Is <PingMessage>(m => m.FarAddress.Address.ToString() == _host && m.FarAddress.Port == _port));
        }
        public void EvictCandidateStateWonEvictionTest()
        {
            //adding 3 active nodes
            var managers = new List <INodeLifecycleManager>();

            for (var i = 0; i < 3; i++)
            {
                var host    = "192.168.1." + i;
                var node    = new Node(_nodeIds[i], host, _port);
                var manager = _discoveryManager.GetNodeLifecycleManager(node);
                managers.Add(manager);
                Assert.AreEqual(NodeLifecycleState.New, manager.State);

                _discoveryManager.OnIncomingMessage(new PongMessage {
                    FarAddress = new IPEndPoint(IPAddress.Parse(_host), _port), FarPublicKey = _nodeIds[i]
                });
                Assert.AreEqual(NodeLifecycleState.Active, manager.State);
            }

            //table should contain 3 active nodes
            var closestNodes = _nodeTable.GetClosestNodes();

            Assert.IsTrue(closestNodes.Count(x => x.Host == managers[0].ManagedNode.Host) == 1);
            Assert.IsTrue(closestNodes.Count(x => x.Host == managers[1].ManagedNode.Host) == 1);
            Assert.IsTrue(closestNodes.Count(x => x.Host == managers[2].ManagedNode.Host) == 1);

            //adding 4th node - table can store only 3, eviction process should start
            var candidateNode    = new Node(_nodeIds[3], _host, _port);
            var candidateManager = _discoveryManager.GetNodeLifecycleManager(candidateNode);

            Assert.AreEqual(NodeLifecycleState.New, candidateManager.State);

            _discoveryManager.OnIncomingMessage(new PongMessage {
                FarAddress = new IPEndPoint(IPAddress.Parse(_host), _port), FarPublicKey = _nodeIds[3]
            });
            Assert.AreEqual(NodeLifecycleState.Active, candidateManager.State);
            var evictionCandidate = managers.First(x => x.State == NodeLifecycleState.EvictCandidate);

            //receiving pong for eviction candidate - should survive
            _discoveryManager.OnIncomingMessage(new PongMessage {
                FarAddress = new IPEndPoint(IPAddress.Parse(evictionCandidate.ManagedNode.Host), _port), FarPublicKey = evictionCandidate.ManagedNode.Id
            });

            //Thread.Sleep(100);

            //3th node should survive, 4th node should be active but not in the table
            Assert.That(() => candidateManager.State, Is.EqualTo(NodeLifecycleState.ActiveExcluded).After(100, 50));
            Assert.That(() => evictionCandidate.State, Is.EqualTo(NodeLifecycleState.Active).After(100, 50));

            //Assert.AreEqual(NodeLifecycleState.ActiveExcluded, candidateManager.State);
            //Assert.AreEqual(NodeLifecycleState.Active, evictionCandidate.State);
            closestNodes = _nodeTable.GetClosestNodes();
            Assert.That(() => closestNodes.Count(x => x.Host == managers[0].ManagedNode.Host) == 1, Is.True.After(100, 50));
            Assert.That(() => closestNodes.Count(x => x.Host == managers[1].ManagedNode.Host) == 1, Is.True.After(100, 50));
            Assert.That(() => closestNodes.Count(x => x.Host == managers[2].ManagedNode.Host) == 1, Is.True.After(100, 50));
            Assert.That(() => closestNodes.Count(x => x.Host == candidateNode.Host) == 0, Is.True.After(100, 50));

            //Assert.IsTrue(closestNodes.Count(x => x.Host == managers[0].ManagedNode.Host) == 1);
            //Assert.IsTrue(closestNodes.Count(x => x.Host == managers[1].ManagedNode.Host) == 1);
            //Assert.IsTrue(closestNodes.Count(x => x.Host == managers[2].ManagedNode.Host) == 1);
            //Assert.IsTrue(closestNodes.Count(x => x.Host == candidateNode.Host) == 0);
        }
Example #5
0
        protected override void ChannelRead0(IChannelHandlerContext ctx, DatagramPacket packet)
        {
            IByteBuffer content = packet.Content;
            EndPoint    address = packet.Sender;

            byte[] msg = new byte[content.ReadableBytes];
            content.ReadBytes(msg);

            Interlocked.Add(ref Metrics.DiscoveryBytesReceived, msg.Length);

            if (msg.Length < 98)
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Incorrect discovery message, length: {msg.Length}, sender: {address}");
                }
                return;
            }

            byte typeRaw = msg[97];

            if (!Enum.IsDefined(typeof(MessageType), (int)typeRaw))
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Unsupported message type: {typeRaw}, sender: {address}, message {msg.ToHexString()}");
                }
                return;
            }

            MessageType type = (MessageType)typeRaw;

            if (_logger.IsTrace)
            {
                _logger.Trace($"Received message: {type}");
            }

            DiscoveryMessage message;

            try
            {
                message            = Deserialize(type, msg);
                message.FarAddress = (IPEndPoint)address;
            }
            catch (Exception e)
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Error during deserialization of the message, type: {type}, sender: {address}, msg: {msg.ToHexString()}, {e.Message}");
                }
                return;
            }

            try
            {
                ReportMessageByType(message);

                if (!ValidateMessage(message, type, address, ctx, packet))
                {
                    return;
                }

                _discoveryManager.OnIncomingMessage(message);
            }
            catch (Exception e)
            {
                if (_logger.IsDebug)
                {
                    _logger.Error($"DEBUG/ERROR Error while processing message, type: {type}, sender: {address}, message: {message}", e);
                }
            }
        }
        protected override void ChannelRead0(IChannelHandlerContext ctx, DatagramPacket packet)
        {
            var content = packet.Content;
            var address = packet.Sender;

            byte[] msg = new byte[content.ReadableBytes];
            content.ReadBytes(msg);

            if (msg.Length < 98)
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Incorrect discovery message, length: {msg.Length}, sender: {address}");
                }
                ctx.DisconnectAsync();
                return;
            }

            var typeRaw = msg[97];

            if (!Enum.IsDefined(typeof(MessageType), (int)typeRaw))
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Unsupported message type: {typeRaw}, sender: {address}, message {msg.ToHexString()}");
                }
                ctx.DisconnectAsync();
                return;
            }

            var type = (MessageType)typeRaw;

            if (_logger.IsTrace)
            {
                _logger.Trace($"Received message: {type}");
            }

            DiscoveryMessage message;

            try
            {
                message            = Deserialize(type, msg);
                message.FarAddress = (IPEndPoint)address;
            }
            catch (Exception e)
            {
                if (_logger.IsDebug)
                {
                    _logger.Debug($"Error during deserialization of the message, type: {type}, sender: {address}, msg: {msg.ToHexString()}, {e.Message}");
                }
                ctx.DisconnectAsync();
                return;
            }

            try
            {
                if ((ulong)message.ExpirationTime < _timestamper.EpochSeconds)
                {
                    if (_logger.IsDebug)
                    {
                        _logger.Debug($"Received a discovery message that has expired, type: {type}, sender: {address}, message: {message}");
                    }
                    ctx.DisconnectAsync();
                    return;
                }

                if (!message.FarAddress.Equals((IPEndPoint)packet.Sender))
                {
                    if (_logger.IsDebug)
                    {
                        _logger.Debug($"Discovery fake IP detected - pretended {message.FarAddress} but was {ctx.Channel.RemoteAddress}, type: {type}, sender: {address}, message: {message}");
                    }
                    ctx.DisconnectAsync();
                    return;
                }

                if (message.FarPublicKey == null)
                {
                    if (_logger.IsDebug)
                    {
                        _logger.Debug($"Discovery message without a valid signature {message.FarAddress} but was {ctx.Channel.RemoteAddress}, type: {type}, sender: {address}, message: {message}");
                    }
                    ctx.DisconnectAsync();
                    return;
                }

                _discoveryManager.OnIncomingMessage(message);
            }
            catch (Exception e)
            {
                if (_logger.IsDebug)
                {
                    _logger.Error($"DEBUG/ERROR Error while processing message, type: {type}, sender: {address}, message: {message}", e);
                }
                ctx.DisconnectAsync();
            }
        }