Esempio n. 1
0
        public void TestSimpleDatabaseStoreLeaseSetEd25519Creation()
        {
            var linfo  = new I2PLeaseInfo(Public, PublicSigningEd25519, Private, PrivateSigningEd25519);
            var leases = new List <I2PLease>();

            for (int i = 0; i < 5; ++i)
            {
                leases.Add(new I2PLease(new I2PIdentHash(true), (uint)((i * 72 + 6) * i * 1314 + 5) % 40000, I2PDate.Now));
            }
            var ls = new I2PLeaseSet(new I2PDestination(Public, PublicSigningEd25519), leases, linfo);

            var dbsm = new DatabaseStoreMessage(ls);

            var data = dbsm.Header16.HeaderAndPayload;

            var recreated = I2NPMessage.ReadHeader16(new BufRefLen(data));

            Assert.IsTrue(recreated.MessageType == I2NPMessage.MessageTypes.DatabaseStore);
            var rdsm = (DatabaseStoreMessage)recreated.Message;

            Assert.IsTrue(rdsm.LeaseSet.Leases.Count == 5);

            Assert.IsTrue(BufUtils.Equal(ls.Destination.ToByteArray(), rdsm.LeaseSet.Destination.ToByteArray()));
            Assert.IsTrue(BufUtils.Equal(ls.PublicKey.ToByteArray(), rdsm.LeaseSet.PublicKey.ToByteArray()));
            Assert.IsTrue(BufUtils.Equal(ls.PublicSigningKey.ToByteArray(), rdsm.LeaseSet.PublicSigningKey.ToByteArray()));
            for (int i = 0; i < 5; ++i)
            {
                Assert.IsTrue(BufUtils.Equal(ls.Leases[i].ToByteArray(), rdsm.LeaseSet.Leases[i].ToByteArray()));
            }

            Assert.IsTrue(rdsm.LeaseSet.VerifySignature());
        }
Esempio n. 2
0
 public void Add(I2NPMessage msg)
 {
     lock ( Messages )
     {
         Messages.Add(msg);
     }
 }
Esempio n. 3
0
 public virtual void SendRaw(I2NPMessage msg)
 {
     lock ( SendQueue )
     {
         SendRawQueue.AddFirst(msg);
     }
 }
Esempio n. 4
0
        public void TestSimpleTunnelDataCreation()
        {
            var smalldata = BufUtils.RandomBytes(38);

            var srcmsgs = new List <TunnelMessage>();

            srcmsgs.Add(new TunnelMessageLocal(new DeliveryStatusMessage(1234)));
            var msgfrags = TunnelDataMessage.MakeFragments(srcmsgs, 0x3e5c);

            Assert.IsTrue(msgfrags.Count() == 1);

            var firstmsg   = msgfrags.First();
            var serialized = firstmsg.CreateHeader16.HeaderAndPayload;

            var recovered = I2NPMessage.ReadHeader16(new BufRefLen(serialized));

            var reassembler     = new TunnelDataFragmentReassembly();
            var reassembledmsgs = reassembler.Process(
                new TunnelDataMessage[]
            {
                (TunnelDataMessage)recovered.Message
            }, out var _);

            Assert.IsTrue(reassembledmsgs.Count() == 1);

            var firstrecinstr = reassembledmsgs.First();

            Assert.IsTrue(firstrecinstr.Delivery == TunnelMessage.DeliveryTypes.Local);
            Assert.IsTrue(firstrecinstr.Message.MessageType == I2NPMessage.MessageTypes.DeliveryStatus);
            Assert.IsTrue(((DeliveryStatusMessage)firstrecinstr.Message).StatusMessageId == 1234);
        }
Esempio n. 5
0
        public void TestSimpleDatabaseHeader5StoreCreation()
        {
            var mapping = new I2PMapping();

            mapping["One"] = "1";
            mapping["2"]   = "Two";

            var ri = new I2PRouterInfo(
                new I2PRouterIdentity(Public, PublicSigning),
                I2PDate.Now,
                new I2PRouterAddress[] { new I2PRouterAddress(new IPAddress(424242L), 773, 42, "SSU") },
                mapping,
                PrivateSigning);

            var dbsm = new DatabaseStoreMessage(ri);

            var data = dbsm.CreateHeader16.HeaderAndPayload;

            var recreated = I2NPMessage.ReadHeader16(new BufRefLen(data));

            Assert.IsTrue(recreated.MessageType == I2NPMessage.MessageTypes.DatabaseStore);
            var rdsm = (DatabaseStoreMessage)recreated.Message;

            Assert.IsTrue(rdsm.RouterInfo.Options["One"] == "1");
            Assert.IsTrue(rdsm.RouterInfo.Options["2"] == "Two");
            Assert.IsTrue(rdsm.RouterInfo.VerifySignature());
        }
Esempio n. 6
0
        public void Send(I2NPMessage msg)
        {
            if (Terminated)
            {
                throw new EndOfStreamEncounteredException();
            }

            lock ( SendQueue )
            {
                var len = SendQueue.Count;

                if (len < SendQueueLengthUpperLimit)
                {
                    SendQueue.AddLast(msg.Header5);
                }
#if DEBUG
                else
                {
                    DebugUtils.LogWarning(
                        string.Format("SSUSession {0}: SendQueue is {1} messages long! Dropping new message. Max queue: {2} ({3:###0}s)",
                                      DebugId, len, SessionMaxSendQueueLength, MinTimeBetweenSendQueueLogs.DeltaToNow.ToSeconds));
                }

                SessionMaxSendQueueLength = Math.Max(SessionMaxSendQueueLength, len);

                if ((len > SendQueueLengthWarningLimit) && (MinTimeBetweenSendQueueLogs.DeltaToNowMilliseconds > 4000))
                {
                    DebugUtils.LogWarning(
                        string.Format("SSUSession {0}: SendQueue is {1} messages long! Max queue: {2} ({3:###0}s)",
                                      DebugId, len, SessionMaxSendQueueLength, MinTimeBetweenSendQueueLogs.DeltaToNow.ToSeconds));
                    MinTimeBetweenSendQueueLogs.SetNow();
                }
#endif
            }
        }
