Author: toad
Date: 2006-08-12 20:55:25 +0000 (Sat, 12 Aug 2006)
New Revision: 10050

Modified:
   trunk/freenet/src/freenet/node/NodeClientCore.java
   trunk/freenet/src/freenet/node/RequestStarterGroup.java
   trunk/freenet/src/freenet/node/ThrottleWindowManager.java
   trunk/freenet/src/freenet/support/SimpleFieldSet.java
   
trunk/freenet/src/freenet/support/math/BootstrappingDecayingRunningAverage.java
Log:
write load limiting data to disk every minute

Modified: trunk/freenet/src/freenet/node/NodeClientCore.java
===================================================================
--- trunk/freenet/src/freenet/node/NodeClientCore.java  2006-08-12 19:54:58 UTC 
(rev 10049)
+++ trunk/freenet/src/freenet/node/NodeClientCore.java  2006-08-12 20:55:25 UTC 
(rev 10050)
@@ -186,6 +186,9 @@


        public void start(Config config) throws NodeInitException {
+               
+               requestStarters.start();
+               
                // TMCI
                try{
                        TextModeClientInterfaceServer.maybeCreate(node, config);

Modified: trunk/freenet/src/freenet/node/RequestStarterGroup.java
===================================================================
--- trunk/freenet/src/freenet/node/RequestStarterGroup.java     2006-08-12 
19:54:58 UTC (rev 10049)
+++ trunk/freenet/src/freenet/node/RequestStarterGroup.java     2006-08-12 
20:55:25 UTC (rev 10050)
@@ -1,10 +1,19 @@
 package freenet.node;

+import java.io.BufferedOutputStream;
+import java.io.File;
+import java.io.FileNotFoundException;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.OutputStreamWriter;
+import java.io.UnsupportedEncodingException;
+
 import freenet.client.async.ClientRequestScheduler;
 import freenet.config.Config;
 import freenet.config.SubConfig;
 import freenet.crypt.RandomSource;
 import freenet.support.Logger;
+import freenet.support.SimpleFieldSet;
 import freenet.support.math.BootstrappingDecayingRunningAverage;

 public class RequestStarterGroup {
@@ -18,6 +27,7 @@
        final RequestStarter sskRequestStarter;
        final MyRequestThrottle sskInsertThrottle;
        final RequestStarter sskInsertStarter;
+       final File nodeDir;

        public final ClientRequestScheduler chkFetchScheduler;
        public final ClientRequestScheduler chkPutScheduler;
@@ -27,6 +37,8 @@
        RequestStarterGroup(Node node, NodeClientCore core, int portNumber, 
RandomSource random, Config config) {
                SubConfig schedulerConfig = new SubConfig("node.scheduler", 
config);

+               this.nodeDir = node.nodeDir;
+               
                throttleWindow = new ThrottleWindowManager(2.0);
                chkRequestThrottle = new MyRequestThrottle(throttleWindow, 
5000, "CHK Request");
                chkRequestStarter = new RequestStarter(core, 
chkRequestThrottle, "CHK Request starter ("+portNumber+")", 
node.requestOutputThrottle, node.requestInputThrottle, 
node.localChkFetchBytesSentAverage, node.localChkFetchBytesReceivedAverage);
@@ -55,7 +67,15 @@
                sskInsertStarter.start();

                schedulerConfig.finishedInitialization();
+               
        }
+
+       public void start() {
+               ThrottlePersister persister = new ThrottlePersister();
+               Thread t = new Thread(persister, "Throttle data persister 
thread");
+               t.setDaemon(true);
+               t.start();
+       }

        public class MyRequestThrottle implements BaseRequestThrottle {

@@ -87,6 +107,12 @@
                public String toString() {
                        return "rtt: "+roundTripTime.currentValue()+" 
_s="+throttleWindow.currentValue();
                }
+
+               public SimpleFieldSet exportFieldSet() {
+                       SimpleFieldSet fs = new SimpleFieldSet();
+                       fs.put("RoundTripTime", roundTripTime.exportFieldSet());
+                       return fs;
+               }
        }

        public BaseRequestThrottle getCHKRequestThrottle() {
@@ -105,5 +131,87 @@
                return sskInsertThrottle;
        }

+       // FIXME convert these kind of threads to Checkpointed's and implement 
a handler
+       // using the PacketSender/Ticker. Would save a few threads.

+       class ThrottlePersister implements Runnable {
+
+               public void run() {
+                       while(true) {
+                               try {
+                                       persistThrottle();
+                               } catch (Throwable t) {
+                                       Logger.error(this, "Caught "+t, t);
+                               }
+                               try {
+                                       Thread.sleep(60*1000);
+                               } catch (InterruptedException e) {
+                                       // Maybe it's time to wake up?
+                               }
+                       }
+               }
+               
+       }
+
+       public void persistThrottle() {
+               SimpleFieldSet fs = persistToFieldSet();
+               File target = new File(nodeDir, "throttle.dat");
+               File tmp = new File(nodeDir, "throttle.dat.tmp");
+               try {
+                       FileOutputStream fos = new FileOutputStream(tmp);
+                       // FIXME common pattern, reuse it.
+                       BufferedOutputStream bos = new 
BufferedOutputStream(fos);
+                       OutputStreamWriter osw = new OutputStreamWriter(bos, 
"UTF-8");
+                       try {
+                               fs.writeTo(osw);
+                       } catch (IOException e) {
+                               try {
+                                       fos.close();
+                                       tmp.delete();
+                                       return;
+                               } catch (IOException e1) {
+                                       // Ignore
+                               }
+                       }
+                       try {
+                               osw.close();
+                       } catch (IOException e) {
+                               // Huh?
+                               Logger.error(this, "Caught while closing: "+e, 
e);
+                               return;
+                       }
+                       // Try an atomic rename
+                       if(!tmp.renameTo(target)) {
+                               // Not supported on some systems (Windows)
+                               if(!target.delete()) {
+                                       if(target.exists()) {
+                                               Logger.error(this, "Could not 
delete "+target+" - check permissions");
+                                       }
+                               }
+                               if(!tmp.renameTo(target)) {
+                                       Logger.error(this, "Could not rename 
"+tmp+" to "+target+" - check permissions");
+                               }
+                       }
+               } catch (FileNotFoundException e) {
+                       Logger.error(this, "Could not store throttle data to 
disk: "+e, e);
+                       return;
+               } catch (UnsupportedEncodingException e) {
+                       Logger.error(this, "Unsupported encoding: UTF-8 !!!!: 
"+e, e);
+               }
+               
+       }
+
+       /**
+        * Persist the throttle data to a SimpleFieldSet.
+        */
+       private SimpleFieldSet persistToFieldSet() {
+               SimpleFieldSet fs = new SimpleFieldSet();
+               fs.put("ThrottleWindow", throttleWindow.exportFieldSet());
+               fs.put("CHKRequestThrottle", 
chkRequestThrottle.exportFieldSet());
+               fs.put("SSKRequestThrottle", 
sskRequestThrottle.exportFieldSet());
+               fs.put("CHKInsertThrottle", chkInsertThrottle.exportFieldSet());
+               fs.put("SSKInsertThrottle", sskInsertThrottle.exportFieldSet());
+               return fs;
+       }
+       
 }

Modified: trunk/freenet/src/freenet/node/ThrottleWindowManager.java
===================================================================
--- trunk/freenet/src/freenet/node/ThrottleWindowManager.java   2006-08-12 
19:54:58 UTC (rev 10049)
+++ trunk/freenet/src/freenet/node/ThrottleWindowManager.java   2006-08-12 
20:55:25 UTC (rev 10050)
@@ -1,6 +1,7 @@
 package freenet.node;

 import freenet.support.Logger;
+import freenet.support.SimpleFieldSet;

 public class ThrottleWindowManager {

@@ -39,4 +40,13 @@
                                + _simulatedWindowSize + ", d:"
                                + (((float) _droppedPackets / (float) 
_totalPackets)) + "="+_droppedPackets+"/"+_totalPackets;
        }
+
+       public SimpleFieldSet exportFieldSet() {
+               SimpleFieldSet fs = new SimpleFieldSet();
+               fs.put("Type", "ThrottleWindowManager");
+               fs.put("TotalPackets", _totalPackets);
+               fs.put("DroppedPackets", _droppedPackets);
+               fs.put("SimulatedWindowSize", _simulatedWindowSize);
+               return fs;
+       }
 }

Modified: trunk/freenet/src/freenet/support/SimpleFieldSet.java
===================================================================
--- trunk/freenet/src/freenet/support/SimpleFieldSet.java       2006-08-12 
19:54:58 UTC (rev 10049)
+++ trunk/freenet/src/freenet/support/SimpleFieldSet.java       2006-08-12 
20:55:25 UTC (rev 10050)
@@ -208,6 +208,10 @@
                put(key, Boolean.toString(b));
        }

+       public void put(String key, double windowSize) {
+               put(key, Double.toString(windowSize));
+       }
+
     /**
      * Write the contents of the SimpleFieldSet to a Writer.
      * @param osr

Modified: 
trunk/freenet/src/freenet/support/math/BootstrappingDecayingRunningAverage.java
===================================================================
--- 
trunk/freenet/src/freenet/support/math/BootstrappingDecayingRunningAverage.java 
    2006-08-12 19:54:58 UTC (rev 10049)
+++ 
trunk/freenet/src/freenet/support/math/BootstrappingDecayingRunningAverage.java 
    2006-08-12 20:55:25 UTC (rev 10050)
@@ -5,6 +5,7 @@
 import java.io.IOException;

 import freenet.support.Logger;
+import freenet.support.SimpleFieldSet;


 /**
@@ -140,4 +141,14 @@
     public synchronized  long countReports() {
         return reports;
     }
+
+       public SimpleFieldSet exportFieldSet() {
+               SimpleFieldSet fs = new SimpleFieldSet();
+               fs.put("Type", "BootstrappingDecayingRunningAverage");
+               fs.put("CurrentValue", currentValue);
+               fs.put("Reports", reports);
+               fs.put("Zeros", zeros);
+               fs.put("Ones", ones);
+               return fs;
+       }
 }


Reply via email to