Ejemplo n.º 1
0
        public override async Task DoReceiveMessageAsync()
        {
            // receive bytes
            UdpReceiveResult udpRes;

            try
            {
                udpRes = await _udpClient.ReceiveAsync().WithCancellation(CloseToken);
            }
            catch (OperationCanceledException)
            {
                // the socket has been closed
                return;
            }

            var buf = AlternativeCompositeByteBuf.CompBuffer();

            buf.WriteBytes(udpRes.Buffer.ToSByteArray());

            var localEp = (IPEndPoint)Socket.LocalEndPoint;

            RemoteEndPoint = udpRes.RemoteEndPoint;

            var dgram = new DatagramPacket(buf, localEp, RemoteEndPoint);

            Logger.Debug("Received {0}. {1} : {2}", dgram, Convenient.ToHumanReadable(udpRes.Buffer.Length), Convenient.ToString(udpRes.Buffer));

            // execute inbound pipeline
            if (Session.IsTimedOut)
            {
                return;
            }
            Session.Read(dgram);
            Session.Reset();
        }
Ejemplo n.º 2
0
        private void VerifySignature(AlternativeCompositeByteBuf buffer, long readerBefore, long len, bool donePayload) // TODO throw exceptions?
        {
            if (!Message.IsSign)
            {
                return;
            }

            // if we read the complete data, we also read the signature
            // for the verification, we should not used this for the signature
            var length = donePayload ? len - (Number160.ByteArraySize + Number160.ByteArraySize) : len;

            MemoryStream[] byteBuffers = null;                                           // TODO no clue how to port this

            var signature = _signatureFactory.Update(Message.PublicKey(0), byteBuffers); // TODO what's going on here?

            if (donePayload)
            {
                byte[] signatureReceived = Message.ReceivedSignature.Encode();
                if (true) // TODO implement .NET signature verification
                {
                    // set the public key only if the signature is correct
                    Message.SetVerified();
                    Logger.Debug("Signature check OK.");
                }
                else
                {
                    Logger.Warn("Signature check NOT OK. Message: {0}.", Message);
                }
            }
        }
Ejemplo n.º 3
0
        /// <summary>
        /// Decodes a message object.
        /// The format looks as follows: 28 bit P2P version, 4 bit message type, 32 bit message ID, 8 bit message command,
        /// 160 bit senderSocket ID, 16 bit senderSocket TCP port, 16 bit senderSocket UDP port, 160 bit recipientSocket ID, 32 bit content types, 8 bit options.
        /// In total, the header is of size 58 bytes.
        /// </summary>
        /// <param name="buffer">The buffer to decode from.</param>
        /// <param name="recipientSocket">The recipientSocket of the message.</param>
        /// <param name="senderSocket">The senderSocket of the packet, which has been set in the socket class.</param> // TODO check if true
        /// <returns>The partial message where only the header fields are set.</returns>
        public static Message DecodeHeader(AlternativeCompositeByteBuf buffer, IPEndPoint recipientSocket, IPEndPoint senderSocket)
        {
            Logger.Debug("Decode message. Recipient: {0}, Sender: {1}", recipientSocket, senderSocket);

            var message = new Message();

            int versionAndType = buffer.ReadInt(); // 4

            message.SetVersion(versionAndType >> 4);
            message.SetType((Message.MessageType)(versionAndType & Utils.Utils.Mask0F)); // TODO does this work? (2x)
            message.SetMessageId(buffer.ReadInt());                                      // 8
            message.SetCommand(buffer.ReadByte());                                       // 9 // TODO check conversion with Java version
            var senderId     = ReadId(buffer);                                           // 29
            int tcpPort      = buffer.ReadUShort();                                      // 31 // TODO check if should be read as short (same as encode)
            int udpPort      = buffer.ReadUShort();                                      // 33
            var recipientId  = ReadId(buffer);                                           // 53
            int contentTypes = buffer.ReadInt();                                         // 57
            int options      = buffer.ReadUByte();                                       // 58 // TODO check if should be read as unsigned/signed

            message.SetRecipient(new PeerAddress(recipientId, recipientSocket));
            message.HasContent(contentTypes != 0);
            message.SetContentType(DecodeContentTypes(contentTypes, message));
            message.SetOptions(options & Utils.Utils.Mask0F);

            // set the address as we see it, important for port forwarding identification
            int senderOptions = options >> 4;
            var pa            = new PeerAddress(senderId, senderSocket.Address, tcpPort, udpPort, senderOptions);

            message.SetSender(pa);
            message.SetSenderSocket(senderSocket);
            message.SetRecipientSocket(recipientSocket);

            return(message);
        }
Ejemplo n.º 4
0
        private static Buffer CreateTestBuffer()
        {
            var acbb = AlternativeCompositeByteBuf.CompBuffer();

            acbb.WriteBytes(TestRawBytes);
            return(new Buffer(acbb));
        }
Ejemplo n.º 5
0
        private bool DecodeHeader(AlternativeCompositeByteBuf buffer, IPEndPoint recipient, IPEndPoint sender)
        {
            if (Message == null)
            {
                if (buffer.ReadableBytes < MessageHeaderCodec.HeaderSize)
                {
                    // we don't have the header yet, we need the full header first
                    // wait for more data
                    return(false);
                }

                Message = MessageHeaderCodec.DecodeHeader(buffer, recipient, sender);
                // we have set the content types already
                Message.SetPresetContentTypes(true);

                foreach (var content in Message.ContentTypes)
                {
                    if (content == Message.Content.Empty)
                    {
                        break;
                    }
                    if (content == Message.Content.PublicKeySignature)
                    {
                        Message.SetHintSign();
                    }
                    _contentTypes.Enqueue(content);
                }
                Logger.Debug("Parsed message {0}.", Message);
                return(true);
            }
            return(false);
        }
Ejemplo n.º 6
0
        public static sbyte[] ReadJavaBytes(byte[] bytes)
        {
            AlternativeCompositeByteBuf buf = AlternativeCompositeByteBuf.CompBuffer();

            buf.WriteBytes(bytes.ToSByteArray());
            return(ExtractBytes(buf).ToSByteArray());
        }