Esempio n. 7
0
 public GarlicClove(GarlicCloveDelivery delivery)
 {
     Delivery   = delivery;
     Message    = delivery.Message;
     CloveId    = BufUtils.RandomUint();
     Expiration = new I2PDate(DateTime.UtcNow + TimeSpan.FromSeconds(8));
 }
Esempio n. 8
0
 public GarlicClove(GarlicCloveDelivery delivery, I2PDate exp)
 {
     Delivery   = delivery;
     Message    = delivery.Message;
     CloveId    = BufUtils.RandomUint();
     Expiration = exp;
 }
        public void MakeAndReadFragmentsWithSerialize()
        {
            var origmsgs = new List <TunnelMessage>();

            for (int i = 0; i < 200; ++i)
            {
                switch (BufUtils.RandomInt(3))
                {
                case 0:
                    var adatarec = new DataMessage(
                        new BufLen(
                            BufUtils.RandomBytes(2048 + BufUtils.RandomInt(1024))));

                    origmsgs.Add(new TunnelMessageLocal(adatarec));
                    break;

                case 1:
                    var arec = new DatabaseLookupMessage(
                        new I2PIdentHash(true),
                        new I2PIdentHash(true),
                        DatabaseLookupMessage.LookupTypes.RouterInfo);

                    origmsgs.Add(new TunnelMessageRouter(
                                     arec,
                                     new I2PIdentHash(true)));
                    break;

                case 2:
                    var adatarec2 = new DataMessage(
                        new BufLen(
                            BufUtils.RandomBytes(2048 + BufUtils.RandomInt(1024))));

                    origmsgs.Add(new TunnelMessageTunnel(adatarec2,
                                                         new I2PIdentHash(true),
                                                         BufUtils.RandomUint()));
                    break;
                }
            }

            var msgs     = TunnelDataMessage.MakeFragments(origmsgs, BufUtils.RandomUint());
            var recvlist = new List <TunnelDataMessage>();

            foreach (var msg in msgs)
            {
                recvlist.Add((TunnelDataMessage)I2NPMessage.ReadHeader16(
                                 new BufRefLen(msg.CreateHeader16.HeaderAndPayload)).Message);
            }

            var mkmsg     = new TunnelDataFragmentReassembly();
            var recvtmsgs = mkmsg.Process(recvlist, out var _);

            foreach (var rmsg in recvtmsgs)
            {
                Assert.IsTrue(origmsgs.SingleOrDefault(m =>
                                                       m.Delivery == rmsg.Delivery &&
                                                       m.Message.CreateHeader16.HeaderAndPayload == rmsg.Message.CreateHeader16.HeaderAndPayload
                                                       ) != null);
            }
        }
Esempio n. 10
0
 public GarlicClove(BufRef reader)
 {
     Delivery   = GarlicCloveDelivery.CreateGarlicCloveDelivery(reader);
     Message    = I2NPMessage.ReadHeader16(reader).Message;
     CloveId    = reader.Read32();
     Expiration = new I2PDate(reader);
     reader.Seek(3);   // Cert
 }
Esempio n. 11
0
        public DeliveryStatusMessage()
        {
            AllocateBuffer(12);
            var writer = new BufRefLen(Payload);

            Timestamp       = new I2PDate(DateTime.UtcNow);
            StatusMessageId = I2NPMessage.GenerateMessageId();
        }
Esempio n. 12
0
        public virtual void MessageReceived(I2NPMessage msg, int recvdatasize)
        {
#if LOG_ALL_TUNNEL_TRANSFER
            Logging.LogDebug($"{this}: MessageReceived {msg.Message}");
#endif
            Bandwidth.DataReceived(recvdatasize);

            //Logging.LogDebug( $"{this}: MessageReceived {msg.MessageType} TDM len {recvsize}" );
            ReceiveQueue.Enqueue(msg);
        }
Esempio n. 13
0
        public BufLen GenerateData(I2NPMessage msg)
        {
            if (NTCPContext == null)
            {
                throw new Exception("NTCP Session not negotiated!");
            }
            if (NTCPContext.Encryptor == null)
            {
                throw new Exception("NTCP encryptor not available");
            }

            var data = msg != null ? msg.Header16.HeaderAndPayload: null;

            var datalength = msg == null ? 4 : data.Length;
            var buflen     = 2 + datalength + 4;
            var padlength  = BufUtils.Get16BytePadding(buflen);

            buflen += padlength;

            var buf    = new BufLen(new byte[buflen]);
            var writer = new BufRefLen(buf);

            // Length
            if (msg == null)
            {
                // Send timestamp
                writer.Write16(0);
                writer.WriteFlip32((uint)(DateTime.UtcNow - I2PDate.RefDate).TotalSeconds);
            }
            else
            {
                if (data.Length > 16378)
                {
                    throw new ArgumentException("NTCP data can be max 16378 bytes long!");
                }
                writer.WriteFlip16((ushort)data.Length);
                writer.Write(data);
            }

            // Pad
            writer.Write(BufUtils.Random(writer.Length - 4));

            // Checksum
            var checkbuf = new BufLen(buf, 0, writer - buf);
            var checksum = LZUtils.Adler32(1, checkbuf);

            writer.WriteFlip32(checksum);

            // Encrypt
            NTCPContext.Encryptor.ProcessBytes(buf);

            return(buf);
        }
