Changeset 54ec878
- Timestamp:
- Jul 19, 2013 12:18:08 AM (8 years ago)
- Branches:
- master
- Children:
- 8505e8a
- Parents:
- e93beb7 (diff), ea4606f (diff)
Note: this is a merge changeset, the changes displayed below correspond to the merge itself.
Use the(diff)
links above to see all the changes relative to each parent. - Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
apps/ministreaming/java/src/net/i2p/client/streaming/I2PSocketOptionsImpl.java
re93beb7 r54ec878 94 94 } 95 95 96 protected static double getDouble(Properties opts, String name, double defaultVal) { 97 if (opts == null) return defaultVal; 98 String val = opts.getProperty(name); 99 if (val == null) { 100 return defaultVal; 101 } else { 102 try { 103 return Double.parseDouble(val); 104 } catch (NumberFormatException nfe) { 105 return defaultVal; 106 } 107 } 108 } 109 96 110 /** 97 111 * How long we will wait for the ACK from a SYN, in milliseconds. -
apps/streaming/java/src/net/i2p/client/streaming/ConnectionOptions.java
re93beb7 r54ec878 28 28 private int _rtt; 29 29 private int _rttDev; 30 private int _rto ;30 private int _rto = INITIAL_RTO; 31 31 private int _resendDelay; 32 32 private int _sendAckDelay; … … 52 52 private int _maxConns; 53 53 private boolean _disableRejectLog; 54 54 55 /** state of a connection */ 56 private enum AckInit { 57 INIT, // just created 58 FIRST, // first received ack 59 STEADY 60 } 61 62 /** LOCKING: this */ 63 private AckInit _initState = AckInit.INIT; 64 55 65 // NOTE - almost all the options are below, but see 56 66 // I2PSocketOptions in ministreaming for a few more … … 66 76 public static final int INACTIVITY_ACTION_SEND = 2; 67 77 78 /* 79 * These values are specified in RFC 6298 80 * Do not change unless you know what you're doing 81 */ 82 private static final double TCP_ALPHA = 1.0/8; 83 private static final double TCP_BETA = 1.0/4; 84 private static final double TCP_KAPPA = 4; 85 86 private static final String PROP_INITIAL_RTO = "i2p.streaming.initialRTO"; 87 private static final int INITIAL_RTO = 12000; 88 68 89 public static final String PROP_CONNECT_DELAY = "i2p.streaming.connectDelay"; 69 90 public static final String PROP_PROFILE = "i2p.streaming.profile"; 70 91 public static final String PROP_MAX_MESSAGE_SIZE = "i2p.streaming.maxMessageSize"; 71 92 public static final String PROP_MAX_RESENDS = "i2p.streaming.maxResends"; 72 public static final String PROP_INITIAL_RTT = "i2p.streaming.initialRTT";73 93 public static final String PROP_INITIAL_RESEND_DELAY = "i2p.streaming.initialResendDelay"; 74 94 public static final String PROP_INITIAL_ACK_DELAY = "i2p.streaming.initialAckDelay"; … … 296 316 setConnectDelay(opts.getConnectDelay()); 297 317 setProfile(opts.getProfile()); 318 setRTTDev(opts.getRTTDev()); 298 319 setRTT(opts.getRTT()); 299 320 setRequireFullySigned(opts.getRequireFullySigned()); … … 333 354 setProfile(getInt(opts, PROP_PROFILE, PROFILE_BULK)); 334 355 setMaxMessageSize(getInt(opts, PROP_MAX_MESSAGE_SIZE, DEFAULT_MAX_MESSAGE_SIZE)); 335 setRTT(getInt(opts, PROP_INITIAL_RTT, DEFAULT_INITIAL_RTT));336 356 setReceiveWindow(getInt(opts, PROP_INITIAL_RECEIVE_WINDOW, 1)); 337 357 setResendDelay(getInt(opts, PROP_INITIAL_RESEND_DELAY, 1000)); … … 361 381 _maxTotalConnsPerDay = getInt(opts, PROP_MAX_TOTAL_CONNS_DAY, 0); 362 382 _maxConns = getInt(opts, PROP_MAX_STREAMS, 0); 383 384 _rto = getInt(opts, PROP_INITIAL_RTO, INITIAL_RTO); 363 385 } 364 386 … … 378 400 if (opts.containsKey(PROP_MAX_MESSAGE_SIZE)) 379 401 setMaxMessageSize(getInt(opts, PROP_MAX_MESSAGE_SIZE, Packet.MAX_PAYLOAD_SIZE)); 380 if (opts.containsKey(PROP_INITIAL_RTT))381 setRTT(getInt(opts, PROP_INITIAL_RTT, DEFAULT_INITIAL_RTT));382 402 if (opts.containsKey(PROP_INITIAL_RECEIVE_WINDOW)) 383 403 setReceiveWindow(getInt(opts, PROP_INITIAL_RECEIVE_WINDOW, 1)); … … 428 448 if (opts.containsKey(PROP_MAX_STREAMS)) 429 449 _maxConns = getInt(opts, PROP_MAX_STREAMS, 0); 450 451 _rto = getInt(opts, PROP_INITIAL_RTO, INITIAL_RTO); 430 452 } 431 453 … … 516 538 * @return round trip time estimate in ms 517 539 */ 518 public int getRTT() { return _rtt; }540 public synchronized int getRTT() { return _rtt; } 519 541 public void setRTT(int ms) { 520 if (_rto == 0) {521 _rttDev = ms / 2;522 _rto = ms + ms / 2;523 }524 542 synchronized (_trend) { 525 543 _trend[0] = _trend[1]; … … 533 551 } 534 552 535 _rtt = ms; 536 if (_rtt > 60*1000) 537 _rtt = 60*1000; 538 } 539 540 public int getRTO() { return _rto; } 541 542 /** for debugging @since 0.7.13 */ 543 int getRTTDev() { return _rttDev; } 553 synchronized(this) { 554 _rtt = ms; 555 if (_rtt > 60*1000) 556 _rtt = 60*1000; 557 } 558 } 559 560 public synchronized int getRTO() { return _rto; } 561 562 /** used in TCB @since 0.9.8 */ 563 synchronized int getRTTDev() { return _rttDev; } 564 private synchronized void setRTTDev(int rttDev) { _rttDev = rttDev; } 565 566 /** 567 * Loads options from TCB cache. 568 */ 569 synchronized void loadFromCache(int rtt, int rttDev, int wdw) { 570 _initState = AckInit.STEADY; 571 setRTT(rtt); 572 setRTTDev(rttDev); 573 setWindowSize(wdw); 574 computeRTO(); 575 } 576 577 /** 578 * computes RTO based on formula in RFC 579 */ 580 private synchronized void computeRTO() { 581 switch(_initState) { 582 case INIT : 583 throw new IllegalStateException(); 584 case FIRST : 585 _rto = _rtt + _rtt / 2; 586 break; 587 case STEADY : 588 _rto = _rtt + (int) (_rttDev * TCP_KAPPA); 589 break; 590 } 591 592 if (_rto < Connection.MIN_RESEND_DELAY) 593 _rto = (int)Connection.MIN_RESEND_DELAY; 594 else if (_rto > Connection.MAX_RESEND_DELAY) 595 _rto = (int)Connection.MAX_RESEND_DELAY; 596 } 544 597 545 598 /** … … 559 612 } 560 613 561 /** rtt = rtt*RTT_DAMPENING + (1-RTT_DAMPENING)*currentPacketRTT */562 /** This is the value specified in RFC 2988, let's try it */563 private static final double RTT_DAMPENING = 0.875;564 565 public void updateRTT(int measuredValue) {566 // the rttDev calculation matches that recommended in RFC 2988 (beta = 1/4)567 _rttDev = _rttDev + (int)(0.25d*(Math.abs(measuredValue-_rtt)-_rttDev));568 int smoothed = (int)(RTT_DAMPENING*_rtt + (1-RTT_DAMPENING)*measuredValue);569 // K = 4570 _rto = smoothed + (_rttDev<<2);571 if (_rto < Connection.MIN_RESEND_DELAY)572 _rt o = (int)Connection.MIN_RESEND_DELAY;573 else if (_rto > Connection.MAX_RESEND_DELAY)574 _rto = (int)Connection.MAX_RESEND_DELAY;575 576 setRTT(smoothed);614 public synchronized void updateRTT(int measuredValue) { 615 switch(_initState) { 616 case INIT: 617 _initState = AckInit.FIRST; 618 setRTT(measuredValue); // no smoothing first sample 619 _rttDev = _rtt / 2; 620 break; 621 case FIRST: 622 _initState = AckInit.STEADY; // fall through 623 case STEADY: 624 // calculation matches that recommended in RFC 6298 625 _rttDev = (int) ((1-TCP_BETA) *_rttDev + TCP_BETA * Math.abs(measuredValue-_rtt)); 626 int smoothed = (int)((1-TCP_ALPHA)*_rtt + TCP_ALPHA*measuredValue); 627 setRTT(smoothed); 628 } 629 computeRTO(); 577 630 } 578 631 -
apps/streaming/java/src/net/i2p/client/streaming/TCBShare.java
re93beb7 r54ec878 3 3 import java.util.Iterator; 4 4 import java.util.Map; 5 import java.util.Properties; 5 6 import java.util.concurrent.ConcurrentHashMap; 6 7 … … 9 10 import net.i2p.util.Log; 10 11 import net.i2p.util.SimpleTimer2; 12 13 import static net.i2p.client.streaming.I2PSocketOptionsImpl.getDouble; 11 14 12 15 /** … … 26 29 private final Map<Destination, Entry> _cache; 27 30 private final CleanEvent _cleaner; 31 private final double _rttDampening, _wdwDampening, _rttDevDampening; 28 32 29 33 private static final long EXPIRE_TIME = 30*60*1000; 30 34 private static final long CLEAN_TIME = 10*60*1000; 35 ///// constants defined in rfc 2140 36 ///// do not change unless you know what you're doing 31 37 private static final double RTT_DAMPENING = 0.75; 38 private static final double RTTDEV_DAMPENING = 0.75; 32 39 private static final double WDW_DAMPENING = 0.75; 40 private static final String RTT_DAMP_PROP="i2p.streaming.tcbcache.rttDampening"; 41 private static final String WDW_DAMP_PROP="i2p.streaming.tcbcache.wdwDampening"; 42 private static final String RTTDEV_DAMP_PROP="i2p.streaming.tcbcache.rttDampening"; 43 ///// 33 44 private static final int MAX_RTT = ((int) Connection.MAX_RESEND_DELAY) / 2; 45 private static final int MAX_RTT_DEV = (int) (MAX_RTT * 1.5); 34 46 private static final int MAX_WINDOW_SIZE = ConnectionPacketHandler.MAX_SLOW_START_WINDOW; 35 47 … … 37 49 _context = ctx; 38 50 _log = ctx.logManager().getLog(TCBShare.class); 51 52 final Properties props = ctx.getProperties(); 53 _rttDampening = getDouble(props, RTT_DAMP_PROP, RTT_DAMPENING); 54 _wdwDampening = getDouble(props, WDW_DAMP_PROP, WDW_DAMPENING); 55 _rttDevDampening = getDouble(props, RTTDEV_DAMP_PROP, RTTDEV_DAMPENING); 56 39 57 _cache = new ConcurrentHashMap<Destination,Entry>(4); 40 58 _cleaner = new CleanEvent(timer); 41 59 _cleaner.schedule(CLEAN_TIME); 60 61 if (_log.shouldLog(Log.DEBUG)) { 62 String log = "Creating TCBCache with rttDamp=%s, rttDevDamp=%s, wdwDamp=%s, "+ 63 "expire=%d, clean=%d"; 64 log = String.format(log,_rttDampening,_rttDevDampening,_wdwDampening, 65 EXPIRE_TIME,CLEAN_TIME); 66 _log.debug(log); 67 } 42 68 } 43 69 … … 61 87 if (e == null || e.isExpired()) 62 88 return; 63 if (_log.shouldLog(Log.DEBUG)) 89 final int rtt, rttDev, wdw; 90 synchronized(e) { 91 rtt = e.getRTT(); 92 rttDev = e.getRTTDev(); 93 wdw = e.getWindowSize(); 94 } 95 if (_log.shouldLog(Log.DEBUG)) { 64 96 _log.debug("From cache: " + 65 97 con.getSession().getMyDestination().calculateHash().toBase64().substring(0, 4) + 66 98 '-' + 67 99 dest.calculateHash().toBase64().substring(0, 4) + 68 " RTT: " + e.getRTT() + " wdw: " + e.getWindowSize()); 69 opts.setRTT(e.getRTT()); 70 opts.setWindowSize(e.getWindowSize()); 100 " RTT: " + rtt + 101 " RTTDev: "+ rttDev + 102 " wdw: " + wdw ); 103 } 104 opts.loadFromCache(rtt,rttDev,wdw); 71 105 } 72 106 … … 83 117 int old = -1; 84 118 int oldw = -1; 119 int oldDev = -1; 85 120 Entry e = _cache.get(dest); 86 121 if (e == null || e.isExpired()) { 87 e = new Entry(opts.getRTT(), opts.getWindowSize() );122 e = new Entry(opts.getRTT(), opts.getWindowSize(), opts.getRTTDev()); 88 123 _cache.put(dest, e); 89 124 } else { … … 91 126 old = e.getRTT(); 92 127 oldw = e.getWindowSize(); 128 oldDev = e.getRTTDev(); 93 129 e.setRTT(opts.getRTT()); 94 130 e.setWindowSize(opts.getWindowSize()); 131 e.setRTTDev(opts.getRTTDev()); 95 132 } 96 133 } 97 if (_log.shouldLog(Log.DEBUG)) 134 if (_log.shouldLog(Log.DEBUG)) { 98 135 _log.debug("To cache: " + 99 136 con.getSession().getMyDestination().calculateHash().toBase64().substring(0, 4) + … … 101 138 dest.calculateHash().toBase64().substring(0, 4) + 102 139 " old: " + old + " con: " + opts.getRTT() + " new: " + e.getRTT() + 140 " oldDev: " + oldDev + " conDev: " + opts.getRTTDev() + " newDev: " + e.getRTTDev() + 103 141 " oldw: " + oldw + " conw: " + opts.getWindowSize() + " neww: " + e.getWindowSize()); 142 } 104 143 } 105 144 … … 107 146 int _rtt; 108 147 int _wdw; 148 int _rttDev; 109 149 long _updated; 110 150 111 public Entry(int ms, int wdw ) {151 public Entry(int ms, int wdw, int rttDev) { 112 152 _rtt = ms; 113 153 _wdw = wdw; 154 _rttDev = rttDev; 114 155 _updated = _context.clock().now(); 115 156 } 116 157 public synchronized int getRTT() { return _rtt; } 117 158 public synchronized void setRTT(int ms) { 118 _rtt = (int)( RTT_DAMPENING*_rtt + (1-RTT_DAMPENING)*ms);159 _rtt = (int)(_rttDampening*_rtt + (1-_rttDampening)*ms); 119 160 if (_rtt > MAX_RTT) 120 161 _rtt = MAX_RTT; 121 162 _updated = _context.clock().now(); 122 163 } 164 public synchronized int getRTTDev() { return _rttDev; } 165 public synchronized void setRTTDev(int count) { 166 _rttDev = (int)(_rttDevDampening*_rttDev + (1-_rttDevDampening)*count); 167 if (_rttDev > MAX_RTT_DEV) 168 _rttDev = MAX_RTT_DEV; 169 _updated = _context.clock().now(); 170 } 123 171 public synchronized int getWindowSize() { return _wdw; } 124 172 public synchronized void setWindowSize(int wdw) { 125 _wdw = (int)(0.5 + WDW_DAMPENING*_wdw + (1-WDW_DAMPENING)*wdw);173 _wdw = (int)(0.5 + _wdwDampening*_wdw + (1-_wdwDampening)*wdw); 126 174 if (_wdw > MAX_WINDOW_SIZE) 127 175 _wdw = MAX_WINDOW_SIZE; -
history.txt
re93beb7 r54ec878 1 2012-07-19 zab 2 * Streaming: 3 - initialize streaming RTT from sample, trac #979, RFC 6298 4 - store rttDev in TCBCache 5 1 6 * 2013-07-15 0.9.7 released 2 7 -
router/java/src/net/i2p/router/RouterVersion.java
re93beb7 r54ec878 19 19 public final static String ID = "Monotone"; 20 20 public final static String VERSION = CoreVersion.VERSION; 21 public final static long BUILD = 0;21 public final static long BUILD = 1; 22 22 23 23 /** for example "-test" */
Note: See TracChangeset
for help on using the changeset viewer.