Ejemplo n.º 7
0
        /// <summary>
        /// Decodes a message object.
        /// The format looks as follows: 28 bit P2P version, 4 bit message type, 32 bit message ID, 8 bit message command,
        /// 160 bit senderSocket ID, 16 bit senderSocket TCP port, 16 bit senderSocket UDP port, 160 bit recipientSocket ID, 32 bit content types, 8 bit options.
        /// In total, the header is of size 58 bytes.
        /// </summary>
        /// <param name="buffer">The buffer to decode from.</param>
        /// <param name="recipientSocket">The recipientSocket of the message.</param>
        /// <param name="senderSocket">The senderSocket of the packet, which has been set in the socket class.</param> // TODO check if true
        /// <returns>The partial message where only the header fields are set.</returns>
        public static Message DecodeHeader(AlternativeCompositeByteBuf buffer, IPEndPoint recipientSocket, IPEndPoint senderSocket)
        {
            Logger.Debug("Decode message. Recipient: {0}, Sender: {1}", recipientSocket, senderSocket);

            var message = new Message();

            int versionAndType = buffer.ReadInt(); // 4
            message.SetVersion(versionAndType >> 4);
            message.SetType((Message.MessageType)(versionAndType & Utils.Utils.Mask0F)); // TODO does this work? (2x)
            message.SetMessageId(buffer.ReadInt()); // 8
            message.SetCommand(buffer.ReadByte()); // 9 // TODO check conversion with Java version
            var senderId = ReadId(buffer); // 29
            int tcpPort = buffer.ReadUShort(); // 31 // TODO check if should be read as short (same as encode)
            int udpPort = buffer.ReadUShort(); // 33
            var recipientId = ReadId(buffer); // 53
            int contentTypes = buffer.ReadInt(); // 57
            int options = buffer.ReadUByte(); // 58 // TODO check if should be read as unsigned/signed

            message.SetRecipient(new PeerAddress(recipientId, recipientSocket));
            message.HasContent(contentTypes != 0);
            message.SetContentType(DecodeContentTypes(contentTypes, message));
            message.SetOptions(options & Utils.Utils.Mask0F);

            // set the address as we see it, important for port forwarding identification
            int senderOptions = options >> 4;
            var pa = new PeerAddress(senderId, senderSocket.Address, tcpPort, udpPort, senderOptions);

            message.SetSender(pa);
            message.SetSenderSocket(senderSocket);
            message.SetRecipientSocket(recipientSocket);

            return message;
        }
Ejemplo n.º 8
0
        /// <summary>
        /// Reads a <see cref="Number160"/> from a buffer.
        /// </summary>
        /// <param name="buffer"></param>
        /// <returns></returns>
        private static Number160 ReadId(AlternativeCompositeByteBuf buffer)
        {
            var me = new sbyte[Number160.ByteArraySize];

            buffer.ReadBytes(me);
            return(new Number160(me));
        }
Ejemplo n.º 9
0
            public Buffer Reply(PeerAddress sender, Buffer requestBuffer, bool complete)
            {
                int i = requestBuffer.BackingBuffer.ReadInt();

                Console.WriteLine("Got {0}.", i);
                var buffer = AlternativeCompositeByteBuf.CompBuffer().WriteInt(i);

                return(new Buffer(buffer));
            }
Ejemplo n.º 10
0
        public static byte[] ExtractBytes(AlternativeCompositeByteBuf buf)
        {
            var buffer = buf.NioBuffer();
            buffer.Position = 0;

            var bytes = new byte[buffer.Remaining()];
            buffer.Get(bytes, 0, bytes.Length);
            return bytes;
        }
Ejemplo n.º 11
0
        /// <summary>
        /// Encodes a provided message into a byte array.
        /// </summary>
        /// <param name="message">The message to be encoded.</param>
        /// <returns>The encoded message as byte array.</returns>
        public static byte[] EncodeMessage(Message message)
        {
            var encoder = new Encoder(null);
            AlternativeCompositeByteBuf buf = AlternativeCompositeByteBuf.CompBuffer();

            encoder.Write(buf, message, null);

            return(InteropUtil.ExtractBytes(buf));
        }
Ejemplo n.º 12
0
        public async void TestOrder()
        {
            Peer           sender = null;
            Peer           recv1  = null;
            ChannelCreator cc     = null;

            try
            {
                sender = new PeerBuilder(new Number160("0x50"))
                         .SetMaintenanceTask(Utils2.CreateInfiniteIntervalMaintenanceTask())
                         .SetChannelServerConfiguration(Utils2.CreateInfiniteTimeoutChannelServerConfiguration(2525, 2525))
                         .SetP2PId(55)
                         .SetPorts(2525)
                         .Start();
                recv1 = new PeerBuilder(new Number160("0x20"))
                        .SetMaintenanceTask(Utils2.CreateInfiniteIntervalMaintenanceTask())
                        .SetChannelServerConfiguration(Utils2.CreateInfiniteTimeoutChannelServerConfiguration(9099, 9099))
                        .SetP2PId(55)
                        .SetPorts(8088)
                        .Start();
                recv1.RawDataReply(new TestOrderRawDataReply());

                for (int i = 0; i < 500; i++)
                {
                    cc = await sender.ConnectionBean.Reservation.CreateAsync(0, 1);

                    var sendDirectBuilder = new SendDirectBuilder(sender, (PeerAddress)null);
                    var buffer            = AlternativeCompositeByteBuf.CompBuffer().WriteInt(i);
                    sendDirectBuilder.SetBuffer(new Buffer(buffer));
                    sendDirectBuilder.SetIsStreaming();

                    var tr = sender.DirectDataRpc.SendAsync(recv1.PeerAddress, sendDirectBuilder, cc);
                    Core.Utils.Utils.AddReleaseListener(cc, tr);
                    tr.ContinueWith(t =>
                    {
                        int j = t.Result.Buffer(0).BackingBuffer.ReadInt();
                        Console.WriteLine("Received {0}.", j);
                    });
                }
            }
            finally
            {
                if (sender != null)
                {
                    sender.ShutdownAsync().Wait();
                }
                if (recv1 != null)
                {
                    recv1.ShutdownAsync().Wait();
                }
                if (cc != null)
                {
                    cc.ShutdownAsync().Wait();
                }
            }
        }
Ejemplo n.º 13
0
        protected static Buffer CreateSampleBuffer()
        {
            var acbb = AlternativeCompositeByteBuf.CompBuffer();

            for (int i = 0; i < BufferSizeBytes; i++)
            {
                acbb.WriteByte(i % 256);
            }
            return(new Buffer(acbb));
        }
Ejemplo n.º 14
0
        private void DecodeSignature(AlternativeCompositeByteBuf buffer, long readerBefore, bool donePayload)
        {
            var readerAfter = buffer.ReaderIndex;
            var len         = readerAfter - readerBefore;

            if (len > 0)
            {
                VerifySignature(buffer, readerBefore, len, donePayload);
            }
        }
Ejemplo n.º 15
0
        /// <summary>
        /// Converts data to a byte buffer. The first two bytes contain the size of this simple bloom filter. Thus, the bloom filter can only be of length 65536.
        /// </summary>
        /// <param name="buffer"></param>
        public void ToByteBuffer(AlternativeCompositeByteBuf buffer)
        {
            sbyte[] tmp = BitArray.ToByteArray();
            int     currentByteArraySize = tmp.Length;

            buffer.WriteShort((short)(_byteArraySize + SizeHeader));
            buffer.WriteInt(ExpectedElements);
            buffer.WriteBytes(tmp);
            buffer.WriteZero(_byteArraySize - currentByteArraySize);
        }