Esempio n. 14
0
        public void Send(I2NPMessage msg)
        {
            if (Terminated)
            {
                throw new EndOfStreamEncounteredException();
            }

            var sendqlen = SendQueue.Count;

#if DEBUG
            SessionMaxSendQueueLength = Math.Max(SessionMaxSendQueueLength, sendqlen);

            if ((SendQueue.Count > SendQueueLengthWarningLimit) && (MinTimeBetweenSendQueueLogs.DeltaToNowMilliseconds > 4000))
            {
                DebugUtils.LogWarning(
                    string.Format("NTCPClient {0}: SendQueue is {1} messages long! Max queue: {2} ({3:###0}s)",
                                  DebugId, sendqlen, SessionMaxSendQueueLength, MinTimeBetweenSendQueueLogs.DeltaToNow.ToSeconds));
                MinTimeBetweenSendQueueLogs.SetNow();
            }
#endif

            lock ( SendQueue )
            {
                if (sendqlen < SendQueueLengthUpperLimit)
                {
                    SendQueue.AddLast(msg);
                }
#if DEBUG
                else
                {
                    DebugUtils.LogWarning(
                        string.Format("NTCPClient {0}: SendQueue is {1} messages long! Dropping new message. Max queue: {2} ({3:###0}s)",
                                      DebugId, sendqlen, SessionMaxSendQueueLength, MinTimeBetweenSendQueueLogs.DeltaToNow.ToSeconds));
                }
#endif
            }

            try
            {
                TryInitiateSend();
            }
            catch (SocketException ex)
            {
                if (NTCPContext.RemoteRouterIdentity != null)
                {
                    NetDb.Inst.Statistics.FailedToConnect(NTCPContext.RemoteRouterIdentity.IdentHash);
                }
                throw new EndOfStreamEncounteredException(ex.ToString());
            }
        }
Esempio n. 15
0
        public void TestGarlicCreate()
        {
            var ls = new I2PDate(DateTime.Now + TimeSpan.FromMinutes(5));

            var origmessage = new DeliveryStatusMessage(I2NPMessage.GenerateMessageId());
            var bigmessage  = new DataMessage(new BufLen(BufUtils.RandomBytes(14 * 1024)));

            var garlic = new Garlic(
                new GarlicClove(
                    new GarlicCloveDeliveryLocal(origmessage),
                    ls),
                new GarlicClove(
                    new GarlicCloveDeliveryLocal(bigmessage),
                    ls)
                );

            var egmsg = Garlic.EGEncryptGarlic(
                garlic,
                Public,
                new I2PSessionKey(),
                null);

            var origegdata  = I2NPMessage.Clone(egmsg);
            var origegdata2 = I2NPMessage.Clone(egmsg);

            // Decrypt

            var(aesblock, sessionkey1) = Garlic.EGDecryptGarlic(origegdata, Private);

            var newgarlic = new Garlic((BufRefLen)aesblock.Payload);

            var g1 = new BufLen(garlic.ToByteArray());
            var g2 = new BufLen(newgarlic.ToByteArray());

            Assert.IsTrue(g1 == g2);

            // Retrieve

            var(aesblock2, sessionkey2) = Garlic.RetrieveAESBlock(origegdata2, Private, null);

            newgarlic = new Garlic((BufRefLen)aesblock2.Payload);

            g1 = new BufLen(garlic.ToByteArray());
            g2 = new BufLen(newgarlic.ToByteArray());

            Assert.IsTrue(g1 == g2);
            Assert.IsTrue(sessionkey1 == sessionkey2);
        }
Esempio n. 16
0
        public void TestEncodeDecodeAES()
        {
            var m1 = new DeliveryStatusMessage(0x4321);
            var m2 = new DeliveryStatusMessage(0xa3c2);

            var garlic = new Garlic(
                new GarlicClove(
                    new GarlicCloveDeliveryDestination(
                        m1,
                        Destination.IdentHash)),
                new GarlicClove(
                    new GarlicCloveDeliveryDestination(
                        m2,
                        Destination.IdentHash))
                );

            // No tags

            var sessionkey = new I2PSessionKey();
            var sessiontag = new I2PSessionTag();

            var cg     = Garlic.AESEncryptGarlic(garlic, sessionkey, sessiontag, null);
            var egdata = I2NPMessage.Clone(cg);

            var(aesblock, sk) = Garlic.RetrieveAESBlock(egdata, Private, (t) => sessionkey);
            var g2 = new Garlic((BufRefLen)aesblock.Payload);

            Assert.IsTrue(BufUtils.Equal(garlic.ToByteArray(), g2.ToByteArray()));

            // With tags
            var tags = new List <I2PSessionTag>();

            for (int i = 0; i < 30; ++i)
            {
                tags.Add(new I2PSessionTag());
            }

            cg     = Garlic.AESEncryptGarlic(garlic, sessionkey, sessiontag, null);
            egdata = I2NPMessage.Clone(cg);

            (aesblock, sk) = Garlic.RetrieveAESBlock(egdata, Private, (t) => sessionkey);
            g2             = new Garlic((BufRefLen)aesblock.Payload);

            Assert.IsTrue(BufUtils.Equal(garlic.ToByteArray(), g2.ToByteArray()));
        }
