public void TestOrder() { NullTransport t = new NullTransport(); MockConnexion cnx = new MockConnexion(); cnx.Scheduler = new ImmediatePacketScheduler(cnx); cnx.Transports.Add(t); uint lastBytesSent = 0; for (int i = 0; i < 6; i++) { cnx.Scheduler.Schedule(new ObjectMessage(0, i), MessageDeliveryRequirements.LeastStrict, null); Assert.IsTrue(lastBytesSent < t.BytesSent); lastBytesSent = t.BytesSent; } cnx.Flush(); Assert.IsTrue(t.BytesSent == lastBytesSent, "Flush() should have made no difference to bytes sent"); // check order int msgNo = 0; foreach (TransportPacket tp in cnx.SentPackets) { while (tp.Length > 0) { cnx.Marshaller.Unmarshal(tp, t, delegate(object sender, MessageEventArgs mea) { Assert.AreEqual(msgNo, ((ObjectMessage)mea.Message).Object, "message was sent out of order!"); }); msgNo++; } } }
public void TestAggregationSendsNothingUntilFlush() { NullTransport t = new NullTransport(); MockConnexion cnx = new MockConnexion(); cnx.Scheduler = new RoundRobinPacketScheduler(cnx); cnx.Transports.Add(t); for (int i = 0; i < 6; i++) { cnx.Scheduler.Schedule(new ObjectMessage(0, i), MessageDeliveryRequirements.LeastStrict, null); Assert.AreEqual(0, t.BytesSent); Assert.AreEqual(0, cnx.SentPackets.Count); } cnx.Flush(); Assert.IsTrue(t.BytesSent > 0); Assert.IsTrue(cnx.SentPackets.Count > 0); }
public void TestImmediateComesFirst() { NullTransport t = new NullTransport(); MockConnexion cnx = new MockConnexion(); cnx.Scheduler = new RoundRobinPacketScheduler(cnx); cnx.Transports.Add(t); /// Send a bunch of messages that should be aggregated. /// Then send a message that should go immediately (i.e., sent /// before any of the aggregated messages). for (int i = 1; i < 6; i++) { cnx.Scheduler.Schedule(new ObjectMessage((byte)(i % 2), i), MessageDeliveryRequirements.LeastStrict, null); Assert.AreEqual(0, t.BytesSent); Assert.AreEqual(0, cnx.SentPackets.Count); } cnx.Scheduler.Schedule(new StringMessage(0, "foo"), new MessageDeliveryRequirements(Reliability.Unreliable, MessageAggregation.Immediate, Ordering.Unordered), null); Assert.IsTrue(t.BytesSent > 0); Assert.IsTrue(cnx.SentPackets.Count > 0); int msgNo = 0; foreach (TransportPacket tp in cnx.SentPackets) { if (msgNo == 0) { // Firt message should be the immediate message cnx.Marshaller.Unmarshal(tp, t, delegate(object sender, MessageEventArgs mea) { Assert.IsInstanceOfType(typeof(StringMessage), mea.Message); Assert.AreEqual("foo", ((StringMessage)mea.Message).Text); }); msgNo++; } while(tp.Length > 0) { cnx.Marshaller.Unmarshal(tp, t, delegate(object sender, MessageEventArgs mea) { Assert.AreEqual(msgNo, ((ObjectMessage)mea.Message).Object); Assert.AreEqual(msgNo % 2, ((ObjectMessage)mea.Message).ChannelId); }); msgNo++; } } }
public void TestSendsOnSameChannelInOrder() { NullTransport t = new NullTransport(); MockConnexion cnx = new MockConnexion(); cnx.Scheduler = new RoundRobinPacketScheduler(cnx); cnx.Transports.Add(t); for (int i = 0; i < 6; i++) { cnx.Scheduler.Schedule(new ObjectMessage(0, i), MessageDeliveryRequirements.LeastStrict, null); Assert.AreEqual(0, t.BytesSent); Assert.AreEqual(0, cnx.SentPackets.Count); } cnx.Flush(); Assert.IsTrue(t.BytesSent > 0); Assert.IsTrue(cnx.SentPackets.Count > 0); int msgNo = 0; foreach (TransportPacket tp in cnx.SentPackets) { while (tp.Length > 0) { cnx.Marshaller.Unmarshal(tp, t, delegate(object sender, MessageEventArgs mea) { Assert.AreEqual(msgNo, ((ObjectMessage)mea.Message).Object); }); msgNo++; } } }
public void TestSendFragmentedPacket() { NullTransport t = new NullTransport(); t.MaximumPacketSize = 100; t.Reliability = Reliability.Reliable; t.Ordering = Ordering.Ordered; MockConnexion cnx = new MockConnexion(); cnx.Marshaller = new LargeObjectMarshaller(new DotNetSerializingMarshaller()); cnx.Scheduler = new RoundRobinPacketScheduler(cnx); cnx.Transports.Add(t); cnx.ErrorEvents += delegate(ErrorSummary es) { Assert.Fail(es.ToString()); }; byte[] sentData = new byte[500]; for (int i = 0; i < 6; i++) { uint bytesSent = t.BytesSent; cnx.Scheduler.Schedule(new BinaryMessage(0, sentData), MessageDeliveryRequirements.MostStrict, null); Assert.IsTrue(cnx.SentPackets.Count > 0); Assert.IsTrue(t.BytesSent - bytesSent > 500); // should be 500 + message headers } int lastSentPacketsCount = cnx.SentPackets.Count; cnx.Flush(); Assert.IsTrue(cnx.SentPackets.Count == lastSentPacketsCount, "there should not be any data remaining"); int msgNo = 0; foreach (TransportPacket tp in cnx.SentPackets) { while (tp.Length > 0) { cnx.Marshaller.Unmarshal(tp, t, delegate(object sender, MessageEventArgs mea) { Assert.IsInstanceOfType(typeof(BinaryMessage), mea.Message); Assert.AreEqual(sentData, ((BinaryMessage)mea.Message).Bytes); msgNo++; }); } } Assert.AreEqual(6, msgNo); }
public void TestLeakyBucketTransport() { NullTransport nt = new NullTransport(); // drain at 128 bytes every 100 milliseconds, and buffer up to // 384 bytes (or 3 packets of 128 bytes) // (100ms may seem long, but it seems to help avoid possible // race conditions in the test such as where the AvailableCapacity // is is suddenly recalcd and available) LeakyBucketTransport lbt = new LeakyBucketTransport(nt, 128, TimeSpan.FromMilliseconds(100), 384); bool backlogged = false; lbt.ErrorEvent += delegate(ErrorSummary es) { if (es.ErrorCode == SummaryErrorCode.TransportBacklogged) { backlogged = true; } }; for(int i = 0; i < 5; i++) { Assert.IsFalse(backlogged); uint startBytesSent = nt.BytesSent; Assert.AreEqual(128, lbt.AvailableCapacity); Assert.AreEqual(384, lbt.RemainingBucketCapacity); Assert.IsFalse(backlogged); lbt.SendPacket(new TransportPacket(new byte[128])); // should send Assert.AreEqual(0, lbt.AvailableCapacity); Assert.AreEqual(384, lbt.RemainingBucketCapacity); Assert.IsFalse(backlogged); lbt.SendPacket(new TransportPacket(new byte[128])); // should be buffered Assert.AreEqual(0, lbt.AvailableCapacity); Assert.AreEqual(256, lbt.RemainingBucketCapacity); Assert.IsFalse(backlogged); lbt.SendPacket(new TransportPacket(new byte[128])); // should be buffered Assert.AreEqual(0, lbt.AvailableCapacity); Assert.AreEqual(128, lbt.RemainingBucketCapacity); Assert.IsFalse(backlogged); lbt.SendPacket(new TransportPacket(new byte[128])); // should be buffered Assert.AreEqual(0, lbt.AvailableCapacity); Assert.AreEqual(0, lbt.RemainingBucketCapacity); Assert.IsFalse(backlogged); lbt.SendPacket(new TransportPacket(new byte[128])); // should exceed bucket capacity Assert.IsTrue(backlogged); backlogged = false; Assert.AreEqual(128, nt.BytesSent - startBytesSent); // Drain the bucket do { Thread.Sleep(20); lbt.Update(); Assert.IsFalse(backlogged); } while (lbt.RemainingBucketCapacity < lbt.MaximumCapacity || lbt.AvailableCapacity != 128); } }
public void SetUp() { wrapped = new NullTransport(Reliability.Unreliable, Ordering.Unordered, 0, 1024); wrappedPacketsSent = 0; wrapped.PacketSent += delegate { wrappedPacketsSent++; }; transport = new NetworkEmulatorTransport(wrapped); effects = new Bag<NetworkEmulatorTransport.PacketEffect>(); transport.PacketDisposition += (mode, effect, packet) => effects.Add(effect); }
public void TestTokenBucketTransport() { NullTransport nt = new NullTransport(); TokenBucketTransport tbt = new TokenBucketTransport(nt, 512, 1024); bool backlogged = false; tbt.ErrorEvent += delegate(ErrorSummary es) { if (es.ErrorCode == SummaryErrorCode.TransportBacklogged) { backlogged = true; } }; Assert.IsTrue(tbt.AvailableCapacity == 1024, "starting capacity is the maximum capacity"); for (int i = 0; i < 5; i++) { uint startBytesSent = nt.BytesSent; Assert.IsFalse(backlogged); Assert.IsTrue(tbt.AvailableCapacity >= tbt.MaximumCapacity); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); Assert.AreEqual(1024, nt.BytesSent - startBytesSent); // this packet will not be sent though tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsTrue(backlogged); backlogged = false; Assert.AreEqual(1024, nt.BytesSent - startBytesSent); // Build up some capacity while(tbt.AvailableCapacity < 128) { Thread.Sleep(200); tbt.Update(); } //Console.WriteLine("Test: slept {0}ms", timer.ElapsedMilliseconds); // plus the outstanding packet while (tbt.AvailableCapacity > 128) { Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsFalse(backlogged); } // we should now have little capacity again, so sending another packet will backlog Assert.IsTrue(tbt.AvailableCapacity < 128); // this packet will not be sent next though Assert.IsFalse(backlogged); tbt.SendPacket(new TransportPacket(new byte[128])); Assert.IsTrue(backlogged); backlogged = false; // Sleep until there is plenty of capacity do { Thread.Sleep(200); tbt.Update(); Assert.IsFalse(backlogged); } while (tbt.AvailableCapacity < tbt.MaximumCapacity); } }