Ejemplo n.º 16
0
        public DatagramPacket(AlternativeCompositeByteBuf content, IPEndPoint recipient, IPEndPoint sender)
        {
            if (content == null)
            {
                throw new NullReferenceException("content");
            }

            _content = content;
            _recipient = recipient;
            _sender = sender;
        }
Ejemplo n.º 17
0
        public static byte[] ExtractBytes(AlternativeCompositeByteBuf buf)
        {
            var buffer = buf.NioBuffer();

            buffer.Position = 0;

            var bytes = new byte[buffer.Remaining()];

            buffer.Get(bytes, 0, bytes.Length);
            return(bytes);
        }
Ejemplo n.º 18
0
        public DatagramPacket(AlternativeCompositeByteBuf content, IPEndPoint recipient, IPEndPoint sender)
        {
            if (content == null)
            {
                throw new NullReferenceException("content");
            }

            _content   = content;
            _recipient = recipient;
            _sender    = sender;
        }
Ejemplo n.º 19
0
        private void EncodeData(AlternativeCompositeByteBuf buffer, Data data, bool isConvertMeta, bool isReply)
        {
            data = isConvertMeta ? data.DuplicateMeta() : data.Duplicate();

            if (isReply)
            {
                var ttl = (int)((data.ExpirationMillis - Convenient.CurrentTimeMillis()) / 1000);
                data.SetTtlSeconds(ttl < 0 ? 0 : ttl);
            }

            data.EncodeHeader(buffer, _signatureFactory);
            data.EncodeBuffer(buffer);
            data.EncodeDone(buffer, _signatureFactory, Message.PrivateKey);
        }
Ejemplo n.º 20
0
        protected override async Task ProcessRequestAsync(object state)
        {
            var udpRes = (UdpReceiveResult)state;

            // prepare new session
            var buf     = AlternativeCompositeByteBuf.CompBuffer();
            var session = Pipeline.CreateNewServerSession(this);

            session.TriggerActive();

            // process content
            buf.WriteBytes(udpRes.Buffer.ToSByteArray());

            var localEp  = (IPEndPoint)_udpClient.Client.LocalEndPoint;
            var remoteEp = udpRes.RemoteEndPoint;

            var dgram = new DatagramPacket(buf, localEp, remoteEp);

            Logger.Debug("Received {0}. {1} : {2}", dgram, Convenient.ToHumanReadable(udpRes.Buffer.Length),
                         Convenient.ToString(udpRes.Buffer));

            // execute inbound pipeline
            var readRes = session.Read(dgram); // resets timeout

            if (session.IsTimedOut)
            {
                session.TriggerInactive();
                return;
            }

            // execute outbound pipeline
            var writeRes = session.Write(readRes); // resets timeout

            if (session.IsTimedOut)
            {
                session.TriggerInactive();
                return;
            }

            // send back
            var bytes = ConnectionHelper.ExtractBytes(writeRes);
            await _udpClient.SendAsync(bytes, bytes.Length, remoteEp);

            NotifyWriteCompleted(); // resets timeout
            Logger.Debug("Sent {0} : {1}", Convenient.ToHumanReadable(udpRes.Buffer.Length),
                         Convenient.ToString(udpRes.Buffer));

            session.TriggerInactive();
        }
Ejemplo n.º 21
0
        /// <summary>
        /// Encodes a message object.
        /// The format looks as follows: 28 bit P2P version, 4 bit message type, 32 bit message ID, 8 bit message command,
        /// 160 bit senderSocket ID, 16 bit senderSocket TCP port, 16 bit senderSocket UDP port, 160 bit recipientSocket ID, 32 bit content types, 8 bit options.
        /// In total, the header is of size 58 bytes.
        /// </summary>
        /// <param name="buffer">The buffer to encode to.</param>
        /// <param name="message">The message with the header that will be encoded.</param>
        public static void EncodeHeader(AlternativeCompositeByteBuf buffer, Message message)
        {
            // TODO add log statemet, also in Java version
            int versionAndType = message.Version << 4 | ((int)message.Type & Utils.Utils.Mask0F); // TODO check if ordinal works

            buffer.WriteInt(versionAndType);                                                      // 4
            buffer.WriteInt(message.MessageId);                                                   // 8
            buffer.WriteByte(message.Command);                                                    // 9
            buffer.WriteBytes(message.Sender.PeerId.ToByteArray());                               // 29
            buffer.WriteShort((short)message.Sender.TcpPort);                                     // 31
            buffer.WriteShort((short)message.Sender.UdpPort);                                     // 33
            buffer.WriteBytes(message.Recipient.PeerId.ToByteArray());                            // 53
            buffer.WriteInt(EncodeContentTypes(message.ContentTypes));                            // 57
            buffer.WriteByte((sbyte)(message.Sender.Options << 4 | message.Options));             // 58 // TODO check if works
        }
Ejemplo n.º 22
0
        public void TestDecodeByte()
        {
            var bytes = JarRunner.RequestJavaBytes();

            var buf = AlternativeCompositeByteBuf.CompBuffer();

            buf.WriteBytes(bytes.ToSByteArray());

            // Java byte is signed
            for (int i = sbyte.MinValue; i <= sbyte.MaxValue; i++) // -128 ... 127
            {
                sbyte b = buf.ReadByte();
                Assert.IsTrue(i == b);
            }
        }
Ejemplo n.º 23
0
        /// <summary>
        /// Encodes a message object.
        /// The format looks as follows: 28 bit P2P version, 4 bit message type, 32 bit message ID, 8 bit message command,
        /// 160 bit senderSocket ID, 16 bit senderSocket TCP port, 16 bit senderSocket UDP port, 160 bit recipientSocket ID, 32 bit content types, 8 bit options.
        /// In total, the header is of size 58 bytes.
        /// </summary>
        /// <param name="buffer">The buffer to encode to.</param>
        /// <param name="message">The message with the header that will be encoded.</param>
        public static void EncodeHeader(AlternativeCompositeByteBuf buffer, Message message)
        {
            // TODO add log statemet, also in Java version
            int versionAndType = message.Version << 4 | ((int)message.Type & Utils.Utils.Mask0F); // TODO check if ordinal works

            buffer.WriteInt(versionAndType); // 4
            buffer.WriteInt(message.MessageId); // 8
            buffer.WriteByte(message.Command); // 9
            buffer.WriteBytes(message.Sender.PeerId.ToByteArray()); // 29
            buffer.WriteShort((short) message.Sender.TcpPort); // 31 
            buffer.WriteShort((short) message.Sender.UdpPort); // 33
            buffer.WriteBytes(message.Recipient.PeerId.ToByteArray()); // 53
            buffer.WriteInt(EncodeContentTypes(message.ContentTypes)); // 57
            buffer.WriteByte((sbyte) (message.Sender.Options << 4 | message.Options)); // 58 // TODO check if works
        }
