Author: toad
Date: 2006-12-12 14:57:37 +0000 (Tue, 12 Dec 2006)
New Revision: 11356
Modified:
trunk/freenet/src/freenet/clients/http/DarknetConnectionsToadlet.java
trunk/freenet/src/freenet/clients/http/StatisticsToadlet.java
trunk/freenet/src/freenet/io/xfer/PacketThrottle.java
trunk/freenet/src/freenet/node/KeyTracker.java
trunk/freenet/src/freenet/node/PeerNode.java
trunk/freenet/src/freenet/node/PeerNodeStatus.java
trunk/freenet/src/freenet/node/RequestStarterGroup.java
Log:
More stats on load balancing (Statistics page) and congestion control (Darknet
page).
Modified: trunk/freenet/src/freenet/clients/http/DarknetConnectionsToadlet.java
===================================================================
--- trunk/freenet/src/freenet/clients/http/DarknetConnectionsToadlet.java
2006-12-12 13:14:23 UTC (rev 11355)
+++ trunk/freenet/src/freenet/clients/http/DarknetConnectionsToadlet.java
2006-12-12 14:57:37 UTC (rev 11356)
@@ -22,6 +22,7 @@
import freenet.io.comm.IOStatisticCollector;
import freenet.io.comm.PeerParseException;
import freenet.io.comm.ReferenceSignatureVerificationException;
+import freenet.io.xfer.PacketThrottle;
import freenet.node.FSParseException;
import freenet.node.Node;
import freenet.node.NodeClientCore;
@@ -382,6 +383,7 @@
if(advancedEnabled) {
peerTableHeaderRow.addChild("th",
"%\u00a0Time Routable");
peerTableHeaderRow.addChild("th",
"Total\u00a0Traffic\u00a0(in/out)");
+ peerTableHeaderRow.addChild("th",
"Congestion\u00a0Control");
}
for (int peerIndex = 0, peerCount =
peerNodeStatuses.length; peerIndex < peerCount; peerIndex++) {
@@ -464,6 +466,15 @@
peerRow.addChild("td", "class",
"peer-idle" /* FIXME */).addChild("#",
fix1.format(peerNodeStatus.getPercentTimeRoutableConnection()));
// total traffic column
peerRow.addChild("td", "class",
"peer-idle" /* FIXME */).addChild("#",
SizeUtil.formatSize(peerNodeStatus.getTotalInputBytes())+" /
"+SizeUtil.formatSize(peerNodeStatus.getTotalOutputBytes()));
+ // congestion control
+ PacketThrottle t =
peerNodeStatus.getThrottle();
+ String val;
+ if(t == null)
+ val = "none";
+ else
+ val = (int)((1000.0 /
t.getDelay()) * 1024.0)+"B/sec delay "+
+
t.getDelay()+"ms (RTT "+t.getRoundTripTime()+"ms window "+t.getWindowSize();
+ peerRow.addChild("td", "class",
"peer-idle" /* FIXME */).addChild("#", val);
}
if
(path.endsWith("displaymessagetypes.html")) {
Modified: trunk/freenet/src/freenet/clients/http/StatisticsToadlet.java
===================================================================
--- trunk/freenet/src/freenet/clients/http/StatisticsToadlet.java
2006-12-12 13:14:23 UTC (rev 11355)
+++ trunk/freenet/src/freenet/clients/http/StatisticsToadlet.java
2006-12-12 14:57:37 UTC (rev 11356)
@@ -259,8 +259,24 @@
peerStatsListenOnlyListItem.addChild("span",
":\u00a0" + numberOfListenOnly);
}
- // Peer routing backoff reason box
if(advancedEnabled) {
+
+ // Load balancing box
+ // Include overall window, and RTTs for each
+ RequestStarterGroup starters =
core.requestStarters;
+ double window = starters.getWindow();
+ HTMLNode loadStatsInfobox =
nextTableCell.addChild("div", "class", "infobox");
+ loadStatsInfobox.addChild("div", "class",
"infobox-header", "Load limiting");
+ HTMLNode loadStatsContent =
loadStatsInfobox.addChild("div", "class", "infobox-content");
+ HTMLNode loadStatsList =
loadStatsContent.addChild("ul");
+ loadStatsList.addChild("ul", "Global window:
"+window);
+ loadStatsList.addChild("ul",
starters.statsPageLine(false, false));
+ loadStatsList.addChild("ul",
starters.statsPageLine(true, false));
+ loadStatsList.addChild("ul",
starters.statsPageLine(false, true));
+ loadStatsList.addChild("ul",
starters.statsPageLine(true, true));
+ nextTableCell = overviewTableRow.addChild("td");
+
+ // Peer routing backoff reason box
nextTableCell = overviewTableRow.addChild("td",
"class", "last");
HTMLNode backoffReasonInfobox =
nextTableCell.addChild("div", "class", "infobox");
backoffReasonInfobox.addChild("div", "class",
"infobox-header", "Peer backoff reasons");
@@ -277,10 +293,8 @@
}
}
}
- }
- //Swap statistics box
- if(advancedEnabled) {
+ //Swap statistics box
overviewTableRow = overviewTable.addChild("tr");
nextTableCell = overviewTableRow.addChild("td",
"class", "first");
int startedSwaps = node.getStartedSwaps();
@@ -336,10 +350,8 @@
locationSwapList.addChild("li",
"swapsRejectedRecognizedID:\u00a0" + swapsRejectedRecognizedID);
}
nextTableCell = overviewTableRow.addChild("td");
- }
- // Bandwidth box
- if (advancedEnabled) {
+ // Bandwidth box
HTMLNode bandwidthInfobox =
nextTableCell.addChild("div", "class", "infobox");
bandwidthInfobox.addChild("div", "class",
"infobox-header", "Bandwidth");
HTMLNode bandwidthInfoboxContent =
bandwidthInfobox.addChild("div", "class", "infobox-content");
@@ -366,10 +378,8 @@
bandwidthList.addChild("li", "Output
Rate:\u00a0" + SizeUtil.formatSize(output_rate, true) + "ps
(of\u00a0"+SizeUtil.formatSize(outputBandwidthLimit, true)+"ps)");
bandwidthList.addChild("li", "Input
Rate:\u00a0" + SizeUtil.formatSize(input_rate, true) + "ps
(of\u00a0"+SizeUtil.formatSize(inputBandwidthLimit, true)+"ps)");
nextTableCell = overviewTableRow.addChild("td");
- }
- // store size box
- if (advancedEnabled) {
+ // store size box
HTMLNode storeSizeInfobox = nextTableCell.addChild("div",
"class", "infobox");
storeSizeInfobox.addChild("div", "class", "infobox-header",
"Store size");
HTMLNode storeSizeInfoboxContent =
storeSizeInfobox.addChild("div", "class", "infobox-content");
@@ -424,12 +434,10 @@
storeSizeList.addChild("li",
"Avg. access rate:\u00a0" +
thousendPoint.format(overallAccesses/nodeUptimeSeconds) + "/s");
- }
- nextTableCell = advancedEnabled ? overviewTableRow.addChild("td")
: overviewTableRow.addChild("td", "class", "last");
+ nextTableCell = advancedEnabled ?
overviewTableRow.addChild("td") : overviewTableRow.addChild("td", "class",
"last");
- // jvm stats box
- if (advancedEnabled) {
+ // jvm stats box
HTMLNode jvmStatsInfobox = nextTableCell.addChild("div",
"class", "infobox");
jvmStatsInfobox.addChild("div", "class", "infobox-header",
"JVM info");
HTMLNode jvmStatsInfoboxContent =
jvmStatsInfobox.addChild("div", "class", "infobox-content");
@@ -451,10 +459,8 @@
jvmStatsList.addChild("li", "Maximum Java memory:\u00a0" +
SizeUtil.formatSize(maxJavaMem, true));
jvmStatsList.addChild("li", "Available CPUs:\u00a0" +
availableCpus);
jvmStatsList.addChild("li", "Running threads:\u00a0" +
thousendPoint.format(threadCount));
- }
- // unclaimedFIFOMessageCounts box
- if(advancedEnabled) {
+ // unclaimedFIFOMessageCounts box
overviewTableRow = overviewTable.addChild("tr");
nextTableCell = overviewTableRow.addChild("td",
"class", "first");
Map unclaimedFIFOMessageCountsMap =
node.getUSM().getUnclaimedFIFOMessageCounts();
@@ -487,10 +493,8 @@
}
unclaimedFIFOMessageCountsList.addChild("li",
"Unclaimed Messages Considered:\u00a0" + totalCount);
nextTableCell = overviewTableRow.addChild("td");
- }
- // node version information box
- if (advancedEnabled) {
+ // node version information box
HTMLNode versionInfobox = nextTableCell.addChild("div",
"class", "infobox");
versionInfobox.addChild("div", "class", "infobox-header",
"Node Version Information");
HTMLNode versionInfoboxContent =
versionInfobox.addChild("div", "class", "infobox-content");
@@ -501,7 +505,7 @@
} else {
versionInfoboxContent.addChild("#",
"Freenet-ext Build #" + NodeStarter.extBuildNumber + " r" +
NodeStarter.extRevisionNumber);
}
- }
+ }
}
this.writeReply(ctx, 200, "text/html", "OK",
pageNode.generate());
Modified: trunk/freenet/src/freenet/io/xfer/PacketThrottle.java
===================================================================
--- trunk/freenet/src/freenet/io/xfer/PacketThrottle.java 2006-12-12
13:14:23 UTC (rev 11355)
+++ trunk/freenet/src/freenet/io/xfer/PacketThrottle.java 2006-12-12
14:57:37 UTC (rev 11356)
@@ -116,4 +116,12 @@
lastScheduledDelay += getDelay();
return lastScheduledDelay;
}
+
+ public long getRoundTripTime() {
+ return _roundTripTime;
+ }
+
+ public double getWindowSize() {
+ return _simulatedWindowSize;
+ }
}
Modified: trunk/freenet/src/freenet/node/KeyTracker.java
===================================================================
--- trunk/freenet/src/freenet/node/KeyTracker.java 2006-12-12 13:14:23 UTC
(rev 11355)
+++ trunk/freenet/src/freenet/node/KeyTracker.java 2006-12-12 14:57:37 UTC
(rev 11356)
@@ -519,7 +519,7 @@
Logger.minor(this, "Executed "+cbCount+" callbacks");
}
- private PacketThrottle getThrottle() {
+ PacketThrottle getThrottle() {
// pn.getPeer() cannot be null as it has already connected.
return PacketThrottle.getThrottle(pn.getPeer(), Node.PACKET_SIZE);
}
Modified: trunk/freenet/src/freenet/node/PeerNode.java
===================================================================
--- trunk/freenet/src/freenet/node/PeerNode.java 2006-12-12 13:14:23 UTC
(rev 11355)
+++ trunk/freenet/src/freenet/node/PeerNode.java 2006-12-12 14:57:37 UTC
(rev 11356)
@@ -47,6 +47,7 @@
import freenet.io.comm.PeerContext;
import freenet.io.comm.PeerParseException;
import freenet.io.comm.ReferenceSignatureVerificationException;
+import freenet.io.xfer.PacketThrottle;
import freenet.keys.ClientSSK;
import freenet.keys.FreenetURI;
import freenet.keys.USK;
@@ -3054,4 +3055,14 @@
public int getVersionNumber() {
return Version.getArbitraryBuildNumber(getVersion());
}
+
+ public PacketThrottle getThrottle() {
+ if(currentTracker != null)
+ return currentTracker.getThrottle();
+ if(unverifiedTracker != null)
+ return unverifiedTracker.getThrottle();
+ if(previousTracker != null)
+ return previousTracker.getThrottle();
+ return null;
+ }
}
Modified: trunk/freenet/src/freenet/node/PeerNodeStatus.java
===================================================================
--- trunk/freenet/src/freenet/node/PeerNodeStatus.java 2006-12-12 13:14:23 UTC
(rev 11355)
+++ trunk/freenet/src/freenet/node/PeerNodeStatus.java 2006-12-12 14:57:37 UTC
(rev 11356)
@@ -8,6 +8,7 @@
import freenet.clients.http.DarknetConnectionsToadlet;
import freenet.io.comm.Peer;
+import freenet.io.xfer.PacketThrottle;
/**
* Contains various status information for a {@link PeerNode}. Used e.g. in
@@ -84,6 +85,8 @@
private long totalBytesOut;
private double percentTimeRoutableConnection;
+
+ private PacketThrottle throttle;
public PeerNodeStatus(PeerNode peerNode) {
this.name = peerNode.getName();
@@ -125,6 +128,7 @@
this.totalBytesIn = peerNode.getTotalInputBytes();
this.totalBytesOut = peerNode.getTotalOutputBytes();
this.percentTimeRoutableConnection =
peerNode.getPercentTimeRoutableConnection();
+ this.throttle = peerNode.getThrottle();
}
/**
@@ -363,4 +367,8 @@
public double getPercentTimeRoutableConnection() {
return percentTimeRoutableConnection;
}
+
+ public PacketThrottle getThrottle() {
+ return throttle;
+ }
}
Modified: trunk/freenet/src/freenet/node/RequestStarterGroup.java
===================================================================
--- trunk/freenet/src/freenet/node/RequestStarterGroup.java 2006-12-12
13:14:23 UTC (rev 11355)
+++ trunk/freenet/src/freenet/node/RequestStarterGroup.java 2006-12-12
14:57:37 UTC (rev 11356)
@@ -9,6 +9,7 @@
import freenet.crypt.RandomSource;
import freenet.support.Logger;
import freenet.support.SimpleFieldSet;
+import freenet.support.TimeUtil;
import freenet.support.math.BootstrappingDecayingRunningAverage;
public class RequestStarterGroup {
@@ -32,27 +33,27 @@
SubConfig schedulerConfig = new SubConfig("node.scheduler",
config);
throttleWindow = new ThrottleWindowManager(2.0, fs == null ?
null : fs.subset("ThrottleWindow"));
- chkRequestThrottle = new MyRequestThrottle(throttleWindow,
5000, "CHK Request", fs == null ? null : fs.subset("CHKRequestThrottle"));
+ chkRequestThrottle = new MyRequestThrottle(throttleWindow,
5000, "CHK Request", fs == null ? null : fs.subset("CHKRequestThrottle"),
32768);
chkRequestStarter = new RequestStarter(core,
chkRequestThrottle, "CHK Request starter ("+portNumber+ ')',
node.requestOutputThrottle, node.requestInputThrottle,
node.localChkFetchBytesSentAverage, node.localChkFetchBytesReceivedAverage,
false);
chkFetchScheduler = new ClientRequestScheduler(false, false,
random, chkRequestStarter, node, schedulerConfig, "CHKrequester");
chkRequestStarter.setScheduler(chkFetchScheduler);
chkRequestStarter.start();
//insertThrottle = new ChainedRequestThrottle(10000, 2.0F,
requestThrottle);
// FIXME reenable the above
- chkInsertThrottle = new MyRequestThrottle(throttleWindow,
20000, "CHK Insert", fs == null ? null : fs.subset("CHKInsertThrottle"));
+ chkInsertThrottle = new MyRequestThrottle(throttleWindow,
20000, "CHK Insert", fs == null ? null : fs.subset("CHKInsertThrottle"), 32768);
chkInsertStarter = new RequestStarter(core, chkInsertThrottle,
"CHK Insert starter ("+portNumber+ ')', node.requestOutputThrottle,
node.requestInputThrottle, node.localChkInsertBytesSentAverage,
node.localChkInsertBytesReceivedAverage, true);
chkPutScheduler = new ClientRequestScheduler(true, false,
random, chkInsertStarter, node, schedulerConfig, "CHKinserter");
chkInsertStarter.setScheduler(chkPutScheduler);
chkInsertStarter.start();
- sskRequestThrottle = new MyRequestThrottle(throttleWindow,
5000, "SSK Request", fs == null ? null : fs.subset("SSKRequestThrottle"));
+ sskRequestThrottle = new MyRequestThrottle(throttleWindow,
5000, "SSK Request", fs == null ? null : fs.subset("SSKRequestThrottle"), 1024);
sskRequestStarter = new RequestStarter(core,
sskRequestThrottle, "SSK Request starter ("+portNumber+ ')',
node.requestOutputThrottle, node.requestInputThrottle,
node.localSskFetchBytesSentAverage, node.localSskFetchBytesReceivedAverage,
false);
sskFetchScheduler = new ClientRequestScheduler(false, true,
random, sskRequestStarter, node, schedulerConfig, "SSKrequester");
sskRequestStarter.setScheduler(sskFetchScheduler);
sskRequestStarter.start();
//insertThrottle = new ChainedRequestThrottle(10000, 2.0F,
requestThrottle);
// FIXME reenable the above
- sskInsertThrottle = new MyRequestThrottle(throttleWindow,
20000, "SSK Insert", fs == null ? null : fs.subset("SSKInsertThrottle"));
+ sskInsertThrottle = new MyRequestThrottle(throttleWindow,
20000, "SSK Insert", fs == null ? null : fs.subset("SSKInsertThrottle"), 1024);
sskInsertStarter = new RequestStarter(core, sskInsertThrottle,
"SSK Insert starter ("+portNumber+ ')', node.requestOutputThrottle,
node.requestInputThrottle, node.localSskInsertBytesSentAverage,
node.localSskFetchBytesReceivedAverage, true);
sskPutScheduler = new ClientRequestScheduler(true, true,
random, sskInsertStarter, node, schedulerConfig, "SSKinserter");
sskInsertStarter.setScheduler(sskPutScheduler);
@@ -64,10 +65,13 @@
public class MyRequestThrottle implements BaseRequestThrottle {
- private final BootstrappingDecayingRunningAverage
roundTripTime;
+ private final BootstrappingDecayingRunningAverage roundTripTime;
+ /** Data size for purposes of getRate() */
+ private final int size;
- public MyRequestThrottle(ThrottleWindowManager throttleWindow,
int rtt, String string, SimpleFieldSet fs) {
+ public MyRequestThrottle(ThrottleWindowManager throttleWindow,
int rtt, String string, SimpleFieldSet fs, int size) {
roundTripTime = new
BootstrappingDecayingRunningAverage(rtt, 10, 5*60*1000, 10, fs == null ? null :
fs.subset("RoundTripTime"));
+ this.size = size;
}
public synchronized long getDelay() {
@@ -99,6 +103,14 @@
fs.put("RoundTripTime", roundTripTime.exportFieldSet());
return fs;
}
+
+ public double getRTT() {
+ return roundTripTime.currentValue();
+ }
+
+ public long getRate() {
+ return (long) ((1000.0 / getDelay()) * size);
+ }
}
public BaseRequestThrottle getCHKRequestThrottle() {
@@ -130,4 +142,42 @@
return fs;
}
+ public double getWindow() {
+ return throttleWindow.currentValue();
+ }
+
+ public double getRTT(boolean isSSK, boolean isInsert) {
+ return getThrottle(isSSK, isInsert).getRTT();
+ }
+
+ public double getDelay(boolean isSSK, boolean isInsert) {
+ return getThrottle(isSSK, isInsert).getDelay();
+ }
+
+ MyRequestThrottle getThrottle(boolean isSSK, boolean isInsert) {
+ if(isSSK) {
+ if(isInsert) return sskInsertThrottle;
+ else return sskRequestThrottle;
+ } else {
+ if(isInsert) return chkInsertThrottle;
+ else return chkRequestThrottle;
+ }
+ }
+
+ public String statsPageLine(boolean isSSK, boolean isInsert) {
+ StringBuffer sb = new StringBuffer(100);
+ sb.append(isSSK ? "SSK" : "CHK");
+ sb.append(' ');
+ sb.append(isInsert ? "Insert" : "Request");
+ sb.append(' ');
+ MyRequestThrottle throttle = getThrottle(isSSK, isInsert);
+ sb.append(TimeUtil.formatTime((long)throttle.getRTT(), 2,
true));
+ sb.append(" RTT ");
+ sb.append(TimeUtil.formatTime((long)throttle.getDelay(), 2,
true));
+ sb.append(" delay = ");
+ sb.append((long)throttle.getRate());
+ sb.append("B/sec");
+ return sb.toString();
+ }
+
}