Esempio n. 17
0
        public void TestSimpleDatabaseStoreLeaseSetCreation()
        {
            var linfo = new I2PLeaseInfo(Public, PublicSigning, Private, PrivateSigning);

            var leases = new List <I2PLease>();

            for (int i = 0; i < 5; ++i)
            {
                leases.Add(new I2PLease(
                               new I2PIdentHash(true),
                               new I2PTunnelId()));
            }

            var ls = new I2PLeaseSet(new I2PDestination(Public, PublicSigning), leases, linfo);

            var dbsm = new DatabaseStoreMessage(ls);

            var data = dbsm.CreateHeader16.HeaderAndPayload.Clone();

            var recreated = I2NPMessage.ReadHeader16(new BufRefLen(data));

            Assert.IsTrue(recreated.MessageType == I2NPMessage.MessageTypes.DatabaseStore);
            var rdsm = (DatabaseStoreMessage)recreated.Message;

            Assert.IsTrue(rdsm.LeaseSet.Leases.Count() == 5);

            Assert.IsTrue(BufUtils.Equal(ls.Destination.ToByteArray(), rdsm.LeaseSet.Destination.ToByteArray()));
            Assert.IsTrue(BufUtils.Equal(ls.PublicKey.ToByteArray(), rdsm.LeaseSet.PublicKey.ToByteArray()));
            Assert.IsTrue(BufUtils.Equal(ls.PublicSigningKey.ToByteArray(), rdsm.LeaseSet.PublicSigningKey.ToByteArray()));

            var rdsmlsar = rdsm.LeaseSet.Leases.ToArray();
            var lsar     = ls.Leases.ToArray();

            // Order should be maintained
            for (int i = 0; i < 5; ++i)
            {
                Assert.IsTrue(
                    BufUtils.Equal(
                        lsar[i].ToByteArray(),
                        rdsmlsar[i].ToByteArray()));
            }

            Assert.IsTrue(rdsm.LeaseSet.VerifySignature(PublicSigning));
        }
Esempio n. 18
0
        public void TestSingleLargeTunnelDataCreation()
        {
            var sourcedata = new BufLen(BufUtils.RandomBytes(9000));

            var srcmsgs = new List <TunnelMessage>();

            srcmsgs.Add(new TunnelMessageTunnel(new DataMessage(sourcedata), new I2PIdentHash(true), 4242));
            var msgfrags = TunnelDataMessage.MakeFragments(srcmsgs, 0x3e5c);

            Assert.IsTrue(msgfrags.Count() == 10);

            var serbuf = new List <byte>();

            foreach (var frag in msgfrags)
            {
                serbuf.AddRange(frag.CreateHeader16.HeaderAndPayload);
            }
            var serbufarray = serbuf.ToArray();

            var reassembler = new TunnelDataFragmentReassembly();
            var reader      = new BufRefLen(serbufarray);
            var readmsgs    = new List <TunnelDataMessage>();

            while (reader.Length > 0)
            {
                readmsgs.Add((TunnelDataMessage)(I2NPMessage.ReadHeader16(reader)).Message);
            }

            var reassembledmsgs = reassembler.Process(readmsgs, out var _);

            Assert.IsTrue(reassembledmsgs.Count() == 1);
            Assert.IsTrue(reassembler.BufferedFragmentCount == 0);

            var firstrecinstr = reassembledmsgs.First();

            Assert.IsTrue(firstrecinstr.Delivery == TunnelMessage.DeliveryTypes.Tunnel);
            Assert.IsTrue(((TunnelMessageTunnel)firstrecinstr).Tunnel == 4242);
            Assert.IsTrue(firstrecinstr.Message.MessageType == I2NPMessage.MessageTypes.Data);

            var datamsg = (DataMessage)firstrecinstr.Message;

            Assert.IsTrue(datamsg.DataMessagePayloadLength == sourcedata.Length);
            Assert.IsTrue(datamsg.DataMessagePayload == sourcedata);
        }
        private static void AddTunnelMessage(List <TunnelMessage> result, TunnelDataFragment initialfragment, byte[] buf)
        {
            switch (initialfragment.Delivery)
            {
            case TunnelMessage.DeliveryTypes.Local:
                result.Add(new TunnelMessageLocal(I2NPMessage.ReadHeader16(new BufRef(buf))));
                break;

            case TunnelMessage.DeliveryTypes.Router:
                result.Add(new TunnelMessageRouter(I2NPMessage.ReadHeader16(new BufRef(buf)),
                                                   new I2PIdentHash((BufRefLen)initialfragment.ToHash)));
                break;

            case TunnelMessage.DeliveryTypes.Tunnel:
                result.Add(new TunnelMessageTunnel(I2NPMessage.ReadHeader16(new BufRef(buf)),
                                                   new I2PIdentHash((BufRefLen)initialfragment.ToHash), initialfragment.Tunnel));
                break;
            }
        }
Esempio n. 20
0
        void DestinationMessageReceived(I2NPMessage msg)
        {
#if LOG_ALL_TUNNEL_TRANSFER
            DebugUtils.LogDebug("ClientDestination: DestinationMessageReceived: " + msg.ToString());
#endif
            if (msg.MessageType == I2NPMessage.MessageTypes.Data && DataReceived != null)
            {
                var dmsg = (DataMessage)msg.Header16.Message;
                DataReceived(dmsg.Payload);
            }

            if (msg.MessageType == I2NPMessage.MessageTypes.DatabaseStore)
            {
                var dbsmsg = (DatabaseStoreMessage)msg.Header16.Message;
                if (dbsmsg.LeaseSet != null)
                {
                    Destinations.RemoteLeaseSetUpdated(dbsmsg.LeaseSet);
                }
            }
        }