Ejemplo n.º 24
0
        public void TestEncodeByte()
        {
            var buffer = AlternativeCompositeByteBuf.CompBuffer();

            // Java byte is signed
            for (int i = sbyte.MinValue; i <= sbyte.MaxValue; i++) // -128 ... 127
            {
                buffer.WriteByte((sbyte)i);
            }

            var bytes = InteropUtil.ExtractBytes(buffer);

            bool interopResult = JarRunner.WriteBytesAndTestInterop(bytes);

            Assert.IsTrue(interopResult);
        }
Ejemplo n.º 25
0
        /// <summary>
        /// Creates a peer address from a byte buffer.
        /// </summary>
        /// <param name="buffer">The channel buffer to read from.</param>
        public PeerAddress(AlternativeCompositeByteBuf buffer)
        {
            long readerIndex = buffer.ReaderIndex;

            // get the type
            int options = buffer.ReadByte();

            IsIPv6          = (options & Net6) > 0;
            IsFirewalledUdp = (options & FirewallUdp) > 0;
            IsFirewalledTcp = (options & FirewallTcp) > 0;
            IsRelayed       = (options & Relayed) > 0;

            // get the relays
            int relays = buffer.ReadByte();

            RelaySize = (relays >> TypeBitSize) & Mask07;
            var b = (byte)(relays & Mask1F);  // TODO check if works (2x)

            _relayType = new BitArray(b);

            // get the ID
            var me = new sbyte[Number160.ByteArraySize];

            buffer.ReadBytes(me);
            PeerId = new Number160(me);

            PeerSocketAddress = PeerSocketAddress.Create(buffer, IsIPv4);

            if (RelaySize > 0)
            {
                PeerSocketAddresses = new List <PeerSocketAddress>(RelaySize);
                for (int i = 0; i < RelaySize; i++)
                {
                    PeerSocketAddresses.Add(PeerSocketAddress.Create(buffer, !_relayType.Get(i)));
                }
            }
            else
            {
                PeerSocketAddresses = EmptyPeerSocketAddresses;
            }

            Size = buffer.ReaderIndex - readerIndex;

            Offset    = -1; // not used here
            _hashCode = PeerId.GetHashCode();
        }
Ejemplo n.º 26
0
        public bool Decode(ChannelHandlerContext ctx, AlternativeCompositeByteBuf buffer, IPEndPoint recipient, IPEndPoint sender)
        {
            Logger.Debug("Decoding of TomP2P starts now. Readable: {0}.", buffer.ReadableBytes);

            try
            {
                long readerBefore = buffer.ReaderIndex;
                // set the sender of this message for handling timeout
                var attrInetAddr = ctx.Attr(InetAddressKey);
                attrInetAddr.Set(sender);

                if (Message == null)
                {
                    bool doneHeader = DecodeHeader(buffer, recipient, sender);
                    if (doneHeader)
                    {
                        // store the sender as an attribute
                        var attrPeerAddr = ctx.Attr(PeerAddressKey);
                        attrPeerAddr.Set(Message.Sender);

                        Message.SetIsUdp(ctx.Channel.IsUdp);
                        if (Message.IsFireAndForget() && Message.IsUdp)
                        {
                            TimeoutFactory.RemoveTimeout(ctx);
                        }
                    }
                    else
                    {
                        return(false);
                    }
                }

                bool donePayload = DecodePayload(buffer);
                //DecodeSignature(buffer, readerBefore, donePayload);

                // TODO discardSomeReadBytes -> performance improvement
                return(donePayload);
            }
            catch (Exception ex)
            {
                ctx.FireExceptionCaught(ex);
                Console.WriteLine(ex.ToString());
                return(true);
            }
        }
Ejemplo n.º 27
0
        public override void Read(ChannelHandlerContext ctx, object msg)
        {
            // .NET-specific: use a content wrapper for TCP, similar to TomP2PSinglePacketUdp
            var piece = msg as StreamPiece;

            if (piece == null)
            {
                //ctx.FireRead(msg);
                return;
            }

            var buf       = piece.Content;
            var sender    = piece.Sender;
            var recipient = piece.Recipient;

            Logger.Debug("{0}: Cumulating TCP stream piece.", this);
            try
            {
                if (_cumulation == null)
                {
                    _cumulation = AlternativeCompositeByteBuf.CompBuffer(buf);
                }
                else
                {
                    // add to overhead from last TCP packet
                    _cumulation.AddComponent(buf);
                }
                Decoding(ctx, sender, recipient);
            }
            catch (Exception)
            {
                Logger.Error("Error in TCP decoding.");
                throw;
            }
            finally
            {
                // If the currently read buffer is read, it can be deallocated.
                // In case another TCP packet follows, a new buffer is created.
                if (_cumulation != null && !_cumulation.IsReadable)
                {
                    _cumulation = null;
                    // Java: no need to discard bytes as this was done in the decoder already
                }
            }
        }
Ejemplo n.º 28
0
        public bool Decode(ChannelHandlerContext ctx, AlternativeCompositeByteBuf buffer, IPEndPoint recipient, IPEndPoint sender)
        {
            Logger.Debug("Decoding of TomP2P starts now. Readable: {0}.", buffer.ReadableBytes);

            try
            {
                long readerBefore = buffer.ReaderIndex;
                // set the sender of this message for handling timeout
                var attrInetAddr = ctx.Attr(InetAddressKey);
                attrInetAddr.Set(sender);

                if (Message == null)
                {
                    bool doneHeader = DecodeHeader(buffer, recipient, sender);
                    if (doneHeader)
                    {
                        // store the sender as an attribute
                        var attrPeerAddr = ctx.Attr(PeerAddressKey);
                        attrPeerAddr.Set(Message.Sender);

                        Message.SetIsUdp(ctx.Channel.IsUdp);
                        if (Message.IsFireAndForget() && Message.IsUdp)
                        {
                            TimeoutFactory.RemoveTimeout(ctx);
                        }
                    }
                    else
                    {
                        return false;
                    }
                }

                bool donePayload = DecodePayload(buffer);
                //DecodeSignature(buffer, readerBefore, donePayload);

                // TODO discardSomeReadBytes -> performance improvement
                return donePayload;
            }
            catch (Exception ex)
            {
                ctx.FireExceptionCaught(ex);
                Console.WriteLine(ex.ToString());
                return true;
            }
        }
Ejemplo n.º 29
0
        public void TestDecodeBytes()
        {
            var bytes = JarRunner.RequestJavaBytes();

            var buf = AlternativeCompositeByteBuf.CompBuffer();

            buf.WriteBytes(bytes.ToSByteArray());

            // Java byte is signed
            var byteArray = new sbyte[256];

            buf.ReadBytes(byteArray);

            for (int i = 0, b = sbyte.MinValue; i <= sbyte.MaxValue; i++, b++) // -128 ... 127
            {
                Assert.IsTrue(b == byteArray[i]);
            }
        }
