diff --git a/apps/i2ptunnel/java/src/net/i2p/i2ptunnel/I2PTunnelHTTPClient.java b/apps/i2ptunnel/java/src/net/i2p/i2ptunnel/I2PTunnelHTTPClient.java index 594e37096..bee288e53 100644 --- a/apps/i2ptunnel/java/src/net/i2p/i2ptunnel/I2PTunnelHTTPClient.java +++ b/apps/i2ptunnel/java/src/net/i2p/i2ptunnel/I2PTunnelHTTPClient.java @@ -649,7 +649,7 @@ public class I2PTunnelHTTPClient extends I2PTunnelClientBase implements Runnable "http://i2host.i2p/cgi-bin/i2hostjump?", // "http://orion.i2p/jump/", "http://stats.i2p/cgi-bin/jump.cgi?a=", - "http://trevorreznik.i2p/cgi-bin/jump.php?hostname=", + // "http://trevorreznik.i2p/cgi-bin/jump.php?hostname=", "http://i2jump.i2p/" }; private static void writeErrorMessage(byte[] errMessage, OutputStream out, String targetRequest, diff --git a/history.txt b/history.txt index 4359d9b3b..d2fa66902 100644 --- a/history.txt +++ b/history.txt @@ -1,3 +1,16 @@ +2008-05-20 zzz + * Reachability: + - Call the previously unused profile.tunnelTestFailed() + (redefined to include a probability argument) + and severely downgrade a peer's capacity upon failures, + depending on tunnel length and direction. + This will help push unreachable and malicious peers + out of the High Capacity tier. + - Put recent fail rate on profiles.jsp + * ProfileOrganizer: Logging cleanup + * eepsite_index.html: Update add-host and jump links + * HTTP Proxy: Remove trevorreznik jump server from list + 2008-05-20 welterde * implemented PrivateKeyFile diff --git a/installer/resources/eepsite_index.html b/installer/resources/eepsite_index.html index 57241a406..2fe80c8c1 100644 --- a/installer/resources/eepsite_index.html +++ b/installer/resources/eepsite_index.html @@ -55,9 +55,7 @@ such as stats.i2p. That is, you must enter your eepsite name and key into a web interface on one or more of these sites. - Here is the key entry form at stats.i2p, - and - here is the key entry form at trevorreznik.i2p. + Here is the key entry form at stats.i2p. Again, your key is the entire "Local destination" key on the eepsite i2ptunnel configuration page. Be sure you get the whole thing, ending with "AAAA". @@ -70,14 +68,15 @@ and add a couple of these - http://tino.i2p/hosts.txt, http://stats.i2p/cgi-bin/newhosts.txt, - http://i2jump.i2p/hosts.txt, - http://trevorreznik.i2p/hosts.txt and hit "Save". + http://i2host.i2p/cgi-bin/i2hostetag, + and hit "Save". Now you will get updates too!
  • If you are in a hurry and can't wait a few hours, you can tell people to use a "jump" address helper redirection service. - This will work within a few minutes of your entering the key to an address book. + This will work within a few minutes of your entering the key to an address book on the same site. Test it yourself first by entering http://stats.i2p/cgi-bin/jump.cgi?a=something.i2p or - or http://trevorreznik.i2p/cgi-bin/jump.php?hostname=something.i2p into your browser. + or http://i2host.i2p/cgi-bin/i2hostjump?something.i2p + into your browser. Once it's working, then you can tell others to use it.
  • Some people check eepsite lists such as inproxy.tino.i2p/status.php for new eepsites, so you may start getting diff --git a/router/java/src/net/i2p/router/ProfileManager.java b/router/java/src/net/i2p/router/ProfileManager.java index f49142184..20e3d95cb 100644 --- a/router/java/src/net/i2p/router/ProfileManager.java +++ b/router/java/src/net/i2p/router/ProfileManager.java @@ -85,7 +85,7 @@ public interface ProfileManager { * been the peer's fault however. * */ - void tunnelFailed(Hash peer); + void tunnelFailed(Hash peer, int pct); /** * Note that the peer was able to return the valid data for a db lookup diff --git a/router/java/src/net/i2p/router/RouterVersion.java b/router/java/src/net/i2p/router/RouterVersion.java index 7099c1f5d..4c90a8a1b 100644 --- a/router/java/src/net/i2p/router/RouterVersion.java +++ b/router/java/src/net/i2p/router/RouterVersion.java @@ -17,7 +17,7 @@ import net.i2p.CoreVersion; public class RouterVersion { public final static String ID = "$Revision: 1.548 $ $Date: 2008-02-10 15:00:00 $"; public final static String VERSION = "0.6.1.33"; - public final static long BUILD = 6; + public final static long BUILD = 7; public static void main(String args[]) { System.out.println("I2P Router version: " + VERSION + "-" + BUILD); System.out.println("Router ID: " + RouterVersion.ID); diff --git a/router/java/src/net/i2p/router/peermanager/CapacityCalculator.java b/router/java/src/net/i2p/router/peermanager/CapacityCalculator.java index 6c576600e..be96a875d 100644 --- a/router/java/src/net/i2p/router/peermanager/CapacityCalculator.java +++ b/router/java/src/net/i2p/router/peermanager/CapacityCalculator.java @@ -103,8 +103,12 @@ public class CapacityCalculator extends Calculator { double stretch = ((double)ESTIMATE_PERIOD) / period; double val = eventCount * stretch; long failed = 0; + // Let's say a failure is 4 times worse than a rejection. + // It's actually much worse than that, but with 2-hop tunnels and a 8-peer + // fast pool, for example, you have a 1/7 chance of being falsely blamed. + // We also don't want to drive everybody's capacity to zero, that isn't helpful. if (curFailed != null) - failed = curFailed.getCurrentEventCount() + curFailed.getLastEventCount(); + failed = (long) (0.5 + (4.0 * (curFailed.getCurrentTotalValue() + curFailed.getLastTotalValue()) / 100.0)); if (failed > 0) { //if ( (period <= 10*60*1000) && (curFailed.getCurrentEventCount() > 0) ) // return 0.0d; // their tunnels have failed in the last 0-10 minutes diff --git a/router/java/src/net/i2p/router/peermanager/ProfileManagerImpl.java b/router/java/src/net/i2p/router/peermanager/ProfileManagerImpl.java index e82c96590..6cf63418d 100644 --- a/router/java/src/net/i2p/router/peermanager/ProfileManagerImpl.java +++ b/router/java/src/net/i2p/router/peermanager/ProfileManagerImpl.java @@ -150,13 +150,14 @@ public class ProfileManagerImpl implements ProfileManager { /** * Note that the peer participated in a tunnel that failed. Its failure may not have * been the peer's fault however. + * Blame the peer with a probability of pct/100. * */ - public void tunnelFailed(Hash peer) { + public void tunnelFailed(Hash peer, int pct) { PeerProfile data = getProfile(peer); if (data == null) return; data.setLastHeardFrom(_context.clock().now()); - data.getTunnelHistory().incrementFailed(); + data.getTunnelHistory().incrementFailed(pct); } /** diff --git a/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java b/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java index 4e0266da5..85e22bdd9 100644 --- a/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java +++ b/router/java/src/net/i2p/router/peermanager/ProfileOrganizer.java @@ -563,6 +563,7 @@ public class ProfileOrganizer { if (_log.shouldLog(Log.INFO)) _log.info("Profiles reorganized. averages: [integration: " + _thresholdIntegrationValue + ", capacity: " + _thresholdCapacityValue + ", speed: " + _thresholdSpeedValue + "]"); + /***** if (_log.shouldLog(Log.DEBUG)) { StringBuffer buf = new StringBuffer(512); for (Iterator iter = _strictCapacityOrder.iterator(); iter.hasNext(); ) { @@ -572,6 +573,7 @@ public class ProfileOrganizer { _log.debug("Strictly organized (highest capacity first): " + buf.toString()); _log.debug("fast: " + _fastPeers.values()); } + *****/ } long total = System.currentTimeMillis()-start; @@ -601,16 +603,18 @@ public class ProfileOrganizer { if ( (!_fastPeers.containsKey(cur.getPeer())) && (!cur.getIsFailing()) ) { if (!isSelectable(cur.getPeer())) { // skip peers we dont have in the netDb - if (_log.shouldLog(Log.INFO)) - _log.info("skip unknown peer from fast promotion: " + cur.getPeer().toBase64()); + // if (_log.shouldLog(Log.INFO)) + // _log.info("skip unknown peer from fast promotion: " + cur.getPeer().toBase64()); continue; } if (!cur.getIsActive()) { // skip inactive - if (_log.shouldLog(Log.INFO)) - _log.info("skip inactive peer from fast promotion: " + cur.getPeer().toBase64()); + // if (_log.shouldLog(Log.INFO)) + // _log.info("skip inactive peer from fast promotion: " + cur.getPeer().toBase64()); continue; } + if (_log.shouldLog(Log.INFO)) + _log.info("Fast promoting: " + cur.getPeer().toBase64()); _fastPeers.put(cur.getPeer(), cur); // no need to remove it from any of the other groups, since if it is // fast, it has a high capacity, and it is not failing @@ -969,8 +973,8 @@ public class ProfileOrganizer { if (netDb == null) return true; if (_context.router() == null) return true; if ( (_context.shitlist() != null) && (_context.shitlist().isShitlisted(peer)) ) { - if (_log.shouldLog(Log.DEBUG)) - _log.debug("Peer " + peer.toBase64() + " is shitlisted, dont select it"); + // if (_log.shouldLog(Log.DEBUG)) + // _log.debug("Peer " + peer.toBase64() + " is shitlisted, dont select it"); return false; // never select a shitlisted peer } @@ -983,18 +987,18 @@ public class ProfileOrganizer { } else { boolean exclude = TunnelPeerSelector.shouldExclude(_context, info); if (exclude) { - if (_log.shouldLog(Log.WARN)) - _log.warn("Peer " + peer.toBase64() + " has capabilities or other stats suggesting we avoid it"); + // if (_log.shouldLog(Log.WARN)) + // _log.warn("Peer " + peer.toBase64() + " has capabilities or other stats suggesting we avoid it"); return false; } else { - if (_log.shouldLog(Log.INFO)) - _log.info("Peer " + peer.toBase64() + " is locally known, allowing its use"); + // if (_log.shouldLog(Log.INFO)) + // _log.info("Peer " + peer.toBase64() + " is locally known, allowing its use"); return true; } } } else { - if (_log.shouldLog(Log.WARN)) - _log.warn("Peer " + peer.toBase64() + " is NOT locally known, disallowing its use"); + // if (_log.shouldLog(Log.WARN)) + // _log.warn("Peer " + peer.toBase64() + " is NOT locally known, disallowing its use"); return false; } } diff --git a/router/java/src/net/i2p/router/peermanager/ProfileOrganizerRenderer.java b/router/java/src/net/i2p/router/peermanager/ProfileOrganizerRenderer.java index cf61aa672..1a5541f91 100644 --- a/router/java/src/net/i2p/router/peermanager/ProfileOrganizerRenderer.java +++ b/router/java/src/net/i2p/router/peermanager/ProfileOrganizerRenderer.java @@ -143,6 +143,14 @@ class ProfileOrganizerRenderer { if (_context.shitlist().isShitlisted(peer)) buf.append("Shitlist"); if (prof.getIsFailing()) buf.append(" Failing"); if (_context.commSystem().wasUnreachable(peer)) buf.append(" Unreachable"); + Rate failed = prof.getTunnelHistory().getFailedRate().getRate(30*60*1000); + long fails = failed.getCurrentEventCount() + failed.getLastEventCount(); + if (fails > 0) { + Rate accepted = prof.getTunnelCreateResponseTime().getRate(30*60*1000); + long total = fails + accepted.getCurrentEventCount() + accepted.getLastEventCount(); + if (total / fails <= 10) // hide if < 10% + buf.append(' ').append(fails).append('/').append(total).append(" Test Fails"); + } buf.append(" "); //buf.append("profile.txt "); //buf.append(" netDb"); diff --git a/router/java/src/net/i2p/router/peermanager/TunnelHistory.java b/router/java/src/net/i2p/router/peermanager/TunnelHistory.java index c50d19f8c..2ea23099d 100644 --- a/router/java/src/net/i2p/router/peermanager/TunnelHistory.java +++ b/router/java/src/net/i2p/router/peermanager/TunnelHistory.java @@ -108,9 +108,12 @@ public class TunnelHistory { // dont increment the reject rate in this case } } - public void incrementFailed() { + + // Define this rate as the probability it really failed + // @param pct = probability * 100 + public void incrementFailed(int pct) { _lifetimeFailed++; - _failRate.addData(1, 1); + _failRate.addData(pct, 1); _lastFailed = _context.clock().now(); } diff --git a/router/java/src/net/i2p/router/tunnel/pool/TunnelPool.java b/router/java/src/net/i2p/router/tunnel/pool/TunnelPool.java index e9894b20c..24a3686b9 100644 --- a/router/java/src/net/i2p/router/tunnel/pool/TunnelPool.java +++ b/router/java/src/net/i2p/router/tunnel/pool/TunnelPool.java @@ -332,6 +332,7 @@ public class TunnelPool { } _manager.tunnelFailed(); + tellProfileFailed(cfg); _lifetimeProcessed += cfg.getProcessedMessagesCount(); updateRate(); @@ -343,6 +344,33 @@ public class TunnelPool { } } + // Blame all the other peers in the tunnel, with a probability + // inversely related to the tunnel length + private void tellProfileFailed(PooledTunnelCreatorConfig cfg) { + int len = cfg.getLength(); + if (len < 2) + return; + int start = 0; + int end = len; + if (cfg.isInbound()) + end--; + else + start++; + for (int i = start; i < end; i++) { + int pct = 100/(len-1); + // if inbound, it's probably the gateway's fault + if (cfg.isInbound() && len > 2) { + if (i == start) + pct *= 2; + else + pct /= 2; + } + if (_log.shouldLog(Log.WARN)) + _log.warn(toString() + ": Blaming " + cfg.getPeer(i) + ' ' + pct + '%'); + _context.profileManager().tunnelFailed(cfg.getPeer(i), pct); + } + } + void updateRate() { long now = _context.clock().now(); long et = now - _lastRateUpdate;