Esempio n. 21
0
        internal void Add(I2PIdentHash dest, I2NPMessage msg)
        {
            if (CurrentlyUnresolvableRouters.Contains(dest))
            {
                throw new RouterUnresolvableException($"Destination is tagged as unresolvable {dest}");
            }

            var sendlookup = false;

            lock ( QueuedMessages )
            {
                if (!QueuedMessages.ContainsKey(dest))
                {
                    var newld = new LookupDestination(dest);
                    newld.Add(msg);
                    QueuedMessages[dest] = newld;
                    sendlookup           = true;
                }
                else
                {
                    var queue = QueuedMessages[dest];
                    if (queue.Messages.Count < MaxMessagesInQueue)
                    {
                        queue.Add(msg);
                    }
#if DEBUG
                    else
                    {
                        Logging.LogWarning("UnknownRouterQueue: Add: Too many messages in queue. Dropping new message.");
                    }
#endif
                }
            }

            if (sendlookup)
            {
                NetDb.Inst.IdentHashLookup.LookupRouterInfo(dest);
            }
        }
Esempio n. 22
0
 protected GarlicCloveDelivery(I2NPMessage msg, DeliveryMethod mtd)
 {
     Message = msg;
     Flag    = (byte)mtd;
 }
Esempio n. 23
0
        public override SSUState HandleMessage(SSUHeader header, BufRefLen reader)
        {
            DataSent();
#if LOG_ALL_TRANSPORT
            DebugUtils.Log("SSU EstablishedState +" + Session.TransportInstance.ToString() + "+ received: " +
                           header.MessageType.ToString() + ": " + SSUHost.SSUDateTime(header.TimeStamp).ToString());
#endif
            switch (header.MessageType)
            {
            case SSUHeader.MessageTypes.Data:
                try
                {
                    var datamsg = new SSUDataMessage(reader, Session.Defragmenter);
                    if (datamsg.ExplicitAcks != null)
                    {
                        Session.Fragmenter.GotAck(datamsg.ExplicitAcks);
                    }
                    if (datamsg.AckBitfields != null)
                    {
                        Session.Fragmenter.GotAck(datamsg.AckBitfields);
                    }
                    if (datamsg.NewMessages != null)
                    {
                        foreach (var msg in datamsg.NewMessages)
                        {
                            var i2npmsg = I2NPMessage.ReadHeader5((BufRefLen)msg.GetPayload());

#if LOG_ALL_TRANSPORT
                            DebugUtils.Log("SSU EstablishedState +" + Session.TransportInstance.ToString() + "+ complete message " +
                                           msg.MessageId.ToString() + ": " + i2npmsg.Expiration.ToString());
#endif

                            if (i2npmsg.MessageType == I2PCore.Tunnel.I2NP.Messages.I2NPMessage.MessageTypes.DeliveryStatus)
                            {
                                if (((DeliveryStatusMessage)i2npmsg.Message).IsNetworkId((ulong)I2PConstants.I2P_NETWORK_ID))
                                {
                                    continue;
                                }
                            }

                            Session.MessageReceived(i2npmsg);
                        }
                    }
                }
                catch (Exception ex)
                {
                    DebugUtils.Log("EstablishedState: SSUHost.SSUMessageTypes.Data", ex);
                }
                break;

            case SSUHeader.MessageTypes.SessionDestroyed:
                DebugUtils.LogDebug(() => string.Format("SSU EstablishedState {0}: SessionDestroyed received.", Session.DebugId));
                SendSessionDestroyed();
                return(null);

            case SSUHeader.MessageTypes.PeerTest:
                HandleIncomingPeerTestPackage(reader);
                break;

            case SSUHeader.MessageTypes.RelayResponse:
                DebugUtils.LogDebug(() => string.Format("SSU EstablishedState {0}: RelayResponse received from {1}.",
                                                        Session.DebugId, Session.RemoteEP));
                var response = new RelayResponse(reader);
                Session.Host.ReportRelayResponse(header, response, Session.RemoteEP);
                break;

            case SSUHeader.MessageTypes.RelayIntro:
                var intro = new RelayIntro(reader);
                DebugUtils.LogDebug(() => $"SSU EstablishedState {Session.DebugId}: RelayIntro received from {Session.RemoteEP} for {intro.AliceEndpoint}.");
                Session.Host.Send(intro.AliceEndpoint, new BufLen(new byte[0]));
                break;

            case SSUHeader.MessageTypes.RelayRequest:
                // if ( !SSUHost.IntroductionSupported ) throw new Exception( "SSU relay introduction not supported" );
                DebugUtils.LogDebug(() => string.Format("SSU EstablishedState {0}: Relay introduction not supported.", Session.DebugId));
                break;

            case SSUHeader.MessageTypes.SessionRequest:
                DebugUtils.LogDebug(() => string.Format("SSU EstablishedState {0}: SessionRequest received. Ending session.", Session.DebugId));
                SendSessionDestroyed();
                return(null);

            default:
                DebugUtils.LogDebug(() => string.Format("SSU EstablishedState {0}: Unexpected message received: {1}.",
                                                        Session.DebugId, header.MessageType));
                break;
            }

            return(this);
        }