Ejemplo n.º 30
0
        public void TestEncodeBytes()
        {
            AlternativeCompositeByteBuf buffer = AlternativeCompositeByteBuf.CompBuffer();

            // Java byte is signed
            sbyte[] byteArray = new sbyte[256];
            for (int i = 0, b = sbyte.MinValue; b <= sbyte.MaxValue; i++, b++) // -128 ... 127
            {
                byteArray[i] = (sbyte)b;
            }

            buffer.WriteBytes(byteArray);

            var bytes = InteropUtil.ExtractBytes(buffer);

            bool interopResult = JarRunner.WriteBytesAndTestInterop(bytes);

            Assert.IsTrue(interopResult);
        }
Ejemplo n.º 31
0
        /// <summary>
        /// Decodes a message from the provided byte array.
        /// </summary>
        /// <param name="bytes">The message bytes from Java encoding.</param>
        /// <returns>The .NET message version.</returns>
        public static Message DecodeMessage(byte[] bytes)
        {
            var decoder = new Decoder(null);

            // mock a non-working ChannelHandlerContext
            var pipeline = new Pipeline();
            var channel  = new MyTcpClient(new IPEndPoint(IPAddress.Any, 0), pipeline);
            var session  = new PipelineSession(channel, pipeline, new List <IInboundHandler>(), new List <IOutboundHandler>());
            var ctx      = new ChannelHandlerContext(channel, session);

            // create dummy sender for decoding
            var message = Utils2.CreateDummyMessage();
            AlternativeCompositeByteBuf buf = AlternativeCompositeByteBuf.CompBuffer();

            buf.WriteBytes(bytes.ToSByteArray());
            decoder.Decode(ctx, buf, message.Recipient.CreateSocketTcp(), message.Sender.CreateSocketTcp());

            return(decoder.Message);
        }
Ejemplo n.º 32
0
        public override void Read(ChannelHandlerContext ctx, object msg)
        {
            // .NET-specific: use a content wrapper for TCP, similar to TomP2PSinglePacketUdp
            var piece = msg as StreamPiece;
            if (piece == null)
            {
                //ctx.FireRead(msg);
                return;
            }

            var buf = piece.Content;
            var sender = piece.Sender;
            var recipient = piece.Recipient;
            Logger.Debug("{0}: Cumulating TCP stream piece.", this);
            try
            {
                if (_cumulation == null)
                {
                    _cumulation = AlternativeCompositeByteBuf.CompBuffer(buf);
                }
                else
                {
                    // add to overhead from last TCP packet
                    _cumulation.AddComponent(buf);
                }
                Decoding(ctx, sender, recipient);
            }
            catch (Exception)
            {
                Logger.Error("Error in TCP decoding.");
                throw;
            }
            finally
            {
                // If the currently read buffer is read, it can be deallocated.
                // In case another TCP packet follows, a new buffer is created.
                if (_cumulation != null && !_cumulation.IsReadable)
                {
                    _cumulation = null;
                    // Java: no need to discard bytes as this was done in the decoder already
                }
            }
        }
Ejemplo n.º 33
0
        public override async Task DoReceiveMessageAsync()
        {
            // TODO find zero-copy way, use same buffer
            // receive bytes
            var bytesRecv = new byte[256];
            var buf       = AlternativeCompositeByteBuf.CompBuffer();

            var stream     = _tcpClient.GetStream();
            var pieceCount = 0;

            do
            {
                Array.Clear(bytesRecv, 0, bytesRecv.Length);
                buf.Clear();
                int nrBytes;
                try
                {
                    nrBytes = await stream.ReadAsync(bytesRecv, 0, bytesRecv.Length).WithCancellation(CloseToken);
                }
                catch (OperationCanceledException)
                {
                    // the socket has been closed
                    return;
                }
                buf.WriteBytes(bytesRecv.ToSByteArray(), 0, nrBytes);

                var localEp = (IPEndPoint)Socket.LocalEndPoint;
                RemoteEndPoint = (IPEndPoint)Socket.RemoteEndPoint;

                var piece = new StreamPiece(buf, localEp, RemoteEndPoint);
                Logger.Debug("[{0}] Received {1}. {2} : {3}", ++pieceCount, piece, Convenient.ToHumanReadable(nrBytes), Convenient.ToString(bytesRecv));

                // execute inbound pipeline, per piece (reset session!)
                if (Session.IsTimedOut)
                {
                    return;
                }
                Session.Read(piece);
                Session.Reset();
            } while (!IsClosed && stream.DataAvailable && !Session.IsTimedOut);
        }
Ejemplo n.º 34
0
        /// <summary>
        /// Decodes a <see cref="PeerSocketAddress"/> from a buffer.
        /// </summary>
        /// <param name="buffer">The buffer.</param>
        /// <param name="isIPv4">Whether the address is IPv4 or IPv6.</param>
        /// <returns>The <see cref="PeerSocketAddress"/> and the new offset.</returns>
        public static PeerSocketAddress Create(AlternativeCompositeByteBuf buffer, bool isIPv4)
        {
            int tcpPort = buffer.ReadUShort();
            int udpPort = buffer.ReadUShort();

            IPAddress address;

            sbyte[] me;
            if (isIPv4)
            {
                me = new sbyte[Utils.Utils.IPv4Bytes];
                buffer.ReadBytes(me);
                address = Utils.Utils.Inet4AddressFromBytes(me, 0);
            }
            else
            {
                me = new sbyte[Utils.Utils.IPv6Bytes];
                buffer.ReadBytes(me);
                address = Utils.Utils.Inet6AddressFromBytes(me, 0);
            }
            return(new PeerSocketAddress(address, tcpPort, udpPort, buffer.ReaderIndex));
        }
Ejemplo n.º 35
0
        public bool Write(AlternativeCompositeByteBuf buffer, Message message, ISignatureCodec signatureCodec)
        {
            Message = message;
            Logger.Debug("Message for outbound {0}.", message);

            if (!_header)
            {
                MessageHeaderCodec.EncodeHeader(buffer, message);
                _header = true;
            }
            else
            {
                Logger.Debug("Send a follow-up message {0}.", message);
                _resume = true;
            }

            bool done = Loop(buffer);

            Logger.Debug("Message encoded {0}.", message);

            // write out what we have
            if (buffer.IsReadable && done)
            {
                // check if message needs to be signed
                if (message.IsSign)
                {
                    // we sign if we did not provide a signature already
                    if (signatureCodec == null)
                    {
                        signatureCodec = _signatureFactory.Sign(message.PrivateKey, buffer);
                    }
                    // in case of relay, we have a signature, so we need to resuse this
                    signatureCodec.Write(buffer);
                }
            }

            return(done);
        }
