Author: toad
Date: 2006-08-15 18:42:21 +0000 (Tue, 15 Aug 2006)
New Revision: 10094

Modified:
   trunk/freenet/src/freenet/io/xfer/BlockTransmitter.java
   trunk/freenet/src/freenet/io/xfer/PacketThrottle.java
Log:
Schedule all transfers for a peer collectively.
Throttles start in TCP-like "slow start" mode, which rapidly increases 
bandwidth until a packet is lost.
NEEDS TESTING!

Modified: trunk/freenet/src/freenet/io/xfer/BlockTransmitter.java
===================================================================
--- trunk/freenet/src/freenet/io/xfer/BlockTransmitter.java     2006-08-15 
18:39:59 UTC (rev 10093)
+++ trunk/freenet/src/freenet/io/xfer/BlockTransmitter.java     2006-08-15 
18:42:21 UTC (rev 10094)
@@ -143,11 +143,11 @@
                        /** @return True if _sendComplete */
                        private void delay(long startCycleTime) {

-                               // Get the current inter-packet delay
-                               long delay = throttle.getDelay();
-                               Logger.minor(this, "Throttle delay: "+delay);
-                               
                                long startThrottle = System.currentTimeMillis();
+
+                               // Get the current inter-packet delay
+                               long end = 
throttle.scheduleDelay(startThrottle);
+
                                _masterThrottle.blockingGrab(PACKET_SIZE);

                                long now = System.currentTimeMillis();
@@ -156,8 +156,6 @@

                                
((PeerNode)_destination).reportThrottledPacketSendTime(delayTime);

-                               long end = startCycleTime + delay;
-                               
                                if(now > end) return;
                                while(now < end) {
                                        now = System.currentTimeMillis();

Modified: trunk/freenet/src/freenet/io/xfer/PacketThrottle.java
===================================================================
--- trunk/freenet/src/freenet/io/xfer/PacketThrottle.java       2006-08-15 
18:39:59 UTC (rev 10093)
+++ trunk/freenet/src/freenet/io/xfer/PacketThrottle.java       2006-08-15 
18:42:21 UTC (rev 10094)
@@ -26,8 +26,9 @@

 public class PacketThrottle {

-       protected static final float PACKET_DROP_DECREASE_MULTIPLE = 0.875f;
-       protected static final float PACKET_TRANSMIT_INCREMENT = (4 * (1 - 
(PACKET_DROP_DECREASE_MULTIPLE * PACKET_DROP_DECREASE_MULTIPLE))) / 3;
+       protected static final double PACKET_DROP_DECREASE_MULTIPLE = 0.875;
+       protected static final double PACKET_TRANSMIT_INCREMENT = (4 * (1 - 
(PACKET_DROP_DECREASE_MULTIPLE * PACKET_DROP_DECREASE_MULTIPLE))) / 3;
+       protected static final double SLOW_START_DIVISOR = 3.0;
        protected static final long MAX_DELAY = 1000;
        protected static final long MIN_DELAY = 25;
        public static final String VERSION = "$Id: PacketThrottle.java,v 1.3 
2005/08/25 17:28:19 amphibian Exp $";
@@ -37,6 +38,9 @@
        private long _roundTripTime = 500, _totalPackets, _droppedPackets;
        private float _simulatedWindowSize = 2;
        private final int PACKET_SIZE;
+       /** Last return of scheduleDelay(); time before which no packet may be 
sent */
+       private long lastScheduledDelay;
+       private boolean slowStart = true;

        /**
         * Create a PacketThrottle for a given peer.
@@ -67,12 +71,17 @@
                _droppedPackets++;
                _totalPackets++;
                _simulatedWindowSize *= PACKET_DROP_DECREASE_MULTIPLE;
+               slowStart = false;
        Logger.minor(this, "notifyOfPacketLost(): "+this);
     }

     public synchronized void notifyOfPacketAcknowledged() {
         _totalPackets++;
-        _simulatedWindowSize += (PACKET_TRANSMIT_INCREMENT / 
_simulatedWindowSize);
+       if(slowStart) {
+               _simulatedWindowSize += _simulatedWindowSize / 
SLOW_START_DIVISOR;
+       } else {
+               _simulatedWindowSize += (PACKET_TRANSMIT_INCREMENT / 
_simulatedWindowSize);
+       }
        Logger.minor(this, "notifyOfPacketAcked(): "+this);
     }

@@ -93,4 +102,16 @@
                                + _simulatedWindowSize + ", r:" + 
_roundTripTime + ", d:"
                                + (((float) _droppedPackets / (float) 
_totalPackets)) + ") for "+_peer;
        }
+
+       /**
+        * Schedule a delay. This method implements the global congestion 
window for a given
+        * peer.
+        * @param now The current time, in millis.
+        * @return The time, in millis, after which a packet may be sent.
+        */
+       public synchronized long scheduleDelay(long now) {
+               if(now > lastScheduledDelay) lastScheduledDelay = now;
+               lastScheduledDelay += getDelay();
+               return lastScheduledDelay;
+       }
 }


Reply via email to