Esempio n. 24
0
        private static bool Send(I2PIdentHash dest, I2NPMessage data, int reclvl)
        {
            ITransport transp = null;

            try
            {
                if (dest == RouterContext.Inst.MyRouterIdentity.IdentHash)
                {
                    Logging.LogTransport($"TransportProvider: Loopback {data}");
                    TransportProvider.Inst.DistributeIncomingMessage(null, data.CreateHeader16);
                    return(true);
                }

                lock ( TransportSelectionLock )
                {
                    if (TransportProvider.Inst.CurrentlyUnknownRouters.Contains(dest))
                    {
                        TransportProvider.Inst.CurrentlyUnknownRouters.Add(dest, data);
                        return(true);
                    }

                    transp = TransportProvider.Inst.GetEstablishedTransport(dest, false);
                    if (transp != null)
                    {
                        transp.Send(data);
                        return(true);
                    }

                    if (NetDb.Inst.Contains(dest))
                    {
                        transp = TransportProvider.Inst.GetTransport(dest);
                        if (transp == null)
                        {
                            throw new FailedToConnectException($"Unable to contact {dest}");
                        }
                        transp.Send(data);
                    }
                    else
                    {
                        if (TransportProvider.Inst.CurrentlyUnresolvableRouters.Contains(dest))
                        {
                            throw new ArgumentException($"Unable to resolve {dest}");
                        }

                        TransportProvider.Inst.CurrentlyUnknownRouters.Add(dest, data);
                    }
                }
            }
            catch (FailedToConnectException ex)
            {
                if (transp != null)
                {
                    TransportProvider.Inst.Remove(transp);
                }

                if (dest != null && NetDb.Inst != null)
                {
                    NetDb.Inst.Statistics.FailedToConnect(dest);
                }
                Logging.LogTransport($"TransportProvider.Send: {( transp == null ? "<>" : transp.DebugId )}" +
                                     $" Exception {ex.GetType()}");

                return(false);
            }
            catch (EndOfStreamEncounteredException ex)
            {
                TransportProvider.Inst.Remove(transp);

                Logging.LogTransport($"TransportProvider.Send: Connection {( transp == null ? "<>" : transp.DebugId )}" +
                                     $" closed exception: {ex.GetType()}");

                if (reclvl > 1 || !Send(dest, data, reclvl + 1))
                {
                    Logging.LogTransport($"TransportProvider.Send: Recconnection failed to {dest.Id32Short}, reclvl: {reclvl}.");
                    throw;
                }
            }
            catch (RouterUnresolvableException ex)
            {
                if (dest != null)
                {
                    NetDb.Inst.Statistics.DestinationInformationFaulty(dest);
                }
                Logging.LogTransport($"TransportProvider.Send: Unresolvable router: {ex.Message}");

                return(false);
            }
            catch (Exception ex)
            {
                if (transp != null)
                {
                    TransportProvider.Inst.Remove(transp);
                }

                if (dest != null)
                {
                    NetDb.Inst.Statistics.DestinationInformationFaulty(dest);
                }
                Logging.LogTransport($"TransportProvider.Send: Exception {ex.GetType()}, {ex.Message}");

                throw;
            }
            return(true);
        }
Esempio n. 25
0
 public static bool Send(I2PIdentHash dest, I2NPMessage data)
 {
     return(Send(dest, data, 0));
 }
Esempio n. 26
0
        private bool HandleTunnelMessage(I2NPMessage msg)
        {
#if LOG_ALL_TUNNEL_TRANSFER
            Logging.LogDebug($"{this} HandleReceiveQueue: {msg.MessageType}");
#endif

            switch (msg.MessageType)
            {
            case I2NPMessage.MessageTypes.TunnelBuildReply:
            case I2NPMessage.MessageTypes.TunnelData:
                throw new NotImplementedException($"Should not happen {TunnelDebugTrace}");

            case I2NPMessage.MessageTypes.VariableTunnelBuildReply:
                ThreadPool.QueueUserWorkItem(cb =>
                {
                    TunnelProvider.Inst.HandleTunnelBuildReply((VariableTunnelBuildReplyMessage)msg);
                });
                return(true);

            case I2NPMessage.MessageTypes.DeliveryStatus:
#if LOG_ALL_TUNNEL_TRANSFER
                Logging.LogDebug($"{this}: DeliveryStatus: {msg.Message}");
#endif

                ThreadPool.QueueUserWorkItem(cb =>
                {
                    lock ( DeliveryStatusReceivedLock )
                    {
                        DeliveryStatusReceived?.Invoke((DeliveryStatusMessage)msg);
                    }
                });
                break;

            case I2NPMessage.MessageTypes.DatabaseStore:
                var ds = (DatabaseStoreMessage)msg;
                ThreadPool.QueueUserWorkItem(cb =>
                {
                    Router.HandleDatabaseStore(ds);
                });
                break;

            case I2NPMessage.MessageTypes.DatabaseSearchReply:
                var dsr = (DatabaseSearchReplyMessage)msg;
                ThreadPool.QueueUserWorkItem(cb =>
                {
                    NetDb.Inst.AddDatabaseSearchReply(dsr);
                });
                break;

            case I2NPMessage.MessageTypes.Garlic:
                var garlic = (GarlicMessage)msg;

#if LOG_ALL_TUNNEL_TRANSFER || LOG_ALL_LEASE_MGMT
                Logging.Log($"{this}: Garlic received");
#endif

                ThreadPool.QueueUserWorkItem(cb =>
                {
                    lock ( GarlicMessageReceivedLock )
                    {
                        GarlicMessageReceived?.Invoke(garlic);
                    }
                });
                break;

            default:
                Logging.LogWarning($"{this}: HandleReceiveQueue: Dropped {msg}");
                break;
            }

            return(true);
        }