Ejemplo n.º 36
0
        private static Message CreateMessageByteBuffer()
        {
            // write some random bytes
            var buf = AlternativeCompositeByteBuf.CompBuffer();

            for (int i = 0; i < 300; i++)
            {
                switch (i % 3)
                {
                case 0:
                    buf.WriteBytes(_sampleBytes1);
                    break;

                case 1:
                    buf.WriteBytes(_sampleBytes2);
                    break;

                case 2:
                    buf.WriteBytes(_sampleBytes3);
                    break;
                }
            }

            // decompose buffer and use the resulting 8 ByteBufs in the list
            var decoms = buf.Decompose(0, buf.ReadableBytes);

            var m = Utils2.CreateDummyMessage();

            m.SetBuffer(new Buffer(decoms[0]));
            m.SetBuffer(new Buffer(decoms[1]));
            m.SetBuffer(new Buffer(decoms[2]));
            m.SetBuffer(new Buffer(decoms[3]));
            m.SetBuffer(new Buffer(decoms[4]));
            m.SetBuffer(new Buffer(decoms[5]));
            m.SetBuffer(new Buffer(decoms[6]));
            m.SetBuffer(new Buffer(decoms[7]));
            return(m);
        }
Ejemplo n.º 37
0
        private void VerifySignature(AlternativeCompositeByteBuf buffer, long readerBefore, long len, bool donePayload) // TODO throw exceptions?
        {
            if (!Message.IsSign)
            {
                return;
            }

            // if we read the complete data, we also read the signature
            // for the verification, we should not used this for the signature
            var length = donePayload ? len - (Number160.ByteArraySize + Number160.ByteArraySize) : len;
            MemoryStream[] byteBuffers = null; // TODO no clue how to port this

            var signature = _signatureFactory.Update(Message.PublicKey(0), byteBuffers); // TODO what's going on here?

            if (donePayload)
            {
                byte[] signatureReceived = Message.ReceivedSignature.Encode();
                if (true) // TODO implement .NET signature verification
                {
                    // set the public key only if the signature is correct
                    Message.SetVerified();
                    Logger.Debug("Signature check OK.");
                }
                else
                {
                    Logger.Warn("Signature check NOT OK. Message: {0}.", Message);
                }
            }
        }
Ejemplo n.º 38
0
        public override void ChannelInactive(ChannelHandlerContext ctx)
        {
            var sender = ctx.Channel.RemoteEndPoint;
            var recipient = ctx.Channel.LocalEndPoint;

            try
            {
                if (_cumulation != null)
                {
                    Decoding(ctx, sender, recipient);
                }
            }
            catch (Exception ex)
            {
                Logger.Error("Error in TCP decoding. (Inactive)", ex);
                throw;
            }
            finally
            {
                _cumulation = null;
                // TODO ctx.FireInactive needed?
            }
        }
Ejemplo n.º 39
0
        private bool DecodeHeader(AlternativeCompositeByteBuf buffer, IPEndPoint recipient, IPEndPoint sender)
        {
            if (Message == null)
            {
                if (buffer.ReadableBytes < MessageHeaderCodec.HeaderSize)
                {
                    // we don't have the header yet, we need the full header first
                    // wait for more data
                    return false;
                }

                Message = MessageHeaderCodec.DecodeHeader(buffer, recipient, sender);
                // we have set the content types already
                Message.SetPresetContentTypes(true);

                foreach (var content in Message.ContentTypes)
                {
                    if (content == Message.Content.Empty)
                    {
                        break;
                    }
                    if (content == Message.Content.PublicKeySignature)
                    {
                        Message.SetHintSign();
                    }
                    _contentTypes.Enqueue(content);
                }
                Logger.Debug("Parsed message {0}.", Message);
                return true;
            }
            return false;
        }
