Author: toad
Date: 2008-03-19 22:33:13 +0000 (Wed, 19 Mar 2008)
New Revision: 18634
Modified:
trunk/freenet/src/freenet/node/CHKInsertHandler.java
trunk/freenet/src/freenet/node/PeerNode.java
trunk/freenet/src/freenet/node/RequestSender.java
Log:
Separate backoff code for transfer failures.
Modified: trunk/freenet/src/freenet/node/CHKInsertHandler.java
===================================================================
--- trunk/freenet/src/freenet/node/CHKInsertHandler.java 2008-03-19
21:22:03 UTC (rev 18633)
+++ trunk/freenet/src/freenet/node/CHKInsertHandler.java 2008-03-19
22:33:13 UTC (rev 18634)
@@ -403,6 +403,7 @@
freenet.support.Logger.OSThread.logPID(this);
if(logMINOR) Logger.minor(this, "Receiving data for
"+CHKInsertHandler.this);
try {
+ // Don't log whether the transfer succeeded or failed as the
transfer was initiated by the source therefore could be unreliable evidence.
br.receive();
if(logMINOR) Logger.minor(this, "Received data for
"+CHKInsertHandler.this);
synchronized(CHKInsertHandler.this) {
Modified: trunk/freenet/src/freenet/node/PeerNode.java
===================================================================
--- trunk/freenet/src/freenet/node/PeerNode.java 2008-03-19 21:22:03 UTC
(rev 18633)
+++ trunk/freenet/src/freenet/node/PeerNode.java 2008-03-19 22:33:13 UTC
(rev 18634)
@@ -2472,7 +2472,7 @@
fs.putSingle("peerAddedTime",
Long.toString(peerAddedTime));
fs.putSingle("lastRoutingBackoffReason",
lastRoutingBackoffReason);
fs.putSingle("routingBackoffPercent",
Double.toString(backedOffPercent.currentValue() * 100));
- fs.putSingle("routingBackoff",
Long.toString((Math.max(routingBackedOffUntil - now, 0))));
+ fs.putSingle("routingBackoff",
Long.toString((Math.max(Math.max(routingBackedOffUntil, transferBackedOffUntil)
- now, 0))));
fs.putSingle("routingBackoffLength",
Integer.toString(routingBackoffLength));
fs.putSingle("overloadProbability",
Double.toString(getPRejected() * 100));
fs.putSingle("percentTimeRoutableConnection",
Double.toString(getPercentTimeRoutableConnection() * 100));
@@ -2581,7 +2581,7 @@
public boolean isRoutingBackedOff() {
long now = System.currentTimeMillis();
synchronized(this) {
- return now < routingBackedOffUntil;
+ return now < routingBackedOffUntil || now <
transferBackedOffUntil;
}
}
long routingBackedOffUntil = -1;
@@ -2593,6 +2593,15 @@
/** Maximum upper limit to routing backoff slow or fast */
static final int MAX_ROUTING_BACKOFF_LENGTH = 3 * 60 * 60 * 1000; // 3
hours
/** Current nominal routing backoff length */
+
+ // Transfer Backoff
+
+ long transferBackedOffUntil = -1;
+ static final int INITIAL_TRANSFER_BACKOFF_LENGTH = 30*1000; // 60
seconds, but it starts at twice this.
+ static final int TRANSFER_BACKOFF_MULTIPLIER = 2;
+ static final int MAX_TRANSFER_BACKOFF_LENGTH = 3 * 60 * 60 * 1000; // 3
hours
+
+ int transferBackoffLength = INITIAL_TRANSFER_BACKOFF_LENGTH;
int routingBackoffLength = INITIAL_ROUTING_BACKOFF_LENGTH;
/** Last backoff reason */
@@ -2603,7 +2612,7 @@
public final RunningAverage backedOffPercent;
/* time of last sample */
private long lastSampleTime = Long.MAX_VALUE;
-
+
/**
* Got a local RejectedOverload.
* Back off this node for a while.
@@ -2693,6 +2702,69 @@
}
setPeerNodeStatus(now);
}
+
+ /**
+ * Got a local RejectedOverload.
+ * Back off this node for a while.
+ */
+ public void transferFailed(String reason) {
+ pRejected.report(1.0);
+ if(logMINOR)
+ Logger.minor(this, "Transfer failed (" + reason + ") on
" + this + " : pRejected=" + pRejected.currentValue());
+ long now = System.currentTimeMillis();
+ Peer peer = getPeer();
+ reportBackoffStatus(now);
+ // We need it because of nested locking on getStatus()
+ synchronized(this) {
+ // Don't back off any further if we are already backed
off
+ if(now > transferBackedOffUntil) {
+ transferBackoffLength = transferBackoffLength *
TRANSFER_BACKOFF_MULTIPLIER;
+ if(transferBackoffLength >
MAX_TRANSFER_BACKOFF_LENGTH)
+ transferBackoffLength =
MAX_TRANSFER_BACKOFF_LENGTH;
+ int x =
node.random.nextInt(transferBackoffLength);
+ transferBackedOffUntil = now + x;
+ String reasonWrapper = "";
+ if(0 <= reason.length())
+ reasonWrapper = " because of '" +
reason + '\'';
+ if(logMINOR)
+ Logger.minor(this, "Backing off
(transfer)" + reasonWrapper + ": transferBackoffLength=" +
transferBackoffLength + ", until " + x + "ms on " + peer);
+ } else {
+ if(logMINOR)
+ Logger.minor(this, "Ignoring transfer
failure: " + (transferBackedOffUntil - now) + "ms remaining on transfer backoff
on " + peer);
+ return;
+ }
+ setLastBackoffReason(reason);
+ }
+ setPeerNodeStatus(now);
+ }
+
+ /**
+ * Didn't get RejectedOverload.
+ * Reset routing backoff.
+ */
+ public void transferSuccess() {
+ pRejected.report(0.0);
+ if(logMINOR)
+ Logger.minor(this, "Transfer success on " + this + " :
pRejected=" + pRejected.currentValue());
+ Peer peer = getPeer();
+ long now = System.currentTimeMillis();
+ reportBackoffStatus(now);
+ synchronized(this) {
+ // Don't un-backoff if still backed off
+ if(now > transferBackedOffUntil) {
+ routingBackoffLength =
INITIAL_TRANSFER_BACKOFF_LENGTH;
+ if(logMINOR)
+ Logger.minor(this, "Resetting transfer
backoff on " + peer);
+ } else {
+ if(logMINOR)
+ Logger.minor(this, "Ignoring transfer
success: " + (transferBackedOffUntil - now) + "ms remaining on transfer backoff
on " + peer);
+ return;
+ }
+ }
+ setPeerNodeStatus(now);
+ }
+
+
Object pingSync = new Object();
// Relatively few as we only get one every 200ms*#nodes
// We want to get reasonably early feedback if it's dropping all of
them...
@@ -2733,7 +2805,7 @@
}
public synchronized long getRoutingBackedOffUntil() {
- return routingBackedOffUntil;
+ return Math.max(routingBackedOffUntil, transferBackedOffUntil);
}
public synchronized String getLastBackoffReason() {
Modified: trunk/freenet/src/freenet/node/RequestSender.java
===================================================================
--- trunk/freenet/src/freenet/node/RequestSender.java 2008-03-19 21:22:03 UTC
(rev 18633)
+++ trunk/freenet/src/freenet/node/RequestSender.java 2008-03-19 22:33:13 UTC
(rev 18634)
@@ -268,6 +268,7 @@
try {
if(logMINOR) Logger.minor(this,
"Receiving data");
byte[] data = br.receive();
+ pn.transferSuccess();
if(logMINOR) Logger.minor(this,
"Received data");
// Received data
try {
@@ -287,6 +288,7 @@
else
Logger.error(this, "Transfer for offer failed
("+e.getReason()+"/"+RetrievalException.getErrString(e.getReason())+"): "+e+"
from "+pn, e);
finish(GET_OFFER_TRANSFER_FAILED, pn,
true);
+
pn.transferFailed("RequestSenderGetOfferedTransferFailed");
offers.deleteLastOffer();
node.nodeStats.failedBlockReceive();
return;
@@ -764,6 +766,7 @@
try {
if(logMINOR) Logger.minor(this,
"Receiving data");
byte[] data = br.receive();
+ next.transferSuccess();
next.successNotOverload();
if(logMINOR) Logger.minor(this,
"Received data");
// Received data
@@ -785,6 +788,7 @@
next.localRejectedOverload("TransferFailedRequest"+e.getReason());
finish(TRANSFER_FAILED, next, false);
node.failureTable.onFinalFailure(key,
next, htl, FailureTable.REJECT_TIME, source);
+
next.transferFailed("RequestSenderTransferFailed");
return;
}
} finally {