Esempio n. 27
0
        void TestOneOutboundTunnel()
        {
            if (OutboundTunnels.IsEmpty)
            {
                return;
            }

            if (!OutboundTunnels.TryDequeue(out var outtunnel))
            {
                return;
            }
            if (!outtunnel.Active || outtunnel.Metrics.PassedTunnelTest)
            {
                return;
            }
            OutboundTunnels.Enqueue(outtunnel);

            var run = OutstandingTests.Get(outtunnel);

            if (run != null)
            {
                // Run has finished?
                if (run.TestedPartners.Count >= RunsPerTest)
                {
                    if (run.LastRun.DeltaToNow < TimeBetweenTests)
                    {
                        return;
                    }
                    run.OutstandingProbes.Clear();
                    run.SuccessPartners.Clear();
                    run.TestedPartners.Clear();
                }
            }
            else
            {
                run = new TestRun2(outtunnel);
                OutstandingTests[outtunnel] = run;
            }

            var test = TestResults.Get(outtunnel, () => new TunnelTestResult(outtunnel));

            var intunnels = TunnelProvider.Inst.GetInboundTunnels()
                            .Where(t => t.Active)
                            .Shuffle()
                            .Take(RunsPerTest * 2)
                            .ToArray();

            if (!intunnels.Any())
            {
                //Logging.LogDebug( "TunnelTester: Failed to get a established inbound tunnel." );
                return;
            }

            run.LastRun.SetNow();

            string tunneldbginfo = "";

            foreach (var intunnel in intunnels)
            {
                if (run.FailurePartners.Contains(intunnel) ||
                    run.SuccessPartners.Contains(intunnel) ||
                    run.TestedPartners.Contains(intunnel))
                {
                    continue;
                }

                run.TestedPartners.Add(intunnel);
                var probe = new ProbesSent()
                {
                    Tunnel    = outtunnel,
                    Partner   = intunnel,
                    MessageId = I2NPMessage.GenerateMessageId(),
                    TotalHops = outtunnel.Config.Info.Hops.Count + intunnel.Config.Info.Hops.Count
                };

                tunneldbginfo += $"({intunnel.TunnelDebugTrace}:{probe.MessageId})";

                run.OutstandingProbes.Add(probe);
                OutstandingProbeIds[probe.MessageId] = probe;
                outtunnel.Send(new TunnelMessageTunnel(new DeliveryStatusMessage(probe.MessageId), intunnel));
            }

            if (tunneldbginfo.Length > 0)
            {
                Logging.LogDebug(
                    $"TunnelTester: Starting outbound tunnel {outtunnel.TunnelDebugTrace} test with tunnels: {tunneldbginfo}");
            }
        }
Esempio n. 28
0
 public override void SendRaw(I2NPMessage msg)
 {
     throw new NotImplementedException();
 }
Esempio n. 29
0
        void Run()
        {
            try
            {
                try
                {
                    NTCPContext.TransportInstance = TransportInstance;

                    Watchdog.Inst.StartMonitor(Thread.CurrentThread, 20000);

                    try
                    {
                        MySocket = CreateSocket();

                        RemoteDescription = MySocket.RemoteEndPoint.ToString();

#if LOG_ALL_TRANSPORT
                        DebugUtils.LogDebug("My local endpoint IP#   : " + ((IPEndPoint)MySocket.LocalEndPoint).Address.ToString());
                        DebugUtils.LogDebug("My local endpoint Port  : " + ((IPEndPoint)MySocket.LocalEndPoint).Port.ToString());
#endif

                        DHNegotiate();
                    }
                    catch (SocketException ex)
                    {
                        if (NTCPContext.RemoteRouterIdentity != null)
                        {
                            NetDb.Inst.Statistics.FailedToConnect(NTCPContext.RemoteRouterIdentity.IdentHash);
                        }
                        throw new FailedToConnectException(ex.ToString());
                    }
                    catch (FormatException)
                    {
                        if (NTCPContext.RemoteRouterIdentity != null)
                        {
                            NetDb.Inst.Statistics.DestinationInformationFaulty(NTCPContext.RemoteRouterIdentity.IdentHash);
                        }
                        throw;
                    }
                    catch (NotSupportedException)
                    {
                        if (NTCPContext.RemoteRouterIdentity != null)
                        {
                            NetDb.Inst.Statistics.DestinationInformationFaulty(NTCPContext.RemoteRouterIdentity.IdentHash);
                        }
                        throw;
                    }
                    catch (ThreadInterruptedException)
                    {
                        if (NTCPContext.RemoteRouterIdentity != null)
                        {
                            NetDb.Inst.Statistics.SlowHandshakeConnect(NTCPContext.RemoteRouterIdentity.IdentHash);
                        }
                        throw;
                    }
                    catch (ThreadAbortException)
                    {
                        if (NTCPContext.RemoteRouterIdentity != null)
                        {
                            NetDb.Inst.Statistics.SlowHandshakeConnect(NTCPContext.RemoteRouterIdentity.IdentHash);
                        }
                        throw;
                    }

                    DHSucceeded = true;

                    Watchdog.Inst.UpdateTimeout(Thread.CurrentThread, InactivityTimeoutSeconds * 1000);

                    TryInitiateSend();

#if DEBUG
                    if (ConnectionEstablished == null)
                    {
                        DebugUtils.LogWarning("NTCPClient: No observers for ConnectionEstablished!");
                    }
#endif
                    if (ConnectionEstablished != null)
                    {
                        ConnectionEstablished(this);
                    }
                    NetDb.Inst.Statistics.SuccessfulConnect(NTCPContext.RemoteRouterIdentity.IdentHash);

                    var reader = new NTCPReader(MySocket, NTCPContext);

                    while (!Terminated)
                    {
                        var data = reader.Read();
                        //DebugUtils.LogDebug( "Read: " + data.Length );

                        Watchdog.Inst.Ping(Thread.CurrentThread);

                        if (reader.NTCPDataSize == 0)
                        {
                            //if ( TimeSyncReceived != null ) TimeSyncReceived( this, data );
                        }
                        else
                        {
#if DEBUG
                            if (DataBlockReceived == null)
                            {
                                DebugUtils.LogWarning("NTCPClient: No observers for DataBlockReceived !");
                            }
#endif
                            if (DataBlockReceived != null)
                            {
                                DataBlockReceived(this, I2NPMessage.ReadHeader16(new BufRefLen(data)));
                            }
                        }
                    }
                }
                catch (ThreadAbortException)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {0} Aborted", DebugId));
                }
                catch (ThreadInterruptedException)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {0} Interrupted", DebugId));
                }
                catch (FailedToConnectException)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {0} Failed to connect", DebugId));
                }
                catch (EndOfStreamEncounteredException)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {0} Disconnected", DebugId));
                }
                catch (IOException ex)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {1} Exception: {0}", ex, DebugId));
                }
                catch (SocketException ex)
                {
                    DebugUtils.LogDebug(string.Format("NTCP {1} Exception: {0}", ex, DebugId));
                }
                catch (Exception ex)
                {
#if DEBUG
                    if (ConnectionException == null)
                    {
                        DebugUtils.LogWarning("NTCPClient: No observers for ConnectionException!");
                    }
#endif
                    if (ConnectionException != null)
                    {
                        ConnectionException(this, ex);
                    }
                    DebugUtils.LogDebug(string.Format("NTCP {1} Exception: {0}", ex, DebugId));
                }
            }

            finally
            {
                Terminated = true;
                Watchdog.Inst.StopMonitor(Thread.CurrentThread);

                try
                {
                    if (!DHSucceeded && NTCPContext.RemoteRouterIdentity != null)
                    {
                        NetDb.Inst.Statistics.FailedToConnect(NTCPContext.RemoteRouterIdentity.IdentHash);
                    }
                }
                catch (Exception ex)
                {
                    DebugUtils.Log(DebugId, ex);
                }

                DebugUtils.LogDebug(string.Format("NTCP {0} Shut down. {1}", DebugId, RemoteDescription));

                try
                {
#if DEBUG
                    if (ConnectionShutDown == null)
                    {
                        DebugUtils.LogWarning("NTCPClient: No observers for ConnectionShutDown!");
                    }
#endif
                    if (ConnectionShutDown != null)
                    {
                        ConnectionShutDown(this);
                    }
                }
                catch (Exception ex)
                {
                    DebugUtils.Log(DebugId, ex);
                }

                if (MySocket != null)
                {
                    try
                    {
                        MySocket.Shutdown(SocketShutdown.Both);
                        MySocket.Close();
                    }
                    catch (Exception ex)
                    {
                        DebugUtils.Log(DebugId, ex);
                    }
                    finally
                    {
                        MySocket = null;
                    }
                }
            }
        }