Ejemplo n.º 40
0
        private bool DecodePayload(AlternativeCompositeByteBuf buffer)
        {
            Logger.Debug("About to pass message {0} to {1}. Buffer to read: {2}.", Message, Message.SenderSocket, buffer.ReadableBytes);

            if (!Message.HasContent())
            {
                return true;
            }

            int size;
            IPublicKey receivedPublicKey;

            while (_contentTypes.Count > 0)
            {
                Message.Content content = _contentTypes.Peek();
                Logger.Debug("Go for content: {0}.", content);

                switch (content)
                {
                    case Message.Content.Integer:
                        if (buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        Message.SetIntValue(buffer.ReadInt());
                        LastContent = _contentTypes.Dequeue();
                        break;
                    case Message.Content.Long:
                        if (buffer.ReadableBytes < Utils.Utils.LongByteSize)
                        {
                            return false;
                        }
                        Message.SetLongValue(buffer.ReadLong());
                        LastContent = _contentTypes.Dequeue();
                        break;
                    case Message.Content.Key:
                        if (buffer.ReadableBytes < Number160.ByteArraySize)
                        {
                            return false;
                        }
                        var keyBytes = new sbyte[Number160.ByteArraySize];
                        buffer.ReadBytes(keyBytes);
                        Message.SetKey(new Number160(keyBytes));
                        LastContent = _contentTypes.Dequeue();
                        break;
                    case Message.Content.BloomFilter:
                        if (buffer.ReadableBytes < Utils.Utils.ShortByteSize)
                        {
                            return false;
                        }
                        size = buffer.GetUShort(buffer.ReaderIndex);
                        if (buffer.ReadableBytes < size)
                        {
                            return false;
                        }
                        Message.SetBloomFilter(new SimpleBloomFilter<Number160>(buffer));
                        LastContent = _contentTypes.Dequeue();
                        break;
                    case Message.Content.SetNeighbors:
                        if (_neighborSize == -1 && buffer.ReadableBytes < Utils.Utils.ByteByteSize)
                        {
                            return false;
                        }
                        if (_neighborSize == -1)
                        {
                            _neighborSize = buffer.ReadByte();
                        }
                        if (_neighborSet == null)
                        {
                            _neighborSet = new NeighborSet(-1, new List<PeerAddress>(_neighborSize));
                        }
                        for (int i = _neighborSet.Size; i < _neighborSize; i++)
                        {
                            if (buffer.ReadableBytes < Utils.Utils.ShortByteSize)
                            {
                                return false;
                            }
                            int header = buffer.GetUShort(buffer.ReaderIndex);
                            size = PeerAddress.CalculateSize(header);
                            if (buffer.ReadableBytes < size)
                            {
                                return false;
                            }
                            var pa = new PeerAddress(buffer);
                            _neighborSet.Add(pa);
                        }
                        Message.SetNeighborSet(_neighborSet);
                        LastContent = _contentTypes.Dequeue();
                        _neighborSize = -1; // TODO why here? not in prepareFinish()?
                        _neighborSet = null;
                        break;
                    case Message.Content.SetPeerSocket:
                        if (_peerSocketAddressSize == -1 && buffer.ReadableBytes < Utils.Utils.ByteByteSize)
                        {
                            return false;
                        }
                        if (_peerSocketAddressSize == -1)
                        {
                            _peerSocketAddressSize = buffer.ReadUByte();
                        }
                        if (_peerSocketAddresses == null)
                        {
                            _peerSocketAddresses = new List<PeerSocketAddress>(_peerSocketAddressSize);
                        }
                        for (int i = _peerSocketAddresses.Count; i < _peerSocketAddressSize; i++)
                        {
                            if (buffer.ReadableBytes < Utils.Utils.ByteByteSize)
                            {
                                return false;
                            }
                            int header = buffer.GetUByte(buffer.ReaderIndex);
                            bool isIPv4 = header == 0; // TODO check if works
                            size = PeerSocketAddress.Size(isIPv4);
                            if (buffer.ReadableBytes < size + Utils.Utils.ByteByteSize)
                            {
                                return false;
                            }
                            // skip the ipv4/ipv6 header
                            buffer.SkipBytes(1);
                            _peerSocketAddresses.Add(PeerSocketAddress.Create(buffer, isIPv4));
                        }
                        Message.SetPeerSocketAddresses(_peerSocketAddresses);
                        LastContent = _contentTypes.Dequeue();
                        _peerSocketAddressSize = -1; // TODO why here? not in prepareFinish()?
                        _peerSocketAddresses = null;
                        break;
                    case Message.Content.SetKey640:
                        if (_keyCollectionSize == -1 && buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        if (_keyCollectionSize == -1)
                        {
                            _keyCollectionSize = buffer.ReadInt();
                        }
                        if (_keyCollection == null)
                        {
                            _keyCollection = new KeyCollection(new List<Number640>(_keyCollectionSize));
                        }
                        for (int i = _keyCollection.Size; i < _keyCollectionSize; i++)
                        {
                            if (buffer.ReadableBytes < 4 * Number160.ByteArraySize)
                            {
                                return false;
                            }
                            var me = new sbyte[Number160.ByteArraySize];

                            buffer.ReadBytes(me);
                            var locationKey = new Number160(me);

                            buffer.ReadBytes(me);
                            var domainKey = new Number160(me);

                            buffer.ReadBytes(me);
                            var contentKey = new Number160(me);

                            buffer.ReadBytes(me);
                            var versionKey = new Number160(me);

                            _keyCollection.Add(new Number640(locationKey, domainKey, contentKey, versionKey));
                        }
                        Message.SetKeyCollection(_keyCollection);
                        LastContent = _contentTypes.Dequeue();
                        _keyCollectionSize = -1; // TODO why here? not in prepareFinish()?
                        _keyCollection = null;
                        break;
                    case Message.Content.MapKey640Data:
                        if (_mapSize == -1 && buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        if (_mapSize == -1)
                        {
                            _mapSize = buffer.ReadInt();
                        }
                        if (_dataMap == null)
                        {
                            _dataMap = new DataMap(new Dictionary<Number640, Data>(2 * _mapSize));
                        }
                        if (_data != null)
                        {
                            if (!_data.DecodeBuffer(buffer))
                            {
                                return false;
                            }
                            if (!_data.DecodeDone(buffer, Message.PublicKey(0), _signatureFactory))
                            {
                                return false;
                            }
                            _data = null; // TODO why here? not in prepareFinish()?
                            _key = null;
                        }
                        for (int i = _dataMap.Size; i < _mapSize; i++)
                        {
                            if (_key == null)
                            {
                                if (buffer.ReadableBytes < 4 * Number160.ByteArraySize)
                                {
                                    return false;
                                }
                                var me = new sbyte[Number160.ByteArraySize];
                                buffer.ReadBytes(me);
                                var locationKey = new Number160(me);
                                buffer.ReadBytes(me);
                                var domainKey = new Number160(me);
                                buffer.ReadBytes(me);
                                var contentKey = new Number160(me);
                                buffer.ReadBytes(me);
                                var versionKey = new Number160(me);

                                _key = new Number640(locationKey, domainKey, contentKey, versionKey);
                            }
                            _data = Data.DeocdeHeader(buffer, _signatureFactory);
                            if (_data == null)
                            {
                                return false;
                            }
                            _dataMap.BackingDataMap.Add(_key, _data);

                            if (!_data.DecodeBuffer(buffer))
                            {
                                return false;
                            }
                            if (!_data.DecodeDone(buffer, Message.PublicKey(0), _signatureFactory))
                            {
                                return false;
                            }
                            // if we have signed the message, set the public key anyway, but only if we indicated so
                            if (Message.IsSign && Message.PublicKey(0) != null && _data.HasPublicKey
                                && (_data.PublicKey == null || _data.PublicKey == PeerBuilder.EmptyPublicKey))
                            // TODO check empty key condition
                            {
                                _data.SetPublicKey(Message.PublicKey(0));
                            }
                            _data = null; // TODO why here? not in prepareFinish()?
                            _key = null;
                        }

                        Message.SetDataMap(_dataMap);
                        LastContent = _contentTypes.Dequeue();
                        _mapSize = -1; // TODO why here? not in prepareFinish()?
                        _dataMap = null;
                        break;
                    case Message.Content.MapKey640Keys:
                        if (_keyMap640KeysSize == -1 && buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        if (_keyMap640KeysSize == -1)
                        {
                            _keyMap640KeysSize = buffer.ReadInt();
                        }
                        if (_keyMap640Keys == null)
                        {
                            _keyMap640Keys = new KeyMap640Keys(new SortedDictionary<Number640, ICollection<Number160>>());
                            // TODO check TreeMap equivalent
                        }

                        const int meta = 4 * Number160.ByteArraySize;

                        for (int i = _keyMap640Keys.Size; i < _keyMap640KeysSize; i++)
                        {
                            if (buffer.ReadableBytes < meta + Utils.Utils.ByteByteSize)
                            {
                                return false;
                            }
                            size = buffer.GetUByte(buffer.ReaderIndex + meta);

                            if (buffer.ReadableBytes <
                                meta + Utils.Utils.ByteByteSize + (size * Number160.ByteArraySize))
                            {
                                return false;
                            }
                            var me = new sbyte[Number160.ByteArraySize];
                            buffer.ReadBytes(me);
                            var locationKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var domainKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var contentKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var versionKey = new Number160(me);

                            int numBasedOn = buffer.ReadByte();
                            var value = new HashSet<Number160>();
                            for (int j = 0; j < numBasedOn; j++)
                            {
                                buffer.ReadBytes(me);
                                var basedOnKey = new Number160(me);
                                value.Add(basedOnKey);
                            }

                            _keyMap640Keys.Put(new Number640(locationKey, domainKey, contentKey, versionKey), value);
                        }

                        Message.SetKeyMap640Keys(_keyMap640Keys);
                        LastContent = _contentTypes.Dequeue();
                        _keyMap640KeysSize = -1; // TODO why here? not in prepareFinish()?
                        _keyMap640Keys = null;
                        break;
                    case Message.Content.MapKey640Byte:
                        if (_keyMapByteSize == -1 && buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        if (_keyMapByteSize == -1)
                        {
                            _keyMapByteSize = buffer.ReadInt();
                        }
                        if (_keyMapByte == null)
                        {
                            _keyMapByte = new KeyMapByte(new Dictionary<Number640, sbyte>(2 * _keyMapByteSize));
                        }

                        for (int i = _keyMapByte.Size; i < _keyMapByteSize; i++)
                        {
                            if (buffer.ReadableBytes < 4 * Number160.ByteArraySize + 1)
                            {
                                return false;
                            }
                            var me = new sbyte[Number160.ByteArraySize];
                            buffer.ReadBytes(me);
                            var locationKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var domainKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var contentKey = new Number160(me);
                            buffer.ReadBytes(me);
                            var versionKey = new Number160(me);

                            sbyte value = buffer.ReadByte();
                            _keyMapByte.Put(new Number640(locationKey, domainKey, contentKey, versionKey), value);
                        }

                        Message.SetKeyMapByte(_keyMapByte);
                        LastContent = _contentTypes.Dequeue();
                        _keyMapByteSize = -1; // TODO why here? not in prepareFinish()?
                        _keyMapByte = null;
                        break;
                    case Message.Content.ByteBuffer:
                        if (_bufferSize == -1 && buffer.ReadableBytes < Utils.Utils.IntegerByteSize)
                        {
                            return false;
                        }
                        if (_bufferSize == -1)
                        {
                            _bufferSize = buffer.ReadInt();
                        }
                        if (_buffer == null)
                        {
                            _buffer = new DataBuffer();
                        }

                        int already = _buffer.AlreadyTransferred;
                        int remaining = _bufferSize - already;
                        // already finished
                        if (remaining != 0)
                        {
                            int read = _buffer.TransferFrom(buffer, remaining);
                            if (read != remaining)
                            {
                                Logger.Debug(
                                    "Still looking for data. Indicating that its not finished yet. Already Transferred = {0}, Size = {1}.",
                                    _buffer.AlreadyTransferred, _bufferSize);
                                return false;
                            }
                        }

                        ByteBuf buf2 = AlternativeCompositeByteBuf.CompBuffer(_buffer.ToByteBufs());
                        Message.SetBuffer(new Buffer(buf2, _bufferSize));
                        LastContent = _contentTypes.Dequeue();
                        _bufferSize = -1;
                        _buffer = null;
                        break;
                    case Message.Content.SetTrackerData:
                        if (_trackerDataSize == -1 && buffer.ReadableBytes < Utils.Utils.ByteByteSize)
                        {
                            return false;
                        }
                        if (_trackerDataSize == -1)
                        {
                            _trackerDataSize = buffer.ReadUByte();
                        }
                        if (_trackerData == null)
                        {
                            _trackerData = new TrackerData(new Dictionary<PeerAddress, Data>(2 * _trackerDataSize));
                        }
                        if (_currentTrackerData != null)
                        {
                            if (!_currentTrackerData.DecodeBuffer(buffer))
                            {
                                return false;
                            }
                            if (!_currentTrackerData.DecodeDone(buffer, Message.PublicKey(0), _signatureFactory))
                            {
                                return false;
                            }
                            _currentTrackerData = null;
                        }
                        for (int i = _trackerData.Size; i < _trackerDataSize; i++)
                        {
                            if (buffer.ReadableBytes < Utils.Utils.ShortByteSize)
                            {
                                return false;
                            }

                            int header = buffer.GetUShort(buffer.ReaderIndex);
                            size = PeerAddress.CalculateSize(header);
                            if (buffer.ReadableBytes < Utils.Utils.ShortByteSize)
                            {
                                return false;
                            }
                            var pa = new PeerAddress(buffer);

                            _currentTrackerData = Data.DeocdeHeader(buffer, _signatureFactory);
                            if (_currentTrackerData == null)
                            {
                                return false;
                            }
                            _trackerData.PeerAddresses.Add(pa, _currentTrackerData);
                            if (Message.IsSign)
                            {
                                _currentTrackerData.SetPublicKey(Message.PublicKey(0));
                            }
                            if (!_currentTrackerData.DecodeBuffer(buffer))
                            {
                                return false;
                            }
                            if (!_currentTrackerData.DecodeDone(buffer, Message.PublicKey(0), _signatureFactory))
                            {
                                return false;
                            }
                            _currentTrackerData = null; // TODO why here?
                        }

                        Message.SetTrackerData(_trackerData);
                        LastContent = _contentTypes.Dequeue();
                        _trackerDataSize = -1;
                        _trackerData = null;
                        break;
                    case Message.Content.PublicKey: // fall-through
                    case Message.Content.PublicKeySignature:
                        receivedPublicKey = _signatureFactory.DecodePublicKey(buffer);
                        if (content == Message.Content.PublicKeySignature)
                        {
                            if (receivedPublicKey == PeerBuilder.EmptyPublicKey) // TODO check if works
                            {
                                // TODO throw InvalidKeyException
                                throw new SystemException("The public key cannot be empty.");
                            }
                        }
                        if (receivedPublicKey == null)
                        {
                            return false;
                        }

                        Message.SetPublicKey(receivedPublicKey);
                        LastContent = _contentTypes.Dequeue();
                        break;
                    default:
                        break;
                }
            }

            if (Message.IsSign)
            {
                var signatureEncode = _signatureFactory.SignatureCodec;
                size = signatureEncode.SignatureSize;
                if (buffer.ReadableBytes < size)
                {
                    return false;
                }

                signatureEncode.Read(buffer);
                Message.SetReceivedSignature(signatureEncode);
            }
            return true;
        }
Ejemplo n.º 41
0
 private void DecodeSignature(AlternativeCompositeByteBuf buffer, long readerBefore, bool donePayload)
 {
     var readerAfter = buffer.ReaderIndex;
     var len = readerAfter - readerBefore;
     if (len > 0)
     {
         VerifySignature(buffer, readerBefore, len, donePayload);
     }
 }
Ejemplo n.º 42
0
 /// <summary>
 /// Reads a <see cref="Number160"/> from a buffer.
 /// </summary>
 /// <param name="buffer"></param>
 /// <returns></returns>
 private static Number160 ReadId(AlternativeCompositeByteBuf buffer)
 {
     var me = new sbyte[Number160.ByteArraySize];
     buffer.ReadBytes(me);
     return new Number160(me);
 }