Esempio n. 30
0
        public override SSUState HandleMessage(SSUHeader header, BufRefLen reader)
        {
            switch (header.MessageType)
            {
            case SSUHeader.MessageTypes.Data:
                try
                {
                    var datamsg = new SSUDataMessage(reader, Session.Defragmenter);
                    if (datamsg.ExplicitAcks != null)
                    {
                        Session.Fragmenter.GotAck(datamsg.ExplicitAcks);
                    }
                    if (datamsg.AckBitfields != null)
                    {
                        Session.Fragmenter.GotAck(datamsg.AckBitfields);
                    }
                    if (datamsg.NewMessages != null)
                    {
                        foreach (var msg in datamsg.NewMessages)
                        {
                            var i2npmsg = I2NPMessage.ReadHeader16((BufRefLen)msg.GetPayload());

#if LOG_MUCH_TRANSPORT
                            Logging.LogDebugData($"SSU {this} complete message " +
                                                 $"{msg.MessageId}: {i2npmsg.Expiration}");
#endif

                            if (i2npmsg.MessageType == I2NPMessage.MessageTypes.DeliveryStatus)
                            {
                                if (((DeliveryStatusMessage)i2npmsg.Message).IsNetworkId((ulong)I2PConstants.I2P_NETWORK_ID))
                                {
                                    continue;
                                }
                            }

                            Session.MessageReceived(i2npmsg);
                        }
                    }
                }
                catch (Exception ex)
                {
                    Logging.Log("EstablishedState: SSUHost.SSUMessageTypes.Data", ex);
                }
                break;

            case SSUHeader.MessageTypes.PeerTest:
                HandleIncomingPeerTestPackage(reader);
                break;

            case SSUHeader.MessageTypes.RelayResponse:
                Logging.LogTransport($"SSU EstablishedState {Session.DebugId}: RelayResponse received from {Session.RemoteEP}.");
                var response = new RelayResponse(reader);
                Session.Host.ReportRelayResponse(header, response, Session.RemoteEP);
                break;

            case SSUHeader.MessageTypes.RelayIntro:
                var intro = new RelayIntro(reader);
                Logging.LogTransport($"SSU EstablishedState {Session.DebugId}: RelayIntro received from {Session.RemoteEP} for {intro.AliceEndpoint}.");

                var data = new BufLen(new byte[12]);
                data.Randomize();
                Send(intro.AliceEndpoint, data);

                ++Session.Host.EPStatisitcs[Session.RemoteEP].RelayIntrosReceived;
                ++Session.RelayIntroductionsReceived;
                break;

            case SSUHeader.MessageTypes.RelayRequest:
                // TODO: Implement
                // if ( !SSUHost.IntroductionSupported ) throw new Exception( "SSU relay introduction not supported" );
                Logging.LogTransport(string.Format("SSU EstablishedState {0}: Relay introduction not supported.", Session.DebugId));
                break;

            case SSUHeader.MessageTypes.SessionRequest:
                Logging.LogTransport(string.Format("SSU EstablishedState {0}: SessionRequest received. Ending session.", Session.DebugId));
                SendSessionDestroyed();
                return(null);

            default:
                Logging.LogTransport(string.Format("SSU EstablishedState {0}: Unexpected message received: {1}.",
                                                   Session.DebugId, header.MessageType));
                break;
            }

            return(this);
        }